Comments 15
А почему, собственно, не отлаживать чисто QML код на десктопе, вообще без заливки куда-либо?
Есть ряд задач, решать которые можно только на устройстве:
— позиционирование и масштабирование элементов на нескольких устройствах с разными разрешениями и размерами экранов;
— прототипирование пользовательского интерфейса в нескольких вариантах для сравнения юзабилити на реальных устройствах;
— вызов платформозависимого кода, недоступного в Windows. Например то, что раньше называлось Qt Mobility — доступ к местоположению, сенсорам (гироскоп, акселерометр и другие), блютуз, NFC.
— тестирование своих библиотек. Например я сейчас пилю новую версию своей библиотеки AdCtl (https://github.com/kafeg/adctl) где будет возможность авторизации через GPlay и привязка к рейтингам игроков и ачивкам.
Это то что вспомнилось сразу. Наверняка у каждого девелопера есть ещё куча причин тестировать функционал на конечном устройстве.
— позиционирование и масштабирование элементов на нескольких устройствах с разными разрешениями и размерами экранов;
— прототипирование пользовательского интерфейса в нескольких вариантах для сравнения юзабилити на реальных устройствах;
— вызов платформозависимого кода, недоступного в Windows. Например то, что раньше называлось Qt Mobility — доступ к местоположению, сенсорам (гироскоп, акселерометр и другие), блютуз, NFC.
— тестирование своих библиотек. Например я сейчас пилю новую версию своей библиотеки AdCtl (https://github.com/kafeg/adctl) где будет возможность авторизации через GPlay и привязка к рейтингам игроков и ачивкам.
Это то что вспомнилось сразу. Наверняка у каждого девелопера есть ещё куча причин тестировать функционал на конечном устройстве.
Ещё ссылочка в тему сетевой прозрачности: www.slideshare.net/jeremylaine/serving-qml-applications-over-the-network
— позиционирование и масштабирование элементов на нескольких устройствах с разными разрешениями и размерами экранов;Доступно на десктопе
— вызов платформозависимого кода, недоступного в WindowsОтлаживаем платформозависимый код — значит нужна перекомпиляция. Если он уже отлажен, значит интерфейс пишем на десктопе.
2 пункт спорный, 4 схож с третьим.
Но, тем не менее, статья полезная, наверняка кому-нибудь пригодится.
— позиционирование и масштабирование элементов на нескольких устройствах с разными разрешениями и размерами экранов;
К сожалениею не всё так хорошо в Qt с масштабированием, чтобы не заморачиваться тестированием UI на конечном устройстве. К тому же я например не знаю как на десктопе симулировать различные dpi/ppi.
— вызов платформозависимого кода, недоступного в Windows
Пример — библиотека использующая платформозависимый код уже готова и представлена QML-плагином. В этом случае перекомпиляция не нужна, но чтобы настроить связку с библиотекой может потребоваться несколько перезапусков приложения.
К тому же я например не знаю как на десктопе симулировать различные dpi/ppi.
Симулировать нельзя, зато можно обеспечить одинаковый размер элементов на всех девайсах вне зависимости от dpi/ppi — хоть в миллиметрах, хоть в пикселах.
Научите как правильно, перепробовал кучу способов =)
Если детально, то читать вот по этой ссылке статьи снизу-вверх.
Если кратко, то вот код:
Тут размер в миллиметрах полностью надежен, в девайсонезависимых пикселах приблизителен, как и на Android (но надо бы потестить на соответствующих девайсах), pt для единообразия при указании размеров шрифта.
Использвать очень просто — умножаем размеры в любом месте QML кода:
Все собираюсь написать статью по таким базовым вещам, но руки пока не доходят :/
Если кратко, то вот код:
#ifdef Q_OS_ANDROID
// BUG with dpi on some androids: https://bugreports.qt-project.org/browse/QTBUG-35701
// Workaround:
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;");
int density = displayMetrics.getField<int>("densityDpi");
#else
QScreen *screen = qApp->primaryScreen();
float density = screen->physicalDotsPerInch();
#endif
engine.rootContext()->setContextProperty("mm",density / 25.4);
engine.rootContext()->setContextProperty("pt", 1);
double scale = density < 180 ? 1 :
density < 270 ? 1.5 :
density < 360 ? 2 : 3;
engine.rootContext()->setContextProperty("dp", scale);
Тут размер в миллиметрах полностью надежен, в девайсонезависимых пикселах приблизителен, как и на Android (но надо бы потестить на соответствующих девайсах), pt для единообразия при указании размеров шрифта.
Использвать очень просто — умножаем размеры в любом месте QML кода:
Rectangle {
height: 20*mm;
width: 40*dp;
}
Все собираюсь написать статью по таким базовым вещам, но руки пока не доходят :/
разве screen->physicalDotsPerInch() не дает PPI на андроиде?
Зачем лезть в java вызовы?
Зачем лезть в java вызовы?
// BUG with dpi on some androids: bugreports.qt-project.org/browse/QTBUG-35701
// Workaround:
Заодно это выявит все места неправильного использования createComponent (где не учитывается что объект может быть не доступен сразу после вызова).
Единственное — полные имена файлов лучше заменить на относительные чтобы не носиться с assetsLoadPrefix+ по всему проекту
Единственное — полные имена файлов лучше заменить на относительные чтобы не носиться с assetsLoadPrefix+ по всему проекту
Вот кстати да, что касается createComponent, вместо неправильного использования
сразу после создания компонента, точно придётся переписывать эту логику на использование асинхронного вызова
Также выяснится, что вызвать этот метод можно лишь один раз, а дальше от него нужно дёргать createObject необходимое количество раз.
if (myComponent.status == Component.Ready) { ... }
сразу после создания компонента, точно придётся переписывать эту логику на использование асинхронного вызова
myComponent.statusChanged.connect(function() { ... })
Также выяснится, что вызвать этот метод можно лишь один раз, а дальше от него нужно дёргать createObject необходимое количество раз.
If you are certain the QML file to be loaded is a local file, you could omit the finishCreation() function and call createObject() immediatelyТак что использование вполне себе правильное.
Sign up to leave a comment.
Ускоряем отладку и прототипирование мобильных QML-приложений на живом устройстве