AngularJs: требуемая проверка поля и выделение для динамических строк таблицы HTML с contenteditable

у меня есть таблица HTML, как показано ниже:

<tbody>
    <tr ng-repeat="r in targetTable.rows">
      <td contenteditable="true" class=""></td>
      <td contenteditable="true"
          ng-repeat="column in targetTable.columns"
          ng-model="r[column.id]"
          ng-blur="!r.id? addNewRow(r[column.id], r): undefined">
      </td>             
    </tr>
</tbody>

Я использую директиву contenteditable для редактирования ячеек.

app.directive('contenteditable', ['$sce', function($sce) {
  return {
    restrict: 'A',
    require: '?ngModel',
    link: function(scope, element, attrs, ngModel) {
      var disable = (attrs.contenteditable === "false") || !Boolean(attrs.contenteditable);
      if (!ngModel || disable) return; // do nothing if no ng-model

      // Write data to the model
      var read = function(value) {
        var html = element.html() || (typeof value === "string" ? value : "");

        // When we clear the content editable the browser leaves a <br> behind
        // If strip-br attribute is provided then we strip this out
        if (attrs.stripBr && html == '<br>') {
          html = '';
        }
        ngModel.$setViewValue(html);
      };

      // Specify how UI should be updated
      ngModel.$render = function() {
        element.html($sce.getTrustedHtml(ngModel.$viewValue || ''));
      };

      // Listen for change events to enable binding
      element.on('blur keyup change', function() {
        scope.$evalAsync(read);
      });

      setTimeout(function() {
        read(ngModel.$modelValue); // initialize
      });

    }
  };
}]);

Вы можете увидеть Jsfiddle здесь:http://jsfiddle.net/u1vbeos5/144/

Нажмите, чтобы добавить столбец и добавить динамическое поле. Начните вводить строку 1 после того, как она автоматически создаст другую динамическую строку.

теперь я хочу добавить требуемую проверку поля для каждой строки, чтобы при кто-то щелкает сохранить его запускает проверку и выделяет все пустые строки.

Я не уверен, как мы можем сделать это. Я считаю, что мы должны сделать что-то в конце директивы, чтобы найти пустую строку и выделить ее.

какие входы ?

спасибо

2 ответов


нет необходимости менять директиву, встроенный ng-required уже работает. Просто добавьте форма контроллер, как указано в комментариях. Если вы не добавляете контроллер формы, вам нужно будет проверить все поля самостоятельно на $scope.save.

добавить ng-требуется для модели:

<td contenteditable="true"
     ng-repeat="column in targetTable.columns"
     ng-model="r[column.id]"
     ng-blur="!r.id? addNewRow(r[column.id], r): undefined"
     ng-required="!$parent.$last"></td>

ng-required=$parent.$last означает, что поле является обязательным, если это не последняя строка (я предположил это на основе того, как вы добавляете строки). Angularjs установит класс ng-invalid на td элемент, если нет никакого значения.

поскольку, похоже, нет формы, добавьте ng-form к разметке таблицы. Кроме того, это может быть обернуто с form тег, который должен достичь того же.

<table class="table table-bordered"
    ng-form="targetTableForm"
    ng-class="{submitted: targetTableSubmitted}">

при сохранении проверьте правильность формы и отметьте форму как отправленную. Это добавит submitted class к таблице на основе разметки выше.

$scope.save = function() {   
    $scope.targetTableSubmitted = true;

    if ($scope.targetTableForm.$valid) {
        alert('submitted');
    } else {
        alert('please fill table data');
    }
    /**
      * If no form controller is defined, manually loop through all rows
      * and columns to check for a value
      */
  };

затем, наконец, добавьте css, чтобы выделить таблицу ячейка:

.table.submitted td.ng-invalid {
  background-color: red;
}

другой подход будет отключить кнопку Сохранить, если форма недействительна.

обратите внимание, что столбец Name не имеет ng-модели, поэтому он не будет привязан ни к чему, и поэтому он не будет проверен.

обновление jsfiddle


что это <td> не работает. Попробуйте сначала только с одним и посмотреть, как вы можете сделать это для n столбцов и n строк правильно.

когда кто-то нажимает кнопку Сохранить, вы можете передать массив строк и добавить допустимое/недопустимое логическое значение внутри этого объекта, а затем использовать ng-класс для выделения этой ячейки или нет, в зависимости от результата.

<td contenteditable="true" ng-model="r.value"
    ng-class="r.invalid ? 'cell-highlighted' : ''">
</td>
$scope.save = function(rows, columns) {
    rows.forEach(row => {
        if (!row.value || row.value.trim() === '') {
            row.invalid = true;
        } else {
            row.invalid = false;
        }
    })
    alert('please fill table data');
};

Я изменил вашу скрипку с этими изменениями, надеюсь, вы можете использовать он.

http://jsfiddle.net/4t85gw1z/