Search code examples
typesreturncodesys

FB with FB_Init cannot be a return type


Codesys 3.5.16.70

There appears to be no way to return a type of function block if the function block has an FB_Init method. Please see the image below for a simple contrived example. I can return a reference to the function block but I would like to pass the function block type.

The purpose for doing this is, I am configuring the function block and need a temporary copy which I would place in the model of an MVC pattern (not shown in the screen shot below.) The temporary copy is what I configure until the operator saves the configuration at which time the function block is copied back to the original. This, of course, requires a function block return type.

I have thought about putting all the data of the FB in a structure and passing that but it seems an extra step, but maybe that is necessary? I cannot pass an interface of the POU as an interface is essentially a reference to the original object.

Am I missing some key element to the language that would allow me to do this simply, or is there another way to accomplish what I am trying to do?

FB with FB_Init as return type


Solution

  • As far as I know, I don't think you can return a Function Block from a Method (and Property) with a FB_Init Method since Function Blocks need to always be initialized (unless {attribute 'noinit'} is used, which doesn't seem to work with Method/Property return types).

    Your options are:

    1. Return a Reference/Pointer to the Function Block and make a copy locally in the caller:
    fb_ref: REFERENCE TO FB;
    fb_ptr: POINTER TO FB;
    {attribute 'noinit'}
    fb_copy: FB;
    
    fb_ref := InternalFBRef;
    fb_copy := fb_ref;
    
    fb_ptr := InternalFBPtr;
    fb_copy := fb_ptr^;
    
    1. Box the Function Block copy in a Structure:
    TYPE BOXED_FB :
    STRUCT
        {attribute 'noinit'}
        fb: FB;
    END_STRUCT
    END_TYPE
    
    fb_box: BOXED_FB ;
    {attribute 'noinit'}
    fb_copy: FB;
    
    fb_box := InternalFBBox;
    fb_copy := fb_box.fb;
    
    1. Return an Interface that gives you methods to configure the Function Block dirrectly.

    2. What you seem to be trying to do sounds simmilar to the Factory Pattern. Maybe see if doing it that way is more usefull, or perhaps another OOP design pattern is more apropriate here?