Trouble embedding a QComboBox in a QTableWidget - c++

I'm making a GUI using QT, and I'd like to have the final entry in my table be a combo box. The idea is to allow the user to chose new items to put in the table from a drop-down list.
What I seem to be having trouble with is embedding this combo box inside a table cell. I've tried this:
table_widget = new QTableWidget(1, 9, Dialog);
table_widget->setObjectName(QStringLiteral("table_widget"));
add_part_combo = new QComboBox(table_widget);
add_part_combo->setObjectName(QStringLiteral("add_part_menu"));
add_part_combo->addItem(QStringLiteral("Import New Items..."));
table_widget->setCellWidget(1, 1, add_part_combo);
If I construct the combo box with Dialog, it puts the combo box in the upper left corner of the dialog (somewhat under the table). If I instead construct it with table_widget, the combo box appears in the upper left of the table (on top of the first header cell). If I don't supply a parent widget, then it doesn't appear at all.
But in no circumstance does the widget actually appear in cell 1,1.
What am I doing wrong?

The row and column parameters passed to setCellWidget are zero-indexed. Also, you don't need to provide a parent for the QComboBox since the QTableWidget will assume ownership of it when you call setCellWidget. As such, your code should be as follows:
add_part_combo = new QComboBox;
add_part_combo->setObjectName(QStringLiteral("add_part_menu"));
add_part_combo->addItem(QStringLiteral("Import New Items..."));
// Note: Row and column 0, not 1.
table_widget->setCellWidget(0, 0, add_part_combo);

Related

C++ Windows Owner Drawn Main Menu -- itemID

I am attempting to create an owner-drawn main menu, in Windows. I understand setting:
menuiteminfo.ftype = MFT_OWNERDRAW
I also know about handling the WM_MEASUREITEM and WM_DRAWITEM messages.
However, how do I know which main menu item is sending the message? (so that I can fill-in the appropriate box size and text) "itemID" seems to be the only unique identifier. But, how can I associate this pointer/handle to the item in question? I can use "lParam" to determine it is a menu item. But, I can't determine which menu item. "GetMenuItemID" is useless, as it returns "-1" for all main-menu items.
Or, am I going about this all-wrong? I have been searching for answers, for weeks. Really, all I want to do is change the text color of the main menu, from black, to white or light gray, so I can use a dark background.
The itemID field of the MEASUREITEMSTRUCT and DRAWITEMSTRUCT structs tells you exactly which menu item is being measured/drawn. This is the ID that you specify when you create/modify a menu item. That ID is specified via either:
the uIDNewItem parameter of AppendMenu(), InsertMenu(), or ModifyMenu().
the item parameter of InsertMenuItem() or SetMenuItemInfo()
the wID field of the MENUITEMINFO struct that you pass to InsertMenuItem() or SetMenuItemInfo().
Use whatever IDs you want, as long as they are unique for your menus.
You can also use the itemData field of MEASUREITEMSTRUCT and DRAWITEMSTRUCT to receive any custom data you want for owner-drawn menu items, if you so desire (like, for example, a pointer to a buffer that contains a menu item's text string). This custom value can be anything you want that is meaningful for you. You set this value in the dwItemData field of the MENUITEMINFO struct that you pass to InsertMenuItem() or SetMenuItemInfo().
This is all covered in the documentation:
Using Menus: Creating Owner Drawn Menu Items
Thank you Remy. Through the items that you mentioned, and researching the documentation for each, I was able to find a buried secret. For a Main Menu item, the "itemID" in both the MEASUREITEMSTRUCT and DRAWITEMSTRUCT is the handle to the drop-down menu of that item. From that, I added this line of code to WM_CREATE, to associate the itemID with the numerical (zero-based) position:
mItemID[i] = int(GetSubMenu(hMenu, i));
'i' is the numerical position, from left to right. I can then use a comparison statement like this, in WM_MEASUREITEM and WM_DRAWITEM:
lpmis=(LPMEASUREITEMSTRUCT)lParam; if(lpmis->itemID==mItemID[i])

qt QTableWidget programattic select of cell - how to make ready with cursor in?

Environment:
Qt 4.7.1
Qt Creator 2.1.0
c++
Problem:
I have a QTableWidget. I add a row, and then select the first cell.
What I want is to be able to immediately type into the cell after the program selects it, so I don't have to reach for the mouse.
The behavior of the select is to highlight the cell, not put a cursor in it. I have to click on the cell with the mouse before I can type.
Everything I've found so far to do with selection behavior has to do with row, column, or cell selection options; nothing about what the selection of a cell actually does.
Here's my code thus far, works as described; rc is the index to the last row, already determined:
ui->thetable->scrollToBottom();
QModelIndex index = ui->thetable->model()->index(rc, 0);
ui->thetable->selectionModel()->select(index,QItemSelectionModel::Select);
You can use the edit method this way:
ui->thetable->edit(index);
using the index you already computed, or you could connect a custom signal of yours to void QAbstractItemView::edit ( const QModelIndex & index ) slot inherited by QTableWidget's items.

Select item from one ComboBox and remove that item from other ComboBoxes

Im writing an QT application, where I have 3 QComboBoxes, with a list of values. I'm trying to do so, when I select one item in a QComboBox, I will remove it from the other QComboBoxes, and when I select another or nothing, it will reappear in the other QComboBoxes again.
Do you have any ideas for this?
Edit:
I have tried to use QStringList, where I had a slot, which removed it from the other QComboBoxes, but it was very bugged and often inserted 2 whitespaces and the same drink twice.
If all comboboxes contain the same items, then you can use the current index of one combobox to disable and hide that index of other comboboxes.
You can just subclass QComboBox and create a slot like this:
void MyComboBox::disableItem(int index)
{
QListView *list_view = qobject_cast<QListView*>(view());
if(list_view)
{
QStandardItemModel *model = qobject_cast<QStandardItemModel*>(list_view->model());
list_view->setRowHidden(index, true);
if(model)
{
model->item(index, 0)->setEnabled(false);
}
}
}
Then you just connect the QComboBox::currentIndexChanged(int index) signal from other comboboxes to this slot. Do this for all 3 comboboxes.
You should also create a logic for enabling and showing the items again when they shouldn't be disabled. It's almost the same function as the one above. You could just create a list of indexes that should be hidden for that combobox and use that to show all the other indexes.

QListWidgetItem with Radio Button

I'm working on my first QT application and I have a problem with QListWidgetItems.
I will be having different kind of list.
for checkboxed list using:
listElement[i]->setFlags(Qt::ItemIsEnabled);
listElement[i]->setCheckState(Qt::Unchecked);
works exactly as wanted.
But now I want a Radio Button list. so my question is in two parts
can use the same logic that I used for checkBox to create Radio Buttons?
I have used:
listElement[i]->setFlags(Qt::ItemIsEnabled);
QRadioButton *radio1 = new QRadioButton(0);
dlList->setItemWidget(listElement[i],radio1);
this will display Items in the list with a radio Button, the problem is that the text is Over the Radio Button:
going to try to demonstrate without image
This is a test
o
for elements 1
instead for checkbox I have
This is a test
[]
for element 1
how can I get the radioButton to align correctly with text?
New Questions:
Thanks alot for the answers my text is next to my RadioButton now.
Only thing there is no WordWrap, My text is Longer than maximum Size of the RadioButton. How can I get it to wordwrap:
rButton = new QRadioButton();
rButton->setFixedSize(LIST_TEXT_WIDTH_WO_ICON, LIST_TEXT_HEIGHT);
rButton->setStyleSheet("border:none");
rButton->setFont(segoe18Font);
rButton->setText("This is just a test for elementsss of type euh!!!");
rButton->setSizePolicy(QSizePolicy::Fixed, QSizePolicy::Preferred);
dropListWidget->setItemWidget(listElement, rButton);
As you may have read, there are two approaches to achieve what you want.
The most flexible one: use a QListView, implement a new delegate and a model if necessary.
Keep using the classic item-based interface (QListWidget) and change the item's widgets either by sub-classing QListWidgetItem or calling QListWidgetItem::setItemWidget.
Since the question points towards the second one, I'll try to provide the simplest item-based solution.
The following piece of code generates the list widget in the picture.
QListWidgetItem *it;
it = new QListWidgetItem(ui->listWidget);
ui->listWidget->setItemWidget(it, new QRadioButton(tr("Item 1")));
it = new QListWidgetItem(ui->listWidget);
ui->listWidget->setItemWidget(it, new QRadioButton(tr("Item 2")));
// .
// .
// .
it = new QListWidgetItem(ui->listWidget);
ui->listWidget->setItemWidget(it, new QRadioButton(tr("Item N")));
where ui->listWidget is a pointer to the QListWidget that holds the items.
I hope this helps. As far as I understand, that's what you need.

Add button to QTableWidget cell alongside with entry

I have a QTableWidget and one column of it is for specifying file path. I want to provide user with two options, writing the path, or specifying it using QFileDialog. When I added a button as cell widget, it covered whole cell and the entry disappeared.
QPushButton *browseButton = new QPushButton("...", tableWidget);
tableWidget->setCellWidget(rowCount, 3, browseButton);
How can I insert QPushButton or QAction with QIcon alongside with entry?