第03章-核心架构与基础概念
第三章:核心架构与基础概念
3.1 ReoGrid架构概述
3.1.1 整体架构
ReoGrid采用分层架构设计,从下至上分为以下几层:
┌─────────────────────────────────────────┐
│ 应用层 (Application Layer) │
│ 用户代码、业务逻辑、事件处理 │
└─────────────────────────────────────────┘
↓ ↑ 使用 / 事件
┌─────────────────────────────────────────┐
│ 控件层 (Control Layer) │
│ ReoGridControl、WorksheetControl │
└─────────────────────────────────────────┘
↓ ↑ 操作 / 通知
┌─────────────────────────────────────────┐
│ 核心层 (Core Layer) │
│ Workbook、Worksheet、Cell、Range │
└─────────────────────────────────────────┘
↓ ↑ 数据 / 状态
┌─────────────────────────────────────────┐
│ 功能层 (Feature Layer) │
│ Formula、Chart、Print、IO、Actions │
└─────────────────────────────────────────┘
↓ ↑ 调用 / 结果
┌─────────────────────────────────────────┐
│ 渲染层 (Rendering Layer) │
│ Graphics、ViewportController、Painter │
└─────────────────────────────────────────┘
↓ ↑ 绘制 / 输入
┌─────────────────────────────────────────┐
│ 平台层 (Platform Layer) │
│ WinForms、WPF、Android、Drawing │
└─────────────────────────────────────────┘
3.1.2 核心组件关系
// 组件关系示意
ReoGridControl // 主控件
└─ Workbook // 工作簿
├─ Worksheets[] // 工作表集合
│ └─ Worksheet // 单个工作表
│ ├─ Cells[,] // 单元格网格
│ ├─ Rows[] // 行集合
│ ├─ Columns[] // 列集合
│ ├─ Ranges[] // 命名区域
│ ├─ Charts[] // 图表集合
│ ├─ FloatingObjects[] // 浮动对象
│ └─ Settings // 工作表设置
├─ ActionManager // 操作管理器
│ ├─ UndoStack // 撤销栈
│ └─ RedoStack // 重做栈
└─ FormulaEngine // 公式引擎
├─ Functions[] // 内置函数
└─ CustomFunctions[] // 自定义函数
3.1.3 数据流向
用户操作
↓
输入处理 (MouseHandler / KeyboardHandler)
↓
动作创建 (Action)
↓
动作执行 (DoAction)
↓
数据模型更新 (Cell / Range Update)
↓
事件触发 (CellDataChanged Event)
↓
公式计算 (Formula Calculation)
↓
视图失效 (Invalidate)
↓
重新渲染 (Render)
↓
界面更新
3.2 Workbook工作簿
3.2.1 Workbook概念
Workbook是ReoGrid的顶层容器,代表一个完整的电子表格文件。
using unvell.ReoGrid;
// 获取Workbook实例
var workbook = grid.Workbook;
// Workbook属性
Console.WriteLine($"工作表数量: {workbook.Worksheets.Count}");
Console.WriteLine($"当前工作表: {workbook.CurrentWorksheet.Name}");
3.2.2 Workbook管理
创建和管理工作表
using unvell.ReoGrid;
public class WorkbookManager
{
private ReoGridControl grid;
public WorkbookManager(ReoGridControl gridControl)
{
grid = gridControl;
}
/// <summary>
/// 创建新工作表
/// </summary>
public Worksheet CreateWorksheet(string name)
{
var sheet = grid.CreateWorksheet(name);
return sheet;
}
/// <summary>
/// 获取指定工作表
/// </summary>
public Worksheet GetWorksheet(string name)
{
return grid.Worksheets[name];
}
/// <summary>
/// 删除工作表
/// </summary>
public void RemoveWorksheet(string name)
{
var sheet = grid.Worksheets[name];
grid.RemoveWorksheet(sheet);
}
/// <summary>
/// 切换当前工作表
/// </summary>
public void SwitchToWorksheet(string name)
{
grid.CurrentWorksheet = grid.Worksheets[name];
}
/// <summary>
/// 重命名工作表
/// </summary>
public void RenameWorksheet(string oldName, string newName)
{
var sheet = grid.Worksheets[oldName];
sheet.Name = newName;
}
/// <summary>
/// 复制工作表
/// </summary>
public Worksheet CopyWorksheet(string sourceName, string targetName)
{
var sourceSheet = grid.Worksheets[sourceName];
var newSheet = grid.CreateWorksheet(targetName);
// 复制数据和样式
CopyWorksheetContent(sourceSheet, newSheet);
return newSheet;
}
private void CopyWorksheetContent(Worksheet source, Worksheet target)
{
// 复制单元格数据
for (int row = 0; row < source.RowCount; row++)
{
for (int col = 0; col < source.ColumnCount; col++)
{
var cell = source.GetCell(row, col);
if (cell != null)
{
target[row, col] = cell.Data;
target.SetCellStyles(row, col, cell.Style);
}
}
}
}
}
3.2.3 Workbook设置
using unvell.ReoGrid;
public class WorkbookConfiguration
{
public static void ConfigureWorkbook(ReoGridControl grid)
{
// 公式相关
grid.SetSettings(WorkbookSettings.Formula_AutoCalculate, true);
grid.SetSettings(WorkbookSettings.Formula_AutoUpdateReferenceCell, true);
// 编辑相关
grid.SetSettings(WorkbookSettings.Edit_Readonly, false);
grid.SetSettings(WorkbookSettings.Edit_AllowSelectRange, true);
grid.SetSettings(WorkbookSettings.Edit_AutoFormatCell, true);
grid.SetSettings(WorkbookSettings.Edit_DragSelectionToMoveCells, true);
grid.SetSettings(WorkbookSettings.Edit_DragSelectionToFillSerial, true);
// 视图相关
grid.SetSettings(WorkbookSettings.View_ShowGridLine, true);
grid.SetSettings(WorkbookSettings.View_ShowRowHeader, true);
grid.SetSettings(WorkbookSettings.View_ShowColumnHeader, true);
grid.SetSettings(WorkbookSettings.View_ShowPageBreaks, false);
grid.SetSettings(WorkbookSettings.View_ShowFrozenLine, true);
// 行为相关
grid.SetSettings(WorkbookSettings.Behavior_BeforeRangeMove, true);
grid.SetSettings(WorkbookSettings.Behavior_BeforeRangeDelete, true);
}
}
3.3 Worksheet工作表
3.3.1 Worksheet概念
Worksheet是实际包含数据的工作表,是用户操作的主要对象。
using unvell.ReoGrid;
// 获取当前工作表
var sheet = grid.CurrentWorksheet;
// 工作表基本信息
Console.WriteLine($"工作表名称: {sheet.Name}");
Console.WriteLine($"行数: {sheet.MaxContentRow}");
Console.WriteLine($"列数: {sheet.MaxContentCol}");
Console.WriteLine($"是否只读: {sheet.IsReadonly}");
3.3.2 工作表操作
尺寸管理
using unvell.ReoGrid;
public class WorksheetSizeManager
{
private Worksheet sheet;
public WorksheetSizeManager(Worksheet worksheet)
{
sheet = worksheet;
}
/// <summary>
/// 设置默认行高
/// </summary>
public void SetDefaultRowHeight(ushort height)
{
sheet.SetRowsHeight(0, sheet.RowCount, height);
}
/// <summary>
/// 设置默认列宽
/// </summary>
public void SetDefaultColumnWidth(ushort width)
{
sheet.SetColumnsWidth(0, sheet.ColumnCount, width);
}
/// <summary>
/// 设置指定行的高度
/// </summary>
public void SetRowHeight(int row, ushort height)
{
sheet.SetRowsHeight(row, 1, height);
}
/// <summary>
/// 设置指定列的宽度
/// </summary>
public void SetColumnWidth(int col, ushort width)
{
sheet.SetColumnsWidth(col, 1, width);
}
/// <summary>
/// 自动调整列宽
/// </summary>
public void AutoFitColumn(int col)
{
sheet.AutoFitColumnWidth(col);
}
/// <summary>
/// 自动调整行高
/// </summary>
public void AutoFitRow(int row)
{
sheet.AutoFitRowHeight(row);
}
/// <summary>
/// 隐藏行
/// </summary>
public void HideRow(int row)
{
sheet.HideRows(row, 1);
}
/// <summary>
/// 显示行
/// </summary>
public void ShowRow(int row)
{
sheet.ShowRows(row, 1);
}
}
插入和删除
using unvell.ReoGrid;
public class WorksheetEditManager
{
private Worksheet sheet;
public WorksheetEditManager(Worksheet worksheet)
{
sheet = worksheet;
}
/// <summary>
/// 插入行
/// </summary>
public void InsertRows(int row, int count)
{
sheet.InsertRows(row, count);
}
/// <summary>
/// 删除行
/// </summary>
public void DeleteRows(int row, int count)
{
sheet.DeleteRows(row, count);
}
/// <summary>
/// 插入列
/// </summary>
public void InsertColumns(int col, int count)
{
sheet.InsertColumns(col, count);
}
/// <summary>
/// 删除列
/// </summary>
public void DeleteColumns(int col, int count)
{
sheet.DeleteColumns(col, count);
}
/// <summary>
/// 清空工作表
/// </summary>
public void Clear()
{
sheet.Reset();
}
/// <summary>
/// 清空指定区域
/// </summary>
public void ClearRange(string range)
{
sheet.DeleteRangeData(new RangePosition(range));
}
}
3.3.3 工作表事件
using System;
using unvell.ReoGrid;
using unvell.ReoGrid.Events;
public class WorksheetEventHandler
{
private Worksheet sheet;
public WorksheetEventHandler(Worksheet worksheet)
{
sheet = worksheet;
RegisterEvents();
}
private void RegisterEvents()
{
// 单元格数据变化事件
sheet.CellDataChanged += OnCellDataChanged;
// 选择变化事件
sheet.SelectionRangeChanged += OnSelectionChanged;
// 单元格编辑事件
sheet.BeforeCellEdit += OnBeforeCellEdit;
sheet.CellEdit += OnCellEdit;
// 行列变化事件
sheet.RowsInserted += OnRowsInserted;
sheet.RowsDeleted += OnRowsDeleted;
sheet.ColumnsInserted += OnColumnsInserted;
sheet.ColumnsDeleted += OnColumnsDeleted;
}
private void OnCellDataChanged(object sender, CellEventArgs e)
{
Console.WriteLine($"单元格 [{e.Cell.Row}, {e.Cell.Column}] 数据已更改");
Console.WriteLine($"新值: {e.Cell.Data}");
}
private void OnSelectionChanged(object sender, RangeEventArgs e)
{
Console.WriteLine($"选择区域已更改: {e.Range}");
}
private void OnBeforeCellEdit(object sender, CellBeforeEditEventArgs e)
{
// 可以在这里阻止编辑
if (e.Cell.Row == 0) // 禁止编辑第一行
{
e.IsCancelled = true;
}
}
private void OnCellEdit(object sender, CellEditEventArgs e)
{
Console.WriteLine($"单元格正在编辑: {e.Cell.Position}");
}
private void OnRowsInserted(object sender, RowsInsertedEventArgs e)
{
Console.WriteLine($"插入了 {e.Count} 行,起始行: {e.Index}");
}
private void OnRowsDeleted(object sender, RowsDeletedEventArgs e)
{
Console.WriteLine($"删除了 {e.Count} 行,起始行: {e.Index}");
}
private void OnColumnsInserted(object sender, ColumnsInsertedEventArgs e)
{
Console.WriteLine($"插入了 {e.Count} 列,起始列: {e.Index}");
}
private void OnColumnsDeleted(object sender, ColumnsDeletedEventArgs e)
{
Console.WriteLine($"删除了 {e.Count} 列,起始列: {e.Index}");
}
}
3.4 Cell单元格
3.4.1 Cell概念与结构
using unvell.ReoGrid.Data;
// Cell的核心属性
public class CellStructure
{
public void ShowCellInfo(Cell cell)
{
if (cell != null)
{
// 位置信息
Console.WriteLine($"行: {cell.Row}");
Console.WriteLine($"列: {cell.Column}");
Console.WriteLine($"地址: {cell.Address}");
// 数据信息
Console.WriteLine($"数据类型: {cell.DataFormat}");
Console.WriteLine($"数据值: {cell.Data}");
Console.WriteLine($"显示文本: {cell.DisplayText}");
// 样式信息
Console.WriteLine($"字体: {cell.Style.FontName}");
Console.WriteLine($"字号: {cell.Style.FontSize}");
Console.WriteLine($"背景色: {cell.Style.BackColor}");
// 公式信息
if (cell.HasFormula)
{
Console.WriteLine($"公式: {cell.Formula}");
}
// 状态信息
Console.WriteLine($"是否只读: {cell.IsReadonly}");
Console.WriteLine($"是否合并: {cell.IsMergedCell}");
}
}
}
3.4.2 单元格数据操作
using System;
using unvell.ReoGrid;
using unvell.ReoGrid.Data;
public class CellDataOperations
{
private Worksheet sheet;
public CellDataOperations(Worksheet worksheet)
{
sheet = worksheet;
}
/// <summary>
/// 设置单元格数据
/// </summary>
public void SetCellData()
{
// 方式1:使用地址
sheet["A1"] = "文本";
// 方式2:使用索引
sheet[0, 1] = 123;
// 方式3:使用Position
sheet.SetCellData(new CellPosition(0, 2), DateTime.Now);
// 方式4:使用SetCellData
sheet.SetCellData(0, 3, "数据", CellDataFormatFlag.Text);
}
/// <summary>
/// 读取单元格数据
/// </summary>
public object GetCellData(int row, int col)
{
var cell = sheet.GetCell(row, col);
if (cell != null)
{
// 获取原始数据
var data = cell.Data;
// 获取显示文本
var text = cell.DisplayText;
// 获取特定类型数据
if (cell.DataFormat == CellDataFormatFlag.Number)
{
return Convert.ToDouble(data);
}
else if (cell.DataFormat == CellDataFormatFlag.DateTime)
{
return Convert.ToDateTime(data);
}
return data;
}
return null;
}
/// <summary>
/// 批量设置数据
/// </summary>
public void BatchSetData(int startRow, int startCol, object[,] data)
{
int rows = data.GetLength(0);
int cols = data.GetLength(1);
for (int r = 0; r < rows; r++)
{
for (int c = 0; c < cols; c++)
{
sheet[startRow + r, startCol + c] = data[r, c];
}
}
}
/// <summary>
/// 清除单元格数据
/// </summary>
public void ClearCellData(int row, int col)
{
sheet[row, col] = null;
}
}
3.4.3 单元格样式
using System.Drawing;
using unvell.ReoGrid.Data;
using unvell.ReoGrid.Graphics;
public class CellStyleOperations
{
private Worksheet sheet;
public CellStyleOperations(Worksheet worksheet)
{
sheet = worksheet;
}
/// <summary>
/// 设置基础样式
/// </summary>
public void SetBasicStyle(string address)
{
sheet.SetCellStyle(address, new WorksheetRangeStyle
{
Flag = PlainStyleFlag.FontName |
PlainStyleFlag.FontSize |
PlainStyleFlag.FontColor,
FontName = "微软雅黑",
FontSize = 12,
FontColor = Color.Blue
});
}
/// <summary>
/// 设置背景和边框
/// </summary>
public void SetBackgroundAndBorder(string address)
{
sheet.SetCellStyle(address, new WorksheetRangeStyle
{
Flag = PlainStyleFlag.BackColor | PlainStyleFlag.Border,
BackColor = Color.LightYellow,
Border = new RangeBorderStyle
{
Left = new BorderStyle
{
Color = Color.Black,
Style = BorderLineStyle.Solid
},
Top = new BorderStyle
{
Color = Color.Black,
Style = BorderLineStyle.Solid
},
Right = new BorderStyle
{
Color = Color.Black,
Style = BorderLineStyle.Solid
},
Bottom = new BorderStyle
{
Color = Color.Black,
Style = BorderLineStyle.Solid
}
}
});
}
/// <summary>
/// 设置对齐方式
/// </summary>
public void SetAlignment(string address)
{
sheet.SetCellStyle(address, new WorksheetRangeStyle
{
Flag = PlainStyleFlag.HorizontalAlign | PlainStyleFlag.VerticalAlign,
HAlign = ReoGridHorAlign.Center,
VAlign = ReoGridVerAlign.Middle
});
}
/// <summary>
/// 设置数字格式
/// </summary>
public void SetNumberFormat(string address, CellDataFormatFlag format)
{
sheet.SetRangeDataFormat(address, format);
}
/// <summary>
/// 设置自定义格式
/// </summary>
public void SetCustomFormat(string address, string formatString)
{
sheet.SetRangeDataFormat(address,
CellDataFormatFlag.Custom,
new NumberDataFormatter.NumberFormatArgs
{
Pattern = formatString
});
}
}
3.5 Range区域
3.5.1 Range概念
Range代表工作表中的一个或多个连续单元格区域。
using unvell.ReoGrid;
public class RangeOperations
{
/// <summary>
/// 创建Range的多种方式
/// </summary>
public void CreateRangeExamples()
{
// 方式1:使用字符串地址
var range1 = new RangePosition("A1:C10");
// 方式2:使用行列索引
var range2 = new RangePosition(0, 0, 10, 3); // row, col, rows, cols
// 方式3:使用开始和结束位置
var range3 = new RangePosition(
new CellPosition(0, 0), // 起始位置
new CellPosition(9, 2) // 结束位置
);
// Range信息
Console.WriteLine($"起始行: {range1.Row}");
Console.WriteLine($"起始列: {range1.Col}");
Console.WriteLine($"行数: {range1.Rows}");
Console.WriteLine($"列数: {range1.Cols}");
Console.WriteLine($"地址: {range1.ToAddress()}");
}
}
3.5.2 区域操作
using System;
using unvell.ReoGrid;
using unvell.ReoGrid.Data;
public class RangeManager
{
private Worksheet sheet;
public RangeManager(Worksheet worksheet)
{
sheet = worksheet;
}
/// <summary>
/// 设置区域样式
/// </summary>
public void SetRangeStyle(string range, WorksheetRangeStyle style)
{
sheet.SetRangeStyles(range, style);
}
/// <summary>
/// 复制区域
/// </summary>
public void CopyRange(string sourceRange, string targetRange)
{
var data = sheet.GetPartialGrid(new RangePosition(sourceRange));
sheet.SetPartialGrid(new RangePosition(targetRange), data);
}
/// <summary>
/// 移动区域
/// </summary>
public void MoveRange(string sourceRange, string targetAddress)
{
var source = new RangePosition(sourceRange);
var target = new CellPosition(targetAddress);
sheet.MoveRange(source, target);
}
/// <summary>
/// 填充区域
/// </summary>
public void FillRange(string range, object value)
{
var rangePos = new RangePosition(range);
for (int r = rangePos.Row; r < rangePos.EndRow; r++)
{
for (int c = rangePos.Col; c < rangePos.EndCol; c++)
{
sheet[r, c] = value;
}
}
}
/// <summary>
/// 序列填充
/// </summary>
public void FillSerial(string range, int start, int step)
{
var rangePos = new RangePosition(range);
int value = start;
for (int r = rangePos.Row; r < rangePos.EndRow; r++)
{
for (int c = rangePos.Col; c < rangePos.EndCol; c++)
{
sheet[r, c] = value;
value += step;
}
}
}
/// <summary>
/// 查找和替换
/// </summary>
public int FindAndReplace(string range, object findValue, object replaceValue)
{
var rangePos = new RangePosition(range);
int count = 0;
for (int r = rangePos.Row; r < rangePos.EndRow; r++)
{
for (int c = rangePos.Col; c < rangePos.EndCol; c++)
{
var cell = sheet.GetCell(r, c);
if (cell != null && Equals(cell.Data, findValue))
{
sheet[r, c] = replaceValue;
count++;
}
}
}
return count;
}
}
3.6 渲染机制
3.6.1 渲染流程
用户操作/数据变化
↓
Invalidate() - 标记区域失效
↓
Paint事件触发
↓
BeginDraw() - 开始绘制
↓
DrawGrid() - 绘制网格
↓
DrawCells() - 绘制单元格
├─ DrawCellBackground() - 绘制背景
├─ DrawCellBorder() - 绘制边框
├─ DrawCellText() - 绘制文本
└─ DrawCellContent() - 绘制内容
↓
DrawSelection() - 绘制选择框
↓
DrawFloatingObjects() - 绘制浮动对象
↓
EndDraw() - 结束绘制
3.6.2 视口与虚拟化
using unvell.ReoGrid;
public class ViewportManager
{
private Worksheet sheet;
public ViewportManager(Worksheet worksheet)
{
sheet = worksheet;
}
/// <summary>
/// 获取可见区域
/// </summary>
public RangePosition GetVisibleRange()
{
return sheet.VisibleRange;
}
/// <summary>
/// 滚动到指定单元格
/// </summary>
public void ScrollToCell(string address)
{
var pos = new CellPosition(address);
sheet.ScrollToCell(pos);
}
/// <summary>
/// 滚动到指定区域
/// </summary>
public void ScrollToRange(string range)
{
var rangePos = new RangePosition(range);
sheet.ScrollToRange(rangePos);
}
/// <summary>
/// 设置缩放级别
/// </summary>
public void SetZoom(float scale)
{
sheet.SetScale(scale);
}
}
3.7 Action操作系统
3.7.1 Action概念
Action是ReoGrid中所有可撤销操作的基础,采用命令模式实现。
using unvell.ReoGrid.Actions;
// Action的生命周期
DoAction() // 执行操作
↓
Undo() // 撤销操作
↓
Redo() // 重做操作
3.7.2 使用Action
using unvell.ReoGrid;
using unvell.ReoGrid.Actions;
public class ActionExample
{
private ReoGridControl grid;
public ActionExample(ReoGridControl gridControl)
{
grid = gridControl;
}
/// <summary>
/// 使用Action设置数据
/// </summary>
public void SetDataWithAction(int row, int col, object data)
{
var action = new SetCellDataAction(row, col, data);
grid.DoAction(action);
}
/// <summary>
/// 撤销操作
/// </summary>
public void UndoLastAction()
{
if (grid.CanUndo())
{
grid.Undo();
}
}
/// <summary>
/// 重做操作
/// </summary>
public void RedoLastAction()
{
if (grid.CanRedo())
{
grid.Redo();
}
}
/// <summary>
/// 重复上次操作
/// </summary>
public void RepeatLastAction(RangePosition targetRange)
{
grid.RepeatLastAction(targetRange);
}
}
3.8 本章小结
✅ 本章学习内容
-
ReoGrid架构
- 整体架构层次
- 核心组件关系
- 数据流向
-
Workbook工作簿
- Workbook概念
- 工作表管理
- 全局设置
-
Worksheet工作表
- 工作表操作
- 尺寸管理
- 事件处理
-
Cell单元格
- 单元格结构
- 数据操作
- 样式设置
-
Range区域
- 区域概念
- 区域操作
- 批量处理
-
渲染机制
- 渲染流程
- 视口管理
- 虚拟化技术
-
Action系统
- Action概念
- 撤销重做
- 操作管理
📚 下一章预告
在第四章中,我们将详细学习:
- 单元格数据读写的各种方法
- 数据类型与格式化
- 批量数据操作
- 数据验证
- 导入导出
继续学习第四章:工作表与单元格操作!

浙公网安备 33010602011771号