根据从

时间:2016-12-23 12:18:48

标签: .net vb.net winforms

这更多的是出于好奇而非必要性的问题:

情况

我一直在开发一个类库,它在某种程度上具有一个表单,该表单生成一个按钮的“网格”,每个按钮的顶部都有一个标签。这些按钮的生成都是通过代码动态完成的。按钮被格式化,因此它们都以“矩阵式”对齐并添加到面板中。在每个按钮内部,我有一个文本值(“1”到“5”)。沿顶部运行的标题标签具有分析年份文本(类似于“01”到“60”或“001”到“100”,具体取决于用户指定的分析年数 - 我匹配数字,以便这一切都很好地对齐)。输出看起来像这样:

good output

当我调用此库并在开发人员环境中测试它时,一切看起来都很好(如上所示)。奇怪的是,当我将这个库编译并部署到主应用程序中时,文本会被截断,并且它不再适合它的控制,如下所示:

bad output

我知道Windows窗体在处理分辨率和调整控件大小方面非常糟糕,但我无法理解为什么只有在部署后才会发生这种情况。也许我从主应用程序继承了一些字体大小 - 但我不明白为什么会覆盖代码中的显式字体集?

代码

Private Const PAD = 15                          '//Spacing around controls
Private _runningYearWidth As integer
Private _xPoints As List(Of Integer)
Private _yPoints As List(Of Integer)
Private Sub GenerateMatrix()
    Dim n = _profile.ComponentProfiles.Count    '//y-values
    Dim m = _AnalysisPeriod                     '//x-values

    '//Generate component labels
    '.....   

    '//Generate year labels
    _xPoints = New List(Of Integer)
    _runningYearWidth = PAD
    For i = 1 To m
        Dim lbl As New Label
        FormatYearLabel(lbl, i, i.ToString)
    Next

    '//Generate matrix buttons
    For i = 1 To n
        For j = 1 To m
            Dim btn As New Button
            '//N.B. This function only generates the buttons and aligns them in a grid. 
            '//The model needs to run in order to populate these controls with values
            FormatMatrixButton(btn, j, i)
        Next
    Next
End Sub

Private Readonly _yearFont = New Font("Segoe UI", 9, FontStyle.Bold)
Private Sub FormatYearLabel(l As Label, index As Integer, yearText As string)
    const y = 5
    Dim x = _runningYearWidth
    yearText = FormatYearText(yearText)            '//Returns "01" for year(1) if analysis years is 2 digits long
    Dim w = GetFontWidth(_yearFont, yearText) + 2  '//+1 pixel either side
    Dim h = GetFontHeight(_yearFont, yearText) + 2 '//+1 pixel either side
    With l
        .Font = _yearFont
        .TextAlign = ContentAlignment.TopCenter
        .Width = w
        .Height = h
        .Text = yearText
        .Location = New Point(x, y)
        .Name = String.Format("lblYear{0}", index)
    End With
    panelMatrixDeterioration.Controls.Add(l)
    _runningYearWidth += (w + PAD)  '//X Co-Ord for next year-label
    _xPoints.AddRange({l.left, l.right})
End Sub

Private Function GetFontWidth(f As Font, txt As String) As Integer
    Dim g = panelMatrixComponents.CreateGraphics()
    Return g.MeasureString(txt, f).Width
End Function

Private Readonly _matrixFont = New Font("Consolas", 9, FontStyle.Bold)
Private Sub FormatMatrixButton(b As Button, x As Integer, y As Integer)
    '//Get this button's alignment points associated with the previously generated axis-labels
    Dim topleft = New Point(_xPoints((x-1)*2), _yPoints((y-1)*2))
    Dim bottomRight = New Point(_xPoints((x-1)*2 + 1), _yPoints((y-1)*2 + 1))
    With b
        .Font = _matrixFont
        .Location = topleft
        .Width = (bottomRight.X - topleft.X)
        .Height = (bottomRight.Y - topleft.Y)
        .Name = String.Format("btn{0}_{1}", x, y)
        .FlatStyle = FlatStyle.Flat
        AddHandler .Click, AddressOf MatrixButton_Click
    End With
    panelMatrixDeterioration.Controls.Add(b)
End Sub

'//===============Run Model....

基本上,上面的代码显示的是标签的大小(边界)是基于每个标签中文本的测量宽度。矩阵中按钮的大小(边界)与标题或“轴”处的标签对齐。

N.B。上面没有显示y轴(_yPoints),但逻辑与x轴非常相似。

最后

现在我已经做了一个快速修复,并在每个控件周围添加了一些额外的间距,当我编译库并在已部署的应用程序中运行它时它看起来很好 - 只是略大一点。

我想知道的是为什么有不同的视觉行为只会根据调用库的位置而变得明显?

0 个答案:

没有答案