好吧,您可以使用“自己的” dp 计算。
主文件
int density = 0;
float logicalDensity = 0;
float yDpi = 0; float xDpi = 0;
#if defined(ANDROID)
QAndroidJniObject qtActivity = QAndroidJniObject::callStaticObjectMethod("org/qtproject/qt5/android/QtNative", "activity", "()Landroid/app/Activity;");
QAndroidJniObject resources = qtActivity.callObjectMethod("getResources", "()Landroid/content/res/Resources;");
QAndroidJniObject displayMetrics = resources.callObjectMethod("getDisplayMetrics", "()Landroid/util/DisplayMetrics;");
density = displayMetrics.getField<int>("densityDpi");
logicalDensity = displayMetrics.getField<float>("density");
yDpi = displayMetrics.getField<float>("ydpi");
xDpi = displayMetrics.getField<float>("xdpi");
qDebug() << "Native Android Call =>>> | Logical Density: " << logicalDensity << " | DensityDPI: " << density << " | " << "++++++++++++++++++++++++";
#endif
[...]
// Set Android pixel data for QML context
engine.rootContext()->setContextProperty("densityData", density);
engine.rootContext()->setContextProperty("logicalDensityData",logicalDensity);
engine.rootContext()->setContextProperty("xDpiData",xDpi);
engine.rootContext()->setContextProperty("yDpiData",yDpi);
为您的ApplicationWindow
组件添加以下内容:
main.qml
Component.onCompleted: {
Units.pixelDensity = Qt.binding(function() {
if (Qt.platform.os === "android") {
return densityData / 25.4; // densityData is per inch but we need per mm
}
return Screen.pixelDensity
});
function calculateDiagonal() {
if (Qt.platform.os === "android") {
return Math.sqrt(Math.pow(Screen.width, 2) +
Math.pow(Screen.height, 2)) / densityData;
}
return Math.sqrt(Math.pow(Screen.width, 2) +
Math.pow(Screen.height, 2)) / (Screen.pixelDensity * 25.4);
}
Units.multiplier = Qt.binding(function() {
var diagonal = calculateDiagonal();
Device.diagonal = diagonal;
var baseMultiplier = 1;
if (diagonal >= 3.5 && diagonal < 5.1) { //iPhone 1st generation to phablet
return 0.8;
} else if (diagonal >= 5.1 && diagonal < 6.5) {
return 1;
} else if (diagonal >= 6.5 && diagonal < 15.1) {
return baseMultiplier;
} else if (diagonal >= 15.1 && diagonal < 29) {
return 1.4 * baseMultiplier;
} else if (diagonal >= 29 && diagonal < 92) {
return 1.4 * baseMultiplier;
} else {
return 1.4 * baseMultiplier;
}
});
Device.type = Qt.binding(function () {
var diagonal = calculateDiagonal();
Device.diagonal = diagonal;
if (diagonal >= 3.5 && diagonal < 5) { //iPhone 1st generation to phablet
return Device.phone;
} else if (diagonal >= 5 && diagonal < 7.2) {
return Device.phone;
} else if (diagonal >= 7.2 && diagonal < 15.1) {
return Device.tablet;
} else if (diagonal >= 15.1 && diagonal < 29) {
return Device.desktop;
} else if (diagonal >= 29 && diagonal < 92) {
return Device.tv;
} else {
return Device.unknown;
}
});
// Nasty hack because singletons cannot import the module they were declared in, so
// the grid unit cannot be defined in either Device or Units, because it requires both.
// See https://bugreports.qt.io/browse/QTBUG-39703
Units.gridUnit = Qt.binding(function() {
return Device.type === Device.phone || Device.type === Device.phablet
? Units.dp(48) : Device.type == Device.tablet ? Units.dp(56) : Units.dp(64)
});
}
单位.qml
Object {
id: units
/*!
\internal
This holds the pixel density used for converting millimeters into pixels. This is the exact
value from \l Screen:pixelDensity, but that property only works from within a \l Window type,
so this is hardcoded here and we update it from within \l ApplicationWindow
*/
property real pixelDensity: 4.46
property real multiplier: 1.4 //default multiplier, but can be changed by user
/*!
This is the standard function to use for accessing device-independent pixels. You should use
this anywhere you need to refer to distances on the screen.
*/
function dp(number) {
return Math.round(number*((pixelDensity*25.4)/160)*multiplier);
}
function gu(number) {
return number * gridUnit
}
property int gridUnit: dp(64)
}
设备.qml
import QtQuick 2.0
pragma Singleton
/*!
\qmltype Device
\inqmlmodule Material 0.1
\brief A singleton that provides information about the current device.
*/
Object {
id: device
//some kind of enum, by screen size
property int type: desktop
property int diagonal: -1
readonly property int phone: 0
readonly property int phablet: 1
readonly property int tablet: 2
readonly property int desktop: 3
readonly property int tv: 4
readonly property int unknown: 5 //it's either bigger than tv or smaller than phone
readonly property string name: {
switch (type) {
case 0:
return "phone";
case 1:
return "phablet";
case 2:
return "tablet";
case 3:
return "computer";
case 4:
return "TV";
case 5:
return "device";
}
}
readonly property string iconName: {
switch (type) {
case 0:
return "hardware/smartphone";
case 1:
return "hardware/tablet";
case 2:
return "hardware/tablet";
case 3:
return "hardware/desktop_windows";
case 4:
return "hardware/tv";
case 5:
return "hardware/computer";
}
}
readonly property bool isMobile: type == phone || type == phablet || type == tablet
}
单位和设备组件取自这里 qml-material 项目“ https://github.com/papyros/qml-material ”
添加后,您应该能够将每个像素语句包装到width: Units.dp(30)