Ember.js 如何使用路由器基础设施标记活动菜单项

Ember.js 如何使用路由器基础设施标记活动菜单项,ember.js,ember-old-router,Ember.js,Ember Old Router,我正在尝试创建导航选项卡(取自): 活动选项卡标记为class=“active” 这里有一个很好的静态导航栏和路由器/出口功能的例子,但是 我不明白如何创建动态导航栏/菜单/选项卡视图 据我所知,可以在每个菜单项中使用类绑定: classNameBindings:['isActive:active'] 但是,在哪里切换isActive属性是正确的呢?不确定它是否是非常动态的,但请尝试在以下位置查看解决方案: 主要目的是检查应用程序的状态 JavaScript: function s

我正在尝试创建导航选项卡(取自):

活动选项卡标记为
class=“active”

这里有一个很好的静态导航栏和路由器/出口功能的例子,但是 我不明白如何创建动态导航栏/菜单/选项卡视图

据我所知,可以在每个菜单项中使用类绑定:

classNameBindings:['isActive:active']

但是,在哪里切换isActive属性是正确的呢?

不确定它是否是非常动态的,但请尝试在以下位置查看解决方案: 主要目的是检查应用程序的状态

JavaScript:

function stateFlag(name) {
  return Ember.computed(function() {
    var state = App.router.currentState;
    while(state) {
      if(state.name === name) return true;
      state = state.get('parentState');
    }
    return false;
  }).property('App.router.currentState');
}

ApplicationController: Ember.Controller.extend({
    isHome: stateFlag('home'),
    isSections: stateFlag('sections'),
    isItems: stateFlag('items')
  })
<li class="home" {{bindAttr class="isHome:active"}}>
</li>
<li class="sections" {{bindAttr class="isSections:active"}}>
</li>
<li class="items" {{bindAttr class="isItems:active"}}>
</li>
把手:

function stateFlag(name) {
  return Ember.computed(function() {
    var state = App.router.currentState;
    while(state) {
      if(state.name === name) return true;
      state = state.get('parentState');
    }
    return false;
  }).property('App.router.currentState');
}

ApplicationController: Ember.Controller.extend({
    isHome: stateFlag('home'),
    isSections: stateFlag('sections'),
    isItems: stateFlag('items')
  })
<li class="home" {{bindAttr class="isHome:active"}}>
</li>
<li class="sections" {{bindAttr class="isSections:active"}}>
</li>
<li class="items" {{bindAttr class="isItems:active"}}>
</li>
  • 更新:
    pangratz的解决方案看起来更漂亮

    如果您使用的是Ember>=1.11,那么下面是正确的答案


    我将创建一个
    导航视图
    ,请参见:

    把手

    
    
      {{{#view view.NavItemView item=“home”}
      repository,它将引导的这些和更多功能包装在Ember.js中

      您还可以将isActive方法更改为如下内容:

      isActive: function() {
          return App.getPath('router.currentState.path') === "root.firms";
      }.property("App.router.currentState"),
      
      {{#active-link}}
        {{link-to "Index" "index"}}
      {{/active-link}}
      


      迟早你会想要改变你的状态的命名或者你必须通过代码和视图来完成的任何事情,同时添加一个函数来转换到每一条路径似乎是不可取的。 我的方法更加程序化和模块化:

      # Parent View-Tamplate, holding the navbar DOM elements
      App.NavView = Ember.View.extend( 
        controller: App.NavArrayController
        templateName: "ember-nav"
      )
      # We push NavItems into this array
      App.NavArrayController = Ember.ArrayController.create(
        content: Ember.A([])
      )
      # NavItem has two settable properties and 
      # an programmatic active state depending on the router
      App.NavItem = Ember.Object.extend(
        title: ''
        goto: null    # <=this is the name of the state we want to go to!
        active: (->
          if App.router.currentState.name == @.get "goto"
            true
          else
            false
        ).property('App.router.currentState.name').cacheable()
      )
      # the actual NavElement which gets the class="active" if the 
      # property "active" is true, plus a on-click binding to
      # make the Router transition to this state
      App.NavItemView = Ember.View.extend(
       tagName: "li"
        classNameBindings: ["active"]
        click: ->
          App.router.transitionTo(@get('goto'))
          false
      )
      
      余烬1.11+:

      {{#link-to "dashboard" tagName="li"}}
        <a href="{{view.href}}">Dashboard</a>
      {{/link-to}}
      

      以下是一个完整的工作解决方案:

      视图:

      模板:

      <ul>
        {{#each item in controller}}
        {{#view App.NavView}}
        {{#linkTo "item" item tagName="li"}}
            <a {{bindAttr href="view.href"}}>
              {{ item.name }}
            </a>
        {{/linkTo}}
        {{/view}}
        {{/each}}
      </ul>
      
        {{{#控制器中的每个项目} {{{#view App.NavView} {{{#链接到“项”项标记名=“li”} {{/linkTo} {{/view} {{/每个}}
      把手

      <ul class="nav">
          <li>{{#linkTo "index"}}Index{{/linkTo}}</li>
          <li>{{#linkTo "about"}}About{{/linkTo}}</li>
      </ul>
      
      它将根据路由自动添加活动类。
      注意:它是使用ember-1.0.0-pre.4.js测试的,我知道这个问题很老了,但是如果您将ember.js升级到RC3,您可以使用标记名属性,如:

      {{#link-to messages tagName="li"}}Messages{{/link-to}}
      

      以下是API-

      上述一些建议对于twitter引导案例仍然有效。你也可以试试这样的东西

      {{#link-to 'dashboard' tagName='li'}} 
        {{#link-to 'dashboard'}}Link Title{{/link-to}}
      {{/link-to}}
      
    • li
      标记名的
      链接将活动类应用于li
    • 指向
    的内部
    链接将是一个
    锚定
    元素,当右键单击时,它将为您提供在新选项卡中打开的
    功能
    
    最近,一个Ember cli插件就可以实现这一点。它被称为

    安装:
    ember安装ember cli活动链接包装器

    您可以这样使用它:

    isActive: function() {
        return App.getPath('router.currentState.path') === "root.firms";
    }.property("App.router.currentState"),
    
    {{#active-link}}
      {{link-to "Index" "index"}}
    {{/active-link}}
    
    其结果是:

    <li class='active'>
        <a href="/" class='active'>Index</a>
    </li>
    

  • 拜朱姆的上述回答基本正确,但在最新版本的余烬中,“绑定属性”被弃用。以下是新的写作方式:

    {{#link-to "dashboard" tagName="li"}}
        <a href="{{view.href}}">Dashboard</a>
    {{/link-to}}
    
    {{#链接到“dashboard”tagName=“li”}
    {{/链接到}
    

    正如你所看到的,它甚至更简单,有点像魔术。

    我知道这是一篇老文章,但这里是《灰烬2.4.0》的更新

    用于创建可以编写的链接

    {{#link-to 'photoGallery'}}
      Great Hamster Photos
    {{/link-to}}
    

    当当前路由与链接的路由匹配时,Ember将自动将class设置为active(在本例中为
    photoGallery

    如果您还想控制其他路由上的“活动”类,可以通过设置
    current when
    属性来实现

    {{#link-to 'photoGallery' current-when='photoGallery photoPreview'}}
      Great Hamster Photos
    {{/link-to}}
    
    此链接在
    photoGallery
    photoPreview
    路径上都有
    active

    从v0.8.0开始,支持导航,包括正确处理激活状态。没有任何指向/tagName的链接的黑客:

    {{#bs-nav type="pills"}}
       {{#bs-nav-item}}
          {{#link-to "foo"}}Foo{{/link-to}}
       {{/bs-nav-item}}
       {{#bs-nav-item}}
         {{#link-to "bar"}}Bar{{/link-to}}
       {{/bs-nav-item}}
     {{/bs-nav}}
    

    请参见

    此处提出的许多解决方案不适用于任何最新的Ember版本(例如,视图被弃用)。此外,仅使用指向
    帮助程序的
    链接并不能解决问题,因为bootstrap希望
    活动的
    类出现在
  • 上,而不是
    
    插件为这个特殊用例提供了一个组件:

    <ul class="nav nav-tabs">
      {{#active-link}}
        {{#link-to "foo"}}Foo{{/link-to}}
      {{/active-link}}
      {{#active-link}}
        {{#link-to "bar"}}Bar{{/link-to}}
      {{/active-link}}
    </ul>
    
    取自

    链接到黑客 有点黑,但无需任何附加插件即可工作:

    <ul class="nav nav-tabs">
      {{#link-to "foo" tagName="li"}} 
        {{#link-to "foo"}}Foo{{/link-to}}
      {{/link-to}}
      {{#link-to "bar" tagName="li"}} 
        {{#link-to "bar"}}Bar{{/link-to}}
      {{/link-to}}
    </ul>
    
      {{#链接到“foo”标记名=“li”} {{{链接到“foo”}foo{{/链接到} {{/链接到} {{#链接到“bar”标记名=“li”} {{{#链接到“bar”}bar{{{/链接到}} {{/链接到}

    正如其他人所说,使用
    {{{link to}}
    链接到现有的
    路由
    ,当该路由是当前URL时,
    {{{link to}}
    将自动将
    活动的
    添加到其CSS类中


    请参见

    FYI:在新路由器中,
    {{linkTo}
    自动提供此行为--您能否更新您的答案以反映新路由器中的更改?退房。非常感谢@pangratz。你是一个摇滚明星。如果你想在不改变url的情况下改变标签呢?(同时仍然使用路由器访问选项卡,例如
    /wizards/:wizard_id/edit
    ,向导中有3个步骤需要编辑,您不想更改url。)FWIW,我更新了pangratz的示例,如@bazzel所示:不幸的是,这不再起作用。这需要成为公认的答案。我只花了10分钟试图在
  • 标签上获得一个
    bindAttr
    ,以按名称引用view.href,直到我发现这一点,并意识到我完全是反向的。这绝对是最简单的方法。这绝对是我在小组中找到的最佳答案。这绝对是最简单的方法!应该是可接受的答案。您将希望在链接元素上显式地将光标样式设置为指针:
    a{cursor:pointer;}
    请看这是否有效,我遇到的唯一问题是
    {{#bs-nav type="pills"}}
       {{#bs-nav-item}}
          {{#link-to "foo"}}Foo{{/link-to}}
       {{/bs-nav-item}}
       {{#bs-nav-item}}
         {{#link-to "bar"}}Bar{{/link-to}}
       {{/bs-nav-item}}
     {{/bs-nav}}
    
    <ul class="nav nav-tabs">
      {{#active-link}}
        {{#link-to "foo"}}Foo{{/link-to}}
      {{/active-link}}
      {{#active-link}}
        {{#link-to "bar"}}Bar{{/link-to}}
      {{/active-link}}
    </ul>
    
    {{#bs-nav type="tabs"}}
       {{#bs-nav-item}}
          {{#link-to "foo"}}Foo{{/link-to}}
       {{/bs-nav-item}}
       {{#bs-nav-item}}
          {{#link-to "bar"}}Bar{{/link-to}}
       {{/bs-nav-item}}
     {{/bs-nav}}
    
    <ul class="nav nav-tabs">
      {{#link-to "foo" tagName="li"}} 
        {{#link-to "foo"}}Foo{{/link-to}}
      {{/link-to}}
      {{#link-to "bar" tagName="li"}} 
        {{#link-to "bar"}}Bar{{/link-to}}
      {{/link-to}}
    </ul>