复位形式原始状态(AngularJS 1.0.x的) [英] Reset form to pristine state (AngularJS 1.0.x)

查看:101
本文介绍了复位形式原始状态(AngularJS 1.0.x的)的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

一个功能重设表单字段原始状态(复位脏状态)的路线图AngularJS 1.1.x中不幸的是这样的功能是从当前稳定版本丢失。

什么是所有表单域重置为初始原始状态AngularJS 1.0.x的最好的方式?

我想知道这是可以解决的一个指令或其他简单的解决方法。我preFER的解决方案,而无需接触到原件AngularJS来源。为了澄清和说明问题,一个链接的jsfiddle。 http://jsfiddle.net/juurlink/FWGxG/7/

所需功能的路线图 - <一个href=\"http://blog.angularjs.org/2012/07/angularjs-10-12-roadmap.html\">http://blog.angularjs.org/2012/07/angularjs-10-12-roadmap.html

功能请求 - <一个href=\"https://github.com/angular/angular.js/issues/856\">https://github.com/angular/angular.js/issues/856

建议的解决方案 pull请求 - <一个href=\"https://github.com/angular/angular.js/pull/1127\">https://github.com/angular/angular.js/pull/1127


更新了可能的解决方法

够好解决办法?

我想通了,我可以重新编译的HTML的一部分,把它放回了DOM。它的工作原理和它的罚款为暂时的解决方案,而且在批示@blesh提到的:

控制器应该用于业务逻辑,不能用于DOM!

 &LT; D​​IV ID =MyForm的&GT;
  &LT;窗​​体类=形横NAME =形式&GT;
  &LT; /表及GT;
&LT; / DIV&GT;

和在我的 resetForm()控制器:


  • 保存原始数据不变HTML

  • 重新编译保存原始的HTML

  • 从DOM删除当前形式

  • 将新编译模板放到DOM

JavaScript的:

  VAR pristineFormTemplate = $('#MyForm的')HTML();
$ scope.resetForm =功能(){
    $('#MyForm的')空()追加($编译(pristineFormTemplate)($范围))。;
}


解决方案

解决方案没有解决方法

我想出了它使用AngularJS没有任何变通的解决方案。这里的技巧是使用AngularJS有多个指令具有相同名称的能力。

正如其他人提到的居然有一个拉请求(<一个href=\"https://github.com/angular/angular.js/pull/1127\">https://github.com/angular/angular.js/pull/1127)这使得它进入AngularJS 1.1.x的分支,让形式进行复位。在提交本拉入请求改变ngModel和形式/ ngForm指令(我本来希望添加一个链接,但#1不希望我增加更多比两个链接)。

现在,我们可以定义自己的ngModel和形式/ ngForm指令,并将它们与在拉请求中提供的功能扩展。

我已经包裹名为resettableForm一个AngularJS模块中的这些指令。所有你需要做的是包含这个模块你的项目,你的AngularJS版本1.0.x的行为就好像它在这方面的一个角1.1.x版本的。

一旦你更新到1.1.x中你甚至不必更新您的code,只是删除模块和你做!

这个模块还通过添加到1.1.x的分行形式重置功能的所有测试。

您可以看到模块中的例子工作中的jsfiddle( http://jsfiddle.net/jupiter/7jwZR/1 / )我创建的。

步骤1:包括resettableform模块项目

 (函数(角){//从AngluarJS复制
功能的indexOf(数组,OBJ){
  如果(array.indexOf)返回array.indexOf(OBJ);  对于(VAR I = 0; I&LT; array.length,我++){
    如果(OBJ ===数组[我])回报我;
  }
  返回-1;
}//从AngularJS复制
功能arrayRemove(数组值){
  VAR指数=的indexOf(数组值);
  如果(索引&gt; = 0)
    方法Array.splice(指数,1);
  返回值;
}//从AngularJS复制
VAR PRISTINE_CLASS ='NG-原始';
VAR DIRTY_CLASS ='NG-脏;VAR formDirectiveFactory =功能(isNgForm){
    返回功能(){
        VAR formDirective = {
            限制:'E',
            要求:['形式'],
            编译:功能(){
                返回{
                    pre:功能(范围,元素,ATTRS,ctrls监视){
                        变种形式= ctrls监视[0];
                        变量$ =的AddControl $形式的AddControl。
                        变量$ removeControl =形式为$ removeControl。
                        无功控制= [];
                        形式。$ =的AddControl功能(控制){
                            controls.push(对照组);
                            $ addControl.apply(这一点,参数);
                        }
                        形式。$ removeControl =功能(控制){
                            arrayRemove(对照组,对照组);
                            $ removeControl.apply(这一点,参数);
                        }
                        形式。$ setPristine =功能(){
                            element.removeClass(DIRTY_CLASS).addClass(PRISTINE_CLASS);
                            。形式为$脏= FALSE;
                            。形式为$质朴= TRUE;
                            angular.forEach(控件,功能(控制){
                                控制$ setPristine()。
                            });
                        }
                    },
                };
            },
        };
        返回isNgForm? angular.extend(angular.copy(formDirective){限制:选管会'}):formDirective;
    };
}
VAR ngFormDirective = formDirectiveFactory(真);
变种formDirective = formDirectiveFactory();
angular.module('resettableForm',[])。
    指令(ngForm',ngFormDirective)。
    指令(形,formDirective)。
    指令(ngModel',函数(){
        返回{
            要求:['ngModel'],
            链接:功能(范围,元素,ATTRS,ctrls监视){
                无功控制= ctrls监视[0];
                控制。$ setPristine =功能(){
                    这$脏= FALSE。
                    这种质朴$ = TRUE。
                    element.removeClass(DIRTY_CLASS).addClass(PRISTINE_CLASS);
                }
            },
        };
    });
})(角度);

步骤2:提供您的控制器上的方法,该方法重置模型

请注意,当你重置表单,您必须重置模型。在你的控制器,你可以这样写:

  VAR对myApp = angular.module('对myApp',['resettableForm']);功能MyCtrl($范围){
    $ scope.reset =功能(){
        。$ scope.form $ setPristine();
        $ scope.model ='';
    };
}

步骤3:在HTML模板这种方法

 &LT; D​​IV NG-应用=对myApp&GT;
&LT; D​​IV NG控制器=MyCtrl&GT;
&LT;表格名称=形式&GT;
    &LT;输入名称=requiredFieldNG模型=model.requiredField要求/&GT; (必填,但没有其他验证)
    &LT; p NG秀=$ form.requiredField errror.required。&GT;现场要求与LT; / P&GT;
    &LT;按钮NG点击=reset()的&GT;复位形式&LT; /按钮&GT;
&LT; /表及GT;
&LT; P&GT;精粹:{{$形式质朴}}&LT; / P&GT;
&LT; / DIV&GT;
&LT; / DVI&GT;

A function to reset form fields to pristine state (reset dirty state) is on the roadmap for AngularJS 1.1.x. Unfortunately such a function is missing from the current stable release.

What is the best way to reset all form fields to their initial pristine state for AngularJS 1.0.x.?

I would like to know if this is fixable with a directive or other simple workaround. I prefer a solution without having to touch the original AngularJS sources. To clarify and demonstrate the problem, a link to JSFiddle. http://jsfiddle.net/juurlink/FWGxG/7/

Desired feature is on the Roadmap - http://blog.angularjs.org/2012/07/angularjs-10-12-roadmap.html
Feature request - https://github.com/angular/angular.js/issues/856
Proposed solution Pull request - https://github.com/angular/angular.js/pull/1127

Updated with possible workaround

Good enough workaround?

I just figured out I can recompile the HTML part and put it back into the DOM. It works and it's fine for a temporarily solution, but also as @blesh mentioned in the comments:

Controllers should be used for business logic only, not for DOM!

<div id="myform">
  <form class="form-horizontal" name="form">
  </form>
</div>

And in my Controller on resetForm():

  • Save the original untouched HTML
  • Recompile the saved original HTML
  • Remove the current form from the DOM
  • Insert the new compiled template into the DOM

The JavaScript:

var pristineFormTemplate = $('#myform').html();
$scope.resetForm = function () {
    $('#myform').empty().append($compile(pristineFormTemplate)($scope));
}

解决方案

Solution without a workaround

I came up with a solution which uses AngularJS without any workaround. The trick here is to use AngularJS ability to have more than one directive with the same name.

As others mentioned there is actually a pull request (https://github.com/angular/angular.js/pull/1127) which made it into the AngularJS 1.1.x branch which allows forms to be reset. The commit to this pull request alters the ngModel and form/ngForm directives (I would have liked to add a link but Stackoverflow doesn't want me to add more than two links).

We can now define our own ngModel and form/ngForm directives and extend them with the functionality provided in the pull request.

I have wrapped these directives in a AngularJS module named resettableForm. All you have to do is to include this module to your project and your AngularJS version 1.0.x behaves as if it was an Angular 1.1.x version in this regard.

''Once you update to 1.1.x you don't even have to update your code, just remove the module and you are done!''

This module also passes all tests added to the 1.1.x branch for the form reset functionality.

You can see the module working in an example in a jsFiddle (http://jsfiddle.net/jupiter/7jwZR/1/) I created.

Step 1: Include the resettableform module in your project

(function(angular) {

// Copied from AngluarJS
function indexOf(array, obj) {
  if (array.indexOf) return array.indexOf(obj);

  for ( var i = 0; i < array.length; i++) {
    if (obj === array[i]) return i;
  }
  return -1;
}

// Copied from AngularJS
function arrayRemove(array, value) {
  var index = indexOf(array, value);
  if (index >=0)
    array.splice(index, 1);
  return value;
}

// Copied from AngularJS
var PRISTINE_CLASS = 'ng-pristine';
var DIRTY_CLASS = 'ng-dirty';

var formDirectiveFactory = function(isNgForm) {
    return function() {
        var formDirective = {
            restrict: 'E',
            require: ['form'],
            compile: function() {
                return {
                    pre: function(scope, element, attrs, ctrls) {
                        var form = ctrls[0];
                        var $addControl = form.$addControl;
                        var $removeControl = form.$removeControl;
                        var controls = [];
                        form.$addControl = function(control) {
                            controls.push(control);
                            $addControl.apply(this, arguments);
                        }
                        form.$removeControl = function(control) {
                            arrayRemove(controls, control);
                            $removeControl.apply(this, arguments);
                        }
                        form.$setPristine = function() {
                            element.removeClass(DIRTY_CLASS).addClass(PRISTINE_CLASS);
                            form.$dirty = false;
                            form.$pristine = true;
                            angular.forEach(controls, function(control) {
                                control.$setPristine();
                            });
                        }
                    },
                };
            },
        };
        return isNgForm ? angular.extend(angular.copy(formDirective), {restrict: 'EAC'}) : formDirective;
    };
}
var ngFormDirective = formDirectiveFactory(true);
var formDirective = formDirectiveFactory();
angular.module('resettableForm', []).
    directive('ngForm', ngFormDirective).
    directive('form', formDirective).
    directive('ngModel', function() {
        return {
            require: ['ngModel'],
            link: function(scope, element, attrs, ctrls) {
                var control = ctrls[0];
                control.$setPristine = function() {
                    this.$dirty = false;
                    this.$pristine = true;
                    element.removeClass(DIRTY_CLASS).addClass(PRISTINE_CLASS);
                }
            },
        };
    });
})(angular);

Step 2: Provide a method on your controller which resets the model

Please be aware that you must reset the model when you reset the form. In your controller you can write:

var myApp = angular.module('myApp', ['resettableForm']);

function MyCtrl($scope) {
    $scope.reset = function() {
        $scope.form.$setPristine();
        $scope.model = '';
    };
}

Step 3: Include this method in your HTML template

<div ng-app="myApp">
<div ng-controller="MyCtrl">
<form name="form">
    <input name="requiredField" ng-model="model.requiredField" required/> (Required, but no other validators)
    <p ng-show="form.requiredField.$errror.required">Field is required</p>
    <button ng-click="reset()">Reset form</button>
</form>
<p>Pristine: {{form.$pristine}}</p>
</div>
</dvi>

这篇关于复位形式原始状态(AngularJS 1.0.x的)的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆