Hey all I'm running into what I thought would be a common routing problem, but I'm unable to figure out a solution. Basically my page has two states, basic and advanced, and I want the URL patterns to be the same for both states but only load the template for the current state at the time (which is transitioned to from within a controller)
config(function ($stateProvider) {
$stateProvider.state('basic', {
url: '/:post',
templateUrl: function (stateParams) {
return 'post-' + stateParams.post + '-tmpl.html';
}
});
$stateProvider.state('advanced', {
url: '/:post',
templateUrl: function (stateParams) {
return 'post-' + stateParams.post + '-advanced-tmpl.html';
}
});
})
controller('myCtrl', function ($state) {
//
// In this case, I would expect only the template from
// the advanced state to load, but both templates are trying
// to load.
$state.transitionTo('advanced', {post: 2});
}
I assume that navigating to the matched pattern loads the given state which is why when it matches, both templates attempt to load. Is there some way to accomplish the same url pattern but with different templates based only on the current state?
Assuming that you cannot have two states with the same URL, why don't you go along and merge the two states into one? Ui-router already allows you to have a custom function to return the template. You just need to add another, hidden custom parameter (let's call it advanced
) to the state declaration:
$stateProvider.state('basicOrAdvanced', {
url: '/:post',
templateUrl: function (stateParams) {
if (stateParams.advanced) {
return 'post-' + stateParams.post + '-advanced-tmpl.html';
} else {
return 'post-' + stateParams.post + '-tmpl.html';
}
},
params: {
advanced: False
}
});
And then you call it with:
$state.transitionTo('basicOrAdvanced', {post: 2, advanced: True})
For another possible solution with nested states and a common controller, see issues #217 and #1096 on ui-router's github page.
The solution presented there creates a third state whose controller does the dispatching work, whereas the two states you want to land in (basic
and advanced
) have empty URLs:
$stateProvider.state('basicOrAdvanced', {
url: '/:post',
controller: function($state, $stateParams) {
if($stateParams.advanced) {
$state.go('advanced', {post: $stateParams.post});
} else {
$state.go('basic', {post: $stateParams.post});
}
},
params: {
advanced: False
}
}
This solution is better if your states differ in more aspects than the simple templateUrl
(e.g. if they have completely separate controllers, etc.)
Also see another question on StackOverflow about a similar issue.
This is very useful in AngularJS,
You Can Specify Dynamic Route for Multiple State with same url pattern
My Code is As follow that can be useful for you,
Module Intialization,
var app = angular.module("koops_app", ['ui.router','ui.bootstrap']); //here you have to define all your required module for your project that you should inject...
Further,
app.config(function ($locationProvider, $httpProvider, $stateProvider, $urlRouterProvider, $wampProvider) {
// When No Routing i.e Default Routing
$urlRouterProvider.when('', '/dashboard');
// 404
$stateProvider.state("404", {
url: "/404",
templateUrl: 'template/404.html',
});
// When Only One Argument i.e. Only Module Name
$stateProvider.state("default", {
url: "/:section",
templateUrl: 'views/View-to-be-load.html', //can use $stateParams.section for dynamic
reload: true,
resolve: {
loadController: ['$q', '$stateParams', '$state',
function ($q, $stateParams, $state) {
var deferred = $q.defer();
deferred.resolve();
return deferred.promise;
}
]
},
controllerProvider: function ($stateParams) {
return 'controllerName';
}
});
// When Two Argument i.e. Module/Controller
$stateProvider.state("default/title", {
url: "/:section/:title",
templateUrl: 'views/View-to-be-load.html', //can use $stateParams.section for dynamic
reload: true,
resolve: {
loadController: ['$q', '$stateParams', '$state',
function ($q, $stateParams, $state) {
var deferred = $q.defer();
deferred.resolve();
return deferred.promise;
}
]
},
controllerProvider: function ($stateParams) {
return 'controllerName';
}
});
// When Three Arguments i.e. Module/Controller/id
$stateProvider.state("default/title/id", {
url: "/:section/:title/:id",
templateUrl: 'views/View-to-be-load.html', //can use $stateParams.section for dynamic
reload: true,
resolve: {
loadController: ['$q', '$stateParams', '$state',
function ($q, $stateParams, $state) {
var deferred = $q.defer();
deferred.resolve();
return deferred.promise;
}
]
},
controllerProvider: function ($stateParams) {
return 'controllerName';
}
});
// Otherwise
$urlRouterProvider.otherwise("/404");
May be this is helpful for you... Enjoy...
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With