成类似下列格式的EXCEL文件?
-----------------------------------
┌───┬────────────┐
│      │                        │
├───┼────────────┤
│      │                        │
├───┼────────────┤
│      │                        │
│      │                        │
│      ├───┬───┬────┤
│      │      │      │        │
│      │      │      │        │
└───┴───┴───┴────┘  
可以参考DEVEXPRESS套间中的dxGrExpt.pas代码的DoWriteHeader方法.
const
  XLSBOF: array[0..4] of Word = ($409, 6, 0, $10, 0);
  XLSGUTS: array[0..5] of Word = ($80, 8, 0, 0, 0, 0);
  XLSPalette: array[0..2] of Word = ($92, 0, 0);
  XLSDimension: array [0..6] of Word = ($200, $0A, 0, $FFFF, 0, $FF, 0);
  XLSEOF: array[0..1] of Word = ($0A, 0);
  XLSFONTH: array[0..9] of Byte = ($31, 2, 0, 0, 0, 0, 0, 0, 8, 0);
  XLSFONTG: array[0..9] of Byte = ($31, 2, 0, 0, 0, 0, 0, 0, 10, 0);
  XLSFONT: array[0..9] of Byte = ($31, 2, 0, 0, 0, 0, 0, 0, 0, 0);
  XLSXF1: array[0..15] of Byte = ($43, 4, $0C, 0, 0, 0, $F5, $FF, $20, 0, 0, $CE, 0, 0, 0, 0);
  XLSXF2: array[0..15] of Byte = ($43, 4, $0C, 0, 1, 0, $F5, $FF, $20, $F4, 0, $CE, 0, 0, 0, 0);
  XLSXF3: array[0..15] of Byte = ($43, 4, $0C, 0, 2, 0, $F5, $FF, $20, $F4, 0, $CE, 0, 0, 0, 0);
  XLSXF4: array[0..15] of Byte = ($43, 4, $0C, 0, 0, 0, $F5, $FF, $20, $F4, 0, $CE, 0, 0, 0, 0);
  XLSXF5: array[0..15] of Byte = ($43, 4, $0C, 0, 0, 0, 1, 0, $20, 0, 0, $CE, 0, 0, 0, 0);
  XLSXF6: array[0..15] of Byte = ($43, 4, $0C, 0, 1, $21, $F5, $FF, $20, $F8, 0, $CE, 0, 0, 0, 0);
  XLSXF7: array[0..15] of Byte = ($43, 4, $0C, 0, 1, $1F, $F5, $FF, $20, $F8, 0, $CE, 0, 0, 0, 0);
  XLSXF8: array[0..15] of Byte = ($43, 4, $0C, 0, 1, $20, $F5, $FF, $20, $F8, 0, $CE, 0, 0, 0, 0);
  XLSXF9: array[0..15] of Byte = ($43, 4, $0C, 0, 1, $1E, $F5, $FF, $20, $F8, 0, $CE, 0, 0, 0, 0);
  XLSXF10: array[0..15] of Byte = ($43, 4, $0C, 0, 1, $0D, $F5, $FF, $20, $F8, 0, $CE, 0, 0, 0, 0);
  XLSXF: array[0..15] of Byte = ($43, 4, $0C, 0, 5, 0, 1, 0, $21, $78, $41, 3, 0, 0, 0, 0);
  XLSXFB: array[0..15] of Byte = ($43, 4, $0C, 0, 8, 0, 1, 0, $22, $78, $41, 2, $71, $71, $71, 0);
  XLSXFH: array[0..15] of Byte = ($43, 4, $0C, 0, 6, 0, 1, 0, $22, $78, $41, 2, $71, $71, $71, $71);
  XLSXFG: array[0..15] of Byte = ($43, 4, $0C, 0, 7, 0, 1, 0, $21, $78, $C1, 2, 0, 0, 0, 0);
  XLSXFF: array[0..15] of Byte = ($43, 4, $0C, 0, 5, 0, 1, 0, $22, $78, $C1, 2, $B9, $B9, $B9, $B9);
  XLSXFF1: array[0..15] of Byte = ($43, 4, $0C, 0, 5, 0, 1, 0, $22, $78, $C1, 2, $B9, 0, $B9, 0);
  XLSXFRF: array[0..15] of Byte = ($43, 4, $0C, 0, 9, 0, 1, 0, $21, $78, $C1, 2, $B9, $B9, $B9, $B9);
  XLSXFRF1: array[0..15] of Byte = ($43, 4, $0C, 0, 9, 0, 1, 0, $21, $78, $C1, 2, $B9, 0, $B9, 0);
  XLSCOL: array[0..7] of Word = ($7D, $0C, 0, 0, 0, $F, 0, 0);
  XLSSFONT: array[0..15] of Byte = ($31, 2, $0C, 0, $C8, 0, 0, 0, $FF, $7F, 5, $41, $72, $69, $61, $6C);
  XLSLabel: array[0..5] of Word = ($204, 0, 0, 0, 0, 0);
  XLSBlank: array[0..4] of Word = ($201, 6, 0, 0, $17);
  XLSBlankF: array[0..4] of Word = ($201, 6, 0, 0, $19);
  XLSBlankRF: array[0..4] of Word = ($201, 6, 0, 0, $1C);
//  XLSBlankH: array[0..4] of Word = ($201, 6, 0, 0, $16);
//  XLSBlankB: array[0..4] of Word = ($201, 6, 0, 0, $1A);
  XLSNumber: array[0..4] of Word = ($203, 14, 0, 0, 0);
  XLSRK: array[0..4] of Word = ($27E, 10, 0, 0, 0);
  XLSFormula: array[0..15] of Word =($406, $1D, 0, 0, $18, 0, 0, 0, 0, 3, $0B, $25, 0, 0, 0, 0);
procedure TdxDBGridExportExcel.DoWriteHeader;
var
  i, j, k: Integer;
  S: string;
begin
with Grid do
begin
  // Draw Bands
  if ShowBands then
  begin
    for i := 0 to GroupColumnCount - 1 do
    begin
      XLSBlank[2] := TotalCount;
      XLSBlank[3] := i;
      Stream.WriteBuffer(XLSBlank, SizeOf(XLSBlank));
    end;
    for j := 0 to VisColCount - 1 do
    begin
      XLSBlank[2] := TotalCount;
      XLSBlank[3] := j + GroupColumnCount;
      Stream.WriteBuffer(XLSBlank, SizeOf(XLSBlank));
    end;
    k := 0;
    for i := 0 to  GetBandCount - 1 do
    begin
      S := GetBandText(i);
      XLSLAbel[1] := Length(S) + 8;
      XLSLabel[2] := TotalCount;
      XLSLabel[3] := k + GroupColumnCount;
      XLSLabel[4] := $1A;
      XLSLabel[5] := Length(S);
      Stream.WriteBuffer(XLSLabel, SizeOf(XLSLabel));
      Stream.WriteBuffer(Pointer(S)^, Length(S));
      for j := 0 to GetHeaderRowCount(i) - 1 do
        k := k + GetHeaderColCount(i,j);
    end;
    Inc(TotalCount);
  end;
  // Draw Heders
  if ShowHeader then
  begin
    for i := 0 to GroupColumnCount - 1 do
    begin
      XLSBlank[2] := TotalCount;
      XLSBlank[3] := i;
      Stream.WriteBuffer(XLSBlank, SizeOf(XLSBlank));
    end;
    for i := 0 to  VisColCount - 1 do
    begin
//      S := GetHeaderText(VisColIndexes[i]);
      S := Columns[VisColIndexes[i]].Caption;
      XLSLAbel[1] := Length(S) + 8;
      XLSLabel[2] := TotalCount;
      XLSLabel[3] := i + GroupColumnCount;
      XLSLabel[4] := $16;
      XLSLabel[5] := Length(S);
      Stream.WriteBuffer(XLSLabel, SizeOf(XLSLabel));
      Stream.WriteBuffer(Pointer(S)^, Length(S));
    end;
    Inc(TotalCount);
  end;
end;
end;
//谁可以解释一下?