AngularJS - templateUrl oluştururken $ routeParams nasıl kullanılır?


96

Uygulamamız 2 seviyeli navigasyona sahiptir. AngularJS'yi $routeProviderdinamik olarak bir <ng-view />. Şu çizgide bir şeyler yapmayı düşünüyordum:

angular.module('myApp', []).
config(['$routeProvider', function($routeProvider) {
    $routeProvider.when('/:primaryNav/:secondaryNav', {
        templateUrl: 'resources/angular/templates/nav/'+<<primaryNavHere>>+'/'+<<secondaryNavHere>>+'.html'
    });
}]);

Sadece içindeki parçaları nasıl dolduracağımı bilmiyorum <<>>. PrimaryNav ve secondNav'ın $ routeParams'a bağlandığını biliyorum, ancak şablonu dinamik olarak sunmak için $ routeParams'a buradan nasıl erişebilirim?

Yanıtlar:


84

$routeParamsHizmeti enjekte etmenin ve kullanmanın bir yolunu bulamadım (ki bunun daha iyi bir çözüm olacağını düşünürdüm) işe yarayacağını düşünerek şunu denedim:

angular.module('myApp', []).
    config(function ($routeProvider, $routeParams) {
        $routeProvider.when('/:primaryNav/:secondaryNav', {
            templateUrl: 'resources/angular/templates/nav/'+$routeParams.primaryNav+'/'+$routeParams.secondaryNav+'.html'
        });
    });

Bu hatayı veren:

Bilinmeyen sağlayıcı: myApp'tan $ routeParams

Bunun gibi bir şey mümkün değilse templateUrl, yalnızca sahip olan kısmi bir HTML dosyasına işaret edecek şekilde değiştirebilir ng-includeve ardından aşağıdaki gibi URL'yi denetleyicinizde ayarlayabilirsiniz $routeParam:

angular.module('myApp', []).
    config(function ($routeProvider) {
        $routeProvider.when('/:primaryNav/:secondaryNav', {
            templateUrl: 'resources/angular/templates/nav/urlRouter.html',
            controller: 'RouteController'
        });
    });

function RouteController($scope, $routeParams) {
        $scope.templateUrl = 'resources/angular/templates/nav/'+$routeParams.primaryNav+'/'+$routeParams.secondaryNav+'.html';
    }

Bununla senin gibi urlRouter.html

<div ng-include src="templateUrl"></div>

7
Birincisinin çalışmama nedeni belgelenen groups.google.com/forum/?fromgroups=#!topic/angular/qNi5lqm-Ps8'dir . Enjeksiyon hedefleri config()gibi gerçek hizmet örnekleri değil, yalnızca sağlayıcılara geçildiğinden $routePrams.
amine

18
Aslında "tek satırlık html dosyasını" oluşturmanız gerekmez - sadece "templateUrl" yerine "template:" anahtarını kullanın ve ona html one-liner ;-) içeren bir dize sağlayın ;-)
DominikGuzei

1
Onun templateyerine kullanamaz templateUrlmısın?
kaiser

1
Bu gerçekten işe yarayacak, ancak seçilen her şablon için bir denetleyici uygulamaya ne dersiniz? Bu yöntemi kullanmak size yalnızca bir "ana" denetleyici bırakacaktır: "RouteController"
Yaniv Efraim

9
Eğer ayarlarsanız templatebir işleve, sen geçebilir $routeParamsbu işlevin içine: $routeProvider.when('/:pNav/:sNav', { template: fn($routeParams) { return $routeParams.pNav + '/' + $routeParams.sNav + '.html' } });. Ancak, bir denetleyiciyi bu şekilde dinamik olarak tanımlayamazsınız :(
jacob

131

Bu çok yararlı özellik artık AngularJS'nin 1.1.2 sürümünden itibaren mevcuttur. Kararsız olduğu düşünülüyor ama kullandım (1.1.3) ve iyi çalışıyor.

Temel olarak, bir templateUrl dizesi oluşturmak için bir işlev kullanabilirsiniz. İşleve, templateUrl dizesini oluşturmak ve döndürmek için kullanabileceğiniz yönlendirme parametreleri iletilir.

var app = angular.module('app',[]);

app.config(
    function($routeProvider) {
        $routeProvider.
            when('/', {templateUrl:'/home'}).
            when('/users/:user_id', 
                {   
                    controller:UserView, 
                    templateUrl: function(params){ return '/users/view/' + params.user_id; }
                }
            ).
            otherwise({redirectTo:'/'});
    }
);

Çekme talebi için https://github.com/lrlopez'e çok teşekkürler .

https://github.com/angular/angular.js/pull/1524


5
Bu artık 1.2'de tamamen destekleniyor ve muhtemelen en iyi yoldur: docs.angularjs.org/api/ngRoute/provider/$routeProvider
Stu

parametrelere dayalı bir dinamik denetleyiciye ne dersiniz?
Meşe

Lütfen, lütfen (lütfen!) Bunun mümkün olduğunu söyle bana controllers...?
Cody

bu durumda denetleyiciye şablondan nasıl erişirsiniz ($ routeProvider tarafından sağlanır)? Normalde, denetleyici ng-controller = "myController" yönergesine bağlıysa, myController'a myCtrl olarak başvurabilirsiniz. Bu durumda myCtrl'i nasıl tanımlarım?
FlavourScape

@FlavorScape Ben de bu sorunu yaşadım - çözüm $ routeProvider.when ("/ foo", {controller: "FooController", controllerAs: "foo", templateUrl: "foo.html"});
Erin Drummond

18

templateUrl, oluşturulan URL'yi döndüren işlev olarak kullanılabilir. RouteParams'ı alan argüman geçerek url'yi işleyebiliriz.

Örneğe bakın.

.when('/:screenName/list',{
    templateUrl: function(params){
         return params.screenName +'/listUI'
    }
})

Umarım bu yardımcı olur.


7

Pekala, sanırım anladım ...

Önce küçük bir arka plan: Buna ihtiyacımın nedeni, Node Express'in üzerine Angular'ı yapıştırmak ve Jade'in benim için parçalarımı işlemesini sağlamaktı.

İşte yapman gereken şey ... (önce bira iç ve 20 saatten fazla harcama !!!) ...

Modülünüzü kurduğunuzda, $routeProviderglobal olarak kaydedin :

// app.js:
var routeProvider
    , app = angular.module('Isomorph', ['ngResource']).config(function($routeProvider){

        routeProvider = $routeProvider;
        $routeProvider
            .when('/', {templateUrl: '/login', controller: 'AppCtrl'})
            .when('/home', {templateUrl: '/', controller: 'AppCtrl'})
            .when('/login', {templateUrl: '/login', controller: 'AppCtrl'})
            .when('/SAMPLE', {templateUrl: '/SAMPLE', controller: 'SAMPLECtrl'})
            .when('/map', {templateUrl: '/map', controller: 'MapCtrl'})
            .when('/chat', {templateUrl: '/chat', controller: 'ChatCtrl'})
            .when('/blog', {templateUrl: '/blog', controller: 'BlogCtrl'})
            .when('/files', {templateUrl: '/files', controller: 'FilesCtrl'})
            .when('/tasks', {templateUrl: '/tasks', controller: 'TasksCtrl'})
            .when('/tasks/new', {templateUrl: '/tasks/new', controller: 'NewTaskCtrl'})
            .when('/tasks/:id', {templateUrl: '/tasks', controller: 'ViewTaskCtrl'})
            .when('/tasks/:id/edit', {templateUrl: '/tasks', controller: 'EditTaskCtrl'})
            .when('/tasks/:id/delete', {templateUrl: '/tasks', controller: 'DeleteTaskCtrl'})
        .otherwise({redirectTo: '/login'});

});

// ctrls.js
...
app.controller('EditTaskCtrl', function($scope, $routeParams, $location, $http){

    var idParam = $routeParams.id;
    routeProvider.when('/tasks/:id/edit/', {templateUrl: '/tasks/' + idParam + '/edit'});
    $location.path('/tasks/' + idParam + '/edit/');

});
...

Bu, ihtiyaç duyulandan daha fazla bilgi olabilir ...

  • Temel olarak, Modülünüzün varlığını $routeProviderküresel olarak depolamak isteyeceksiniz , örneğin routeProviderDenetleyicileriniz tarafından erişilebilmesi için.

  • Sonra sadece routeProviderYENİ bir rota kullanabilir ve oluşturabilirsiniz ('Bir rotayı SIFIRLAYINIZ' / 'Yeniden söz veremezsiniz; yeni bir tane oluşturmalısınız), sadece anlamsal olması için sonuna bir eğik çizgi (/) ekledim İlk olarak.

  • Ardından (Denetleyicinizin içinde), templateUrlvurmak istediğiniz görünüme ayarlayın .

  • Sonsuz bir istek döngüsü elde etmek controlleriçin .when()nesnenin özelliğini çıkarın .

  • Ve son olarak (hala Denetleyicinin içinde), $location.path()az önce oluşturulan rotaya yeniden yönlendirmek için kullanın .

Bir Angular uygulamasını bir Express uygulamasına nasıl yapıştıracağınızla ilgileniyorsanız, depomu buradan çatallayabilirsiniz: https://github.com/cScarlson/isomorph .

Ve bu yöntem ayrıca, WebSockets kullanarak HTML'nizi veritabanınıza bağlamak istemeniz durumunda AngularJS İki Yönlü Veri Bağlamalarını korumanıza olanak tanır: aksi takdirde, bu yöntem olmadan, Açısal veri bağlamalarınız yalnızca çıktı alır {{model.param}}.

Bunu şu anda klonlarsanız, çalıştırmak için makinenizde mongoDB'ye ihtiyacınız olacak.

Umarım bu, sorunu çözer!

Cody

Banyo suyunuzu içmeyin.


3

Yönlendirici: -

...
.when('/enquiry/:page', {
    template: '<div ng-include src="templateUrl" onload="onLoad()"></div>',
    controller: 'enquiryCtrl'
})
...

Denetleyici: -

...
// template onload event
$scope.onLoad = function() {
    console.log('onLoad()');
    f_tcalInit();  // or other onload stuff
}

// initialize
$scope.templateUrl = 'ci_index.php/adminctrl/enquiry/'+$routeParams.page;
...

$ RouteParams'ın yönlendiricinin içinde görünmemesinin angularjs'de bir zayıflık olduğuna inanıyorum. Küçük bir geliştirme, uygulama sırasında dünya çapında bir fark yaratacaktır.


3

Açısal çatalıma bunun için destek ekledim. Belirtmenizi sağlar

$routeProvider
    .when('/:some/:param/:filled/:url', {
          templateUrl:'/:some/:param/:filled/template.ng.html'
     });

https://github.com/jamie-pate/angular.js/commit/dc9be174af2f6e8d55b798209dfb9235f390b934

açısal yönünün tersi olduğu için bunun anlaşılacağından emin değilim, ama benim için yararlı


Kesinlikle doğru! Havent onu henüz kullandı ama GERÇEKTEN ona ihtiyacım var. Dikkat etmem gereken başka uyarılar var mı? Ayrıca, Angular'ın uygulanmasıyla ilgili bir haber var mı? - CDN kullanmayı seviyorum.
Cody

Hiçbir fikrim yok, evrakları asla imzalatmadım, bu bir çıkmaz, ama değişikliği alabilirsin ve kendi başına çekmeye çalışabilirsin daha fazla angularjs peşinde)
Jamie Pate

Tamam, bilgi ve konuya katkınız için teşekkürler - Bir dakika içinde konuyu inceleyip oynayacağım.
Cody

1
//module dependent on ngRoute  
 var app=angular.module("myApp",['ngRoute']);
    //spa-Route Config file
    app.config(function($routeProvider,$locationProvider){
          $locationProvider.hashPrefix('');
          $routeProvider
            .when('/',{template:'HOME'})
            .when('/about/:paramOne/:paramTwo',{template:'ABOUT',controller:'aboutCtrl'})
            .otherwise({template:'Not Found'});
    }
   //aboutUs controller 
    app.controller('aboutCtrl',function($routeParams){
          $scope.paramOnePrint=$routeParams.paramOne;
          $scope.paramTwoPrint=$routeParams.paramTwo;
    });

index.html'de

<a ng-href="#/about/firstParam/secondParam">About</a>

firstParam ve secondParam ihtiyaçlarınıza göre herhangi bir şey olabilir.


0

Benzer bir sorun yaşıyordum ve $stateParamsyerine kullandımrouteParam

Sitemizi kullandığınızda şunları okuyup anladığınızı kabul etmiş olursunuz: Çerez Politikası ve Gizlilik Politikası.
Licensed under cc by-sa 3.0 with attribution required.