Jak odebrat pravidlo z prvku formuláře

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

Našel jsem https://forum.nette.org/…idel-z-prvku a protože už jsou to přeci jen 2 roky, za které se toho mohlo mnoho změnit, ptám se:

Je už možné odebrat z konkrétního prvku pravidla?

Něco jako

$form['name']->removeRules();

nebo

$form['name']->addRule(FALSE);

jako to ostatně už dobře funguje u DibiFluent…

Příklad použití? Asi jeden za všechny – přidávací a editační formulář.

Editační pro úsporu kódu dědí z přidávacího a upraví si jen onSubmit callback a třeba popisek submit buttonu.

protected function createComponentNewArticleForm() {
	$form = new NAppForm;
	$form->addText('name', 'Name:', 80)
		->addRule(NAppForm::FILLED, 'Enter the name of the article');

	$form->addTextArea('content', 'Content:', 90, 15)
		->addRule(NAppForm::FILLED, 'Enter the content of the article');

	$form->addFile('image', 'Image:')
		->setOption('description', '200x200px or smaller, larger images will be resized')
		->addRule(NAppForm::FILLED, 'You cannot publish article without image')
		->addRule(NAppForm::MIME_TYPE, 'Only images are accepted', 'image/*');

	$form->addSubmit('submitPublish', 'Publish');

	$form->onSubmit[] = callback($this, 'proccessAddNewArticle');

	return $form;
}

protected function createComponentModifyArticleForm() {
	$form = $this->createComponentNewArticleForm();

	$form['image']->addRule(FALSE); // it would be nice to make it functional :)

	unset($form->onSubmit[0]);
	$form->onSubmit[] = callback($this, 'proccessModifyArticle');
	return $form;
}

Pokud se k danému elementu při přidávání uploaduje třeba obrázek, při editaci je zřejmé, že nebudu nutit uživatele daný obrázek znova hledat a vyžadovat znova jeho nahrání, tzn. potřebuji dané pole s obrázkem učinit nepovinným.

Je opravdu jediným řešením na současné verzi Nette „přemazání“ celého prvku prvkem bez pravidel?

Mikulas Dite
Člen | 756
+
0
-

Koukám do API a nevidím to tam, takže to implementované není.

Ani v tom příkladu to není potřeba: vždycky stačí „rozšiřovat“ něco menšího, než ořezávat větší. Případně udělej jednoho předka, od kterého bude add i edit pracovat dál.

Martin
Člen | 171
+
0
-

maarlin: Zdravím. Tedy:

  1. Pokud v Nette něco dlohodobě není, asi to tam být nemá.
  2. Čistě to zřejmě nejde, alespoň jsem nic rozumného nenašel.
  3. Zkus tohle (PHP >= 5.?.?, bez záruky, ale zdá se, že to funguje, snad i včetně následného přidání jiných validací):
function _unsetRulesAndConditions(Nette\Forms\FormControl $control) {
    $ref = Nette\Reflection\ClassReflection::from('Nette\Forms\FormControl');
    $idProp = $ref->getProperty('rules');
    $idProp->setAccessible(TRUE);
    $idProp->setValue($control, new Rules($control));
}

Nette\Forms\FormControl::extensionMethod('unsetRulesAndConditions', '_unsetRulesAndConditions');

Fuuuuj, to je teda čuňárnička. Jako bych neměl nic lepšího na práci. Ale když se chci seznámit s Nette i PHP, tak se jakékoli cvičeníčko hodí. Ještě by bylo slušné vyčistit paměť od starých pravidel, ale na to už jsem dost ospalý a v PHP je to asi trochu nesmyslná činnost.

Použití:

$form['image']->unsetRulesAndConditions();

Pozor na drobnost – na jedné stránce nesmíš mít zároveň původní i nový formulář, js validace pak fungují poněkud [ne]čekaně.

Editoval Martin (30. 4. 2011 0:39)

Filip Procházka
Moderator | 4668
+
0
-

Nevidím rozumný důvod proč to dělat.

Co takhle příště neprasit a postavit formulář tak, aby nebylo potřeba z něj nic mazat? Tomu návrhovému vzoru se říká builder, popř je přijatelné i factory (určitě půjde najít i něco v češtině).

Něco si o tom přečtěte prosím… říká se tomu taky znovupoužitelnost!

Martin
Člen | 171
+
0
-

HosipLan: Vždyť jsem psal, že to považuji za naprosto špatné řešení. Jen jsem si jako malé cvičeníčko zkusil použít funkce, které jsi mi doporučil v jiném vlákně :-) Snad jediné využití by mohlo být tam, kde chci použít něčí úžasnou formulářovou třídu (u které autora ovšem nenapadlo, že zrovna tohle pravidlo by někdo nemusel potřebovat) a z licenčních či jiných důvodů nemohu nijak měnit její zdrojový kód. Ale ani v takovém případě to asi není nejlepší řešení.

Editoval Martin (30. 4. 2011 10:37)

maarlin
Člen | 207
+
0
-

Mikulas Dite napsal(a):

Koukám do API a nevidím to tam, takže to implementované není.

Ani v tom příkladu to není potřeba: vždycky stačí „rozšiřovat“ něco menšího, než ořezávat větší. Případně udělej jednoho předka, od kterého bude add i edit pracovat dál.

Ano, nakonec jsem to tak udělal…

Udělal jsem si takový „prototyp“ toho formuláře, na který v patřičných (add/modify) továrničkách navěšuji už jen patřičné správné submit buttony a submit callbacky, eventuálně navěšuji/nenavěšuji pravidla.

Díky za nasměrování.

Editoval maarlin (30. 4. 2011 10:29)