我在Zend Framework 2项目中使用Doctrine 2。现在,我已经创建了一个表单,并使用数据库中的值创建了一个下拉列表。我现在的问题是我想更改使用的值,而不是从存储库取回的值。好的,这里有一些代码可以更好地理解:
$this->add(
array(
'type' => 'DoctrineModule\Form\Element\ObjectSelect',
'name' => 'county',
'options' => array(
'object_manager' => $this->getObjectManager(),
'label' => 'County',
'target_class' => 'Advert\Entity\Geolocation',
'property' => 'county',
'is_method' => true,
'empty_option' => '--- select county ---',
'value_options'=> function($targetEntity) {
$values = array($targetEntity->getCounty() => $targetEntity->getCounty());
return $values;
},
'find_method' => array(
'name' => 'getCounties',
),
),
'allow_empty' => true,
'required' => false,
'attributes' => array(
'id' => 'county',
'multiple' => false,
)
)
);
我想将“选择”的值设置为县名而不是ID。我以为我需要一个需要数组的'value_options'。我像上面一样尝试过,但得到了
错误消息:传递给Zend \ Form \ Element \ Select :: setValueOptions()的参数1必须是数组类型,给定对象
这有可能吗?
我打算建议修改您的代码,尽管在检查了ObjectSelect
代码后,我很惊讶(据我所知),如果不扩展该类,实际上是不可能的。这是因为该值始终是从id生成的。
我使用工厂(不带ObjectSelect
)创建了所有表单元素,特别是需要变化列表的复杂元素。
替代解决方案
首先在存储库中创建一个新方法,该方法返回正确的数组。这将允许您在其他任何地方都需要重用相同的方法(不仅限于表单!)。
class FooRepository extends Repository
{
public function getCounties()
{
// normal method unchanged, returns a collection
// of counties
}
public function getCountiesAsArrayKeyedByCountyName()
{
$counties = array();
foreach($this->getCounties() as $county) {
$counties[$county->getName()] = $county->getName();
}
return $counties;
}
}
接下来,创建一个自定义选择工厂,它将为您设置值选项。
namespace MyModule\Form\Element;
use Zend\Form\Element\Select;
use Zend\ServiceManager\ServiceLocatorInterface;
use Zend\ServiceManager\FactoryInterface;
class CountiesByNameSelectFactory implements FactoryInterface
{
public function createService(ServiceLocatorInterface $formElementManager)
{
$element = new Select;
$element->setValueOptions($this->loadValueOptions($formElementManager));
// set other select options etc
$element->setName('foo')
->setOptions(array('foo' => 'bar'));
return $element;
}
protected function loadValueOptions(ServiceLocatorInterface $formElementManager)
{
$serviceManager = $formElementManager->getServiceLocator();
$repository = $serviceManager->get('DoctrineObjectManager')->getRepository('Foo/Entity/Bar');
return $repository->getCountiesAsArrayKeyedByCountyName();
}
}
通过在Module.php
或中添加新条目,向服务管理器注册新元素module.config.php
。
// Module.php
public function getFormElementConfig()
{
return array(
'factories' => array(
'MyModule\Form\Element\CountiesByNameSelect'
=> 'MyModule\Form\Element\CountiesByNameSelectFactory',
),
);
}
最后,更改表单并删除当前的select元素,然后添加新的select元素(使用您在服务管理器中注册的名称作为类型键)
$this->add(array(
'name' => 'counties',
'type' => 'MyModule\Form\Element\CountiesByNameSelect',
));
看起来似乎有很多代码(因为是这样),但是您将受益于它更加清晰的关注点分离,并且您现在可以在多种表单上重用该元素,并且只需要在一个位置进行配置即可。
本文收集自互联网,转载请注明来源。
如有侵权,请联系[email protected] 删除。
我来说两句