Migration guide from CamiTK 3.x to CamiTK 4.0

The complete guide to migrate your source code from CamiTK 3.x to CamiTK 4.0

This page explains how to modify your CamiTK 3.x code to work on the 4.x version. The CamiTK team tried to do its best to make sure that there are not a lot of changes to make to your CEP source code. Here it a complete step by step.

Prerequisite

First of all, make sure you have compiled and installed CamiTK 4.0 or up on your computer. Please follow the setup guide of this wiki.

As you may have noticed, the main new evolutions in CamiTK 4.0 compared to the previous version are the tools, libraries and frameworks it is build on: cmake version 3, Qt version 5, VTK version 6, and ITK version 4. The CamiTK API itself was not changed, but the upgrade of the version of all “build-depends” have some impact on your code. Basically CamiTK 4.0 is the same API as CamiTK 3.5 and should have the same behavior.

CamiTK 4.1 introduces changes in the API, mainly removal of methods marked deprecated in 4.0 and of obsolete API methods. See the corresponding migration guide for more information.

At this step you need to have a local or global installed CamiTK on your computer. Follow the next explanations to migrate your code on the 4.x version, it is really worth it, especially in terms of speed and memory usage.

From CamiTK 3.x to CamiTK 4.0: step by step

You will see that migrating your code from 3.x to 4.0 is very easy: all the hard work has been done in the CamiTK cmake macros.

1. Start from scratch

First make sure to erase your CEP build directory entirely

Then run the cmake configuration, and make sure that CamiTK 4 is used.

2. New Qt Plugin system

To generate any kind of CamiTK plugin (e.g., action or component extension), CamiTK use the well-defined Qt plugin mechanics. Needless to say, this has been changed in Qt5. It is possible to have a code that works with CamiTK 4.x as well as CamiTK 3.x. Just follow these instructions.

In the ActionExtension or ComponentExtension inherited class implementation file (.cpp), you need to modify the Q_EXPORT_PLUGIN2 line:

// --------------- declare the extension -------------------
#if QT_VERSION < QT_VERSION_CHECK(5, 0, 0)
    Q_EXPORT_PLUGIN2(myactionextension, MyActionExtension);
#endif

In the ActionExtension or ComponentExtension inherited class implementation header (.h), just after the Q_INTERFACES line and before the public: section, you need to add the following:

#if QT_VERSION >= QT_VERSION_CHECK(5, 0, 0)    
    Q_PLUGIN_METADATA(IID "fr.imag.camitk.cepname.exttype.extname")
#endif

Where:

  • cepname should be replaced by the name of your cep (e.g., imaging),
  • exttype should be replaced by either:
    • action, if this is an ActionExtension or
    • component, if this is a ComponentExtension
  • extname should be replaced by the name of your extension (e.g., itkfilters).

The IID is not linked with the copyright or intellectual property of your plugin.

Using this naming convention guarantees the uniqueness of the IID.

There can only be exactly one occurrence of this macro in the source code for a CamiTK plugin.

For an ActionExtension for example, in CamiTK 3.x you had

class MyActionExtension : public camitk::ActionExtension {
    Q_OBJECT
    Q_INTERFACES(camitk::ActionExtension)

public:
...

And in CamiTK 4.x, you should have:

class MyActionExtension : public camitk::ActionExtension {
    Q_OBJECT
    Q_INTERFACES(camitk::ActionExtension)
    Q_PLUGIN_METADATA(IID "fr.imag.camitk.mycep.action.myactionext")

public:
...

3. New VTK 6 version

If you have any compilation error such as:

error: class vtkxxx has no member named Update
error: class vtkyyy has no member named SetInput

(where generally vtkxxx is a data object and vtkyyy is an algorithm/filter), please check the VTK 6 migration guide overview and the whole migration guide to VTK 6. The remaining of this section is just a digest of this overview. Please take the time to read it well.

The main backwards-incompatible change in VTK 6 compared to VTK 5 is the removal of data objects’ dependency on the pipeline.

Therefore, as explain the VTK 6 migration guide overview, you need to change from

vtkSmartPoint<vtkxxx> dataObject = someAlgorithm->GetOutput();
dataObject->Update();

To this:

someAlgorithm->Update();

If you had lines likes

someFilter->SetInput(someReader->GetOutput());

it should be changed to:

someFilter->SetInputConnection(someReader->GetOutputPort());

Beware that in VTK 6, since the data object no longer has a reference to the algorithm that produced it, it is not possible to establish a pipeline connection given only a data object. See the VTK wiki page about the replacement of SetInput method.

In order to make it easy to assign a stand-alone data object as an input to an algorithm, VTK 6 introduced a set of convenience functions, for instance:

someFilter->SetInputData(aDataObject);

that even though the following will compile, it will NOT create a pipeline connection and should not be used in place of SetInputConnection().

someFilter->SetInputData(someReader->GetOutput());

Another advantage of decoupling data objects from pipeline objects is that developers no longer need to create shallow copies of inputs in order to use internal filters. This change removes some circular references from the pipeline making it unnecessary to use the garbage collector. This should have a noticeable impact on the performance of VTK when using large pipelines.

FAQ

Old plugin system used error

If you have the following error message at compilation time:

error: static assertion failed: Old plugin system used
Q_EXPORT_PLUGIN2(xxx, xxx);

Please check step 2 of the step by step procedure

class vtkxxx has no member named Update

See step 3 (migration to VTK6)

class vtkxxx has no member named SetInput

See step 3 (migration to VTK6)