Angular 无法从其他指令更改 ng-model
Angular Can't change ng-model form other directive
我需要通过单击 pdfViewer 指令中的 canvas 来更改 pdfViewerToolbar 指令中的 ng-model (currentPage)。当我点击 canvas 时,控制器中的 self.next 函数被调用,但是 ng-model="currentPage" 在 pdfViewerToolbar 指令中没有改变。
app.angular.module("pdf").directive("pdfViewerToolbar", ["pdfDelegate", function(e) {
return {
restrict: "E",
template: '<div class="pdf_navigation" ng-show="navBar">\
<div class="pdf_buttons">\
<div ng-click="prev()" class="goPrevious" title="previous page"></div>\
<div ng-click="next()" class="goNext" id="goNext" title="next page"></div>\
<div ng-click="zoomOut()" class="zoomIn"></div>\
<div ng-click="zoomIn()" class="zoomOut"></div>\
</div>\
<div class="pdf_page">\
<span>Page</span>\
<input type="text" min=1 ng-model="currentPage" maxlength="4" ng-change="goToPage()" >\
<span>of {{pageCount}}</span>\
</div>\
</div>',
scope: {
pageCount: "=",
navBar: "=",
},
// controller: "PdfCtrl",
link: function(t, n, a) {
var o = a.delegateHandle;
t.currentPage = 1, t.prev = function() {
e.$getByHandle(o).prev(), r()
}, t.next = function() {
e.$getByHandle(o).next(), r()
}, t.zoomIn = function() {
e.$getByHandle(o).zoomIn()
}, t.zoomOut = function() {
e.$getByHandle(o).zoomOut()
}, t.rotate = function() {
e.$getByHandle(o).rotate()
}, t.goToPage = function() {
e.$getByHandle(o).goToPage(t.currentPage)
};
var r = function() {
t.currentPage = e.$getByHandle(o).getCurrentPage()
}
}
}
}])
app.angular.module("pdf").directive("pdfViewer", ["pdfDelegate", function(r) {
return {
restrict: "E",
template: '<div show-control class="pdf_doc"><pdf-viewer-toolbar ng-if="showToolbar" delegate-handle="{{id}}" page-count="pageCount" nav-bar="pdfNavigationBar"></pdf-viewer-toolbar><canvas ng-click="next()" id="pdf-canvas" ></canvas></div>',
scope: false,
controller: "PdfCtrl",
link: function(e, t, n) {
e.id = n.delegateHandle, e.showToolbar = e.$eval(n.showToolbar) || !1
var o = n.delegateHandle;
e.currentPage = 1,
e.next = function() {
r.$getByHandle(o).next(), s()
}
var s = function() {
e.currentPage = r.$getByHandle(o).getCurrentPage()
}
}
}
}]);
app.controller('PdfCtrl', [
'$scope',
'$element',
'$attrs',
'pdfDelegate',
'$log',
'$q', '$rootScope',
function($scope, $element, $attrs, pdfDelegate, $log, $q, $rootScope) {
// Register the instance!
var deregisterInstance = pdfDelegate._registerInstance(this, $attrs.delegateHandle);
// De-Register on destory!
$scope.$on('$destroy', deregisterInstance);
var self = this;
var url = $scope.$eval($attrs.url);
var headers = $scope.$eval($attrs.headers);
var pdfDoc;
$scope.pageCount = 0;
var currentPage = 1;
var angle = 0;
var scale = $attrs.scale ? $attrs.scale : 1;
var canvas = $element.find('canvas')[0];
var ctx = canvas.getContext('2d');
self.next = function() {
if (currentPage >= pdfDoc.numPages)
return;
currentPage = parseInt(currentPage, 10) + 1;
renderPage(currentPage);
console.log('currentPage'+currentPage);
};
return PDFJS
.getDocument(docInitParams)
.then(function (_pdfDoc) {
console.log('loaded');
$rootScope.loadPdf = $scope.pdfNavigationBar = true;
pdfDoc = _pdfDoc;
renderPage(1);
$scope.$apply(function() {
$scope.pageCount = _pdfDoc.numPages;
});
}, function(error) {
$log.error(error);
return $q.reject(error);
})
};
if(url) self.load();
}]);
您需要将 currentPage 变量作为独立指令传递,如下所示。
return {
restrict: "E",
template: '<div class="pdf_navigation" ng-show="navBar">\
<div class="pdf_buttons">\
<div ng-click="prev()" class="goPrevious" title="previous page"></div>\
<div ng-click="next()" class="goNext" id="goNext" title="next page"></div>\
<div ng-click="zoomOut()" class="zoomIn"></div>\
<div ng-click="zoomIn()" class="zoomOut"></div>\
</div>\
<div class="pdf_page">\
<span>Page</span>\
<input type="text" min=1 ng-model="currentPage" maxlength="4" ng-change="goToPage()" >\
<span>of {{pageCount}}</span>\
</div>\
</div>',
scope: {
pageCount: "=",
navBar: "=",
currentPage: "="
},
...
...
...
现在从 pdfViewer 指令模板传递 currentPage,如下所示:
app.angular.module("pdf").directive("pdfViewer", ["pdfDelegate", function(r) {
return {
restrict: "E",
template: '<div show-control class="pdf_doc"><pdf-viewer-toolbar ng-if="showToolbar" delegate-handle="{{id}}" page-count="pageCount" nav-bar="pdfNavigationBar" current-page="currentPage" ></pdf-viewer-toolbar><canvas ng-click="next()" id="pdf-canvas" ></canvas></div>',
scope: false,
controller: "PdfCtrl",
现在在控制器 PdfCtrl 的范围内定义变量并从中进行访问。
app.controller('PdfCtrl', [
'$scope',
'$element',
'$attrs',
'pdfDelegate',
'$log',
'$q', '$rootScope',
function($scope, $element, $attrs, pdfDelegate, $log, $q, $rootScope) {
// Register the instance!
var deregisterInstance = pdfDelegate._registerInstance(this, $attrs.delegateHandle);
// De-Register on destory!
$scope.$on('$destroy', deregisterInstance);
var self = this;
var url = $scope.$eval($attrs.url);
var headers = $scope.$eval($attrs.headers);
var pdfDoc;
$scope.pageCount = 0;
$scope.currentPage = 1;
var angle = 0;
var scale = $attrs.scale ? $attrs.scale : 1;
var canvas = $element.find('canvas')[0];
var ctx = canvas.getContext('2d');
self.next = function() {
if ($scope.currentPage >= pdfDoc.numPages)
return;
$scope.currentPage = parseInt($scope.currentPage, 10) + 1;
renderPage($scope.currentPage);
console.log('currentPage'+$scope.currentPage);
};
在您的 pdfViewerToolbar
指令中 scope
是孤立的,如果您想更改该指令中的某些内容,您可以将其作为具有两种数据绑定的范围元素传递:"="
.
scope: {
pageCount: "=",
navBar: "=",
currentPage:"="
}
并像这样使用你的指令传递控制器模型
<pdf-viewer-toolbar page-count="ctrlModelPageCount" nav-bar="ctrlModelNavBar" current-page="ctrlModelCurrentPage"></pdf-viewer-toolbar>
我需要通过单击 pdfViewer 指令中的 canvas 来更改 pdfViewerToolbar 指令中的 ng-model (currentPage)。当我点击 canvas 时,控制器中的 self.next 函数被调用,但是 ng-model="currentPage" 在 pdfViewerToolbar 指令中没有改变。
app.angular.module("pdf").directive("pdfViewerToolbar", ["pdfDelegate", function(e) {
return {
restrict: "E",
template: '<div class="pdf_navigation" ng-show="navBar">\
<div class="pdf_buttons">\
<div ng-click="prev()" class="goPrevious" title="previous page"></div>\
<div ng-click="next()" class="goNext" id="goNext" title="next page"></div>\
<div ng-click="zoomOut()" class="zoomIn"></div>\
<div ng-click="zoomIn()" class="zoomOut"></div>\
</div>\
<div class="pdf_page">\
<span>Page</span>\
<input type="text" min=1 ng-model="currentPage" maxlength="4" ng-change="goToPage()" >\
<span>of {{pageCount}}</span>\
</div>\
</div>',
scope: {
pageCount: "=",
navBar: "=",
},
// controller: "PdfCtrl",
link: function(t, n, a) {
var o = a.delegateHandle;
t.currentPage = 1, t.prev = function() {
e.$getByHandle(o).prev(), r()
}, t.next = function() {
e.$getByHandle(o).next(), r()
}, t.zoomIn = function() {
e.$getByHandle(o).zoomIn()
}, t.zoomOut = function() {
e.$getByHandle(o).zoomOut()
}, t.rotate = function() {
e.$getByHandle(o).rotate()
}, t.goToPage = function() {
e.$getByHandle(o).goToPage(t.currentPage)
};
var r = function() {
t.currentPage = e.$getByHandle(o).getCurrentPage()
}
}
}
}])
app.angular.module("pdf").directive("pdfViewer", ["pdfDelegate", function(r) {
return {
restrict: "E",
template: '<div show-control class="pdf_doc"><pdf-viewer-toolbar ng-if="showToolbar" delegate-handle="{{id}}" page-count="pageCount" nav-bar="pdfNavigationBar"></pdf-viewer-toolbar><canvas ng-click="next()" id="pdf-canvas" ></canvas></div>',
scope: false,
controller: "PdfCtrl",
link: function(e, t, n) {
e.id = n.delegateHandle, e.showToolbar = e.$eval(n.showToolbar) || !1
var o = n.delegateHandle;
e.currentPage = 1,
e.next = function() {
r.$getByHandle(o).next(), s()
}
var s = function() {
e.currentPage = r.$getByHandle(o).getCurrentPage()
}
}
}
}]);
app.controller('PdfCtrl', [
'$scope',
'$element',
'$attrs',
'pdfDelegate',
'$log',
'$q', '$rootScope',
function($scope, $element, $attrs, pdfDelegate, $log, $q, $rootScope) {
// Register the instance!
var deregisterInstance = pdfDelegate._registerInstance(this, $attrs.delegateHandle);
// De-Register on destory!
$scope.$on('$destroy', deregisterInstance);
var self = this;
var url = $scope.$eval($attrs.url);
var headers = $scope.$eval($attrs.headers);
var pdfDoc;
$scope.pageCount = 0;
var currentPage = 1;
var angle = 0;
var scale = $attrs.scale ? $attrs.scale : 1;
var canvas = $element.find('canvas')[0];
var ctx = canvas.getContext('2d');
self.next = function() {
if (currentPage >= pdfDoc.numPages)
return;
currentPage = parseInt(currentPage, 10) + 1;
renderPage(currentPage);
console.log('currentPage'+currentPage);
};
return PDFJS
.getDocument(docInitParams)
.then(function (_pdfDoc) {
console.log('loaded');
$rootScope.loadPdf = $scope.pdfNavigationBar = true;
pdfDoc = _pdfDoc;
renderPage(1);
$scope.$apply(function() {
$scope.pageCount = _pdfDoc.numPages;
});
}, function(error) {
$log.error(error);
return $q.reject(error);
})
};
if(url) self.load();
}]);
您需要将 currentPage 变量作为独立指令传递,如下所示。
return {
restrict: "E",
template: '<div class="pdf_navigation" ng-show="navBar">\
<div class="pdf_buttons">\
<div ng-click="prev()" class="goPrevious" title="previous page"></div>\
<div ng-click="next()" class="goNext" id="goNext" title="next page"></div>\
<div ng-click="zoomOut()" class="zoomIn"></div>\
<div ng-click="zoomIn()" class="zoomOut"></div>\
</div>\
<div class="pdf_page">\
<span>Page</span>\
<input type="text" min=1 ng-model="currentPage" maxlength="4" ng-change="goToPage()" >\
<span>of {{pageCount}}</span>\
</div>\
</div>',
scope: {
pageCount: "=",
navBar: "=",
currentPage: "="
},
...
...
...
现在从 pdfViewer 指令模板传递 currentPage,如下所示:
app.angular.module("pdf").directive("pdfViewer", ["pdfDelegate", function(r) {
return {
restrict: "E",
template: '<div show-control class="pdf_doc"><pdf-viewer-toolbar ng-if="showToolbar" delegate-handle="{{id}}" page-count="pageCount" nav-bar="pdfNavigationBar" current-page="currentPage" ></pdf-viewer-toolbar><canvas ng-click="next()" id="pdf-canvas" ></canvas></div>',
scope: false,
controller: "PdfCtrl",
现在在控制器 PdfCtrl 的范围内定义变量并从中进行访问。
app.controller('PdfCtrl', [
'$scope',
'$element',
'$attrs',
'pdfDelegate',
'$log',
'$q', '$rootScope',
function($scope, $element, $attrs, pdfDelegate, $log, $q, $rootScope) {
// Register the instance!
var deregisterInstance = pdfDelegate._registerInstance(this, $attrs.delegateHandle);
// De-Register on destory!
$scope.$on('$destroy', deregisterInstance);
var self = this;
var url = $scope.$eval($attrs.url);
var headers = $scope.$eval($attrs.headers);
var pdfDoc;
$scope.pageCount = 0;
$scope.currentPage = 1;
var angle = 0;
var scale = $attrs.scale ? $attrs.scale : 1;
var canvas = $element.find('canvas')[0];
var ctx = canvas.getContext('2d');
self.next = function() {
if ($scope.currentPage >= pdfDoc.numPages)
return;
$scope.currentPage = parseInt($scope.currentPage, 10) + 1;
renderPage($scope.currentPage);
console.log('currentPage'+$scope.currentPage);
};
在您的 pdfViewerToolbar
指令中 scope
是孤立的,如果您想更改该指令中的某些内容,您可以将其作为具有两种数据绑定的范围元素传递:"="
.
scope: {
pageCount: "=",
navBar: "=",
currentPage:"="
}
并像这样使用你的指令传递控制器模型
<pdf-viewer-toolbar page-count="ctrlModelPageCount" nav-bar="ctrlModelNavBar" current-page="ctrlModelCurrentPage"></pdf-viewer-toolbar>