addDynamic – přístup k prvkům v presenteru

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

Potřeboval bych „sáhnout“ na prvky formuláře, které se přidávají dynamicky – měnit parametr pro použití v javascriptu podle jejich pořadí. Ve vytvářecím callbacku by se tohle asi řešit nemělo (a stejně jsem na to nepřišel), ale před vrácením formuláře z továrničky jsem v dynamickém kontejneru žádné prvky nenašel. Zatím to měním před výpisem v šabloně, ale nepřijde mi to pěkné.

Např. bych chtěl mít v atributu data-toggle hodnotu match-round-games-X, kde X je pořadí prvku.

$round->addSelect('score_type', NULL, $score_types)
               ->setAttribute('data-toggle', '#match-round-games-' . $id);
sKopheK
Člen | 207
+
0
-

Taky mám problém s nastavením defaultních hodnot. V callbacku to nastaví jen pro první „sadu“ prvků, další už to ignoruje. A jinak nevím, jak se k nim dostat.

sKopheK
Člen | 207
+
0
-

Když namísto setDefaults použiji setValues, tak to funguje.

sKopheK
Člen | 207
+
0
-

Je možné nastavení např. disabled provádět hromadně?

sKopheK
Člen | 207
+
0
-

Přišel jsem alespoň na trik, jak získat pořadí volání callbacku. Vytvořte si pole hodnot 0 – x a předávejte ho v use closure referencí. V těle callbacku pak získáte hodnotu aktuálního průchodu např. pomocí funkce array_shift().

$order = range(0, 100);
$form->addDynamic('rounds', function(Container $round) use (&$order) {
	$i = array_shift($order);
	...
}, $default_count);
voda
Člen | 561
+
0
-

Lepší než pole je použít normální proměnnou:

$order = 0;
$form->addDynamic('rounds', function(Container $round) use (&$order) {
	// tady můžu s $order pracovat
	...
	$order++;
}, $default_count);
sKopheK
Člen | 207
+
0
-

Pokud potřebuješ jen index, tak ano, jinak je nutné použít pole např. s objekty.

Narazil jsem na podivné chování při odstraňování prvku přes AJAX. Odstranění zvoleného prvku se provede v pořádku, nicméně když jsem odstranil poslední prvek přidaný přes callback v addDynamic, při zobrazování se vypisují parametry jakoby dalšího prvku (pozoroval jsem to u toho indexu předávaný přes referenci). Debugger ukázal, že se prvky vytvoří v pořádku, poté se teprve odstraňuje a při provádění metody v replicatoru se asi děje nějaká magie, i když jsem ve zdrojácích nic podezřelého nenašel.

Konkrétněji:

/** @var \Nette\Application\UI\Presenter */
$presenter = $this;
$invalidateCallback = function () use ($presenter) {
	$presenter->invalidateControl('match-rounds');
};

$order = 0;
$form->addDynamic('rounds', function(Container $round) use (&$order, $invalidateCallback, $types) {

	$i = $order;

	$round->addSelect('score_type', NULL, $types)
              ->setAttribute('data-toggle', sprintf('#round-%d-toggle', $i));

	$round->addSubmit('remove', "Remove")
		->setAttribute('class', 'ajax')
		->setValidationScope(FALSE)
		->addRemoveOnClick($invalidateCallback);

	$order++;
});

Při výpisu v šabloně mají prvky v atributu data-toggle hodnotu round-0-toggle, round-1-toggle atd., ale když odstraním některý z nich, začíná se indexovat od 1.