Retrieve form parameter into fieldset

Hi,
I have passed parameters when calling my form in my controller. My form contains a fieldset in wich I need to retrieve data from table according the passed parameters in my form.
How can I get those parameters ?

Here is my action in my controller :

namespace Application\Controller;

use InvalidArgumentException;

use Commun\Form\Modules\Application\RealisationImpactForm;
use Commun\Model\Entity\Projet;
use Commun\Model\Entity\Supervision;
use Laminas\Hydrator\ArraySerializableHydrator;
use Commun\Controller\NslabsAbstractController;
use Laminas\View\Model\ViewModel;

class SupervisionController extends NslabsAbstractController
{
    public function realisationImpactAction(){
        $post=$this->post;  
        $mapperProjet = $this->SM->get('TPROJET');
        $mapperDoc = $this->SM->get('TDOC');
        //$hydrator = new ArraySerializableHydrator();
        //$reflectionHydrator = new \Laminas\Hydrator\ReflectionHydrator();
        $supervision  = new Supervision();
        
        $id = (int) $this->params()->fromRoute('id');       
        if (0 === $id) {              
            return $this->redirect()->toRoute('front-supervision',['action' =>  'edition-projet','id' => $id]);
        }
        
        $projet = $mapperProjet->fetchRow(['idProjet' => $id]);
        $docs = $mapperDoc->getDocsByProjetId($id);
        
        $realisationImpactForm = $this->formManager->get(RealisationImpactForm::class,['idProjet' => $id,'idSupervision' => 1]);     
        
        //$realisationImpactForm->bind($supervision)->setInputFilter($supervision->getInputFilter())->setData($post);         
        if(!$post){
            return new ViewModel(['form' => $realisationImpactForm,'user' => $this->user,'id' => $id,'projet' => $projet,'docs' => $docs]);
        }                
              
    }
        
}

Here is my form :

namespace Commun\Form\Modules\Application;

use Commun\Form\Modules\Application\Fieldset\RealisationImpactFieldset;

use Commun\Form\CommunForm;

class RealisationImpactForm extends CommunForm 
{
    
    /*private $params;
    public function __construct($params) {
        $this->params = $params;
        parent::__construct('RealisationImpactForm',$this->params);
        
        
    }*/
    public function init() {                
        $this->setName('RealisationImpactForm');        
        $this->addFieldset(RealisationImpactFieldset::class,['use_as_base_fieldset' => true,'params' => $this->params]);
        $this->addSubmitButton('next', 'Poursuivre', 'next', 'btn btn-vert w-100');        
        $this->addSubmitButton('previous', 'Retour', 'previous', 'btn btn-rouge w-100');
    }  
  
}

Here is my fieldset :

namespace Commun\Form\Modules\Application\Fieldset;

use Commun\Model\Entity\Supervision;
use Laminas\InputFilter\InputFilterProviderInterface;
use Laminas\Hydrator\ReflectionHydrator;

use Commun\Form\CommunFormFieldset;


class RealisationImpactFieldset extends CommunFormFieldset implements InputFilterProviderInterface
{
    private $mapper;
    /*private $idProjet;
    private $idSupervision;*/
       
    public function __construct($mappers=[],$options=[])
    {       
        
        $this->mapper = $mappers;
        /*$this->idProjet = $idProjet;
        $this->idSupervision = $idSupervision;*/ 
        parent::__construct('RealisationImpactForm',$options);          
        $this->setHydrator(new ReflectionHydrator());
        $this->setObject(new Supervision());
        $this->setLabel('Realisation Impact');                  
    }
    
    public function init() {
        parent::init();   
        
        //$effets = $this->mapper['supervision']->getRapportEffetByProjetForSuivi($this->idProjet,$this->idSupervision);
        
        
        /*$this->addText('libelle','Intitulé de l\'activité','libelle',['class' => 'form-control champ-requis']);
        $options = $this->mapper['indicateur']->getOptions('idRefIndicateur','libelle','Aucune valeur choisie',null,['libelle']);           
        $this->addSelect('idRefIndicateur','Indicateur de performance',$options,['class' => 'form-control']);
        $this->addText('valeurReference','Valeur de référence','valeurReference',['class' => 'form-control champ_decimal']);
        $this->addText('valeurCible','Valeur cible','valeurCible',['class' => 'form-control champ_decimal']);
        $this->addTextarea('moyenVerification', 'Moyen de vérification', 'moyenVerification', ['class' => 'form-control','rows' => 3]); 
        $this->addTextarea('risqueMesureAttenuation', 'Risques et mesures d\'atténuation', 'risqueMesureAttenuation', ['class' => 'form-control','rows' => 3]);  */        
    }
        
    /**
     * @return array
     */
    public function getInputFilterSpecification()
    {
        return [
            
        ];
    }
}

I need to say that in my form, when I make a var_dump, I see the parameters but I do not know how to get them in the fieldset.

Thanks for any reply

The first problem I see here: setting the value options via some mappers. This should be removed from the forms and fieldsets.
Create custom elements or a custom select which gets the mapper name and field as options to fetch the value options. Otherwise you always have to drag the mappers through all the forms and fieldsets.


The constructor looks good in your form:

public function __construct($params)
{
    $this->params = $params;
    parent::__construct();
}

Or use the options:

public function __construct($params)
{
    parent::__construct(null, ['my_params' => $params]);
    // or
    parent::__construct();
    $this->setOption('my_params', $params);
}

Another way is a custom factory for your form:

final class FormFactory implements FactoryInterface
{
    public function __invoke(ContainerInterface $container, $requestedName, ?array $options = null)
    {
        $form = new $requestedName();
        if ($options !== null) {
            $form->setOptions($options);
        }

        return $form;
    }
}

Here you can overwrite the setOptions method of your form and do what you want.

In your fieldset you also can use the options because these can be set when adding:

$this->add(
    [
        'name'    => 'example_fieldset',
        'type'    => Laminas\Form\Fieldset::class,
        'options' => [
            'my_params' => $this->getOption('my_params'),
        ],
        // …
    ]
);

In your fieldset:

$params = $this->getOption('my_params');

Thank uou @froschdesign , I will test it and keep you posted.

The options of an element / fieldset / form are called “custom options” therefore this suggestion:

1 Like

I tried this and did not get params values in my fieldset :
Here is my Global form wich each form extends

<?php

/**
    * @module     Commun
    * @subpackage Form
    * @author     Samuel NANGUI <nanguisamuel@gmail.com>
    * @copyright  Copyright (c) 2020 Nslabs
    */

namespace Commun\Form;

use Laminas\Form\Form;
use Laminas\Hydrator\ClassMethodsHydrator;
use Laminas\InputFilter\InputFilter;
use Laminas\Form\Element\Select;
use Laminas\Form\Element\Hidden;

class CommunForm extends Form
{
    protected $mapper;
    public $params;
    public function __construct($formName=null,$params=[],$mapper=[]) {
        parent::__construct($formName);
        $this->mapper = $mapper;
        $this->params = $params;
        $this->setHydrator(new ClassMethodsHydrator(false));
        $this->setInputFilter(new InputFilter());
        $this->setAttribute('class', 'form-horizontal'); 
        $this->setOption('params', $params);
    }
    
    public function populateSelect(\Laminas\Form\Element\Select $selectName,$optionValues=[]){
        $selectName->setValueOptions($optionValues);
    }
    
    public function addFieldset($fieldset,$options=[]){        
        $this->add([
            'type' => $fieldset,
            'options' => $options,            
        ]);               
    }
    
    public function addSubmitButton($name,$label,$id='',$className=''){
        $this->add([
            'name' => $name,            
            'type'  => 'submit',            
            'attributes' => [
               'value' => $label,
               'id' =>  $id,
               'class' => $className,
           ]
        ]);        
    }
    
    
    public function addSelect($name,$label){
        $this->add([            
            'name' => $name,
            'type' => Select::class,
            'options' => [
                'label' => $label,
                'value_options' => [
                    '0' => 'French',
                    '1' => 'English',
                    '2' => 'Japanese',
                    '3' => 'Chinese',
                ],
            ],
        ]);
    }
    
    public function addFile($name,$label,$id='',$attributes=[],$labelClass=''){        
        $this->add([
            'name' => $name,
            'type' => 'file',
            'options' => [
                'label' => $label,   
                'id'    => $id,
                'label_attributes' => [
                    'class'  => $labelClass
                ],
            ],            
            'attributes' => $attributes,
        ]);
    }
    
    public function addHiddenElement($name,$attributes=[]){
        $this->add([
            'name' => $name,
            'type' => Hidden::class,            
            'attributes' => $attributes,
        ]);
    }
    
    public function addText($name,$label,$id='',$attributes=[],$labelClass=''){        
        $this->add([
            'name' => $name,
            'type' => 'text',
            'options' => [
                'label' => $label,   
                'id'    => $id,
                'label_attributes' => [
                    'class'  => $labelClass
                ],
            ],
            'attributes' => $attributes,
        ]);
    }
    
    
    
    
}

I added my fieldset with this code :

<?php

/**
    * @module     Commun
    * @subpackage Form\Admin
    * @author     Samuel NANGUI <nanguisamuel@gmail.com>
    * @copyright  Copyright (c) 2021 Nslabs
    */

namespace Commun\Form\Modules\Application;

use Commun\Form\Modules\Application\Fieldset\RealisationImpactFieldset;


use Commun\Form\CommunForm;

class RealisationImpactForm extends CommunForm 
{
    
    
    public function init() { 
        parent::init();                 
        $this->setName('RealisationImpactForm');         
        $this->addFieldset(RealisationImpactFieldset::class,['use_as_base_fieldset' => true,'params' => $this->getOption('params')]);
        $this->addSubmitButton('next', 'Poursuivre', 'next', 'btn btn-vert w-100');        
        $this->addSubmitButton('previous', 'Retour', 'previous', 'btn btn-rouge w-100');        
    }  
  
}

here is my addFieldset function

public function addFieldset($fieldset,$options=[]){        
        $this->add([
            'type' => $fieldset,
            'options' => $options,            
        ]);               
    }

and when I do a var_dump I get the option like this :

But I did not get anything in my fielddet.

Here is my factory

<?php

/**
    * @module     Commun
    * @subpackage Form
    * @author     Samuel NANGUI <nanguisamuel@gmail.com>
    * @copyright  Copyright (c) 2020 Nslabs
    */

namespace Commun\Factory\Form\Fieldset;


use Interop\Container\ContainerInterface;
use Laminas\ServiceManager\Factory\FactoryInterface;
use Commun\Form\Modules\Application\Fieldset\RealisationImpactFieldset;

class RealisationImpactFieldsetFactory implements FactoryInterface
{
    public function __invoke(ContainerInterface $container, $requestedName, array $options = null)
    {                  
        $mappers = ['supervision' => $container->get('TSUPERVISION')];          
        return new RealisationImpactFieldset($mappers);
        
    }
}

Ans here is how I call my form in my controller :
$realisationImpactForm = $this->formManager->get(RealisationImpactForm::class,['idProjet' => $id,'idSupervision' => 1]);

Sorry for the late response!

Maybe I missed something, but where are the options accessed in your fieldset?