我的网站导航包含大量重复使用的代码,我正在尝试创建一些自定义指令来代替使用。
导航中有相当多的逻辑来应用各种 CSS 规则、更改属性等。
<a ng-href="/#/Discovery" class="header"
ng-class="{active_header: $route.current.details[0].tab == 'discovery' && $route.current.details.length == 1, keep_open: $route.current.details[0].tab == 'discovery' && $route.current.details.length > 0}">
<i class="fa fa-search"></i><span translate="reports.discovery.discovery"></span>
</a>
<a class="menu_toggle" data-target="#discovery_menu"
ng-class="{disabled_toggle: $route.current.details[0].tab == 'discovery' && $route.current.details.length == 2, enabled_toggle: $route.current.details[0].tab != 'discovery' || $route.current.details.length != 2}"
ng-attr-data-toggle="{{($route.current.details[0].tab != 'discovery' && $route.current.details.length > 0) || ($route.current.details[0].tab == 'discovery' && $route.current.details.length == 1) ? 'collapse' : ''}}"
ng-attr-tooltip-enable="{{$route.current.details[0].tab == 'discovery' && $route.current.details.length == 2 ? 'true' : 'false'}}"
tooltip-placement="top" tooltip-append-to-body="true" uib-tooltip="{{'tooltips.navopen' | translate}}">
<i class="fa fa-angle-down"></i>
</a>
导航有自己的 Controller ,它使用 $scope 和 $route 并设置
$scope.$route = $route;
如您在上面看到的那样,在导航中使用它来检查当前路线。
我已经成功地为第一部分创建了一个自定义指令,即带有“header”类的 a 标签,它效果很好(仅供引用,使用 typescript )
export class parentTab {
public static Factory() {
return {
restrict: 'E',
scope: {
route: '=',
tabName: '@',
icon: '@'
},
templateUrl: '/app/templates/navigation/parentTab.html',
link: function(scope, element, attrs) {
console.log(scope.$parent.current);
}
}
}
}
// used in html
<parent-tab route="$route" tab-name="discovery" icon="search"></parent-tab>
模板文件与之前的 html 代码完全相同,但使用“{{tabName}}”(例如“discovery”)。
我遇到的问题是为第二部分和最大的部分创建一个指令(我认为我可以为两者使用一个指令,但随着我的学习,我认为最好将它们分成两部分现在并稍后结合)。
当我点击 ng-attr 属性时会出现问题,例如启用工具提示:
ng-attr-tooltip-enable="{{$route.current.details[0].tab == 'discovery' && $route.current.details.length == 2 ? 'true' : 'false'}}"
我无法将“discovery”替换为“{{tabName}},因为整个内容都包含在 {{}} 中,如果我尝试这样做,我会得到:
Lexer Error: Unterminated quote at columns 33-43 ['{{tabName] in expression [(route.current.details[0].tab == '{{tabName]
我尝试删除外部的 {{}},但这不起作用。
从这里我认为最好的选择是在指令本身中执行此逻辑,但我发现我的问题现在是访问导航 Controller 上设置的 $scope.$route 。这是menu_toggle 的指令(与parentTab 非常相似):
export class menuToggle {
public static Factory() {
return {
restrict: 'E',
scope: {
route: '=',
tabName: '@',
},
link: function(scope, element, attrs) {
console.log(scope.route);
},
templateUrl: '/app/templates/navigation/menuToggle.html'
}
}
}
console.log 会导致一个包含应用程序中所有路由的路由对象被注销。它无法访问当前路由或每个路由上设置的详细信息数组,例如
.when('/Discovery', <any> {
controller: 'DiscoveryController',
details: [
{path: '/Discovery', tab: 'discovery'}
]
})
如果我可以从导航 Controller 访问 $scope 和/或 $route ,我想我从那里就可以了,但我似乎根本无法访问。我在网上阅读了各种内容并用谷歌搜索到了地球的尽头。
我希望有人可以提供帮助...谢谢,我也很感激这是一个很长的问题,所以我希望它能理解我正在尝试做的事情,感谢您的阅读,如果您已经做到了到目前为止。 (我正在一个 2 人团队中从事这个项目,如果你想知道先进的东西可能来自哪里,那就是另一个人 - 我仍在学习并掌握所有这些东西。)
更新: 我做了一个测试指令,它只是一个属性,
export class testRel {
public static Factory() {
return {
restrict: 'A',
template: '{{$route.current.details[0].tab}}',
link: function(scope, element, attrs) {
// console.log(scope.$route);
// console.log(scope.$route.current.details[0].tab);
}
}
}
}
模板部分 {{$route.current.details[0].tab}} 可以工作并显示页面上的当前选项卡,但我再次无法在我认为需要的链接中访问它做逻辑?
如果我在链接函数中console.log路由,我会得到一个注销的路由对象,其中有一个“当前”对象以及我需要的相关信息,当我尝试console.log它。
更新 2: 我现在已经成功通过在 console.log 中使用 setTimeout 函数来访问 $route.current - 下一步是尝试将此指令中的逻辑与创建实际模板的指令一起使用。
我会不断更新,谁知道我最终可能会得到答案......但请随时提供您的 2 美分:)
最佳答案
好吧,我最终成功了 - 也许有一天这可能对其他人有帮助。
我发现我可以在 testRel 指令上创建一个 Controller ,并在指令链接函数中访问该 Controller 。
因此,在 testRel 的 Controller 中,我有一个简单的函数,可以设置我想要的变量,例如
controller: function() {
this.tab;
this.setTab = function(tab) {
this.tab = tab;
}
}
然后,在我的链接函数中,我可以像这样访问 setTab 函数:
link: function($scope, element, attrs, testRelCtrl) {
setTimeout(function() {
menuToggleLogicCtrl.setTab('tabname here');
}, 0);
}
下一步是在我的parentTab指令中使用这些数据。 我使用了指令的“require”属性,它允许您将两个指令链接在一起(或多个指令,如菊花链)并访问其数据。
我需要该指令,然后在链接函数内链接数据。
return {
require: '^testRel',
scope: {
....
},
link: function(scope, element, attrs, testRelCtrl) {
scope.testRelCtrl = testRelCtrl;
}
}
有了这一切,我可以设置 bool 值和变量等,然后使用
在指令模板中访问它们{{ testRelCtrl.whateverIWant }}
顺便说一句,我将 testRel 指令设置为一个属性,将 ParentTab 指令设置为一个元素,现在无论我想在哪里使用它,我都必须拥有
<parent-tab test-rel></parent-tab>
以及我传入的、在指令范围内设置的数据的任何属性。
关于javascript - 指令中的访问 Controller $scope 和 $route,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/35631044/