Add a specific more personalized widget for your action

Shows how to add a specific/custom Qt widget to mix with or replace the default parameter editor.

You might want to add some widget or GUI to interact with the parameters of an action you developed. You can choose to:

  • add an action parameters using the addParameter(..) method, this will automatically add an interactive Qt widget to the default action widget (the GUI will depend on the parameter type).
  • replace the default action widget by your own Qt widgets (e.g. created using the Qt designer) or mix the default CamiTK action widget with your own widget. That’s what you will learn with this topic.

How to replace the default action widget?

For you information, QtDesigner is a WYSIWYG application to easily design Qt interface.

  • Add a virtual QWidget *getWidget() override; method to override the default Action getWidget() method
  • Go to the your action class .cpp file and add:
QWidget * myAction::getWidget() {
    return nullptr;
}

By default it doesn’t return anything (nullptr), thus the action viewer doesn’t display anything. You will learn how to change this code to display a new user interface for your action within the action viewer.

  • Open QtDesigner and create a new component inherited from the QWidget class.
  • Select Widget in the dialog box

Select <strong>Widget</strong> in the dialog box

  • Save this file under a .ui extension file in your action project folder (the source directory)
  • Run configure for your project again using CMake. It will automatically detect this .ui file and will generate a Qt Meta Object (moc) file, needed to correctly map the user designed (.ui) file with a corresponding c++ file.
  • Reopen your project in your IDE, you normally have an new header file of the same name of your .ui designed interface. This file is now automatically generated when compiling your project. You will include this file in your code to consider the interface designed using QtDesigner.
  • Include this file and declare an instance of it in your action class (thus you can get access to its declared components).

This reference will let you communicating within your code to any QtDesigner designed components of your interface.

Finally you can easily control your CamiTK action. Simply edit your .ui interface file using QtDesigner. And create the corresponding components c++ functions in your action class.

How to add your own widgets to the default action widget?

How is built the default action widget?

The default action widget is a QWidget. This widget contains a QLayout. This layout contains three objects:

  • The first object (index 0) is the name of the action.
  • The second object (index 1) contains the panel containing the action’s properties (Description, Targets and Parameters).
  • The third object (index 2) is the panel containing the two buttons Apply and Revert.

You can insert your own widget in this layout at one of the previous indice.

Step 1: Create your widget

You can create your widget using the Qt Designer or simply by using Qt objects. For example, to create a new QPushButton:

QPushButton *yourButton = new QPushButton("The text of your button");
QObject::connect(saveButton, SIGNAL(released()), this, SLOT(your_callback()));

Step 2: Insert your widget in the default action widget

And then add your widget in the default widget, ie add your widget in the default action widget layout:

 QLayout *informationFrameLayout = Action::getWidget()->layout();
 informationFrameLayout->addWidget(yourButton); // add the widget at the end of the layout
 Action::getWidget()->setLayout(informationFrameLayout);

You can also declare the action widget as a member of your action class, and instanciate it as the default action widget:

myWidget = new ActionWidget(this);

And then you need to get the layout of the widget to insert your own widget in it:

QBoxLayout * informationFrameLayout = dynamic_cast<QBoxLayout*>(myWidget->layout());
informationFrameLayout->insertWidget(0, yourButton); // insert the widget at the given index

Optional: hide the default Apply and Revert buttons

You might also need to hide the default buttons :

ActionWidget *actionWidget = dynamic_cast<ActionWidget * >(this->actionWidget);
actionWidget->setButtonVisibility(false);