Generování formulářů s parametrem a jejich vykreslení v šabloně

Upozornění: Tohle vlákno je hodně staré a informace nemusí být platné pro současné Nette.
kastanekdavid
Člen | 39
+
0
-

Zdravím a pozdravuji, řeším momentálně menší zádrhel s formulářovými továrnami.

V šabloně vypisuju seznam pravidel, přičemž každé pravidlo existuje proto, aby se pomocí něho vygeneroval seznam mailů, na který se posléze zašle e-mail s marketingovým obsahem. To ale momentálně není důležité.

Problém je v tom, že u každého výpisu pravidla potřebuju zobrazit tlačítko „Regenerovat seznam e-mailů tohoto pravidla“.

Za každé tlačítko dosazuju jednu instanci formuláře, který vygeneruje továrna. Každý takový formulář má submit a jeden hidden, v němž je ukryto ID daného pravidla.

Takhle vypadá továrna:

<?php
use Nette\Forms\Container;
use Nette\Application\UI\Form;

class ForceListRegenFormFactory extends Nette\Object{

	private $db;

    public function __construct(Nette\Database\Connection $db){
        $this->db = $db;
    }

	public function createForm($ruleId){
		$form = new Form;

		$form->addHidden('ruleId', $ruleId);
		$form->addSubmit('send', 'Force list reload')
			->getControlPrototype()
			->onclick("return confirm('Are you sure?')");

		$form->onSuccess[] = callback($this, 'process');

		return $form;
	}

	public function process($button){
		//
    }

}
?>

Takhle posílám vygenerované formuláře do šablony:

<?php
	public function actionOverview($siteId){
		$rulesProperties = $this->model->provideRulesProperties($siteId);
		$forms = array();
		foreach($rulesProperties as $rule) $forms[$rule['id']] = $this->forceListRegenFormFactory->createForm($rule['id']);
		$this->template->forceListRegenForms = $forms;
	}
?>

No a takto celý pohled vykresluju:

<table>
    <tr><th>Rule no.</th><th>Created</th><th>E-mail list</th><th>Regenerate list?</th><th>Delete</th></tr>
    {foreach $rules as $rule}
        <tr><td>{$rule['id']}</td><td>{$rule['created']}</td><td><a href="{plink "List:overview", $rule['id']}">Show</a></td><td>{$forceListRegenForms[$rule['id']]}</td><td></td></tr>
    {/foreach}
</table>

Tlačítka se mi normálně objeví, ale problém je v tom, že formulář každého tlačítka nemá nastavenou action, takže se po kliknutí nic nestane.

Předpokládám, že továrnu používám blbě a bez konstrukce přes metodu createComponentXForm se celej koncept handlování submitu přes jinou metodu sesype.

Mohl by mi, prosím, někdo z vás poradit, jak správně řešit tenhle případ? (kdy potřebuju generovat stejný formulář, akorát s jiným ID prvku)

Vojtěch Dobeš
Gold Partner | 1316
+
0
-

Problém je, že jsi obešel klasický komponentový model, klasické továrničky jak jsou popsány v databázi. Řešením je využít UI\Multiplier:

protected function createComponentRegenForm()
{
	return new Nette\Application\UI\Multiplier(function ($id) {
		return $this->forceListRegenFormFactory->createForm($id);
	});
}

Díky tomu se provede připojení do stromu komponent a tudíž i automatické nastavení action.

V šabloně pak bude vykreslování vypadat takto:

<table>
	<tr><th>Rule no.</th><th>Created</th><th>E-mail list</th><th>Regenerate list?</th><th>Delete</th></tr>
	{foreach $rules as $rule}
		<tr><td>{$rule['id']}</td><td>{$rule['created']}</td><td><a href="{plink "List:overview", $rule['id']}">Show</a></td><td>{control regenForm-$rule['id']}</td><td></td></tr>
	{/foreach}
</table>

Celou tu logiku s $this->template->forceListRegenForms můžeš smazat.

Editoval vojtech.dobes (4. 2. 2014 14:53)

kastanekdavid
Člen | 39
+
0
-

Díky moc, Mistře :)

Kdyby někdo neuměl hledat napoprvé, stejně jako já, tady je to vysvětleno: Nette\Application\UI\Multiplier