如何检测焦点何时超出Div?

时间:2016-10-05 18:50:20

标签: javascript angularjs onblur

我正在处理一个生成多个Div的动态表单。我想检测焦点是否从整个div中丢失,而不仅仅是从一个输入。

enter image description here

如图所示,我有多个相同的表单,这里的问题是如何检测用户是否完成了其中一个表单的编辑?

使用ng-repeat动态创建表单。

<fieldset  data-ng-repeat="response in responces" ng-init="sectionIndex = $index" >
    <div id="customFrom">
    <input type="text" ng-model="response.code" name="" placeholder="Code">
    <input type="text" ng-model="response.rank" name="" placeholder="{{ 'app.forms.responses.rank' | translate }}" >
    <input type="text" ng-model="response.value" name="" placeholder="{{ 'app.forms.responses.value' | translate }}">
    <input type="text" ng-model="response.name" name="" placeholder="{{ 'app.forms.createQuiz.fields.name' | translate }}" class="labelTextQuestionCreation">
    <button class="remove"  ng-click="removeResponse($index)" ng-show="deteteResponceOption">-</button>
    </div>
</fieldset>

当用户从一个表单跳转到另一个表单时,添加操作的最佳方法是什么?我需要检测表单(Div)何时失去焦点才能执行功能。 谢谢。

2 个答案:

答案 0 :(得分:1)

根据您的问题,最佳解决方案是使用ng-model-options

每个具有ng-model的元素都需要以下属性:

ng-model-options="{ updateOn: 'blur' }"

然后看起来像:

<input type="text" ng-model="response.code" name="" ng-model-options="{ updateOn: 'blur' }" placeholder="Code">

使用ng-model-options,只有在表单字段中丢失焦点时才会更新模型。然后,您可以拥有$ watch语句,该语句仅在模型更新时触发。

在$ watch回调中,当检测到主阵列的任何属性发生更改时,您可以通过验证运行模型,以了解是否填写了所有数据并继续执行所需的功能。

$scope.$watch('responces', function (newVal, oldVal) {
    // onBlur triggered an update to an attribute of **responces**
    // run your input validation here
}, true);

答案 1 :(得分:0)

我修复了问题通过使用指示表单索引的隐藏输入,此输入的值将添加到模型中,因为我正在使用ng-repeat,因此每行都有自己的范围。另外,我使用ng-focus指令来检查输入是否有焦点,当它发生时,我调用一个我称为`getSelectedElement(index)的函数,该函数验证索引是否已经改变,如果我们在我们更新/插入数据库中的行的新索引中。以下是我的解决方案代码:

<强> HTML

 <fieldset  data-ng-repeat="response in responces track by $index" ng-init="sectionIndex = $index">
    <div ng-model-options="{ updateOn: 'blur' }"  >
    <input type="text" ng-model="response.code" name="" placeholder="Code"  ng-focus="getSelectedElement(sectionIndex)">
     <input type="text" ng-model="response.index"  ng-init="response.index=sectionIndex"   ng-value="sectionIndex"  ng-focus="getSelectedElement(sectionIndex)" ng-show="false">
    <input type="text" ng-model="response.rank" name="" placeholder="{{ 'app.forms.responses.rank' | translate }}"  ng-focus="getSelectedElement(sectionIndex)">
    <input type="text" ng-model="response.value" name="" placeholder="{{ 'app.forms.responses.value' | translate }}" ng-focus="getSelectedElement(sectionIndex)">
    <input type="text" ng-model="response.name" name="" placeholder="{{ 'app.forms.createQuiz.fields.name' | translate }}" class="labelTextQuestionCreation" ng-focus="getSelectedElement(sectionIndex)" >
    <button class="remove"  ng-click="removeResponse($index)" ng-show="deteteResponceOption">-</button>
    </div>
</fieldset>

<强>的JavaScript

$scope.getSelectedElement=function(index){
 var oldIndex=$scope.responcesSelectedIndex;//Variable to watch, it gets updated when we gain focus. initially it has -1 as a value, and we gain focus on a field it gets updated
 if(oldIndex==-1){//-1 indicates that we are in the first element, no previous index, no need to do any thing just update the old index.
     oldIndex=index;
 }
 $scope.responcesSelectedIndex=index;//Update the old index to be the current so when we call the function again we will have two index values, the new one (As a parameter) and the old one ($scope.responcesSelectedIndex)
 var newIndex=$scope.responcesSelectedIndex;
     if(oldIndex!=newIndex){//Jumping to the new Form
        console.log("Update or Create");
        //Do What You want Here

    }

}

这不是一个完美的解决方案,但它运作得很好。