作成日: 2025/05/20 最終更新日: 2025/05/20
文書種別
制限事項
状況
回避方法あり
詳細
マージした列を水平方向にスクロールすると、2024J v1.1以降ではヘッダテキストが空白となります。
※それよりも前のバージョンでは、マージした列が表示領域から消えるまでヘッダの文字が表示されます。
※それよりも前のバージョンでは、マージした列が表示領域から消えるまでヘッダの文字が表示されます。
回避方法
2024J v1.1(ver.4.8.20241.672)で、より適切な動きになるよう仕様が変更され、本動作になりました。
以前の動作と同じようにするには、オーナー描画を使用して列ヘッダの描画処理をカスタマイズします。最初にC1FlexGridのDrawModeプロパティをOwnerDrawに設定し、OwnerDrawCellイベントにて、描画されたセルがマージされた列ヘッダに属する場合、独自の描画処理を追加してヘッダテキストが表示されたままになるようにします。

以下に独自の描画処理を設定するコードを記載します。
◎サンプルコード(VB)
以前の動作と同じようにするには、オーナー描画を使用して列ヘッダの描画処理をカスタマイズします。最初にC1FlexGridのDrawModeプロパティをOwnerDrawに設定し、OwnerDrawCellイベントにて、描画されたセルがマージされた列ヘッダに属する場合、独自の描画処理を追加してヘッダテキストが表示されたままになるようにします。
以下に独自の描画処理を設定するコードを記載します。
◎サンプルコード(VB)
Imports C1.Win.C1FlexGrid
Public Class Form1
Private Sub Form1_Load(sender As Object, e As EventArgs) Handles MyBase.Load
' FlexGridの設定
C1FlexGrid1.Cols.DefaultSize = 80
' データの設定
Dim dt As DataTable = InitializeDataSource()
C1FlexGrid1.DataSource = dt
C1FlexGrid1(0, 1) = "Col1-3 Merge"
C1FlexGrid1(0, 2) = "Col1-3 Merge"
C1FlexGrid1(0, 3) = "Col1-3 Merge"
' マージの設定
C1FlexGrid1.AllowMerging = AllowMergingEnum.FixedOnly
C1FlexGrid1.Rows(0).AllowMerging = True
' オーナー描画の指定
C1FlexGrid1.DrawMode = DrawModeEnum.OwnerDraw
End Sub
Private Sub C1FlexGrid1_OwnerDrawCell(sender As Object, e As OwnerDrawCellEventArgs) Handles C1FlexGrid1.OwnerDrawCell
If e.Row >= C1FlexGrid1.Rows.Fixed OrElse e.Measuring Then
Return
End If
Dim mergeRange As CellRange = C1FlexGrid1.GetMergedRange(e.Row, e.Col)
If Not mergeRange.IsValid OrElse mergeRange.IsSingleColumn Then
Return
End If
If e.Row <> mergeRange.r1 OrElse e.Col <> mergeRange.c1 Then
Return
End If
Dim cellText As String = Convert.ToString(C1FlexGrid1.Cols(e.Col).Caption)
Dim mergedRect As Rectangle = e.Bounds
Dim leftVisibleCol As Integer = C1FlexGrid1.Cols.Fixed
Dim leftVisibleColX As Integer = C1FlexGrid1.GetCellRect(0, leftVisibleCol).X
Dim textOffset As Integer = 0
If mergedRect.X < leftVisibleColX Then
textOffset = Math.Min(leftVisibleColX - mergedRect.X, mergedRect.Width - 10)
End If
If textOffset <= 0 Then
Return
End If
e.DrawCell(DrawCellFlags.Background Or DrawCellFlags.Border)
e.Handled = True
Dim textRect As New Rectangle(
mergedRect.X + textOffset + 4,
mergedRect.Y,
mergedRect.Width - textOffset - 8,
mergedRect.Height)
If C1FlexGrid1.UseCompatibleTextRendering Then
Using brush As New SolidBrush(e.Style.ForeColor)
e.Graphics.DrawString(cellText, e.Style.Font, brush, textRect, e.Style.StringFormat)
End Using
Else
Dim flags As TextFormatFlags = GetTextFormatFlags(e.Style)
TextRenderer.DrawText(e.Graphics, cellText, e.Style.Font, textRect, e.Style.ForeColor, flags)
End If
End Sub
Private Function GetTextFormatFlags(style As CellStyle) As TextFormatFlags
Dim flags As TextFormatFlags = TextFormatFlags.EndEllipsis
Select Case style.TextAlign
Case TextAlignEnum.LeftTop, TextAlignEnum.LeftCenter, TextAlignEnum.LeftBottom
flags = flags Or TextFormatFlags.Left
Case TextAlignEnum.CenterTop, TextAlignEnum.CenterCenter, TextAlignEnum.CenterBottom
flags = flags Or TextFormatFlags.HorizontalCenter
Case TextAlignEnum.RightTop, TextAlignEnum.RightCenter, TextAlignEnum.RightBottom
flags = flags Or TextFormatFlags.Right
Case TextAlignEnum.GeneralTop, TextAlignEnum.GeneralCenter, TextAlignEnum.GeneralBottom
flags = flags Or TextFormatFlags.Left
End Select
Select Case style.TextAlign
Case TextAlignEnum.LeftTop, TextAlignEnum.CenterTop, TextAlignEnum.RightTop, TextAlignEnum.GeneralTop
flags = flags Or TextFormatFlags.Top
Case TextAlignEnum.LeftCenter, TextAlignEnum.CenterCenter, TextAlignEnum.RightCenter, TextAlignEnum.GeneralCenter
flags = flags Or TextFormatFlags.VerticalCenter
Case TextAlignEnum.LeftBottom, TextAlignEnum.CenterBottom, TextAlignEnum.RightBottom, TextAlignEnum.GeneralBottom
flags = flags Or TextFormatFlags.Bottom
End Select
If style.WordWrap Then
flags = flags Or TextFormatFlags.WordBreak
flags = flags And Not TextFormatFlags.EndEllipsis
End If
If style.Trimming = StringTrimming.EllipsisWord Then
flags = flags Or TextFormatFlags.WordEllipsis
ElseIf style.Trimming = StringTrimming.EllipsisPath Then
flags = flags Or TextFormatFlags.PathEllipsis
End If
flags = flags Or TextFormatFlags.NoPrefix
Return flags
End Function
Private Function InitializeDataSource() As DataTable
Dim dt As New DataTable("Table1")
dt.Columns.Add("Col1", GetType(String))
dt.Columns.Add("Col2", GetType(String))
dt.Columns.Add("Col3", GetType(String))
dt.Columns.Add("Col4", GetType(String))
dt.Columns.Add("Col5", GetType(String))
dt.Columns.Add("Col6", GetType(String))
dt.Columns.Add("Col7", GetType(String))
dt.Columns.Add("Col8", GetType(String))
For i As Integer = 1 To 10
Dim dr As DataRow = dt.NewRow()
dr("Col1") = $"C1R{ i.ToString()}"
dr("Col2") = $"C2R{ i.ToString()}"
dr("Col3") = $"C3R{ i.ToString()}"
dr("Col4") = $"C4R{ i.ToString()}"
dr("Col5") = $"C5R{ i.ToString()}"
dr("Col6") = $"C6R{ i.ToString()}"
dr("Col7") = $"C7R{ i.ToString()}"
dr("Col8") = $"C8R{ i.ToString()}"
dt.Rows.Add(dr)
Next
Return dt
End Function
End Class
◎サンプルコード(C#)
using C1.Win.C1FlexGrid;
namespace prj_C1FlexGrid
{
public partial class Form1 : Form
{
public Form1()
{
InitializeComponent();
}
private void Form1_Load(object sender, EventArgs e)
{
// FlexGridの設定
c1FlexGrid1.Cols.DefaultSize = 80;
// データの設定
DataTable dt = InitializeDataSource();
c1FlexGrid1.DataSource = dt;
c1FlexGrid1[0, 1] = "Col1-3 Merge";
c1FlexGrid1[0, 2] = "Col1-3 Merge";
c1FlexGrid1[0, 3] = "Col1-3 Merge";
// マージの設定
c1FlexGrid1.AllowMerging = AllowMergingEnum.FixedOnly;
c1FlexGrid1.Rows[0].AllowMerging = true;
// オーナー描画の指定
c1FlexGrid1.DrawMode = DrawModeEnum.OwnerDraw;
}
private void C1FlexGrid1_OwnerDrawCell(object sender, OwnerDrawCellEventArgs e)
{
// OwnerDrawCell イベントが
// データ行またはセルサイズの計測時は処理終了。デフォルト描画処理のみ行う。
if (e.Row >= c1FlexGrid1.Rows.Fixed || e.Measuring)
return;
// マージ範囲を取得
CellRange range = c1FlexGrid1.GetMergedRange(e.Row, e.Col);
if (!range.IsValid || range.IsSingleColumn || // 対象セルが無効 または 1列のみなら処理終了
e.Row != range.r1 || e.Col != range.c1) // マージ範囲の最初セル以外の場合処理終了
return;
// 描画位置調整(スクロールによるはみ出し補正)
Rectangle mergedRect = e.Bounds;
// 表示されている最初の列(固定列を除く)の左端X座標を取得
var leftVisibleCol = c1FlexGrid1.Cols.Fixed;
var leftVisibleColX = c1FlexGrid1.GetCellRect(0, leftVisibleCol).X;
// マージセルがグリッドの左端からはみ出ている場合、テキストの描画開始位置を調整
int textOffset = 0;
if (mergedRect.X < leftVisibleColX)
{
textOffset = Math.Min(leftVisibleColX - mergedRect.X, mergedRect.Width - 10);
}
// セルの背景と境界線を描画
e.DrawCell(DrawCellFlags.Background | DrawCellFlags.Border);
e.Handled = true; // カスタム描画したことを通知
// テキスト描画領域を計算
Rectangle textRect = new Rectangle(
mergedRect.X + textOffset + 4, // 左余白
mergedRect.Y,
mergedRect.Width - textOffset - 8, // 右余白
mergedRect.Height
);
// セルに表示するテキストを取得
string cellText = Convert.ToString(c1FlexGrid1[e.Row, e.Col]) ?? "";
// テキスト描画
if (c1FlexGrid1.UseCompatibleTextRendering)
{
using (Brush brush = new SolidBrush(e.Style.ForeColor))
{
e.Graphics.DrawString(cellText, e.Style.Font, brush, textRect, e.Style.StringFormat);
}
}
else
{
TextRenderer.DrawText(
e.Graphics, cellText, e.Style.Font, textRect,
e.Style.ForeColor, GetTextFormatFlags(e.Style)
);
}
}
private TextFormatFlags GetTextFormatFlags(CellStyle style)
{
// 基本フラグ:省略記号とプレフィックス無効
TextFormatFlags flags = TextFormatFlags.EndEllipsis | TextFormatFlags.NoPrefix;
// 横方向の配置
switch (style.TextAlign)
{
case TextAlignEnum.LeftTop:
case TextAlignEnum.LeftCenter:
case TextAlignEnum.LeftBottom:
flags |= TextFormatFlags.Left;
break;
case TextAlignEnum.CenterTop:
case TextAlignEnum.CenterCenter:
case TextAlignEnum.CenterBottom:
flags |= TextFormatFlags.HorizontalCenter;
break;
case TextAlignEnum.RightTop:
case TextAlignEnum.RightCenter:
case TextAlignEnum.RightBottom:
flags |= TextFormatFlags.Right;
break;
default: // Generalなど
flags |= TextFormatFlags.Left;
break;
}
// 縦方向の配置
switch (style.TextAlign)
{
case TextAlignEnum.LeftTop:
case TextAlignEnum.CenterTop:
case TextAlignEnum.RightTop:
case TextAlignEnum.GeneralTop:
flags |= TextFormatFlags.Top;
break;
case TextAlignEnum.LeftCenter:
case TextAlignEnum.CenterCenter:
case TextAlignEnum.RightCenter:
case TextAlignEnum.GeneralCenter:
flags |= TextFormatFlags.VerticalCenter;
break;
case TextAlignEnum.LeftBottom:
case TextAlignEnum.CenterBottom:
case TextAlignEnum.RightBottom:
case TextAlignEnum.GeneralBottom:
flags |= TextFormatFlags.Bottom;
break;
default:
flags |= TextFormatFlags.VerticalCenter; // Generalの場合など
break;
}
// ワードラップ設定
if (style.WordWrap)
{
flags |= TextFormatFlags.WordBreak;
flags &= ~TextFormatFlags.EndEllipsis; // WordBreak時はEndEllipsisを無効化
}
// 文字列の切り詰め方法
switch (style.Trimming)
{
case StringTrimming.EllipsisWord:
flags |= TextFormatFlags.WordEllipsis;
break;
case StringTrimming.EllipsisPath:
flags |= TextFormatFlags.PathEllipsis;
break;
}
return flags;
}
private DataTable InitializeDataSource()
{
var dt = new DataTable("Table1");
dt.Columns.Add("Col1", typeof(string));
dt.Columns.Add("Col2", typeof(string));
dt.Columns.Add("Col3", typeof(string));
dt.Columns.Add("Col4", typeof(string));
dt.Columns.Add("Col5", typeof(string));
dt.Columns.Add("Col6", typeof(string));
dt.Columns.Add("Col7", typeof(string));
dt.Columns.Add("Col8", typeof(string));
for (int i = 1; i <= 10; i++)
{
DataRow dr = dt.NewRow();
dr["Col1"] = $"C1R{i.ToString()}";
dr["Col2"] = $"C2R{i.ToString()}";
dr["Col3"] = $"C3R{i.ToString()}";
dr["Col4"] = $"C4R{i.ToString()}";
dr["Col5"] = $"C5R{i.ToString()}";
dr["Col6"] = $"C6R{i.ToString()}";
dr["Col7"] = $"C7R{i.ToString()}";
dr["Col8"] = $"C8R{i.ToString()}";
dt.Rows.Add(dr);
}
return dt;
}
}
}