设置文本输入字段的初始值而不触发ng-change

设置文本输入字段的初始值而不触发ng-change

问题描述:

这个场景是一个包含JavaScript和AngularJS的Sudoku游戏。设置文本输入字段的初始值而不触发ng-change

Sudoku字段是数组(行)的数组(列)。所有阵列的长度都是9.我将这个Sudoku字段命名为matrix。函数exampleMatrix()返回已经有一些字段已填充的矩阵。

一种updateValue(sudokuMatrix, row, col, val)函数改变在位置行row和列col领域在基质sudokuMatrix为值val

function TestController($scope) { 
    $scope.matrix = exampleMatrix(); 
    $scope.updateValue = updateValue; 
    $scope.getMatrixVal = function getMatrixVal(row, col) { 
     return $scope.matrix[row][col]; 
    }; 
} 

我想要做的是显示矩阵的各个领域,如HTML的<input type="text">场。我希望所有字段初始设置为它们在矩阵中的值。如果文本字段的输入发生更改,我希望在$scope.matrix对象中更新该值。

我可以填补与矩阵的值的字段与下面的HTML/AngularJS代码没有问题:

<div ng-repeat="(rowIndex,row) in matrix track by $index"> 
    <input type="text" size="1" value="{{col}}" 
      ng-repeat="(colIndex,col) in row track by $index"> 
</div> 

但我不能更新在$scope.matrix对象的值呢,当然。

我现在面临的问题是

  1. 如果我在输入字段中更改值时,应matrix更新该值。我可以用ng-change="updateValue(matrix, rowIndex, colIndex, inputVal)"来做到这一点。
  2. 为了能够与ng-change改变matrix在范围内,我需要一个ng-model,其结合该字段的输入到可变:ng-model="inputVal"
  3. 如果我添加这两条线,输入字段不首先用范围的matrix对象中的值填充。

当前的代码看起来是这样的:

<div ng-repeat="(rowIndex,row) in matrix track by $index"> 
    <input type="text" size="1" value="{{getMatrixVal(rowIndex, colIndex)}}" 
      ng-model="inputVal" 
      ng-change="updateValue(matrix, rowIndex, colIndex, inputVal)" 
      ng-repeat="(colIndex,col) in row track by $index"> 
</div> 

我的猜测是,生成网站的时候,ng-model输入字段的空值赋给inputVal,并ng-change立即触发。因此,矩阵的每个字段都会填充一个空值。 AngularJS并没有抛出任何错误,所以我不能确定。无论如何,我在这里感到不知所措,不知道如何将最初的值写入最初的字段,并且仅在之后才被调用。我感谢每一个帮助。

的jsfiddle:https://jsfiddle.net/30xkedmp/

的JavaScript:http://pastebin.com/8cge8BXs HTML:http://pastebin.com/X0YUPU4h

+0

才有可能分享,你已经部署你的代码,以便它会很容易测试网址? – GraveyardQueen

+0

在帖子末尾加上链接到代码。虽然我没有在网上部署它,对不起。 – GeckStar

+0

创造小提琴,这将是我们容易。 https://jsfiddle.net/ – karman

你为什么不只是使用

<div ng-repeat="(rowIndex,row) in matrix track by $index"> 
    <input type="text" size="1" ng-model="matrix[rowIndex][colIndex]" 
      ng-repeat="(colIndex,col) in row track by $index"> 
</div> 

,而不是

<div ng-repeat="(rowIndex,row) in matrix track by $index"> 
    <input type="text" size="1" value="{{getMatrixVal(rowIndex, colIndex)}}" 
      ng-model="inputVal" 
      ng-change="updateValue(matrix, rowIndex, colIndex, inputVal)" 
      ng-repeat="(colIndex,col) in row track by $index"> 
</div> 
+0

没有想到它,使它更清洁。但我仍然有问题,即我写入输入字段的值不会更新控制器中的矩阵。 – GeckStar

+0

ng-model是双向绑定,因此当您更改视图并在更改控制器值时更新视图时,它会更新控制器中的值。 –

+0

您确实是对的,抱歉。我遇到了我的代码问题,因为我使用'updateValue(...)'方法将输入字符串解析为一个int,现在我无法使用ng-model轻松完成此操作。我检查更改的方式并不能识别字符串,在我看来,该值没有被注册。无论如何,你是绝对正确的,这段代码比其他选择更简单(你的答案是第一个),所以我改变了我的投票。 – GeckStar

你可以试试这个代码并看到,我只替换成input标签NG-value属性你的价值属性,如下图所示,

<!DOCTYPE html> 
 
<html ng-app="app"> 
 
<head> 
 
<meta charset="ISO-8859-1"> 
 
<title>Insert title here</title> 
 
    <script src="https://ajax.googleapis.com/ajax/libs/angularjs/1.2.9/angular.min.js"></script> 
 
</head> 
 
<body ng-controller="TestController"> 
 
<div ng-repeat="(rowIndex,row) in matrix track by $index"> 
 
    <input type="text" size="1" ng-value="getMatrixVal(rowIndex, colIndex)" 
 
     ng-model="inputVal" 
 
     ng-change="updateValue(matrix, rowIndex, colIndex, inputVal)" 
 
     ng-repeat="(colIndex,col) in row track by $index"> 
 
</div> 
 
<script> 
 
angular.module('app', []); 
 
angular.module('app').config(['$controllerProvider', function($controllerProvider) { 
 
    $controllerProvider.allowGlobals(); 
 
}]); 
 

 
function emptyRow() { 
 
    return [0, 0, 0, 0, 0, 0, 0, 0, 0]; 
 
} 
 

 
function emptyMatrix() { 
 
    var sudokuMatrix = []; 
 
    for (var i = 0; i < 9; i++) { 
 
    sudokuMatrix[i] = emptyRow(); 
 
    } 
 
    return sudokuMatrix; 
 
} 
 

 
function updateValue(sudokuMatrix, row, col, val) { 
 
    row = parseInt(row); 
 
    col = parseInt(col); 
 
    val = parseInt(val); 
 
    sudokuMatrix[row][col] = val; 
 
} 
 

 
function exampleMatrix() { 
 
    matrix = emptyMatrix(); 
 
    updateValue(matrix, 0, 2, 6); 
 
    updateValue(matrix, 0, 3, 3); 
 
    updateValue(matrix, 0, 4, 2); 
 

 
    updateValue(matrix, 1, 2, 1); 
 
    updateValue(matrix, 1, 5, 5); 
 
    updateValue(matrix, 1, 6, 3); 
 
    updateValue(matrix, 1, 7, 6); 
 

 
    updateValue(matrix, 2, 0, 9); 
 
    updateValue(matrix, 2, 1, 4); 
 
    updateValue(matrix, 2, 3, 6); 
 

 
    updateValue(matrix, 3, 2, 4); 
 

 
    updateValue(matrix, 4, 0, 8); 
 
    updateValue(matrix, 4, 1, 7); 
 
    updateValue(matrix, 4, 3, 1); 
 
    updateValue(matrix, 4, 4, 3); 
 
    updateValue(matrix, 4, 5, 4); 
 
    updateValue(matrix, 4, 7, 5); 
 
    updateValue(matrix, 4, 8, 6); 
 

 
    updateValue(matrix, 5, 6, 1); 
 

 
    updateValue(matrix, 6, 5, 9); 
 
    updateValue(matrix, 6, 7, 4); 
 
    updateValue(matrix, 6, 8, 7); 
 

 
    updateValue(matrix, 7, 1, 1); 
 
    updateValue(matrix, 7, 2, 7); 
 
    updateValue(matrix, 7, 3, 5); 
 
    updateValue(matrix, 7, 6, 2); 
 

 
    updateValue(matrix, 8, 4, 7); 
 
    updateValue(matrix, 8, 5, 2); 
 
    updateValue(matrix, 8, 6, 5); 
 

 
    return matrix; 
 
} 
 

 
function TestController($scope) { 
 
    $scope.matrix = exampleMatrix(); 
 
    $scope.updateValue = updateValue; 
 
    $scope.getMatrixVal = function(row, col) { 
 
    return $scope.matrix[row][col]; 
 
    }; 
 
} 
 

 
</script> 
 
</body> 
 
</html>

的代码片段不会在这里工作,因为它似乎不被接受我已经指定了角度js的版本,但代码的其余部分运行良好。

您可以尝试在你的小提琴被NG-value属性来取代值属性,并尝试

+0

我应该知道必须有一个指令。这正是我所期待的,谢谢!对于任何人都会遇到同样的问题,这里有更多的信息:https://*.com/questions/23865608/what-is-the-difference-between-value-attribute-and-ng-value-attributes-in -an – GeckStar

+0

事实上,在你的情况下,可以使用ng-value来代替ng-model,但是你在这里使用了太多的代码,你需要的仅仅是单一的ng-model,而不需要使用ng-change,getMatrixVal函数或者“ inpuVal“变量。正如我在下面的评论中提到的 - 我的答案 - ng-model指令是双向绑定,所以它自动更新控制器变量; ) 看看这个问题:http://*.com/questions/28717523/whats-the-difference-between-ng-model-and-ng-value –