如何从链接到父/子视图/控制器的路由动态构建导航菜单 [英] How to dynamically build navigation menu from routes linking to parent/child views/controllers

查看:12
本文介绍了如何从链接到父/子视图/控制器的路由动态构建导航菜单的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

这个问题是我原来问题的后续问题从主导航菜单直接链接到父+子视图/控制器

接受的答案很好,但后来当我动态添加第二个childRoute"时,我注意到了一个问题.为了动态构建我的导航,我必须添加具有相同路线"属性的多条路线.(请参阅下面示例代码中的 app.js).唯一的区别是标题"和设置"属性.

configureRouter(config, router){config.title = 'Aurelia';config.map([{ route: 'shared-parent', moduleId: './shared-parent', settings: { childRoute: 'child-a' }, nav: true, title: 'Shared Parent - child-a' },{ route: 'shared-parent', moduleId: './shared-parent', settings: { childRoute: 'child-b' }, nav: true, title: 'Shared Parent - child-b' },...]);this.router = 路由器;}

我在视图中使用的设置属性:

<a if.bind="row.settings.childRoute" href.bind="row.href + '/' + row.settings.childRoute">${row.title}</>

我知道它不漂亮,但它确实导航到了正确的子路径.问题是始终是 2 条具有重复路由"属性的路由中的最后一条标记为活动的.

我添加 settings: {childRoute: 'child-a/b' } 而不是给它们像 route: 'shared-parent/child 这样独特的路由"属性的原因-a'route: 'shared-parent/child-b' 是 url 实际上会匹配 shared-parent/child-a/child-ashared-parent/child-b/child-b 因为我们首先链接到共享父级.

这个 live runnable gist 应该清楚地显示问题(child-a route 永远不会激活):https://gist.run/?id=95469a9cb3a762d79da31e0b64248036

附言.如果您对此问题的标题有更好的想法,请随时对其进行编辑.

解决方案

因此,我在子视图模型的 Activate 生命周期挂钩中使用 EventAggregator 解决了您的问题.

https://gist.run/?id=bfb5df5e39ac0bb73e9e1cae2d2496e2

在子视图模型中,我刚刚发布了一个事件,说明子路由已更新:

activate(params, routeConfig, navigationInstruction) {让有效载荷 = navigationInstruction.parentInstruction.config.title;有效载荷 = 有效载荷.子字符串(0,有效载荷.长度 - 7);this.aggregator.publish("子路由更新", payload + "child-a");}

在 app.js 文件中,我更新了路由标题,并添加了一个 activeChild 属性.接下来,在捕获事件时更新 activeChild 属性:

构造函数(聚合器){this.aggregator = 聚合器;this.aggregator.subscribe("子路由更新了",payload => {this.activeChildRoute = 有效载荷;控制台日志(this.activeChildRoute);});}

最后,我更新了您列表项上的类表达式,以根据该活动子标志进行更新:

 
  • This question is a follow-up question for my original question Linking directly to both parent+child views/controllers from the main navigation menu

    The accepted answer is great, but later when I added a 2nd "childRoute" dynamically, I noticed a problem. In order to build my navigation dynamically I had to add the multiple routes with the same "route" attribute. (see app.js in the example code below). The only difference were the "title" and "settings" attributes.

    configureRouter(config, router){
        config.title = 'Aurelia';
        config.map([
            { route: 'shared-parent', moduleId: './shared-parent', settings: { childRoute: 'child-a' }, nav: true, title: 'Shared Parent - child-a' },
            { route: 'shared-parent', moduleId: './shared-parent', settings: { childRoute: 'child-b' }, nav: true, title: 'Shared Parent - child-b' },
            ...
        ]);
    
        this.router = router;
      }
    

    The settings attribute I used in the view for doing this:

    <a if.bind="row.settings.childRoute" href.bind="row.href + '/' + row.settings.childRoute">${row.title}</a>
    

    I know it's not pretty but it does navigate to the right child route. The problem is that it's always the last of the 2 routes with duplicate "route" attributes that is marked as active.

    The reason why I added the settings: {childRoute: 'child-a/b' } instead of giving them distinct "route" attributes like route: 'shared-parent/child-a' and route: 'shared-parent/child-b' was that the url would actually then match shared-parent/child-a/child-a and shared-parent/child-b/child-b since we're first linking to the shared-parent.

    This live runnable gist should clearly display the problem (child-a route never activating): https://gist.run/?id=95469a9cb3a762d79da31e0b64248036

    Ps. If you have a better idea of what to call the title of this question please feel free to edit it.

    解决方案

    So I took a stab at your problem using the EventAggregator in the Activate lifecycle hook in the child view models.

    https://gist.run/?id=bfb5df5e39ac0bb73e9e1cae2d2496e2

    in the child view models, I just published an event stating the child route was updated:

    activate(params, routeConfig, navigationInstruction) {
      let payload = navigationInstruction.parentInstruction.config.title;
    
      payload = payload.substring(0, payload.length - 7);
    
      this.aggregator.publish("child route updated", payload + "child-a");
    
    }
    

    In the app.js file, I updated the route titles, and added an activeChild property. Next, update the activeChild property when the event is captured:

    constructor(aggregator) { 
    
      this.aggregator = aggregator; 
    
    
    
      this.aggregator.subscribe("child route updated", payload => { 
    
        this.activeChildRoute = payload;
    
        console.log(this.activeChildRoute);
    
      });
    
    }
    

    Finally, I updated the class expression on you list item to update based on that active child Flag:

        <li repeat.for="row of router.navigation" 
            class="${row.title === activeChildRoute ? 'active' : ''}">
    

    这篇关于如何从链接到父/子视图/控制器的路由动态构建导航菜单的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

    查看全文
    登录 关闭
    扫码关注1秒登录
    发送“验证码”获取 | 15天全站免登陆