Komunikace mezi dvěmi komponentami

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

Ahoj, omlouvám se, jestli tento dotaz bude působit triviálně, ale chci si finálně ujasnit jednu věc, u které pořád nemám 100% jasno :-) – když mám v rámci JEDNOHO presenteru vytvořené dvě komponenty, můžou tyto komponenty vzájemně komunikovat pomocí sub-requestů (signálů) nebo je to nemožné a signál si zpracovává pouze komponenta, která si ho poslala (dokumentaci jsem četl mnohokrát, jenom si nejsem jistý, jestli to dobře chápu) ?

Např. mám vedle sebe dvě komponenty (pojmenované např. ‚test‘ a ‚test2‘) pro zjednodušení vytvořené ze stejné třídy a šablony. V jejich šabloně je třeba následující kód:

<a n:href="changeRender! aaa">RENDER A</a>
<a n:href="changeRender! bbb">RENDER B</a>
<a n:href="changeRender! ccc">RENDER C</a>

Je možné, aby komponenta test nějak (případně jak) generovala odkaz changeRender směřující na komponentu test2 atd. ?

Editoval Bilbo (3. 10. 2012 16:00)

Michal Vyšinský
Člen | 608
+
0
-

Cau. Ano je. Pouzij toto:

<a href='{plink test2-changeRender!}'>render a</a>

Nevim jestli je to mozne i s n:href. Jestli jo, tak at me nekdo prosim doplni.
Omluv prosim diakritiku. Pisu z telefonu.

Edit: chybel vykricnik u signalu :)

Editoval CherryBoss (3. 10. 2012 16:39)

pave.kucera
Člen | 122
+
0
-

Čmuchám chybu v návrhu, komponenta by neměla o dalších komponentách nic tušit. Když ví o svém „okolí“, ztrácí znovupoužitelnost. Co když onu komponentu připneš v jiném presenteru? Vytváření odkazů spadne, nebude existovat komponenta, která je volána. Co když komponentu zanoříš do jiné komponenty? Zase to spadne…

Přijatelný způsob, jak z komponenty odkazovat na jinou komponentu, je předat onu komponentu přes konstruktor/setter/public proměnnou, jinak jde o zbytečnou magii.

duke
Člen | 650
+
0
-

Nějaká podpora pro komunikaci mezi komponentami by v Nette asi být mohla. Samozřejmě taková, která by neomezovala znovupoužitelnost. Např. založená na událostech. Koneckonců se Nette prohlašuje za event-driven framework…

Bilbo
Člen | 16
+
0
-

CherryBoss: OK, díky! Makro plink znám, ale myslel jsem, že se používá pouze při odkazování na jiný presenter.

pave.kucera: Žádný návrh ani nemám, jenom se všeobecně ujišťuji, jak věci fungují :-) A ano, v tomhle máš pravdu, to mne nenapadlo, aby byla komponenta znovupoužitelná, tak použití názvu jiné komponenty tuto ideu trochu ničí.

duke: Přesně taková myšlenka mě napadla. V jedné komponentě se něco stane (signál), druhá to nějak přijme a zpracuje (handler).

Co takhle si zvenku uložit do proměnné název jiné komponenty a pak použít v šabloně něco jako:

<a href='{plink $targetCompName-changeRender!}'>render a</a>

???

Editoval Bilbo (4. 10. 2012 17:16)

Bilbo
Člen | 16
+
0
-

BTW jestli tyhle úvahy jdou proti smyslu Nette, tak to budu respektovat a používat to tak, jak je to navržené (viz třeba přes to předávání jak píše pave.kucera), smysl tohoto dotazu byl jenom zjistit, jaké jsou u komponent všechny možnosti.

LeonardoCA
Člen | 296
+
0
-

pave.kucera napsal(a):

Čmuchám chybu v návrhu, komponenta by neměla o dalších komponentách nic tušit. Když ví o svém „okolí“, ztrácí znovupoužitelnost. Co když onu komponentu připneš v jiném presenteru? Vytváření odkazů spadne, nebude existovat komponenta, která je volána. Co když komponentu zanoříš do jiné komponenty? Zase to spadne…

Přijatelný způsob, jak z komponenty odkazovat na jinou komponentu, je předat onu komponentu přes konstruktor/setter/public proměnnou, jinak jde o zbytečnou magii.

Myslím si, že nemusí jít o chybu v návrhu za předpokladu, že komponenty spolu komunikující budou zastřešeny společnou komponentou a bude již z návrhu jasné, že nemohou fungovat samostatně. Tj. z druhého konce, vytvořím komponentu, kterou z praktických důvodů rozdrobím na menší komponenty, ale ty menší komponenty už nebudu programovat se záměrem používat je samostatně.

Pak se zároveň naskýtá možnost komunikaci mezi komponentami svěřit té nadřazené komponentě a odkaz nemusí jít přes prezenter, ale stačí používat

$parent->link(); nebo $parent->invalidateControl();

Editováno:
Ještě jednou jsem si to přečetl. A pro zjednodušení, si myslím, že není nic špatného na tom si definovat, že nějaké komponenty jsou na sobě závislé a bez sebe nebudou fungovat. Samozřejmě se dají vymyslet sofistikovanější řešení, ale v některých případech by byly úplně zbytečné.
A ani není potřeba závislé koponenty obalovat další komponentou jak píšu já, to je už první a nejjednodušší krok k znovupoužitelnosti ve více prezenterech nebo v různých úrovních stromu komponent.

Editoval LeonardoCA (4. 10. 2012 21:07)