Vložení komponenty do html obsahu
- d@rkWolf
- Člen | 167
Zdravím,
už tu hodinu prohledávám fórum, ale buď se špatně ptám, nebo tu
nic není.
Potřeboval bych nějak vložit komponentu k vykreslení do html obsahu, co mám uložený v DB a co se vykresluje v šabloně přes:
{$data->content|noescape}
Jde o to, že mám vytvořenou komponentu, která renderuje vytvořenou fotogalerii(řada 1-x náhledů, v bootstrap gridu s odkazem na velkou fotku do lightboxu)
{control gallery-1}
Používá se multiplier, normálně v latte to funguje, ale potřeboval bych, aby bylo možné tu galerii(nebo třeba několik galerií) vložit kamkoliv do obsahu upravovaném v editoru v administraci, ať už přímo tím kódem {control gallery-X}, nebo nějakým zástupným co prostě půjde uvnitř toho uloženého kódu najít. Něco jako jsou shortcodes ve Wordpressu.
Ve starém systému bez Nette se prostě prohledal obsah na zvolený řetězec(tuším {gal-x}, když se našel, zavolala se funkce, která zjistila, zda taková galerie existuje a pokud jo, vygenerovala celé potřebné html a vrátila ho, to nové html se použilo k nahrazení toho řetězce gal-x a pak se to celé vykreslilo do stránky.
Nemůžu přijít na to, jak tohle udělat s Nette komponentou? Jde to nějak? Nějaký trik, jak to udělat? Asi bych to mohl udělat stejně celý ručně, ale zajímalo by mě, jestli to nejde nějak udělat s tou komponentou, co už jsem si vyrobil, než to dělat celý „znovu“.
Editoval d@rkWolf (29. 4. 2021 17:33)
- Kamil Valenta
- Člen | 820
V DB budeš mít zástupné znaky.
V presenteru si pak ten text z DB rozparsuješ a zavoláš potřebné
továrničky, do hierarchie komponenty přidáš pomocí
$this->addComponent($object, $name);
V latte pak ten text zase rozparsuješ a na vhodných místech zavoláš
{control $name}
Ale já to mám bez multiplieru, protože si uživatel u každé komponenty
může navolit, jakou šablonou se to vyrenderuje a další parametry, takže
každá instance musí existovat ad-hoc.
- Kamil Valenta
- Člen | 820
Martk napsal(a):
A co brání to udělat jako v systému bez Nette?
IMHO to, že budeš sahat na neexistující komponentu.
- Kamil Valenta
- Člen | 820
Pořád asi nerozumím, kde vezmeš potřebný „createComponent“. Rád se inspiruju, ale před rokem jsem lepší řešení nenašel. Někdo se mnou nesouhlasí, ale netuším proč.
- David Matějka
- Moderator | 6445
Pořád asi nerozumím, kde vezmeš potřebný „createComponent“
předpokládá to, že v té komponentě/presenteru budou příslušné createComponent existovat. (ale to tvé registrování přes addComponent může být také řešení)
Někdo se mnou nesouhlasí, ale netuším proč.
protože nevím, proč bych to měl „V latte rozparzovat a na vhodných místech zavolat {control $name}“, když stačí ten preg_replace_callback, který ukázal @Martk
- Kamil Valenta
- Člen | 820
Aha, už chápu. Ono slovo „rozparsovat“ možná bylo moc silné. Možná
jsem měl říct „zprocesovat“. Už rozumím, že se na to s Martkem
díváte z pohledu latte, kde je ten callback alternativa ke {control …}
Já si ty komponenty držím v db samostatně, takže je ani nemusím parsovat
z textu, takže mi control vyšel automaticky nejjednodušší.
Spíš mi šlo o způsob, jak se právě vyhnout v presenteru tomu, že:
- by se musely chystat všechny createComponent, i když zrovna nebudou potřeba (ale pokud jsou ty komponenty dobře napsané, tak to vezme zcela minimální režii, protože se nezavolá render)
- při rozšíření o nový „widget“ se nesmělo zapomenout na úpravu presenteru
- d@rkWolf
- Člen | 167
@KamilValenta no já sem to dal do multiplieru, protože když sem hledal, co potřebuju abych mohl komponentu zobrazit „potenciálně“ víckrát, pokaždé sem narazil na „použijte multiplier“… mám jednu galerii připojitelnou v rámci editace stránky(na konec-za obsah), takže v šabloně presenteru dycky může existovat jedno zavolání té komponenty s patřičným ID, co si user k té stránce přiřadil-jenže tam to má napevno na konec.
Teoreticky s tím multiplierem by ani nemělo být potřeba volat v presenteru to addComponent ne?
Mě akorát úplně nenapadá, jak udělat toto: „V latte pak ten text zase rozparsuješ a na vhodných místech zavoláš {control $name}“ (kromě toho, že mi přijde, že to taková akce do šablony úplně nepatří-i když to mě zas až tak netrápí). Vůbec mě nenapadá, jak proměnnou vykreslovat po částech a nacpat mezi to volání {control}, to je v podstatě ta moje původní představa, akorát mě vůbec nenapadá, jak to udělat.
- Martk
- Člen | 661
@KamilValenta Je to taky řešení, pokud se ti má komponenta zobrazit nahoře nebo dole. Pokud někde v textu, tak upřímně nevím jak probíhá to řešení s {control $name}. Ovšem předpokládám, že si tam stejně musíš tahat všechny továrny, takže to vyjde rychlostně nastejno jako s createComponent
- Kamil Valenta
- Člen | 820
Ne, ne, to já nepopírám, že když je to uvnitř textu, že není výhodnější nahradit to za výstup renderu. Já jsem měl na mysli hlavně to, že
$this->getComponent('gallery-1')->render();
nijak nevytvoří
createComponentGallery()
Pokud je galerie jediný widget v textu, tak je akceptovatelné vytvořit to
natvrdo v presenteru. Já se na to díval tak, že těch widgetů může být
více. V mém případě je N-modulů, které ještě mohou být
povoleny/zakázány a každý z nich může poskytovat N-komponent, které
implementují interface „Widget“. Továrny všechny tahat nemusím, widgety
netahám z DI, což je v mém případě daň za tu automatizaci okolo.
S odstupem roku skutečně ale víc oceňuju to, že kdekoliv můžu vytvořit
komponentu s interfacem Widget a už nikde nic nepřipisovat…
- David Matějka
- Moderator | 6445
@KamilValenta pokud budeš mít uvnitř toho createComponentGallery
Multiplier, tak gallery-1
fungovat bude.
- Kamil Valenta
- Člen | 820
To ano, ale musíš createComponentGallery mít. A pak třeba createComponentArticle, createComponentMap…