0

I have a modal form with angular and uib-tabset.

I have only a footer in modal. Each tabset has a form( A B and C).

When I try enabled/disable the save button on footer, I can´t acesss acesss the forms. They are undefined.

So, in the 'Save' button(see plunker) - formA.$invalid doesn´t works. I think it is a scope problem.

I´d prefer doesn´t put a global form to all tabs.

Is there some workaround to solve it?

Markup:

<div class="modal-content">
    <div class="modal-header bg-primary">
      <button type="button" class="close" ng-click="doCancel()" aria-hidden="true">&times;</button>
      <h4 class="modal-title" id="ativarSmsLabel">
        Test
      </h4>
    </div>
    <div class="modal-body">
        <uib-tabset active="activePill" vertical="false" type="pills">
          <uib-tab index="0" heading="Agendamento">     
                            <form name="formA" novalidate>
                                <input type="text" ng-model="testA"
                             </form>
                        </div>
                    </div>
                </div>
          </uib-tab>
          <uib-tab index="1" heading="Ficha">       
              <form name="formB" novalidate>
                                <input type="text" ng-model="testB"
              </form>
          </uib-tab>
          <uib-tab index="2" heading="Histórico">
                <form name="formC" novalidate>
                   <input type="text" ng-model="testC"
                </form>
          </uib-tab>
        </uib-tabset>
    </div>

     <div class="modal-footer">
               <div class="btn-toolbar">
                   <button type="button" class="btn btn-sm btn-primary pull-right" ng-click="saveItem()"
                    aria-hidden="true" ng-disabled="formA.$invalid">
                    Save
                  </button>
                  <button type="button" class="btn btn-sm pull-right" ng-click="doCancel()"
                    aria-hidden="true">
                    Close
                  </button>
               </div>
      </div>
</div>
Luiz Alves
  • 2,575
  • 4
  • 34
  • 75
  • its difficult to predict this behavior with this small part of your code. I can see that you have not written `ng-controller` in this code, so it seems incomplete. I know it may seem tiresome but it would be more helpful if u can create a plunkr and try. If that doesn't work, please share it here. I would love to look into it. – Shashank Vivek Nov 22 '17 at 19:18
  • @Shashank Vivek I just put a plunker link. – Luiz Alves Nov 22 '17 at 21:41
  • 1
    When asking a question about a problem caused by your code, you will get much better answers if you provide code people can use to reproduce the problem. That code should be… **Minimal** – Use as little code as possible that still produces the same problem. See [How to create a Minimal, Complete, and Verifiable example](https://stackoverflow.com/help/mcve) – georgeawg Nov 22 '17 at 21:48
  • To get around scoping issues with forms, use a top level form with a name and use the [ng-form directive](https://docs.angularjs.org/api/ng/directive/ngForm) for nested forms. – georgeawg Nov 22 '17 at 21:51
  • @georgeawg Thank you, but how do I can access $valid of the nested form? I did your suggestion and I used 'mainForm.nestedForm.$valid' and it doesn´t work – Luiz Alves Nov 22 '17 at 21:54
  • Create a mimimal example of a nested form and if you can't get it working, post that minimal example. – georgeawg Nov 22 '17 at 22:01
  • Sorry my plunker was not saved I will recreate i – Luiz Alves Nov 22 '17 at 22:18
  • @georgeawg You was correct. Using ng-form solved the problem. Thank you. – Luiz Alves Nov 22 '17 at 22:36

1 Answers1

0

Core AngularJS directives such as ng-repeat, ng-switch, ng-view, ng-include and ng-if all create new child scopes. As a result, the form controller will attach its API to that child scope. In this case the uib-tabset directive is transcluding to a child scope.

To access form controls on the parent scope, use the ng-form directive to create a nested form:

<form name="top">
    <div ng-if="AngularExpression">
       <ng-form name="formA" novalidate>
           <input ng-model="userData.testA" required />
       </ng-form>
   </div>
</form>

<div ng-show="top.formA.$error.$required">
   ERROR: input required
</div>

Also it is important to follow the "best practice" of always have a dot, '.', in your ng-models.

For more information, see What are the nuances of scope prototypal / prototypical inheritance in AngularJS?.

georgeawg
  • 48,608
  • 13
  • 72
  • 95