My blog has been moved to ariya.ofilabs.com.

Wednesday, March 15, 2006

Resize Pop-up List of A Combo Box

You want to be able to resize the pop-up list of a combo box. Normally, this pop-up list has always the same width as the combo box. However, in certain cases the width of the combo box needs to be fixed. But if the pop-up list does not expand itself, then only part of the items on the list is visible as illustrated here:

In this particular situation, the look of the pop-up list will be better if it can be resized independently from the combo box itself.

QComboBox unfortunately does not provide public functions to access its pop-up list. Also, the pop-up list widget itself is not accessible. It is possible to create a subclass of QComboBox and reuse its private members (in header file qcombobox_p.h), but this would have required a quite amount of effort.

By looking at the source of QComboBox, we find out that the pop-up widget is QComboBoxPrivateContainer. It is also constructed as a child widget of the combo box. Using run-time introspection feature of Qt, it is very easy to find this widget and change its size:

void resizeComboBoxPopup(QComboBox* comboBox, int width, int height)
{
  if(!comboBox) return;
  
  // force the construction of QComboBoxViewContainer
  comboBox->view();  

  // iterate to find QComboBoxPrivateContainer
  QWidget* popup = 0;
  QObjectList objects = comboBox->children();
  for(int i = 0; i < objects.size(); ++i)
  {
      QObject* obj = objects.at(i);
      if(obj->inherits("QComboBoxPrivateContainer")) 
          popup = qobject_cast<QWidget*>(obj);
  }
  
  if(popup)
    popup->resize(width, height);
}    

Of course, this cheap trick is only a workaround and only works as long as the implementation of QComboBox does not change too much. It can also be considered as a crime to Qt. So, kids, don't try this at home...

3 comments:

Thomas Matelich said...

you could save yourself a few cycles with a break in your if in the for loop.

if(obj->inherits(...)) { popup = ...; break; }

Alex said...

What about:

Q3ComboBox cb = ...
Q3ListBox * lb;
lb = combobox->listBox();
// adjust size of lb here

In Qt Creator, you can promote QComboBox to Q3ComboBox. I did not try it yet but seems clean.

Anonymous said...

http://developer.qt.nokia.com/faq/answer/how_can_i_change_the_width_of_the_popup_list_in_my_combobox Simple way to do it.