Delphi 放置一个devexpress dbgridview单元格';使用不同的文本格式编辑内容

Delphi 放置一个devexpress dbgridview单元格';使用不同的文本格式编辑内容,delphi,devexpress,Delphi,Devexpress,使用Devexpress cxGrid,我有一个tablegridview,其中显示了一个包含三个varchar字段的db表(30);ID、名称和描述 实际cxgrid外观: ID名称描述 1名称1说明1 2名称2说明2 . ... ... X名称X说明3 我希望这两个字段用#13(两行)连接和分隔,每行使用特殊的文本格式(例如,第一行用粗体,第二行用斜体) 我想要的cxgrid外观: ID名称和描述(只有一个字段而不是两个) 1名称1 说明1 2名称2 说明2

使用Devexpress cxGrid,我有一个tablegridview,其中显示了一个包含三个varchar字段的db表(30);ID、名称和描述

实际cxgrid外观:

ID名称描述
1名称1说明1
2名称2说明2
.         ...         ...
X名称X说明3

我希望这两个字段用#13(两行)连接和分隔,每行使用特殊的文本格式(例如,第一行用粗体,第二行用斜体)

我想要的cxgrid外观:

ID名称和描述(只有一个字段而不是两个)
1名称1
说明1
2名称2
说明2
.         名称…
描述
3命名3
描述


任何帮助都将不胜感激

我尝试了评论中建议的两种可能性,即在中使用自定义绘图 标准的DBTableView和使用DBBandeTableView,两者似乎都不提供 开箱即用的理想解决方案

对于像我这样的非专家来说,使用DBTableView很快就会遇到麻烦:

  • 尽管在
    名称
    文本下方绘制
    描述
    文本很简单, 它充满了困难,比如如何确定
    Name
    单元格的边界 绘制
    说明时
    如何避免网格绘制残余轮廓 如果绘制了
    说明
    ,则
    说明
    单元格和标题会是什么 通常
使用DBBandeTableView似乎可以集中到一个可行的解决方案上,只需要很少的细节就可以了 地址。请尝试以下操作:

  • 将ClientDataSet,
    CDS1
    添加到表单中,为ID、名称和描述字段添加持久字段

  • 将DBBandeTableView添加到cxGrid,并使用TDataSource将其连接到
    CDS1

  • 在其中创建两个波段,并为它们提供标题
    Band
    Band2
    ,以便于参考

  • ID
    Name
    Description
    列创建列。设置其
    属性
    属性 编辑文本

  • 在DBBandeTableView编辑器中,将
    ID
    列添加到
    Band
    中,并将
    名称添加到
    
    Description
    列到
    Band2
    使用到
    BandIndex
    列的子属性
    位置
    属性。同时设置
    Description
    列的
    RowIndex
    子属性 到1,使其位于
    名称
    字段下方

如下图所示设置表单代码,编译并运行。如您所见,自定义图形代码所做的只是设置名称和描述字段的字体样式

结果可能不像你想象的那样 指定的,但我会让你解决剩下的细节-如果你被卡住了,说出来

type
  TForm1 = class(TForm)
    CDS1: TClientDataSet;
    CDS1ID: TAutoIncField;
    DS1: TDataSource;
    DBNavigator1: TDBNavigator;
    CDS1Name: TStringField;
    CDS1Description: TStringField;
    cxGrid1Level1: TcxGridLevel;
    cxGrid1: TcxGrid;
    cxGrid1DBBandedTableView1: TcxGridDBBandedTableView;
    cxGrid1DBBandedTableView1ID: TcxGridDBBandedColumn;
    cxGrid1DBBandedTableView1Name: TcxGridDBBandedColumn;
    cxGrid1DBBandedTableView1Description: TcxGridDBBandedColumn;
    procedure FormCreate(Sender: TObject);
  private
    procedure CustomDrawCell(
      Sender: TcxCustomGridTableView; ACanvas: TcxCanvas;
      AViewInfo: TcxGridTableDataCellViewInfo; var ADone: Boolean);
  protected
  public
  end;

var
  Form1: TForm1;

[...]

procedure TForm1.CustomDrawCell(Sender:
    TcxCustomGridTableView; ACanvas: TcxCanvas; AViewInfo:
    TcxGridTableDataCellViewInfo; var ADone: Boolean);
var
  ACol : TcxGridDBBandedColumn;
begin
  ACol := TcxGridDBBandedColumn(AViewInfo.Item);
  if ACol = cxGrid1DBBandedTableView1Name then
    ACanvas.Font.Style := ACanvas.Font.Style + [fsBold]
  else
  if ACol = cxGrid1DBBandedTableView1Description then
    ACanvas.Font.Style := ACanvas.Font.Style + [fsItalic];
end;

procedure TForm1.FormCreate(Sender: TObject);
var
  i : Integer;
begin

  CDS1.CreateDataSet;

  CDS1.InsertRecord([1, 'Name1', 'Description1']);
  CDS1.InsertRecord([2, 'Name12', 'Description2']);

  CDS1.First;

  cxGrid1DBBandedTableView1ID.PropertiesClassName := 'TcxTextEditProperties';
  cxGrid1DBBandedTableView1ID.OnCustomDrawCell := CustomDrawCell;

  cxGrid1DBBandedTableView1Name.PropertiesClassName := 'TcxTextEditProperties';
  cxGrid1DBBandedTableView1Name.OnCustomDrawCell := CustomDrawCell;

  cxGrid1DBBandedTableView1Description.PropertiesClassName := 'TcxTextEditProperties';
  cxGrid1DBBandedTableView1Description.OnCustomDrawCell := CustomDrawCell;
end;

end.

对于如此简单的任务,CustomDrawCell看起来是一个非常繁重的解决方案

理想的解决方案是使用具有HTML列的TCxGrid,因此您只需在其上显示一个计算字段,例如(将[]替换为):

[html][b]名称1[/b][br][i]说明1[/i][html]

问题是TCxGrid没有HTML列,但正如其他人所说,您可以使用RichEdit列。因此,您也可以使用RTF而不是HTML构建此解决方案

使用Word(或Windows文件夹上的Write)创建示例并查找文本的RTF表示形式:

{\rtf1\ansi\ansicpg1252\deff0\deflang3082{\fonttbl{\f0\fnil\fcharset0 Calibri;}}
\viewkind4\uc1\pard\sa200\sl276\slmult1\lang10\b\f0\fs22 Name 1\par
\b0\i Description 1\i0\par
}
现在,向数据集中添加一个计算字段,返回要显示的格式化文本的RTF表示形式:

procedure TMyForm.MyQueryCalcFields(DataSet: TDataSet);
var FormattedText: string;
begin
  FormattedText := '{\rtf1\ansi\ansicpg1252\deff0\deflang3082{\fonttbl{\f0\fnil\fcharset0 Calibri;}}' + sLineBreak +
                   '\viewkind4\uc1\pard\sa200\sl276\slmult1\lang10\b\f0\fs22 ' +
                   Dataset.FieldByName('Name').AsString + '\par' + sLineBreak +
                   '\b0\i ' + Dataset.FieldByName('Description').AsString + '\i0\par' + sLineBreak +
                   '}';

  Dataset.FieldByName('FormattedText').Value := FormattedText;    
end;

最后,您只需将列的属性设置为RichEdit,并将此格式化文本绑定到该列即可获得所需的结果。

最后,尽管有一些困难,但在某些人的帮助下,这是使用OnCustomDraw而不是使用BandeTableView的完美解决方案,RichEditColumn预览方法

procedure TForm1.cxGrid1DBTableView1NameCustomDrawCell(
  Sender: TcxCustomGridTableView; ACanvas: TcxCanvas;
  AViewInfo: TcxGridTableDataCellViewInfo; var ADone: Boolean);
Function VarToText(AVal: Variant): String;
Begin
If VarIsNull(AVal) 
  Then Result := ''
  Else Result := VarToStr(AVal);
End;
Var
  AValue1, AValue2: Variant;
  AText: String;
  ARect: TRect;
Begin
  ARect := AViewInfo.ClientBounds;
  AValue1 := Sender.DataController.Values[AViewInfo.GridRecord.Index, 
  cxGrid1DBTableView1NAME.Index];
  AValue2 := Sender.DataController.Values[AViewInfo.GridRecord.Index, 
  cxGrid1DBTableView1DESCRIPTION.Index];
  ACanvas.Font.Style := [fsBold];
  If VarIsNull(AValue1) 
    Then Begin
           AText := VarToText(AValue2);
           ACanvas.Font.Style := [fsItalic];
           ACanvas.DrawTexT(AText, ARect, taLeftJustify, vaCenter, True, 
                            False);
         End
    Else If VarIsNull(AValue2) 
      Then Begin
             AText := VarToText(AValue1);
             ACanvas.Font.Style := [fsBold];
             ACanvas.DrawTexT(AText, ARect, taLeftJustify, vaCenter, True, 
                              False);
           End
      Else Begin
             ACanvas.DrawTexT(VarToText(AValue1), ARect, taLeftJustify, 
                              vaTop, True, false);
             ARect.Top := ARect.Top + 
             ACanvas.TextHeight(VarToText(AValue1));

             ACanvas.Font.Style := [fsItalic];
             ACanvas.DrawTexT(VarToText(AValue2), ARect, taLeftJustify,               
             vaBottom, True, False);
           End;
  ADone := True;
end;

我来这里是想澄清一下。

在获取数据时,您可能需要在SQL中进行连接。在文档中查找多行,如果我没记错的话,它涉及到对列属性使用备注,并设置视图的OptionView.RowAutoHeight。对于粗体和斜体字体样式,您可以使用列OnGetContentStyle事件。感谢您的回复,但主要问题是如何使两行具有不同的文本格式(粗体和斜体),因为将值串联并将其放入多行在位编辑器并不难。感谢您的澄清,我想你已经把你想要的部分归档了。您是否尝试过使用RichEditProperties作为列的属性?我不认为使用CustomDraw事件是可行的,以不同样式绘制多行文字的部分可能是可归档的,但要与基础设计保持一致,您需要能够正确计算ViewInfo。RichEdit是我首先想到的能够拥有你想要的风格的功能。你是否排除使用带状表格视图?这将允许您将列排列到多行。感谢这种逐步的方法,但结果并不像预期的那么好,顺便说一句,有一种与您类似的解决方案,但使用0行编码,这是预览的实现,因此,通过这两个属性.Preview.Visible=True和.Preview.Column=dbgvDESCRIPTION,并使用两种cxstylerepository样式,粗体表示名称列,斜体表示描述,这将使结果更接近您的结果!因此,我认为DBBandeTableView永远不会