AngularJs’de Routing ve Template
Selamlar;
AngularJs ile uğraşan arkadaşların routing konusu üzerine yaşadıkları sorunlar üzerine bugünkü makaleyi yazmaya karar verdim. Yani bugün AngularJS’de routing kavramı üzerine konuşacağız.
Routing aslında Single Page uygulamalarda, farklı birden çok sayfanın görüntülenmesi için AngularJs’de kullanılan bir özelliktir. Bir başka özelliği de projede dağıtık bir mimari oluşturmayı sağlıyarak, yönetilebilirliği ve erişim kolaylığı sağlamasidir. Kısaca uygulamayı çeşitli sayfalara ayırarak, herbirini farklı controllerlara bağlar.
Öncelikle bir Mvc projesi yaratılıp NuGet’den aşağıdaki paketler indirilir. Projede AngularJS.Core ve Route işlemi için AngularJS.Route script dosyaları indirilmiştir. Ayrıca görsellik için de bootstarp indirilmiştir..
Index.cshtml sayfasına, ilgili script ve css dosyaları aşağıdaki gibi eklenir.
1 2 3 4 5 6 7 8 9 |
<head> <script src="/Scripts/angular.min.js"></script> <script src="/Scripts/angular-route.min.js"></script> <script src="/Scripts/jquery-1.9.1.min.js"></script> <script src="/Scripts/bootstrap.min.js"></script> <link href="/Content/bootstrap.min.css" rel="stylesheet" /> <meta name="viewport" content="width=device-width" /> <title>Index</title> </head> |
Şimdi sıra geldi sayfada sıralı bir menü ve tıklandığında ilgili sayfanın açılacağı kısımın bootstrap ile kodlanmasına. Aşağıda, ana sayfadan sipariş, sipariş detay ve parametre alan bir sayfaya yönlenen list item bir menü bulunmaktadır. Esas önemli kısım “ng-view” directivedir. Amacı oluşturulacak Html templatelerin belirlenen alanda gösterilmesidir. Yani menüye tıklanınca açılacak ilgili sayfa “ng-view” directive’i ile tanımlanmış “<div>”‘in içinde belirecektir.
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 |
<body> <div ng-controller="MainController" class="container"> <div class="well well-sm"><p><b><h1>Bu Ana Sayfadır</h1></b></p></div> <div class="row"> <div class="col-md-3"> <u class="nav"> <li><a href="#Siparis">Siparis Sayfası</a></li> <li><a href="#Detay">Siparis Detay</a></li> <li><a href="#ParameterPage/16789">Detaylı Parametre</a></li> </u> </div> <div class="col-md-9"> <div ng-view></div> </div> </div> </div> </body> |
Şimdi sıra geldi açılacak bu sayfaların tanımlanmasına. “Modules” adında bir klasörün içine aşağıda görüldüğü gibi ilgili sayfalar ve Controller.js’leri yaratılır.
Siparis.Controller.js: İlgili app’e “SiparisController” eklenir. “myName” ve “product” adında iki tane property yaratılmıştır.
1 2 3 4 |
app.controller("SiparisController", ['$scope', function ($scope) { $scope.myName = "Seçil KAŞMER"; $scope.product="Kolye" }]); |
siparis.html: “ng-controller” olarak yukarıda tanımlanan “SiparisController” tanımlanmıştır. İlgili isim ve ürün ekrana bastırılmaktadır.
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 |
<!DOCTYPE html> <html> <head> <title></title> <meta charset="utf-8" /> </head> <body> <div ng-controller="SiparisController"> <div class="panel panel-info"> <div class="panel-heading"><b>Siparis</b></div> <div class="panel-body"> Selamlar, {{myName}}: {{product}}niz gönderilmiştir.</div> </div> </div> </body> </html> |
DetayController.js: Burada üç property tanımlanmıştır. “myName”,”product” ve “price”
1 2 3 4 5 |
app.controller("DetayController", ['$scope', function ($scope) { $scope.myName = "Bora KAŞMER"; $scope.product = "XboxOne"; $scope.price="1200TL" }]); |
detay.html:“DetayController”‘da tanımlanan alanlar ekrana basılmıştır.
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 |
<!DOCTYPE html> <html> <head> <title></title> <meta charset="utf-8" /> </head> <body> <div ng-controller="DetayController"> <div class="panel panel-info"> <div class="panel-heading"><b>Siparis Detay</b></div> <div class="panel-body"> Selam, {{myName}}: Ürününüz {{product}} fiyatı:{{price}} dır.</div> </div> </div> </body> </html> |
ParameterPageController.js: Burada diğerlerinden farklı olarak sayfaya url’de query parameteresi gelmekte ve ilgili parametre “$routeParams” ile tanımlanan “id” property’sine atanmaktadır. Menüden çağrılış şekli yanda görüldüğü gibidir. “#ParameterPage/16789”
1 2 3 4 |
app.controller("ParameterPageController", ['$scope', '$routeParams', function ($scope, $routeParams) { $scope.myName = "Engin Polat"; $scope.id = $routeParams.id; }]); |
ParameterPage.html: Bu sayfada yukarıda “ParameterPageController”‘da tanımlı “myName” ve Url ile gelen “id” parametreleri ekrana basılmaktadır.
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 |
<!DOCTYPE html> <html> <head> <title></title> <meta charset="utf-8" /> </head> <body> <div ng-controller="ParameterPageController"> <div class="panel panel-info"> <div class="panel-heading"><b>Parameter Page:</b></div> <div class="panel-body"> Hi!, {{myName}} Your Id : {{id}} </div> </div> </div> </body> </html> |
Şimdi sıra geldi ilgili sayfaların routing işlemine. Bunun için aşağıda görülen app.js yaratılır. “$routeProvider“‘ ile aynı Mvc’de olduğu gibi Url’den gelen string path’e göre filitreleme işlemi yapılır. “when” koşulu ile belirlenen text’e göre ilgili sayfa bulunduktan sonra, “templateUrl” ile yönlendirileceği sayfa tanımlanır. Sayfanın ait olduğu controller’da “controller” parametresi ile atanır. Böylece menüden seçilen link’e göre, karşımıza gelen url’den önceden belirlenen keyword’lere göre filitreleme islemi yapilip, istenilen sayfaya yönlenilir. Örneğin aşağıda bu keywordler “Siparis, Detay ve ParameterPage” dir. Ayrıca sayfada parametre var ise, örneğin aşağıda “ParameterPage”‘de “:id” şeklinde ilgili parametre routing işleminde tanımlanır.
app.js:
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 |
var app = angular.module("app", ['ngRoute']); app.controller('MainController', ['$scope', function ($scope) { }]); app.config(['$routeProvider', function ($routeProvider) { $routeProvider. when('/Siparis', { templateUrl: 'Modules/Siparis/siparis.html', controller: 'SiparisController' }) . when('/Detay', { templateUrl: 'Modules/Detay/detay.html', controller: 'DetayController' }) . when('/ParameterPage/:id', { templateUrl: 'Modules/ParameterPage/ParameterPage.html', controller: 'ParameterPageController' }) . otherwise( { redirectTo: '' }); } ]); |
Bu sayfalarda kullanılan tüm “.js” dosyaları, anasayfada aşağıdaki gibi tanımlanmaktadır.
1 2 3 4 5 6 7 8 9 10 11 12 13 14 |
<head> <script src="/Scripts/angular.min.js"></script> <script src="/Scripts/angular-route.min.js"></script> <script src="/Scripts/jquery-1.9.1.min.js"></script> <script src="/Scripts/bootstrap.min.js"></script> <script src="/app.js?v=1"></script> <script src="/Modules/Siparis/SiparisController.js"></script> <script src="/Modules/Detay/DetayController.js"></script> <script src="/Modules/ParameterPage/ParameterPageController.js"></script> <link href="/Content/bootstrap.min.css" rel="stylesheet" /> <meta name="viewport" content="width=device-width" /> <title>Index</title> </head> |
Local Viewlar :
Bazen template sayfalar çok küçük olabilir. Örneğin sadece kullanıcının adını göstermek için yeni bir html sayfa yapmak çok da mantıklı değildir. İşte bu durumda ilgili view’ı yeni bir html sayfa yerine aynı sayfa üzerinde “ng-template” directive’i ile göstermek daha doğrudur. Index.cshtml sayfasına bahsedilen local templateler aşağıdaki gibi eklenir.
1 2 3 4 5 6 |
<script type="text/ng-template" id="page4.html"> <h2> Page 4 </h2> Hi, {{myName}} </script> <script type="text/ng-template" id="page5.html"> <h2> Page 5 </h2> Hi, {{myName}} </script> |
Index.cshtml(View):
Index.cshtml(Full): Yeni eklenen templateler, menü kısmına da aşağıda görüldüğü gibi eklenir.
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 |
@{ Layout = null; } <!DOCTYPE html> <html data-ng-app="app"> <head> <script src="/Scripts/angular.min.js"></script> <script src="/Scripts/angular-route.min.js"></script> <script src="/Scripts/jquery-1.9.1.min.js"></script> <script src="/Scripts/bootstrap.min.js"></script> <script src="/app.js?v=1"></script> <script src="/Modules/Siparis/SiparisController.js"></script> <script src="/Modules/Detay/DetayController.js"></script> <script src="/Modules/ParameterPage/ParameterPageController.js"></script> <link href="/Content/bootstrap.min.css" rel="stylesheet" /> <meta name="viewport" content="width=device-width" /> <title>Index</title> </head> <body> <div ng-controller="MainController" class="container"> <div class="well well-sm"><p><b><h1>Bu Ana Sayfadır</h1></b></p></div> <div class="row"> <div class="col-md-3"> <u class="nav"> <li><a href="#Siparis">Siparis Sayfası</a></li> <li><a href="#Detay">Siparis Detay</a></li> <li><a href="#ParameterPage/16789">Detaylı Parametre</a></li> <li><a href="#page4"> Page 4 </a></li> <li><a href="#page5"> Page 5 </a></li> </u> </div> <div class="col-md-9"> <div ng-view></div> </div> <script type="text/ng-template" id="page4.html"> <h2> Page 4 </h2> Hi, {{myName}} </script> <script type="text/ng-template" id="page5.html"> <h2> Page 5 </h2> Hi, {{myName}} </script> </div> </div> </body> </html> |
Yukarıda yaptığımız bu örnekde AngularJs routing konusuna açılık getirmeye çalıştık. Görüldüğü gibi hiç de zor değildir.
Geldik bir makalenin daha sonuna. Yeni bir makalede görüşmek üzere hoşçakalın..
Kaynak: https://www.c-sharpcorner.com/UploadFile/ff2f08/routing-in-angularjs/
Source Code: http://www.borakasmer.com/projects/AngularJSRouting.rar
Merhaba,
Route ve Template işlemleri için angular-route.js dosyası gerekiyor mu gerçekten. Bu dosyalar olmadan çalıştı çünkü.
Selam Erdinç;
Sen böyle deyince, şüphe ettim ve denedim. Malesef çalışmadı. angular-route.js olmadan routing nasıl çalıştı sen de merak ettim:) Büyük ihtimalle projende bir yerde saklanmıştır:)
İyi çalışmalar..
Eğer angular-route.js konmaz ise Console’daki hata mesajı aşağıdaki gibi alınır:
Hocam merhaba,
araştırdım eski sürüm olmasından kaynaklanıyor.
https://docs.angularjs.org/error/$injector/modulerr
n AngularJS 1.2.0 and later, ngRoute has been moved to its own module. If you are getting this error after upgrading to 1.2.x or later, be sure that you’ve installed ngRoute.
aşağıdaki sürümü kullanınca route.js’e gerek kalmıyor.
Hocam selam,
bir sorum olacak. Aşağıdaki şekilde Siparis.html’e ilk tıklamadan sonra hep cache’den getiriyor. Dolayısıyla site açıkken siparis. html sayfasında değişiklik yaptığımda değşikliği algılamıyor.
when(‘/Siparis’,
{
templateUrl: ‘Modules/Siparis/siparis.html’,
controller: ‘SiparisController’
})
Bunu araştırdığımda aşağıdaki gibi bir koda denk geldim. Ama bu kod varken bu sefer local template’ler çalışmıyor. Cache lemyi nasıl engelleyebilirim.
app.run(function ($rootScope, $templateCache) {
$rootScope.$on(‘$viewContentLoaded’, function () {
$templateCache.removeAll();
});
});
Selam Erdinç;
Cache’in hepsiden kalkmasını istemiyor isen aşağıdaki yolu kullan:
.controller(‘SiparisController’, function ($scope, $templateCache) {
$templateCache.remove(‘Modules/Siparis/siparis.html’);
});
İyi çalışmalar….
Teşekkür ederim hocam
Aynı sayfa üzerinde bir den fazla modele veri eklemek için oluşturduğumuz viewları, aynı sayfa üzerinde ng-view komutu ile göstererek insert işlemi yapabilir miyiz?
Eğer mümkün değilse nasıl bir çözüm yolu önerirsiniz ?
Selamlar Volkan,
Insert Islemi için AngularJS’de “$http.Post()” kullanarak ilgili view üzerinden yeni kayıt girişi yapabilirsin. Yani “ng-view” kullanarak farklı viewlardan farklı veri girişini “Json Post” kullanarak ilgili Action’a gönderip yapman gayet mümkün.
İyi çalışmalar.
Hocam iyi günler kafam biraz karışık lise öğrencisiyim css ve javascript’i zaten biliyorum ama angular.js ye nerden nasıl başlıyıcağımı bilmiyorum yardımcı olurmusunuz
Selam Ali,
Site ingilizce de olsa aşağıdaki linkden başlıyabilirsi:
http://campus.codeschool.com/courses/shaping-up-with-angular-js/contents
İyi çalışmalar.