Visual Basic 2005-如何在DataGridView控制項的儲存格同時顯示文字與圖片

摘要:Visual Basic 2005-如何在DataGridView控制項的儲存格同時顯示文字與圖片

 

圖表1

DataGridView 控制項並沒有內建任何功能來讓您在同一個儲存格中顯示出圖片與文字。解決之道,是透過 CellPaint 等事件來完成自訂的繪製作業。 

以下我們建立一個衍生自 DataGridViewTextBoxColumn 的使用者自訂資料行類別,藉此於儲存格內的文字旁邊繪製一個圖片(如圖表 1 所示)。我們使用 DataGridViewCellStyle.Padding 屬性來調整文字位置並覆寫 Paint 方法以便繪製一個圖片: 

Public Class TextAndImageColumn
    Inherits DataGridViewTextBoxColumn

    Private _imageValue As Image
    Private _imageSize As Size

    Public Sub New()
        MyBase.New()
        Me.CellTemplate = New TextAndImageCell
        Me.DefaultCellStyle.Alignment = DataGridViewContentAlignment.MiddleRight
    End Sub

    Public Property Image() As Image
        Get
            Return Me._imageValue
        End Get
        Set(ByVal value As Image)
            Me._imageValue = value
            Me._imageSize = value.Size
            If Me.InheritedStyle IsNot Nothing Then
                Dim inheritedPadding As Padding = Me.InheritedStyle.Padding
                Me.DefaultCellStyle.Padding = New Padding( _

                  ImageSize.Width, inheritedPadding.Top, _

                  inheritedPadding.Right, inheritedPadding.Bottom)
            End If          
        End Set
    End Property

    Private ReadOnly Property TextAndImageCellTemplate() As TextAndImageCell
        Get
            Return CType(Me.CellTemplate, TextAndImageCell)
        End Get
    End Property

    Friend ReadOnly Property ImageSize() As Size
        Get
            Return ImageSize
        End Get
    End Property

    Public Overrides Function Clone() As Object
        Dim c As TextAndImageColumn = CType(MyBase.Clone, TextAndImageColumn)
        c._imageValue = Me._imageValue
        c._imageSize = Me.ImageSize
        Return c
    End Function
End
Class

Public
Class TextAndImageCell
    Inherits DataGridViewTextBoxCell

    Private imageValue As Image
    Private imageSize As Size

    Public Property Image() As Image
        Get
            If ((Me.OwningColumn Is Nothing) _
                      OrElse (Me.OwningTextAndImageColumn Is Nothing)) Then
                Return imageValue
            ElseIf (Me.imageValue IsNot Nothing) Then
                Return Me.imageValue
            Else
                Return Me.OwningTextAndImageColumn.Image
            End If
        End Get
        Set(ByVal value As Image)
            If Not Me.imageValue.Equals(value) Then
                Me.imageValue = value
                Me.imageSize = value.Size
                Dim inheritedPadding As Padding = Me.InheritedStyle.Padding
                Me.Style.Padding = New Padding( _
                  imageSize.Width, inheritedPadding.Top, _
                  inheritedPadding.Right, inheritedPadding.Bottom)
            End If
        End Set
    End Property

    Private ReadOnly Property OwningTextAndImageColumn() As TextAndImageColumn
        Get
            Return CType(Me.OwningColumn, TextAndImageColumn)
        End Get
    End Property

    Public Overrides Function Clone() As Object
        Dim c As TextAndImageCell = CType(MyBase.Clone, TextAndImageCell)
        c.imageValue = Me.imageValue
        c.imageSize = Me.imageSize
        Return c
    End Function

    Protected Overrides Sub Paint(ByVal graphics As Graphics, _

      ByVal clipBounds As Rectangle, ByVal cellBounds As Rectangle, _

      ByVal rowIndex As Integer, _

      ByVal cellState As DataGridViewElementStates, _

      ByVal value As Object, ByVal formattedValue As Object, _

      ByVal errorText As String, ByVal cellStyle As DataGridViewCellStyle, _

      ByVal advancedBorderStyle As DataGridViewAdvancedBorderStyle, _

      ByVal paintParts As DataGridViewPaintParts)

      MyBase.Paint(graphics, clipBounds, cellBounds, rowIndex, _

        cellState, value, formattedValue, errorText, cellStyle, _

        advancedBorderStyle, paintParts)
        If (Not (Me.Image) Is Nothing) Then
            Dim container As System.Drawing.Drawing2D.GraphicsContainer = _

              graphics.BeginContainer
            graphics.SetClip(cellBounds)
            graphics.DrawImageUnscaled(Me.Image, cellBounds.Location)
            graphics.EndContainer(container)
        End If
    End Sub
End
Class