Kdyby/replicator ajax pro přidání a odebrání

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

Zdravím, snažím se rozject Kdyby/replicator pro ajaxové přidávání a odebírání čístí formuláře (celý formulář se bude odesílat klasicky bez ajaxu):


    protected function createComponentSimpleForm()
    {
        $form = new Nette\Application\UI\Form;

        $users = $form->addDynamic('users', function (Container $user) {

            $user->addText('name', 'Jméno:');
            $user->addText('email', 'E-mail:');

            $user->addSubmit('remove', 'Odstranit')
                ->setAttribute('class', 'ajax')
                ->addRemoveOnClick();

        }, 0);

        $users->addSubmit('add', 'Přidat')
            ->setValidationScope(FALSE)
            ->setAttribute('class', 'ajax')
            ->onClick[] = $this->addCallback;

        $form->addSubmit('send', 'Objednat');

        $form->onSuccess[] = $this->simpleFormSubmit;

        return $form;
    }

    public function simpleFormSubmit(Form $form, $values)
    {
        if ($this->isAjax()) {
            //echo "AJAX";exit;
            $this->redrawControl( 'form' );
        }
        if(!$form['send']->isSubmittedBy()) return;//zpracuj pouze pokud je odeslano tlacitkem objednat

        dump($form);
        dump($values);
        exit;
    }

Šablona:

{snippet form}
    {form simpleForm}

        {foreach $form['users']->containers as $id => $user}
            <div>
                <div>
                    {label users-$id-name /}
                    {input users-$id-name}
                </div>
                <div>
                    {label users-$id-email /}
                    {input users-$id-email}
                </div>
                <div>
                    {input users-$id-remove}
                </div>
            </div>
        {/foreach}

        {input users-add}

        {input send}
    {/form}
{/snippet}

Funguje mi dynamické přidávání, ale mám problém s dynamický obebráním. Po kliknutí na tlačítko Odstranit se na pozadí provede ajaxový požadavek, ale formulář se nepřekreslí…
Netušíte někdo co dělám špatně?
Díky

F.Vesely
Člen | 369
+
0
-

Je to kvuli tomu addRemoveOnClick(), kdyz se podivas, jak je ta funkce implementovana, tak zjistis, ze nastavuje $form->onSuccess = array();, proto se ti nezavola simpleFormSubmit(). Muzes si ale vsimnout, ze jako nepovinny parametr bere callback, ktery zavola, takze muzes zkusit neco jako

$user->addSubmit('remove', 'Odstranit')
	->setAttribute('class', 'ajax')
	->addRemoveOnClick(function(){
		if ($this->isAjax()) {
        	$this->redrawControl( 'form' );
    	}
	}
);
motorcb
Člen | 552
+
0
-

@F.Vesely:
Díky, máš u mne pivo

FJP
Člen | 124
+
0
-

Ahoj, řeším podobný problém:

mám v administraci přidávání produktu, s tím, že jsou na stránce taby, a tak bych přidávání fotek k produktu řešil pomocí ajaxu:

	public function buildDefaultForm() {
		$form = new \Nette\Application\UI\Form;
        $removeImageEvent = \Nette\Utils\Callback::closure($this, 'MyFormImageRemoveElementClicked');
        $removeFileEvent = \Nette\Utils\Callback::closure($this, 'MyFormFileRemoveElementClicked');

		$form->addText('code', 'Kód *')->setRequired('Jaký je kód?');
        $form->addText('title', 'Název *')->setRequired('Jaký je název?');
		$form->addTextarea('description', 'Popis');
		$form->addCheckbox('is_visible', 'Viditelný na webu');

        $photos = $form->addDynamic('photos', function (Container $photo) use ($removeImageEvent) {
            $photo->addUpload('file', 'Obrázek');
            $photo->addText('title', 'Název');
            $photo->addTextarea('description', 'Popis');
            $photo->addCheckbox('is_visible', 'Viditelný na webu');
            $photo->addSubmit('remove', 'Odstranit')
                ->setAttribute('class', 'ajax')
                ->addRemoveOnClick(function(){
                        if ($this->isAjax()) {
                            $this->redrawControl( 'form' );
                        }
                    }
                );
        }, 1);
        $photos->addSubmit('add', 'Přidat')
            ->setValidationScope(FALSE)
            ->setAttribute('class', 'ajax')
            ->addCreateOnClick(function(){
                if ($this->isAjax()) {
                        $this->redrawControl('form');
                    }
                }
            )
            ->onClick[] = \Nette\Utils\Callback::closure($this, 'MyFormImageAddElementClicked');


        foreach($this->categories as $key => $category) {
            $form->addCheckbox('category_' . $key, $category);
		}

		return $form;
	}

	public function createComponentAddForm() {
		$form = $this->buildDefaultForm();
		$form->addSubmit('submit', 'Hotovo')
            ->onClick[] = array($this, 'addFormSubmitted');
        return $form;
	}

    public function MyFormImageAddElementClicked(SubmitButton $button) {
        $button->form->setAction('#obrazky');
        $button->parent->createOne();
    }

    public function MyFormImageRemoveElementClicked(SubmitButton $button) {
        $button->form->setAction('#obrazky');
        $id = $button->parent->parent;
        $id->remove($button->parent, TRUE);
    }

	public function addFormSubmitted(SubmitButton $button) {

        if($button->form->submitted === $button->form['submit']) {
           ...
        }

  	}

Editoval FJP (5. 5. 2016 10:54)

FJP
Člen | 124
+
0
-

v šabloně:

    {snippet addForm}
        {form addForm class => 'form-horizontal'}
            <div class="page-header">
                <h1>
                    Přidat produkt
                    {input submit, class => 'btn btn-info pull-right btn-lg'}
                </h1>
            </div>

            <div class="row">
                <div class="col-lg-12">
                    <!-- Nav tabs -->
                    <ul id="zalozky" class="nav nav-tabs" role="tablist">
                      <li role="presentation" class="active"><a href="#detail" aria-controls="detail" role="tab" data-toggle="tab">Detail</a></li>
                      <li role="presentation"><a href="#obrazky" aria-controls="obrazky" role="tab" data-toggle="tab">Obrázky</a></li>
                      <li role="presentation"><a href="#soubory" aria-controls="soubory" role="tab" data-toggle="tab">Soubory</a></li>
                      <li role="presentation"><a href="#kategorie" aria-controls="kategorie" role="tab" data-toggle="tab">Kategorie</a></li>
                    </ul>

                    <!-- Tab panes -->
                    <div class="tab-content">
                        <div role="tabpanel" class="tab-pane active" id="detail">

                                {var $formItems = array('code', 'title', 'description', 'is_visible')}
                                {foreach $formItems as $fI}
                                    <div class="form-group">
                                        {if $fI === 'is_visible'}
                                            <div class="form-group">
                                                {label is_visible class => 'control-label col-sm-2' /}
                                                <div class="col-sm-2 col-sm-offset-2 checkbox">
                                                    {input is_visible class => 'form-control'}
                                                    {if $form["is_visible"]->error}
                                                        <div class="error">{$form["is_visible"]->error}</div>
                                                    {/if}
                                                </div>
                                            </div>
                                        {else}
                                            {label $fI class => 'control-label col-sm-2' /}
                                            <div class="col-sm-5">
                                                {input $fI class => 'form-control'}
                                                {if $form[$fI]->error}
                                                    <div class="error">{$form[$fI]->error}</div>
                                                {/if}
                                            </div>
                                        {/if}
                                    </div>
                                {/foreach}

                        </div>

                        <div role="tabpanel" class="tab-pane fade" id="obrazky">
                            <div class="btn-group btn-group-md pull-right" role="group" aria-label="...">
                                {input photos-add, class => 'ajax btn btn-success pull-right btn-md addPhotoReplicator', data-toggle=>'tabs', data-target=>'#obrazky', aria-expanded=>'false', aria-controls=>'obrazky'}
                            </div>

                            {foreach $form['photos']->containers as $id => $photo}
                                <div class="form-group">
                                    {label photos-$id-file class=>'control-label col-sm-2' /}
                                    <div class="col-sm-5 col-sm-offset-0">
                                        {input photos-$id-file class => 'form-control'}
                                        {if $form["photos-$id-file"]->error}
                                            <div class="error">{$form["photos-$id-file"]->error}</div>
                                        {/if}
                                    </div>
                                    <div class="col-sm-1 col-md-offset-0">
                                        {input photos-$id-remove, class => 'ajax btn btn-danger pull-right btn-md', data-toggle=>'tabs', data-target=>'#obrazky', aria-expanded=>'false', aria-controls=>'obrazky'}
                                    </div>
                                </div>
                                <div class="form-group">
                                    {label photos-$id-title class=>'control-label col-sm-2' /}
                                    <div class="col-sm-5 col-sm-offset-0">
                                        {input photos-$id-title class => 'form-control'}
                                        {if $form["photos-$id-title"]->error}
                                            <div class="error">{$form["photos-$id-title"]->error}</div>
                                        {/if}
                                    </div>
                                </div>
                                <div class="form-group">
                                    {label photos-$id-description class=>'control-label col-sm-2' /}
                                    <div class="col-sm-5 col-sm-offset-0">
                                        {input photos-$id-description class => 'form-control'}
                                        {if $form["photos-$id-description"]->error}
                                            <div class="error">{$form["photos-$id-description"]->error}</div>
                                        {/if}
                                    </div>
                                </div>
                                <div class="form-group">
                                    {label photos-$id-is_visible class=>'control-label col-sm-2' /}
                                    <div class="col-sm-2 col-sm-offset-2 checkbox">
                                        {input photos-$id-is_visible class => 'form-control'}
                                        {if $form["photos-$id-is_visible"]->error}
                                            <div class="error">{$form["photos-$id-is_visible"]->error}</div>
                                        {/if}
                                    </div>
                                </div>
                                {if !$iterator->last}
                                    <hr>
                                {/if}
                            {/foreach}

                        </div>

                        <div role="tabpanel" class="tab-pane fade" id="kategorie">
                            {block #categories}
                                <ul>
                                    {foreach $categoriesFrontTree as $category}
                                        <li>
                                            {label category_$category->id class=>'control-label col-sm-2' /}
                                            {input category_$category->id class => 'form-control'}
                                            {if $form["category_$category->id"]->error}
                                                <div class="error">{$form["category_$category->id"]->error}</div>
                                            {/if}
                                            {? $category = $category->related('category','parent_id')->order('ordering')}
                                            {if $category->count()>0}
                                                {include #categories, categoriesFrontTree => $category}
                                            {/if}
                                        </li>
                                    {/foreach}
                                </ul>
                            {/block}
                        </div>
                    </div>
                </div>
            </div>
        {/form}
    {/snippet}

    <script>
        var url = window.location.href;
        var hash = url.substring(url.indexOf("#"));

        if (hash === "#obrazky") {
            $(function(){
                $('#zalozky a[href="#obrazky"]').tab('show');
            });
        } else if (hash === "#soubory") {
            $(function(){
                $('#zalozky a[href="#soubory"]').tab('show');
            });
        } else if (hash === "#kategorie") {
            $(function(){
                $('#zalozky a[href="#kategorie"]').tab('show');
            });
        } else {
            $(function(){
                $('#zalozky a[href="#detail"]').tab('show');
            });
        }
    </script>


    <script>
        $(".addPhotoReplicator").click(function(){
            $('#zalozky a[href="#obrazky"]').tab('show');
            console.log();
    });
    </script>
FJP
Člen | 124
+
0
-

ale nic nepřybývá a konzole nehlásí žádnou chybu