2014-12-29 43 views
5

在同一页面多次相同的形式类型我试图产生特别是“ProductLanguageType”表单类型。生成的Symfony2

我想产生的ProductLanguageType多次在语言表中现有语言的当前号码。

例如,如果我有(英语,法语,俄语,中国)在语言表,它会产生在同一页上4 ProductLanguageType形式。

我想知道我怎么查询语言表,并生成在同一页面上相同类型的多个形式,表单生成器能够做的或者是有另一种解决方法吗?这段时间以来一直有一些麻烦,并很乐意为此找到一个好的解决方案。

ProductLanguageType:

class ProductLanguageType extends AbstractType 
{ 
public function buildForm(FormBuilderInterface $builder, array $options){ 

    $builder->add('id_language', 'entity', array(
        'class' => 'AdminBundle:Language', 
        'data_class' => 'Main\AdminBundle\Entity\Language', 
        'property' => 'language' 
       ) 
       ) 
      ->add('name', 'text') 
      ->add('description', 'ckeditor', array(
        'config_name' => 'admin', 
        'config' => array(
         'filebrowser_image_browse_url' => array(
          'route'   => 'elfinder', 
          'route_parameters' => array('instance' => 'default'), 
         ), 
        ) 
       )) 
      ->add('short_description', 'text'); 

} 

public function getName(){ 
    return 'productLanguage'; 
} 
} 

ProductType(ProductLanguageType在这里包埋):

class ProductType extends AbstractType 
{ 
public function buildForm(FormBuilderInterface $builder, array $options){ 

    $builder->addEventListener(FormEvents::PRE_SET_DATA, array($this, 'onPreSetData')); 
    $builder->add('productLanguage', new ProductLanguageType()) 
      ->add('id_seller','text') 
      ->add('price','text') 
      ->add('cost_price','text') 
      ->add('retail_price','text') 
      ->add('hot', 'checkbox') 
      ->add('featured', 'checkbox') 
      ->add('new', 'checkbox') 
      ->add('free_shipping', 'checkbox') 
      ->add('status','text') //active or inactive, to be decided if hidden or visible 
      ->add('Add', 'submit'); 

} 
} 
+0

什么关于使用集合? HTTP:// symfony的。com/doc/current/cookbook/form/form_collections.html –

+0

我尝试多次生成表单,但似乎没有出现。 –

回答

4

希望这会帮助别人。

正确的方法是使用Symfony的form.factory服务来创建一个指定的构建器,并依次创建一个表单。我建议创建表单创建过程作为一个函数(我的理解,纠正我,如果我”,错的)每个FormBuilder实例必须是不同的,以创建一个不同的形式。

正如对代码用途的解释: 我需要在帮助系统中显示打开故障单的列表,以便根据用户的登录令牌将其分配给故障单(未经登录授权)。这需要在单个页面上显示N个表格,这些表格将是唯一的,但是如果您愿意,可以从单个“模板”或类型生成。

此代码实现,没有任何黑客。没有简单的方法来创建具有来自控制器AFAIK的特定ID(名称)的FormForm。

ex。

public function generateFormForTicketAssignment(Ticket $ticket) { 

    $ticketAssignType = new TicketAssignInvokeType(); 
    $ticketAssignType->setNameSuffix($ticket->getId()); 

    /** 
    * @var Symfony\Component\Form\FormBuilderInterface 
    */ 
    $builder = $this->get('form.factory')->createNamedBuilder($ticketAssignType->getName(), $ticketAssignType); 
    $builder->setAutoinitialize(true); 
    $formTicket = $builder->getForm(); 

    $formTicket->get('ticket')->setData($ticket); 


    return $formTicket; 
} 

AND(这是重要组成部分)的ticketAssignInvokeType看起来是这样的:

class TicketAssignInvokeType extends AbstractType { 

private $nameSuffix = null; 
private $name = 'ticket_assign_invoke'; 

public function __constructor(string $suffix = null) { 
    //parent::__construct(); 

    $this->nameSuffix = $this->generateNameSuffix(); 
} 

private function generateNameSuffix() { 
    if ($this->nameSuffix == null || $this->nameSuffix == '') { 
     $generator = new SecureRandom(); 
     //change data to alphanumeric string 
     return bin2hex($generator->nextBytes(10)); 
    } 

    return $this->nameSuffix; 
} 

/** 
* 
* @param string $suffix When set suffix added to form will use selected 
* string (note it should be unique for all forms on a page). 
*/ 
public function setNameSuffix($suffix){ 
    $this->nameSuffix = $suffix; 
} 

public function buildForm(FormBuilderInterface $builder, array $options) { 
    $builder 
     ->add('loginToken',new AuthenticateTokenType()) 
     ->add('ticket',new TicketIDType()) 
     ->add('save', 'submit', array('label' => 'form.button.assign')) 
    ; 

} 

public function getName() { 
    if ($this->nameSuffix == null || $this->nameSuffix == "") { 
     $this->nameSuffix = $this->generateNameSuffix(); 
    } 
    return $this->name .'_'. $this->nameSuffix; 
} 

public function configureOptions(OptionsResolver $resolver) { 
    // ... 
} 
} 

这是后缀名有点过于复杂的逻辑和测试,但在某些时候,我无法弄清楚为什么所有的我去没有后缀的表单名称因此是复杂的。

PS。我已经创建了表单作为服务,稍后会测试是否可以使用服务,这是我的第一个意图。

PS2。我不确定setAutoinitialize的方法,但也会测试它更好。

+0

它的确如此,谢谢!我已经删除了setAutoinitialize,因为它默认情况下处于打开状态。也从__construct()中删除未使用的参数。 –

3

现在Symfony的3.0他们改变了createNamedBuilder,因此它可能只打电话来解决这个问题:

use AppBundle\Form\ShippingTrackCodeReturnType; 

$uniqueForm = $this->get('form.factory')->createNamedBuilder('ship_form_'.$orderRecord->getId(), ShippingTrackCodeReturnType::class, $orderRecord)->getForm(); 

所以,你只需要循环显示和保存:

foreach ($invoice->getOrderRecords() as $key => $orderRecord) 
{ 
    // creates the forms with different names 
    $returnShipTrackCodeForm = $this->get('form.factory')->createNamedBuilder('ship_form_'.$orderRecord->getId(), ShippingTrackCodeReturnType::class, $orderRecord)->getForm(); 

    $returnShipTrackCodeForm->handleRequest($request); 
    if ($returnShipTrackCodeForm->isSubmitted() && $returnShipTrackCodeForm->isValid()) 
    { 
     // flush object 
    } 

    $returnForms[$orderRecord->getId()] = $returnShipTrackCodeForm; 
}