Overview | All Modules | Tutorial | User's Guide | Programming Guide
Previous

COVISE Online Documentation

Next


Example Modules

Hello

The "Hello" module shows just the minimal framework needed to build a module. It only defines the basic routines without implementing any functionality.

Hello.h:

Make sure we never include the header twice

#ifndef HELLO_H
#define HELLO_H

// +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
// ++                                                  (C)2000 RUS  ++
// ++ Description: "Hello, world!" in COVISE API                    ++
// ++ Author:                                                       ++
// ++                         Andreas Werner                        ++
// ++            Computing Center University of Stuttgart           ++
// ++                         Allmandring 30                        ++
// ++                        70550 Stuttgart                        ++
// ++                                                               ++
// ++ Date:  10.01.2000  V2.0                                       ++
// +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++

Basic module header file for API and library calls

 
#include <api/coModule.h>

class Hello : public coModule
{
   private:

The compute callback reacts on the execute messages

   
     /// this module has only the compute callback
      virtual void compute(const char *);
   
   public:

Construct the module

      /// this is the Constructor
      Hello(int argc, char *argv[]);

};

#endif

Hello.cpp:

// +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
// ++ Description: "Hello, world!" in COVISE API        (C)2000 RUS ++
// ++ Author:                                                       ++
// ++                         Andreas Werner                        ++
// ++            Computing Center University of Stuttgart           ++
// ++                         Allmandring 30                        ++
// ++                        70550 Stuttgart                        ++
// ++ Date:  10.01.2000  V2.0                                       ++
// +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
 
///// this includes our own class's headers
#include "Hello.h"

///// Constructor : This will set up module port structure
Hello::Hello(int argc, char *argv[])

Set a module description

      :coModule(argc, argv, "Hello, world! program")

This is a really primitive module

{    
      // no parameters, no ports...
}   

///// compute() is called once for every EXECUTE message
void Hello::compute(const char *)

Just send an INFO message

{ 
      sendInfo("Hello, COVISE!");
} 
 
// ++++  What's left to do for the Main program: 
// ++++  create the module and start it 

\hline
   {\bf Create the module} \\
   {\bf And start it ...} \\
\hline

MODULE_MAIN(Examples, Hello)

Filter

The second example implements a scaling of an unstructured grid: The structure information (element list, type list and connectivity) are simply copied while the corner coordinates are scaled by a constant factor.

By convention, we name the implementation class and the main source and header file like the module name, in this case "Enlarge". We also always name the ports and parameters "p_..."

Enlarge.h:

#ifndef ENLARGE_H
#define ENLARGE_H
 
// +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
// ++ Description: Filter program in COVISE API        (C)2000 RUS  ++
// ++ Author:                                                       ++
// ++                         Andreas Werner                        ++
// ++            Computer Center University of Stuttgart            ++
// ++                         Allmandring 30                        ++
// ++                        70550 Stuttgart                        ++
// ++ Date:  10.01.2000  V2.0                                       ++
// +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++  
 
#include <api/coModule.h>
 
class Enlarge : public coModule
{
   private:
                                             

      /// this module has only the compute call-back
      virtual void compute(const char *);

This will be the slider for the enlargement factor

      
      ////////// parameters
      coFloatSliderParam *p_scale;

An input and an output port. By convention, all ports start with "p_"

     
      ////////// ports
      coInputPort  *p_inPort;
      coOutputPort *p_outPort;

          
   public:
 
      Enlarge(int argc, char *argv[]);
};
 
#endif

Enlarge.cpp:

// +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
// ++ Description: Filter program in COVISE API        (C)2000 RUS  ++
// ++ Author:                                                       ++
// ++                         Andreas Werner                        ++
// ++            Computer Center University of Stuttgart            ++
// ++                         Allmandring 30                        ++
// ++                        70550 Stuttgart                        ++
// ++ Date:  10.01.2000  V2.0                                       ++
// +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++  
 
#include "Enlarge.h"
 
// Construct the module 
 
Enlarge::Enlarge(int argc, char *argv[])

The module's description

  
      :coModule(argc, argv, "Enlarge, world! program")
          
{    
   // Parameters
   
   // create the parameter

The parameter is not created with its constructor, but by calling a member of coModule to register it at the module

The parameter's name must be unique, the description doesn't

       
   p_scale = addFloatSliderParam("scale","Scale factor for Grid");

Default values for the enlargement factor: between 0.1 and 5.0, current value 2.0

                                                               
   // set the default values
      
   p_scale->setValue(0.1,5.0,2.0);

Input and output ports: Unique name, Type list (here only one type), and description

// Ports
   p_inPort  =  addInPort("inPort", "UnstructuredGrid",
                                            "Grid input");
   p_outPort = addOutputPort("outPort","UnstructuredGrid",
                                           "Grid output");
 					   
}   


// compute callback: called when new input data arrived
void Enlarge::compute(const char *) 
{ 
   int i;

Retrieve Object from Port

   
   coDistributedObject *obj = p_inPort->getCurrentObject();

Check whether we got an object

     // we should have an object
   if (!obj)  
   {
      sendError("Did not receive object at port %s",
                 p_inPort->getName());
      return;
   }

Check the type: This is not guaranteed by the port types!

  
  // it should be the correct type
   coDoUnstructuredGrid *inGrid = dynamic_cast<coDoUnstructuredGrid *>(obj);
   if ( !inGrid )
     
   {
      sendError("Received illegal type at port '%s'",
                 p_inPort->getName());
      return;
   }

We can safely cast up: we checked the type

 
   // So, this is an unstructured grid
    
   // retrieve the size and the list pointers
   int   numElem,numConn,numCoord,hasTypes;
   int   *inElemList,*inConnList,*inTypeList;
   float *inXCoord,*inYCoord,*inZCoord;

This call retrieves the field sizes from the object

   inGrid->getGridSize(&numElem,&numConn,&numCoord);

Do we have a type list?

       
   hasTypes = inGrid->hasTypeList();

This gives us the pointers to the data in shared memory

                                            
   inGrid->getAddresses(&inElemList,&inConnList,
                        &inXCoord,&inYCoord,&inZCoord);

If we have a type list, we must copy it, too.

    
   if (hasTypes)
      inGrid->getTypeList(&inTypeList);

Now allocate a new, empty USG object

                                       
   
   // allocate new Unstructured grid of same size
   coDoUnstructuredGrid *outGrid  
               = new coDoUnstructuredGrid(p_outPort->getObjName(),                                                                                                 numElem,numConn,numCoord,
                                         hasTypes);

Oops, something went wrong here

       
   if (!outGrid->obj_ok())
   {
      sendError("Failed to create object '%s' for port '%s'",
                 p_outPort->getObjName(),p_outPort->getName());
  
      return;
   }
   
   int   *outElemList,*outConnList,*outTypeList;
   float *outXCoord,*outYCoord,*outZCoord;

This gives us access to the data space in shared memory. Beware of overwriting any fields

   outGrid->getAddresses(&outElemList,&outConnList,
                         &outXCoord,&outYCoord,&outZCoord);

We have a type list. So here it is:

    
   if (hasTypes)
      outGrid->getTypeList(&outTypeList);

We do not change the grid, so we copy all fields except the coordinates

      
   /// copy element list
   for (i=0;i<numElem;i++)
      outElemList[i] = inElemList[i];
   
   /// if we have one, copy the types list
   if (hasTypes)
      for (i=0;i<numElem;i++)
         outTypeList[i] = inTypeList[i];
 
   /// copy connectivity list
   for (i=0;i<numConn;i++)
      outConnList[i] = inConnList[i];

Get the current value from the slider

       
   /// retrieve parameter
   float scale = p_scale->getValue();

Negative or zero values make no sense: correct value and correct parameter on the user interface

       
   if (scale<=0)

Now put scaled coordinates into new object's memory

       
   {
      scale = 1.0;
      p_scale->setValue(1.0)
   }
 
   /// copy coordinates and scale them
   for (i=0;i<numCoord;i++)
   {
       
      outXCoord[i] = inXCoord[i] * scale;
      outYCoord[i] = inYCoord[i] * scale;
      outZCoord[i] = inZCoord[i] * scale;
   }

This is the output object for the port

   // finally, assign object to port
   p_outPort->setCurrentObject(outGrid);
   
}

Important: Never delete the objects you assigned to a port!

     
// +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
// ++++  What's left to do for the Main program: 
// ++++                         create the module and start it 
// +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
 
MODULE_MAIN(Examples, Enlarge)

Try to enhance the module: Different scales for each axis...
PreviousNext


Authors: Martin Aumüller, Ruth Lang, Daniela Rainer, Jürgen Schulze-Döbold, Andreas Werner, Peter Wolf, Uwe Wössner
Copyright © 1993-2022 HLRS, 2004-2014 RRZK, 2005-2014 Visenso
COVISE Version 2021.12