Qml Qt Quick Control 2:无绑定循环缩放字体大小

Qml Qt Quick Control 2: Scale font size without binding loop

我想像这样缩放 Label 的字体大小:

Label {
    font.size: font.size*0.8
}

当然这会创建一个绑定循环。有没有办法在不创建隐藏 Label 元素的情况下做到这一点?

Label {
    id: hiddenLabel
}

Label {
    font.size: hiddenLabel.font.size*0.8
}

缩放整个标签不是最优的,因为文本质量下降:

Label {
    scale: 0.8
}

此致,

您可以使用赋值而不是绑定,方法是在 Component.onCompleted

中设置字体大小
Label {
    text: 'Þetta reddast'
    Component.onCompleted: font.pixelSize *= 0.8
}

这会产生负面影响,即文本布局两次:一次用于较大尺寸,然后一次用于较小尺寸。

我可能会在 style.qml singleton 中定义一组具有正确大小的 fonts 作为 proposed here。在那里你可以使用应用程序的默认字体指标来计算相对大小,这样你以后就不用费心了。

FontMetrics {
    id: fontMetrics
}

Label {
    font.size: fontMetrics.font.size * 0.8
}

除了已经提到的其他选项,还有Qt.application.font:

Label {
    font.pixelSize: Qt.application.font.pixelSize * 0.8
}

This read-only property holds the default application font as returned by QGuiApplication::font().

commit message for the change提到当时考虑的其他选项:

  • "<h3>Large text</h3>" - adds extra space below the text since it's a HTML element, so not really useful if you want a decent layout.
  • Hard-coding a pixel size. Works OK when used in combination with Qt::AA_EnableHighDpiScaling, and so long as you guess the correct size that works for each device/display you're targeting. Doesn't work without setting Qt::AA_EnableHighDpiScaling.
  • Using FontMetrics/TextMetrics. Works fine, but is a bit verbose.
  • Use an empty Text element. Creates an unnecessary item. Was superseded by FontMetrics/TextMetrics.
  • defaultPixelSize/implicitPixelSize and defaultPointSize/implicitPointSize. There are already font-related properties outside of the font grouped property, so this wouldn't be out of place, but the API is already quite large.

如果您确实需要根据您正在使用的特定控件设置字体大小,唯一有保证的方法是创建该控件的 "empty"/"default-constructed" 实例:

Button {
    id: dummyButton
}

Button {
    font.pixelSize: dummyButton.font.pixelSize * 0.8
}

这是因为每种样式对于不同类型的控件都有不同的字体大小。例如,参见 Material style's theme code

我建议在 main.qml 中定义一个全局 属性,而不是在每个元素中单独定义文本大小。
为此,在 main.qml 中定义一个 属性,如下所示:

readonly property Item fontCenter: Item {
    property real heading1PointSize: 21
    property real heading2PointSize: 18
    property real bodyPointSize: 12
}

并像这样在任何地方使用它:

Text {
    text: "sample body text"
    font { pointSize: fontCenter.bodyPointSize }
}

另外,对于您的问题,您可以根据另一个值设置 属性 值:

readonly property Item fontCenter: Item {
    property real bodyPointSize: 12
    property real heading1PointSize: bodyPointSize * 2.0
    property real heading2PointSize: bodyPointSize * 1.8
}

或者对于特殊情况使用如下:

Button {
    text: "Special Offer!"
    font { pointSize: fontCenter.bodyPointSize * 1.3 }
}