そこで双方向通信を利用する方法はありますか?(たとえば、postCommentで行われたAJAX呼び出しからerrmsgフィールドを追加するか、送信時にフォームをクリアしますか?)
独自のコントローラーを備えたディレクティブをお勧めします。このアプローチでは、comment
モデルはディレクティブにカプセル化されます。ディレクティブには2つの情報が必要です。1)postID 2)コメントを保存するために呼び出す関数。サーバーから返されたエラーメッセージの表示をサポートするために、コメントとともにコールバック関数が渡されます。これにより、コントローラーは、保存操作の試行後に必要になる可能性のあるエラーメッセージやその他の情報をディレクティブにフィードできます。
app.directive('commentForm', function() {
var template = '<form name="commentForm" '
+ 'ng-submit="save({comment: comment, callbackFn: callbackFn})">'
+ '<h3>Leave a comment</h3>'
+ 'Name: <input type="text" ng-model="comment.name" name="commentName"> <br>'
+ '<span class="error" ng-show="commentForm.commentName.$error.myError">Error</span><br>'
+ 'Comment: <textarea ng-model="comment.text"></textarea> <br>'
+ '<input type="submit" value="Save comment">'
+ '</form>';
return {
restrict: 'E',
template: template,
scope: { postId: '@', save: '&' },
controller: function($scope) {
$scope.callbackFn = function(args) {
console.log('callback', args);
if(args.error.name) {
$scope.commentForm.commentName.$setValidity("myError", false);
} else {
// clear form
$scope.comment.name = '';
$scope.comment.text = '';
}
};
}
};
});
app.controller('MainCtrl', function($scope, $timeout) {
$scope.post = {id: 1};
$scope.saveComment = function(comment, callbackFn) {
console.log('saving...', comment);
// Call $http here... then call the callback.
// We'll simulate doing something with a timeout.
$timeout(function() {
if(comment.name === "name") {
callbackFn( {error: {name: 'try again'}} );
} else {
callbackFn( {error: {}} );
}
}, 1500)
}
});
次のように使用します。
<comment-form post-id="{{post.id}}" save="saveComment(comment, callbackFn)"></comment-form>
'&'構文に関連するやや奇妙な構文に注意してください。ディレクティブがHTMLで使用される場合、saveComment()関数の引数を指定します。ディレクティブ/テンプレートでは、オブジェクト/マップを使用して、各引数名をその値に関連付けます。値はローカル/ディレクティブスコーププロパティです。
Plnkr。plnkrでは、1.5秒の$timeoutを使用してAJAX投稿をシミュレートしました。名前のテキストボックスに入力name
して[保存]ボタンをクリックすると、1.5秒でエラーが発生します。それ以外の場合、フォームは1.5秒後にクリアされます。
これをどこまで進めたいかに応じて...投稿テンプレートをディレクティブにカプセル化することもできます。
<li ng-repeat="post in posts">
<post=post></post>
<comment-form ...></comment-form>
</li>
コメントフォームをpostディレクティブテンプレート内に配置して、HTMLをさらに単純化することもできます。
<li ng-repeat="post in posts">
<post=post></post>
</li>
post-listディレクティブを使用することもでき、そのテンプレートにはng-repeatが含まれ、HTMLを単一の要素に縮小します。
<post-list posts=posts></post-list>
個人的には、カスタムディレクティブをどこまで使用するかはまだ決めていません。私は人々がこれについて持っているどんなコメントにも非常に興味があります。