AngularJS ui-router - 两个相同的路由组

AngularJS ui-router - two identical route groups

我有两个路由组,'anime' 和 'manga'。 URL 是 /anime/ 或 /manga/,但它们共享完全相同的控制器和模板 (唯一不同的是每个模板使用的配色方案,但这些是在检查正在查看的特定项目是动漫还是漫画的过滤器):

动漫规定定义:

.state('anime', {
    url: "/anime?genres&tags&year&season&page&perpage&sortBy&order",
    templateUrl: "views/titles-index.html",
    controller: 'TitleIndexController',
    data: {
        type: 'anime'
    },
    ncyBreadcrumb: {
        label: 'Anime'
    }
}).state('anime-detail', {
    url: "/anime/:id/:slug",
    controller: 'TitleDetailController',
    templateUrl: "views/titles-detail.html",
    ncyBreadcrumb: {
        parent: 'anime-index',
        label: '{{item.title_main}}'
    }
}).state('anime-detail.anime-reviews', {
    url: '/reviews',
    controller: 'TitleReviewsController',
    templateUrl: 'views/titles-reviews.html',
    ncyBreadcrumb: {
        label: 'Reviews'
    }

漫画状态定义:

}).state('manga', {
    url: "/manga?genres&tags&year&season&page&perpage&sortBy&order",
    templateUrl: "views/titles-index.html",
    controller: 'TitleIndexController',
    data: {
        type: 'manga'
    },
    ncyBreadcrumb: {
        label: 'Manga'
    }
}).state('manga-detail', {
    url: "/manga/:id/:slug",
    controller: 'TitleDetailController',
    templateUrl: "views/titles-detail.html",
    ncyBreadcrumb: {
        parent: 'manga-index',
        label: '{{item.title_main}}'
    }
}).state('manga-detail.manga-reviews', {
    url: '/reviews',
    controller: 'TitleReviewsController',
    templateUrl: 'views/titles-reviews.html',
    ncyBreadcrumb: {
        label: 'Reviews'
    }
})

如你所见,这里面已经有很多重复了,我一点也不喜欢。随着我不断添加新路线,重复只会增加(你已经可以看到漫画评论和动漫评论,还会有更多).

另一个问题是我必须使用长名称,例如 manga-detailanime-detail 而不是普通的 'detail'.

我想过实现一个更简单的样式,比如 /browse//browse/?view=anime 但这看起来更丑陋,我也会遇到 ncyBreadcrumbs 的问题,因为索引不是细节的直接父级。

拥有 /anime//manga/ 网址也更加用户友好,但如果有人有更好的主意,我很乐意切换,只要它摆脱重复.

我必须将其用于 ui-sref:

ui-sref="{{item.title_type}}-detail({id: item.id, slug: slugify(item.title_main)})"

几乎不起作用,对于儿童来说根本不起作用。

我的路由器结构一直让我头疼,老实说,我无法解决这个问题,所以我有点卡住了现在,将不胜感激任何帮助。

a working plunker

此处的解决方案出奇地简单,而且您几乎已经找到了。我们用参数替换 'anime' or/and 'manga' - 例如:oneForBoth

.state('oneForBoth', {
    url: "/:oneForBoth?genres&tags&year&season&page&perpage&sortBy&order",
    templateUrl: "views/titles-index.html",
    controller: 'TitleIndexController',
    data: {
      // should be $stateParams.oneForBoth
      //type: 'anime'
    },
    ncyBreadcrumb: {
      label: '{{$stateParams.oneForBoth}}'
    }
}).state('oneForBoth-detail', {
    url: "/:oneForBoth/:id/:slug",
    controller: 'TitleDetailController',
    templateUrl: "views/titles-detail.html",
    ncyBreadcrumb: {
      parent: 'oneForBoth',
      label: '{{item.title_main}}'
    }
}).state('oneForBoth-detail.oneForBoth-reviews', {
    url: '/reviews',
    controller: 'TitleReviewsController',
    templateUrl: 'views/titles-reviews.html',
    ncyBreadcrumb: {
      label: 'Reviews'
    }

而现在,从用户的角度(也从'ncy-angular-breadcrumb'的角度来看)

<a href="#/manga">
<a href="#/manga/theId/theSlug">
<a href="#/manga/theId/theSlug/reviews">

<a href="#/anime">
<a href="#/anime/theId/theSlug">
<a href="#/anime/theId/theSlug/reviews">

检查一下here

正如 指出的那样,这将支持 'oneForBoth' 的任何值。所以我们可以像这里讨论的那样设置一些限制:

Matching url with array list of words in AngularJS ui-router

这里是the updated plunker

这是我们的扩展代码,只支持动漫和漫画

.state('oneForBoth', {
    url: "/{oneForBoth:(?:anime|manga)}?genres&tags&year&season&page&perpage&sortBy&order",
    templateUrl: "views/titles-index.html",
    controller: 'TitleIndexController',
    data: {
      // should be $stateParams.oneForBoth
      //type: 'anime'
    },
    ncyBreadcrumb: {
      label: '{{$stateParams.oneForBoth}}'
    }

其中最重要的部分是对 url 的限制:

url: "/{oneForBoth:(?:anime|manga)}?

检查here