Groupboxes behaving as radiobuttons - qt

I know it is possible to have Radio Buttons (or any other item) in a GroupBox title, but the behavior of those is not linked.
Here is an image of my interface
Right now, the user can give confirmation either by clicking the "Create lesion" button, or clicking on an existing lesion in the list. I would like to let the user choose either one groupBox or the other, and disable the related information, so as to have a single confirmation button.

Use the label property to add the RadioButton, and ButtonGroup's attached group property to make the group boxes exclusive with each other:
import QtQuick 2.10
import QtQuick.Controls 2.3
import QtQuick.Layouts 1.3
ApplicationWindow {
width: 640
height: 480
visible: true
ButtonGroup {
id: checkGroup
}
RowLayout {
GroupBox {
id: newLesionGroupBox
title: "New lesion"
label: RowLayout {
RadioButton {
id: newLesionRadioButton
checked: true
ButtonGroup.group: checkGroup
}
Label {
text: newLesionGroupBox.title
font: newLesionGroupBox.font
}
}
Column {
enabled: newLesionRadioButton.checked
Label {
text: "Some stuff"
}
Button {
text: "Blah"
}
}
}
GroupBox {
id: existingLesionGroupBox
title: "Existing lesion"
label: RowLayout {
RadioButton {
id: existingLesionRadioButton
ButtonGroup.group: checkGroup
}
Label {
text: existingLesionGroupBox.title
font: existingLesionGroupBox.font
}
}
Column {
enabled: existingLesionRadioButton.checked
Label {
text: "Some stuff"
}
Button {
text: "Blah"
}
}
}
}
}
You can tidy this up a lot by making a reusable component out of the group box.
Each visual part of a control that can be customised has a link to the customisation docs, by the way. In this case, it links here:
https://doc.qt.io/qt-5/qtquickcontrols2-customize.html#customizing-groupbox

Related

How to style MenuBarItem with mnemonics strings in QML

I want to customize MenuBar (from QtQuick.Controls 2.4) in my Qt application, so I followed the example from Qt website (https://doc.qt.io/qt-5/qtquickcontrols2-customize.html#customizing-menubar).
The example does not contain mnemonics, however. Here is my code for the MenuBar which has mnemonics:
import QtQuick 2.9
import QtQuick.Controls 2.4
import QtQuick.Layouts 1.11
import "../singletons"
MenuBar {
Menu {
title: qsTr("&File")
Action { text: qsTr("&Open...") }
Action { text: qsTr("&Save") }
Action { text: qsTr("Save &As...") }
MenuSeparator { }
Action { text: qsTr("&Quit") }
}
Menu {
title: qsTr("&Edit")
Action { text: qsTr("Cu&t") }
Action { text: qsTr("&Copy") }
Action { text: qsTr("&Paste") }
}
Menu {
title: qsTr("&Help")
Action { text: qsTr("&About") }
}
background: Rectangle {
color: Style._ColorPrimaryDark
}
delegate: MenuBarItem {
id: menuBarItem
contentItem: Text {
text: menuBarItem.text
opacity: enabled ? 1.0 : 0.3
color: "white"
verticalAlignment: Text.AlignVCenter
}
}
}
When I run the code, the MenuBar items look like this (the mnemonic shortcuts still work though):
Without the style, the MenuBar items have the mnemonic character underlined as expected:
I couldn't find anything about this problem. Is there any way or workaround so I could keep the mnemonics and customize the looks?
Looks like a bug. The native element uses some private control IconLabel which isn't accessible ( see it here). Using Label also doesn't solve the issue. So the solution is avoiding item customization, or to use some stupid workaround like this:
delegate: MenuBarItem {
id: menuBarItem
function replaceText(txt)
{
var index = txt.indexOf("&");
if(index >= 0)
txt = txt.replace(txt.substr(index, 2), ("<u>" + txt.substr(index + 1, 1) +"</u>"));
return txt;
}
contentItem: Label {
text: replaceText(menuBarItem.text)
color: "white"
verticalAlignment: Text.AlignVCenter
textFormat: Text.RichText
}
}

QML Cannot create Submenu in Menu

I'm trying to create a menu
import QtQuick 2.0
import QtQuick.Controls 2.2
...
Menu {
id: menu
title: "mainMenu"
MenuItem {
text: "menuItem1"
}
MenuItem {
text: "menuItem2"
}
Menu {
title: "contextMenu"
MenuItem {
text: "item1"
}
MenuItem {
text: "item2"
}
}
}
But when I'm trying menu.open() there is no contextMenu
Please find a screenshot below.
How do I fix this?
Qt Quick Controls 2.3 (Qt 5.10) adds support for nested menus and cascading sub-menus.
Maybe you meant to use QtQuick.Controls 1.x where those sub-menus are supported.
In QtQuick.Controls 2.2 - the version you are using - Menu inherits from Popup and therefore behaves like such - meaning, they are closed by default, and you need to set them visible or open() them.
The MenuItem on the other hand are AbstractButtons, that are preconfigured, to close Popups when clicked. If you want to use the QtQuick.Controls 2.x-style Menu you can define your own child type SubMenu which is a button that does not close the parent Popup but opens a second Menu as needed or inserts the right MenuItems when clicked (Accordion-style).
The right implementation depends on your requirements but should not be too challenging. Feel free to ask, if you need more help on this.
Maybe you can use Button instead of MenuItem,and adjust the background of Button yourself,Wrap them up
Item {
id: root
width: 500
height: 500
MouseArea {
id: mouse
anchors.fill: parent
onClicked: {
rootMenu.open()
}
}
Menu {
id: rootMenu
title: "rootMenu"
Button {
text: "menuItem1"
onClicked: {
console.log("choose A")
rootMenu.close()
}
}
Button {
text: "menuItem2"
onClicked: {
console.log("choose B")
rootMenu.close()
}
}
Button {
id: menu_c
text: "menuItem3"
onClicked: secondMenu.open()
}
}
Menu {
id: secondMenu
x: rootMenu.width
y: menu_c.y
MenuItem {
text: "item1"
onTriggered: {
console.log("item1")
rootMenu.close();
}
}
MenuItem {
text: "item2"
onTriggered: {
console.log("item2")
rootMenu.close();
}
}
}
}

Fill TabView from Pages' titles of corresponding SwipeView

Straitforward approach to create a multiple separate visible pages with easy navigation is to use SwipeView and TabBar together:
import QtQuick 2.9
import QtQuick.Controls 2.2
import QtQuick.Layouts 1.3
Page {
id: page
header: TabBar {
id: tabBar
currentIndex: swipeView.currentIndex
TabButton {
text: qsTr("Page1")
}
TabButton {
text: qsTr("Page2")
}
}
SwipeView {
id: swipeView
width: page.width
height: page.height
currentIndex: tabBar.currentIndex
Page {
width: swipeView.width
height: swipeView.height
title: qsTr("Page1")
Pane {
anchors.fill: parent
}
}
Page {
width: swipeView.width
height: swipeView.height
title: qsTr("Page2")
Pane {
anchors.fill: parent
}
}
}
}
There is title property in the Page component. It is not visible in the above case, but it is proper place to store the tab title on my mind. Can I generate (say, using Repeater) a contents of TabBar using some properties of SwipeView pages (namely .title) to fill TabButton.text?
I looked through documentation, but can't find a property of SwipeView, which allows me to get access to its pages by means of indices (e.g. pages[index]).
Qt Quick is great! I found the answer really quickly:
Repeater {
model: swipeView.count
TabButton {
text: swipeView.contentChildren[index].title
}
}
or even simplier
Repeater {
model: swipeView.contentChildren
TabButton {
text: modelData.title
}
}

QT 5.7 QML How to control which Control gets the focus within a TabView

I'd like to arrange for a specific control to get the focus within a TabView Tab. Its seems that the first one gets the focus regardless of what I do. I have tried setting focus:false everywhere else but it doesn't work.
Consider the following code. I have a simple column containing two RadioButtons and a TextField. I'd like to arrange for the TextField to always get focus when the tab is selected, but it always goes to the first RadioButton
import QtQuick 2.7
import QtQuick.Controls 1.4
import QtQuick.Controls.Styles 1.4
import QtQuick.Layouts 1.3
ApplicationWindow
{
visible: true
width: 800
height: 400
TabView
{
anchors.fill: parent
Tab { title: "tab1"; sourceComponent: foo }
Tab { title: "tab2"; sourceComponent: foo }
}
Component
{
id: foo
ColumnLayout
{
spacing: 32
ExclusiveGroup { id: optionGroup }
RadioButton
{
// i always get the focus!!
exclusiveGroup: optionGroup
text: "Click me"
activeFocusOnPress: true
focus: false
}
RadioButton
{
exclusiveGroup: optionGroup
text: "No, click me!"
activeFocusOnPress: true
focus: false
}
TextField
{
// but i want the focus
placeholderText: "type here"
focus: true
}
}
}
}
Press "tab2" to see this,
I tried forcing within TabView by adding,
onCurrentIndexChanged: getTab(currentIndex).item.forceActiveFocus()
But it makes no difference.
I've read the explanation of focus but it hasn't helped in this case.
Thanks for any suggestion or help,
Probably a bug. Try Qt Quick Controls 2.0 instead:
import QtQuick 2.7
import QtQuick.Controls 2.0
import QtQuick.Layouts 1.3
ApplicationWindow {
visible: true
width: 800
height: 400
header: TabBar {
id: bar
width: parent.width
TabButton {
text: qsTr("tab1")
}
TabButton {
text: qsTr("tab2")
}
}
StackLayout {
anchors.fill: parent
currentIndex: bar.currentIndex
ColumnLayout {
id: columnLayout
spacing: 32
ButtonGroup {
id: optionGroup
buttons: columnLayout.children
}
RadioButton {
text: "Click me"
}
RadioButton {
text: "No, click me!"
}
TextField {
placeholderText: "type here"
focus: true
}
}
}
}

how to send text field values from one qml to another qml page in cascades blackberry

I am new to development on BB cascades. I've created two QML Pages. I want to pass data from one QML Page to another.
I want to pass the values phonenumber(id:phonenumber) and amount ( id:amount) from mobile.qml to payment.qml.
Please anyone help me out. Thank you in advance.
Mobile.qml:
import bb.cascades 1.4
import bb.data 1.0
Page {
onCreationCompleted: {
getData()
getCircle()
}
Container {
background: backgroundPaint.imagePaint
attachedObjects: [
ImagePaintDefinition {
id: backgroundPaint
imageSource: "asset:///images/background.png"
}
]
TextField {
id:phonenumber
hintText: "Enter Phone Number"
horizontalAlignment: HorizontalAlignment.Center
verticalAlignment: VerticalAlignment.Center
topMargin: ui.du(3)
// On text change the label text is updated.
input
{
keyLayout: KeyLayout.Text
}
}
TextField {
id:amount
hintText: "Enter Amount"
horizontalAlignment: HorizontalAlignment.Center
verticalAlignment: VerticalAlignment.Center
topMargin: ui.du(3)
// On text change the label text is updated.
input
{
keyLayout: KeyLayout.Text
}
}
Button {
id: newButton
horizontalAlignment: HorizontalAlignment.Center
verticalAlignment: VerticalAlignment.Center
topMargin: ui.du(3)
text: "Recharge"
appearance: ControlAppearance.Primary
color: Color.create("#F93249")
onClicked: {
var blogpage = goToWebView.createObject();
navigationPane.push(blogpage);
}
attachedObjects: ComponentDefinition {
id: goToWebView
source: "payment.qml"
}
}
}
attachedObjects: [
ComponentDefinition {
id: newOptionDef
Option {}
}
]
}
payment.qml:
import bb.cascades 1.4
Page {
Container {
background: backgroundPaint.imagePaint
attachedObjects: [
ImagePaintDefinition {
id: backgroundPaint
imageSource: "asset:///images/background.png"
}
]
}
}
Next time please post only code related to problem. As for your problem you can use parent as a proxy to access one item from another one.
For example, assume we have a component:
Page.qml
import QtQuick 2.4
import QtQuick.Controls 1.2
Item {
id:page
width: 200
height: 200
property int callee
function func() {
txt.text = txt.text + " (changed)"
}
Text {
id: txt
anchors.centerIn: parent
text: "click me"
MouseArea {
anchors.fill: parent
onClicked: {
page.parent.proxyFunction(page.callee);
}
}
}
}
and so Item contains several Pages:
import QtQuick 2.4
import QtQuick.Window 2.0
Window {
width: 400
height: 200
Row {
anchors.fill: parent
function proxyFunction(page) {
children[page].func();
}
Page {callee: 1}
Page {callee: 0}
}
}
So here as you can see clicking Text in one of Pages triggers changing Text in another Page.
In your Page add these lines:
import bb.cascades 1.4
import bb.data 1.0
Page {
id: mobilePage // ADD THIS
property string m_amount // ADD THIS
property string m_phoneNumber // ADD THIS
// the rest of the code
onClicked: { // Buttons onClick
mobilePage.m_amount = amount.text // ADD THIS
mobilePage.m_phoneNumber = phonenumber.text // ADD THIS
var blogpage = goToWebView.createObject()
navigationPane.push(blogpage)
}
}
Now in payment.qml you can use this:
console.log(mobilePage.m_amount)
console.log(mobilePage.m_phoneNumber)
You have to create a property in payment.qml at page level.
Page{
Id: payment
Properly string phonenumber;
Properly string amount;
Container{
Label{
Id: lblphonenumber
text: phonenumber
}
Label{
Id: lblamout
text: amount
}
}
in your main.qml you have to do this:
onClicked: {
var blogpage = goToWebView.createObject();
blogpage.phonenumber = yourvalue;
blogpage.amount = yourvalue;
navigationPane.push(blogpage);
}
This is it :)

Resources