Showing a Dialog onCompleted doesn't work as expected - android

I want to show a Dialog onCompleted under some condition (handling this condition omitted here - a simple if clause)
main.qml:
import QtQuick 2.2
import QtQuick.Controls 1.0
ApplicationWindow
{
id: appWindow
width: 480
height: 640
visible: true
StackView
{
id: stackView
anchors.fill: parent
// Implements back key navigation
focus: true
initialItem: Item
{
width: parent.width
height: parent.height
Button { onClicked: dialog.open() }
// ...
Component.onCompleted: dialog.open()
}
}
MyDialog {id: dialog }
}
MyDialog.qml
import QtQuick 2.0
import QtQuick.Dialogs 1.2
import QtQuick.Layouts 1.0
import QtQuick.Controls 1.0
Dialog
{
id: root
title: "MyDialog"
standardButtons: Qt.NoButton
ColumnLayout
{
id: column
width: parent ? parent.width : 200
Label { text: "hello world"; Layout.fillWidth: true }
}
}
When I launch my app, the screen is dimmed, and the Dialog's shade appears, as though the dialog had width == 0.
Sometimes (rarely) the dialog shows correctly.
If I comment out the Component.onCompleted line and launch the dialog using the Button, it is displayed correctly.
What am I doing wrong?
I'm using Qt 5.5 for Android

Opening the dialog doesn't work correctly if it's opened before the window has a sane geometry.
A safe option is to use the onWidthChanged signal
main.qml
import QtQuick 2.2
import QtQuick.Controls 1.0
ApplicationWindow
{
id: appWindow
width: 480
height: 640
visible: true
StackView
{
id: stackView
anchors.fill: parent
// Implements back key navigation
focus: true
initialItem: Item
{
property bool firstTime: true
width: parent.width
height: parent.height
// ...
// width may be called multiple times
onWidthChanged: if (firstTime) {firstTime = true; dialog.open()}
}
}
MyDialog {id: dialog }
}

Please, refer to official documentation about Dialog QML Type, there you can find next:
Note: do not attempt to bind the width or height of the dialog to the
width or height of its content, because Dialog already tries to size
itself to the content. If your goal is to change or eliminate the
margins, you must override contentItem. If your goal is simply to show
a window (whether modal or not), and your platform supports it, it is
simpler to use Window instead.
So, in your case, it will be better somehow set width of your inner element implicitly. Another quick solution is to add (for example) Rectangle element with given width as only one inner root element of your Dialog. Rest of elements you can place inside this Rectangle.

I'm posting another answer because it is another approach. I remembered how I implemented it on some old project. AFAIK, For now it is the best way. I would be really happy if anyone gave better solution.
You need to add one intermediary element like Timer. This timer (tm in code below) must have small interval (like 30ms) and need to be started on your desired event -- Component.onCompleted. Put your action in onTriggered of this timer.
Here is code:
ApplicationWindow {
title: qsTr("Hello World")
width: 640
height: 480
visible: true
Timer {
id: tm
interval: 30
onTriggered: dialog.open()
}
StackView {
id: stackView
anchors.fill: parent
// Implements back key navigation
focus: true
initialItem: Item {
width: parent.width
height: parent.heonTriggeredight
Button { onClicked: dialog.open() }
Component.onCompleted: tm.start()
}
}
MyDialog { id: dialog }
}

Related

QML, the menu icon will does not show up correctly

The following standard QML code does not work. Instead of the 3 small bar menu icon (unicode u2630), I get a rectangle with a cross inside: it does not find the character. However it finds the u25C0 left arrow (back triangle button) when required.
This is only a cosmetic glitch, as it works perfectly.
Has this anything related to the font, or with a mapping to an icon? How to solve this?
import QtQuick 2.15
import QtQuick.Controls 2.15
ApplicationWindow {
id: window
width: 640
height: 480
visible: true
title: qsTr("Stack")
header: ToolBar {
contentHeight: toolButton.implicitHeight
ToolButton {
id: toolButton
text: stackView.depth > 1 ? "\u25C0" : "\u2630"
font.pixelSize: Qt.application.font.pixelSize * 1.6
onClicked: {
if (stackView.depth > 1) {
stackView.pop()
} else {
drawer.open()
}
}
}
Label {
text: stackView.currentItem.title
anchors.centerIn: parent
}
}
(...)
For those who come here from search I will leave here the answer from a Qt.io forum
https://forum.qt.io/topic/123877/stackview-icon-on-android

QT Android Gboard overlaps input fields

Since the last update of the Gboard Qt seems to have issues with detecting it and push input fields above it accordingly.
Gboard version: 9.7.09.323382208-tv_release-armeabi-v7a
I have a minimal code example in which it can be easily reproduced:
import QtQuick 2.12
import QtQuick.Window 2.12
import QtQuick.Controls 2.12
ApplicationWindow {
width: 1920
height: 1080
visibility: Window.Maximized
color: "#C0C0C0"
Item
{
width: 1920 * 0.7
height: 1080 * 0.8
Item {
width: parent.width
height: parent.height * 0.4
id: we
}
TextField
{
id: input1
width: parent.width
focus: true
anchors.top: we.bottom
onAccepted: input2.focus = true
Keys.onPressed:
{
switch (event.key) {
case Qt.Key_Tab:
case Qt.Key_Down:
event.accepted = true
input2.forceActiveFocus()
break
}
}
}
TextInput
{
id: input2
width: parent.width
anchors.top: input1.bottom
maximumLength: 40
Keys.onPressed:
{
switch (event.key) {
case Qt.Key_Tab:
case Qt.Key_Down:
event.accepted = true
break
case Qt.Key_Up:
event.accepted = true
input1.forceActiveFocus()
break
}
}
}
}
}
I tried to build with Qt versions: 5.12.9, 5.13.2, 5.14.2, 5.15.1 and all have the same issue. However an empty project from Android studio will push the input fields correctly, so the issue must be Qt related.
I also tried to set android:windowSoftInputMode="adjustPan" but it had no effect at all.
What I found is the Qt showSoftwareKeyboard method in QtActivityDelegate.java, I assume it's responsible for displaying the keyboard and adjusting the layouts, so I tried to play around with it a bit (setting some hard-coded values e.g. m_layout.setLayoutParams(m_editText, new QtLayout.LayoutParams(width, 680, 30, 500), false)), rebuild Qt with the changes, but with no success or visible changes, it does print out my custom logs so the changes did apply correctly.
Any ideas how to make it push the input fields?

QML: Why my buttons at the bottom are under the lower Android button bar, before creen rotation

In the code below, the row of buttons shows behing the Android lower bar of button (triangle, circle, square). When I rotate, everything is fine. When I rotate back, everything is fine too.
So it is only the first time that something goes wrong.
Any idea ?
import QtQuick 2.4
import QtQuick.Controls 2.15
import QtQuick.Window 2.15
Item {
property alias unit_add: unit_add
width: Screen.desktopAvailableWidth
height: Screen.desktopAvailableHeight
ListView {
(...)
}
Row {
id: buttons
width: parent.width
height: 43
visible: true
spacing: 16
anchors.bottom: parent.bottom
anchors.topMargin: 10
anchors.bottomMargin: 10
anchors.horizontalCenter: parent.horizontalCenter
Button {
id: unit_add
text: qsTr("Add")
}
Button {
id: unit_delete
text: qsTr("Delete")
}
Button {
id: unit_edit
text: qsTr("Edit")
}
}
}

QML Text having strange behavior? Text not appearing and crashing app

I'm encountering a strange behavior with Text in QML. Which I admit is probably my fault, but I can not figure out what's wrong. I am creating a swipe menu like the ones used on the Gmail/Inbox app for android. As it was answered here I found that the best way to have the swipe menu with buttons inside was to create my own buttons, so I have the following code:
MenuButton:
Item {
id: root
property string text: ""
signal clicked()
width: 100
height: 62
Rectangle {
anchors.fill: parent
}
Text {
anchors.centerIn: parent
text: parent.text
}
MouseArea {
anchors.fill: parent
onClicked: {
parent.clicked();
}
}
}
My SliderMenu is as follows:
Item {
id: root
function showMenu(startX, duration) {
//Start animation to show menu.
}
function hideMenu(startX, duration) {
//Start animation to hide menu.
}
clip: true
visible: false
Item {
id: menu
//shadow adds 1 pixel
property int maxX: -1
property int minX: -width - 1
//Arbitrary number for what is considered fast
property int fastSwipe: 200
y: -1
width: 250
height: parent.height + 1
visible: false
Rectangle {
id: rectMenu
anchors.fill: parent
color: "#ececec"
visible: false
}
DropShadow {
id: menuShadow
anchors.fill: rectMenu
horizontalOffset: 1
verticalOffset: 0
radius: 4
samples: radius * 2
spread: 0
color: "#80000000"
source: rectMenu
transparentBorder: true
}
MenuButton {
x: 10
y: 20
text: "Text"
onClicked: {
console.log("I'm here!");
}
}
SwipeArea {
//Swipe area code
}
NumberAnimation {
//Code of the sliding in animation
}
NumberAnimation {
//Code for the sliding out animation
}
}
}
The slider is opened by clicking on the TopMenu's Button:
Rectangle {
id: root
height: 50
color: "#4285f4"
border.width: 0
border.color: "#00000000"
property SliderMenu slider
ToolButton {
id: slideButton
x: 5
y: 7
width: 36
height: 36
iconSource: "../../resources/MainMenu/slide_menu_icon.png"
onClicked: {
slider.showMenu();
}
}
}
Which is like this on main:
Item {
anchors.fill: parent
z: 1
TopMenu {
x: 0
y: 0
width: parent.width
height: 50
slider: sliderMenu
}
SliderMenu {
id: sliderMenu
x: 0
y: 0
anchors.fill: parent
}
}
When I press the TopMenu's Button to slide the menu into view, 90% of the time (not always) the app will crash. If I remove the Text from the MenuButton it won't crash anymore. Also, I've tried adding a Text anywhere on the SlideMenu instead of the MenuButton and it gives the same result.
I've also tried to make the Menu always visible (so I won't have to press the Button for it to appear) and the app does not crash anymore but 90% of the time the Text is not there!
It only seems to crash if it is initially hidden and, if it doesn't crash at first, it won't anymore, even if I hide the menu and open again.
The crash gives a segmentation fault on Debug.
Anyone has any idea of what this might be?
Thank you for your time.
EDIT: I was running this on windows because it is faster to test and I want it to also run on windows. I've just tested inside an android and it doesn't seem to be crashing. But I get this error on my console every time I open or close the menu:
Drawable.qml:70 ((null)): file:///data/data/org.qtproject.example.OSC_Client/qt-reserved-files/qml/QtQuick/Controls/Styles/Android/drawables/Drawable.qml:70: TypeError:
Cannot read property 'padding' of undefined
W/libOSC-Client.so(25977): file:///data/data/org.qtproject.example.OSC_Client/qt-reserved-files/qml/QtQuick/Controls/Styles/Android/drawables/AnimationDrawable.qml:53 ((null)): file:///data/data/org.qtproject.example.OSC_Client/qt-reserved-files/qml/QtQuick/Controls/Styles/Android/drawables/AnimationDrawable.qml:53:28:
Unable to assign [undefined] to bool
EDIT2: I've just managed to replicate this bug in a simpler manner. This seems to be related to the DropShadow on the rectangle. The simpler code is bellow. When I run it, 90% of the time the text does not appear. Tested on both MinGW and MSVC2012 on windows.
import QtQuick 2.4
import QtQuick.Controls 1.3
import QtGraphicalEffects 1.0
ApplicationWindow {
title: qsTr("Hello World")
width: 640
height: 480
visible: true
Button {
x: 0
y: 350
text: "Show Rectangle"
onClicked: rect.visible = true;
}
Item {
id: rect
x: -1
y: -1
width: 250
height: 300
visible: false
Rectangle {
id: rectMenu
anchors.fill: parent
color: "#ececec"
visible: false
}
DropShadow {
id: menuShadow
anchors.fill: rectMenu
horizontalOffset: 1
verticalOffset: 0
radius: 4
samples: radius * 2
spread: 0
color: "#80000000"
source: rectMenu
transparentBorder: true
}
Text {
anchors.centerIn: parent
text: "Text"
}
}
}
If I remove the DropShadow it'll show the text normally.
qt.qpa.gl Log:
qt.qpa.gl: createPlatformOpenGLContext QSurfaceFormat(version 2.0, options QFlags(), depthBufferSize 24, redBufferSize -1, greenBufferSize -1, blueBufferSize -1, alphaBufferSize -1, stencilBufferSize 8, samples -1, swapBehavior 2, swapInterval 1, profile 0)
qt.qpa.gl: Qt: Using WGL and OpenGL from "opengl32.dll"
qt.qpa.gl: create OpenGL: "Intel","Intel(R) HD Graphics 3000" default ContextFormat: v3.1 profile: 0 options: QFlags(0x4),SampleBuffers, Extension-API present
Extensions: 116
qt.qpa.gl: "choosePixelFormat Attributes: 0x2003 , 0x2027 , 0x2010 , 0x1 , 0x2001 , 0x1 , 0x2014 , 0x18 , 0x2011 , 0x1 , 0x2022 , 0x18 , 0x2013 , 0x202b , 0x201b , 0x8 , 0x2023 , 0x8 , 0x2041 , 0x0 ,
obtained px # 4 of 1
PIXELFORMATDESCRIPTOR dwFlags=0x8225 PFD_DRAW_TO_WINDOW PFD_SUPPORT_OPENGL PFD_SUPPORT_COMPOSITION PFD_DOUBLEBUFFER iPixelType=0 cColorBits=32 cRedBits=8 cRedShift=16 cGreenBits=8 cGreenShift=8 cBlueBits=8 cBlueShift=0 cDepthBits=24 cStencilBits=8 iLayerType=0 cAlphaBits=8 cAlphaShift=24 cAccumBits=64 cAccumRedBits=16 cAccumGreenBits=16 cAccumBlueBits=16 cAccumAlphaBits=16"
qt.qpa.gl: createContext Creating context version 2 . 0 3 attributes
qt.qpa.gl: QWindowsGLContext 0x281246a0 ARB requested: QSurfaceFormat(version 2.0, options QFlags(), depthBufferSize 24, redBufferSize -1, greenBufferSize -1, blueBufferSize -1, alphaBufferSize -1, stencilBufferSize 8, samples -1, swapBehavior 2, swapInterval 1, profile 0)
obtained # 4 ARB QSurfaceFormat(version 3.1, options QFlags(0x4), depthBufferSize 24, redBufferSize 8, greenBufferSize 8, blueBufferSize 8, alphaBufferSize 8, stencilBufferSize 8, samples 0, swapBehavior 2, swapInterval 1, profile 0)
PIXELFORMATDESCRIPTOR dwFlags=0x8225 PFD_DRAW_TO_WINDOW PFD_SUPPORT_OPENGL PFD_SUPPORT_COMPOSITION PFD_DOUBLEBUFFER iPixelType=0 cColorBits=32 cRedBits=8 cRedShift=16 cGreenBits=8 cGreenShift=8 cBlueBits=8 cBlueShift=0 cDepthBits=24 cStencilBits=8 iLayerType=0 cAlphaBits=8 cAlphaShift=24 cAccumBits=64 cAccumRedBits=16 cAccumGreenBits=16 cAccumBlueBits=16 cAccumAlphaBits=16 swap interval: 1
default: ContextFormat: v3.1 profile: 0 options: QFlags(0x4)
HGLRC=0x20000

Cant get button to appear

I'm trying to make some sort of fotboll app for android. The problem i'm facing right now, is that I need to make a button in the corner of the screen, (4 different) which you move the game character with. But I've made 1 button now, for moving up, but it doesnt appear on the screen.
Main file:
import QtQuick 2.0
import QtQuick.Window 2.1
Item {
id:root
width:Screen.width
height:Screen.height-10
focus:true
Keys.onPressed: {
if(event.key===Qt.Key_Up)
{
event.accepted = true;
player.y=(player.y) - 40
}
if(event.Key === Qt.Key_Down){
event.accepted = true;
player.y = (player.y)+ 40
}
if (event.key === Qt.Key_Right)
{ event.accepted=true;
player.x=(player.x)+40
}
if (event.key === Qt.Key_Left)
{event.accepted = true;
player.x=(player.x) -40
}
}
Flickable {
width:Screen.width
height:Screen.height
contentHeight: Screen.height*2
contentWidth:Screen.width
interactive:true
boundsBehavior: Flickable.StopAtBounds
contentY: Math.min(contentHeight-height, Math.max(0, player.y-height/2))
contentX: Math.min(contentWidth-width, Math.max(0, player.x-width/2))
Image{
id: feild
anchors.fill:parent
source:"Namnlös.png"
sourceSize.height:Screen.height*2
sourceSize.width:Screen.width
}
Image {
id: player
source:"asd.png"
x:Screen.width/2
y:Screen.height/2
}
}
}
Button file:
import QtQuick 2.0
import QtQuick.Window 2.1
Rectangle {
id: simplebutton
color: "grey"
width: 100; height: 50
Text {
id: buttonLabel
anchors.centerIn: parent
text: "Up"
}
MouseArea {
id: buttonMouseArea
anchors.fill: parent
onClicked: console.log(buttonLabel.text + "clicked" )
}
}
Rectangle {
id: button
property color buttonColor: "lightblue"
property color onHoverColor: "gold"
property color borderColor: "white"
signal buttonClick()
onButtonClick: {
console.log(buttonLabel.text + " clicked" )
}
MouseArea {
onClicked: buttonClick()
hoverEnabled: true
onEntered: parent.border.color = onHoverColor
onExited: parent.border.color = borderColor
}
color: buttonMouseArea.pressed ? Qt.darker(buttonColor, 1.5) : buttonColor
}
Two things:
1) You need to add your button to your layout! Since there you don't add your button into your main file, it won't appear.
2) You need to split your Button file into two separate qml file, since you can only have one "root" item per file.

Categories

Resources