hocvietcode.com
  • Trang chủ
  • Học lập trình
    • Lập trình C/C++
    • Lập trình HTML
    • Lập trình Javascript
      • Javascript cơ bản
      • ReactJS framework
      • AngularJS framework
      • Typescript cơ bản
      • Angular
    • Lập trình Mobile
      • Lập Trình Dart Cơ Bản
        • Dart Flutter Framework
    • Cơ sở dữ liệu
      • MySQL – MariaDB
      • Micrsoft SQL Server
      • Extensible Markup Language (XML)
      • JSON
    • Lập trình PHP
      • Lập trình PHP cơ bản
      • Laravel Framework
    • Lập trình Java
      • Java Cơ bản
    • Cấu trúc dữ liệu và giải thuật
    • Lập Trình C# Cơ Bản
    • Machine Learning
  • WORDPRESS
    • WordPress cơ bản
    • WordPress nâng cao
    • Chia sẻ WordPress
  • Kiến thức hệ thống
    • Microsoft Azure
    • Docker
    • Linux
  • Chia sẻ IT
    • Tin học văn phòng
      • Microsoft Word
      • Microsoft Excel
    • Marketing
      • Google Adwords
      • Facebook Ads
      • Kiến thức khác
    • Chia sẻ phần mềm
    • Review công nghệ
    • Công cụ – tiện ích
      • Kiểm tra bàn phím online
      • Kiểm tra webcam online
Đăng nhập
  • Đăng nhập / Đăng ký

Please enter key search to display results.

Home
  • AngularJS
Scope và rootScope trong AngularJS

Scope và rootScope trong AngularJS

  • 22-04-2022
  • Toanngo92
  • 0 Comments

Ở các bài trước, chúng ta đã tạm hiểu cấu trúc MVC của AngularJS:

  • View: dữ liệu hiển thị HTML
  • Model: dữ liệu làm việc với view hiện tại
  • Controller: luồng logic được viết bằng angularJS functions, sử dụng để thêm, sửa , xóa dữ liệu

$scope là một object (đối tượng) có nhiệm vụ giao tiếp dữ liệu giữa controller và view của ứng dụng, chúng ta có thể hiểu là cầu nối, khi biến $scope thay đổi, dữ liệu ở controller và view cùng được cập nhật đồng bộ . Nó sẽ thực hiện dưới dạng biểu thức, nghĩa là ở model sẽ được khai báo đúng với quy cách thì đối tượng scope sẽ truyền hành động (function) hoặc dữ liệu tương ứng và ta có thể truyền các sự kiện thông qua đối tượng này.

Scopes cung cấp các biểu thức giống như các template engine hiện nay, ví dụ để hiển thị username thì ta sẽ khai báo là {{username}} và ở controller chúng ta chỉ việc gán $scope.username = ‘toanngo92’ thì đối tượng này sẽ lấy key có tên là username gán vào view {{username}}.

Mục lục

  • Phạm vi ảnh hưởng của $scope
  • $rootScope và cấu trúc phân tầng của $scope
  • Nested Scope (scope lồng nhau)

Phạm vi ảnh hưởng của $scope

Trong một ứng dụng AngularJS thì ta có thể có nhiều Controller, nhiều $scope khác nhau. Quay trở lại ví dụ dưới đây:

<!DOCTYPE html>
<html lang="en">
<head>
    <meta charset="UTF-8">
    <meta http-equiv="X-UA-Compatible" content="IE=edge">
    <meta name="viewport" content="width=device-width, initial-scale=1.0">
    <title>Example Controller</title>
    <script src="https://ajax.googleapis.com/ajax/libs/angularjs/1.8.2/angular.min.js"></script>
</head>
<body>
    <div ng-app="examController">
        <div ng-controller="headerController">
            {{name}} - {{data}}
        </div>
        <div ng-controller="mainController">
            {{name}} - {{data}}
        </div>
        <div ng-controller="footerController">
            {{name}} - {{data}}
        </div>
    </div>
    <script>
        var app = angular.module('examController', []);
        app.controller('headerController', function($scope){
            $scope.name = "This is header";
        });
        app.controller('mainController', function($scope){
            $scope.name = "This is main";
            $scope.data = "main data";
        });
        app.controller('footerController', function($scope){
            $scope.name = "This is footer";
        });
    </script>
</body>
</html>

Chúng ta thấy trong các view liên kết tới controller tương ứng đều giá trị {{data}} khác nhau tuy nhiên mỗi một controller, thuộc tính data trong biến ở mỗi controller khác nhau. Điều này chứng minh cho việc phạm vi của biến $scope chỉ nằm trong controller tương ứng.

$rootScope và cấu trúc phân tầng của $scope

Ví dụ số 1:

<!DOCTYPE html>
<html lang="en">
<head>
    <meta charset="UTF-8">
    <meta http-equiv="X-UA-Compatible" content="IE=edge">
    <meta name="viewport" content="width=device-width, initial-scale=1.0">
    <title>Document</title>
    <script src="angular.min.js"></script>
	<!-- <script src="angular-route.min.js"></script> -->
</head>
<body ng-app="toanApp">
    <div >Data rootscope: {{name}}</div>
    <div ng-controller="indexController">
        <input ng-model="name" value=""/>
        <p> Data scope {{name}}</p>
        <button ng-click="changename()" >click</button>
    </div>
    <script>
        var app = angular.module("toanApp",[]);
        app.run(function($rootScope){
            $rootScope.name = "root scope";
        });
        app.controller(
            "indexController",
            function($scope){
               // console.log(languages);
                $scope.name = "controller scope";
                $scope.changename = function(e){
                    $scope.name = "test";
                }
            }
        );
    </script>
</body>
</html>

Kết quả khi in ra, và tương tác với input

Với ví dụ trên, chúng ta thấy mình có sử dụng một div và gọi model name ra view, tuy nhiên model này không thuộc controller nào, chúng ta hiểu ở dưới tầng script, thông qua phương thức app.run(), chúng ta đã khởi tạo một model toàn cục tên là name, nên mặc dù không nằm trong controller nào, chúng ta vẫn có thể biểu diễn ra biến name. còn đối với model name ở cấu trúc div bên trong indexController, chúng ta thấy khi cập nhật dữ liệu, model ở controller thay đổi nhưng không liên quan gì tới model bên ngooài, điều đó có ý nghĩa, 2 model name nằm trong $scope và $rootScope mặc dù cùng tên nhưng bản chất chúng không liên quan tới nhau

Ví dụ số 2:

bây giờ ta sẽ đổi một chút cú pháp của đoạn mã AngularJS như sau:

Trong đoạn ví dụ này sự khác biệt chính là ở đoạn mã JS Controller thứ nhất có thêm tham số $rootScope, và ở đoạn Controller thứ hai thì không xử lý gì cả. Chạy lên các bạn thấy giao diện như sau:

Như vậy rõ ràng đoạn code trên mình không truyền giá trị cho $scope ở cả 2 controller mà bên view vẫn có? Đó là vì biến $rootScope. Điều này có nghĩa là khi ứng dụng được chạy thì sẽ có một $rootScope được tự động tạo, $rootScope là bậc cao nhất nên sẽ bao quát hết các $scope bên trong nó, điêu này không giống với $scope là chỉ ảnh hưởng trong phạm vi của controller.

Xét ví dụ phía dưới:

<!DOCTYPE html>
<html lang="en">
<head>
    <meta charset="UTF-8">
    <meta http-equiv="X-UA-Compatible" content="IE=edge">
    <meta name="viewport" content="width=device-width, initial-scale=1.0">
    <title>Example Controller</title>
    <script src="https://ajax.googleapis.com/ajax/libs/angularjs/1.8.2/angular.min.js"></script>
</head>
<body>
    <div ng-app="examRootScope">
        <div ng-controller="headerController">
            {{name}} - {{data}} {{data_global}}
        </div>
        <div ng-controller="mainController">
            {{name}} - {{data}}
        </div>
        <div ng-controller="footerController">
            {{name}} - {{data}}
        </div>
    </div>
    <script>
        var app = angular.module('examRootScope', []);
        app.controller('headerController', function($scope,$rootScope){
            $scope.name = "This is header";
            $scope.data= "header data scope";
            $rootScope.data = "header data root scope";
        });
        app.controller('mainController', function($scope){
            $scope.name = "This is main";
            $scope.data = "main data";
        });
        app.controller('footerController', function($scope,$rootScope){
            $scope.name = "This is footer";
            $scope.data = "footer data scope";
            $rootScope.data_global = "thuoc tinh dung chung";
        });
    </script>
</body>
</html>

Kết quả in ra màn hình:

Bổ sung thêm một số thông tin ở ví dụ phía trên, có 2 ý cần quan tâm:

  • Ở headerController, 2 thuộc tính $scope.data và $rootScope.data được đặt tên giống nhau (data), tuy nhiên khi in ra view bằng biểu thức, giá trị sẽ được lấy từ thuộc tính data của bến $scope, chứng minh nếu trong trường hợp model có tên giống nhau, $scope sẽ đưược ưu tiên so với $rootScope
  • Ở footerController, có một thuộc tính có tên data_global do mình tự đặt, tuy nhiên ở tầng view liên kết với headerController, mình lại cố tình gọi model data_global này ra, nhưng views vẫn nhận diện được, điều này chứng minh dữ liệu trong $rootScope có tính toàn cục ( có thể sử dụng để dùng chung hoặc truyền dữ liệu giữa các controller)

Nested Scope (scope lồng nhau)

Trong angularJS, chúng ta có thêm khái niệm các controller lồng nhau, tương tự các scope cũng lồng nhau, với tình huống này cần rất cẩn thận vì sẽ có nhiều tình huống không phân biệt được đang sử dụng scope nào. Xét ví dụ phía dưới:

<!DOCTYPE html>
<html lang="en" ng-app="myApp">

<head>
    <meta charset="UTF-8">
    <meta http-equiv="X-UA-Compatible" content="IE=edge">
    <meta name="viewport" content="width=device-width, initial-scale=1.0">
    <title>Document</title>
    <script src="https://ajax.googleapis.com/ajax/libs/angularjs/1.8.2/angular.min.js"></script>
</head>

<body ng-controller="parentController">
    What controller am I? {{parentVariable}}
    <div ng-controller="childController">
        What controller am I? {{childVariable}} {{parentVariable}}
        <button ng-click="childFunction()"> Click me to override! </button>
    </div>
</body>
<script>
    var app = angular.module('myApp', []);
    app.controller('parentController', function ($scope) {
        $scope.parentVariable = "I'm the parent";
    });

    app.controller('childController', function ($scope) {
        $scope.childVariable = "I'm the child";
        $scope.childFunction = function () {
            $scope.parentVariable = "Parent changed!";
            console.log($scope);
        };
    });
</script>
</html>

Kết quả khi chạy thử và bấm nút override:

Vấn đề ở đây, khi log biến $scope ra, dữ liệu parentVariable đã thay đổi, tuy nhiên parentVariable ở parentController lại không được cập nhật, vấn đề này sẽ thực sự gây khó hiểu và bất tiện trong quá trình coding, nên lời khuyên cho bạn là nên đặt tên biến rõ ràng, nếu có phải sử dụng nested controller thì nên tìm hiểu cấu trúc thật kỹ để tránh phát sinh lỗi không mong muốn.

Ngoài ra, nếu nói về scope thì thực sự sẽ có rất nhiều vấn đề, tuy nhiên trong khuôn khổ tiếp cận, những khái niệm này là những thứ chúng ta cần nắm bắt trước khi đi vào làm một ứng dụng thực tế với angularjs.

Bài viết liên quan:

Factory và Service trong angularJS
Cơ chế dependency Injection (cơ chế tiêm phụ thuộc) trong angularJS
Animation trong angularJS
Form validation trong angularJS
Route (định tuyến) trong angularJS
Filter (bộ lọc) trong angularJS
Service trong AngularJS và các service giao tiếp với máy chủ
Directive (chỉ thị) trong angularJS và danh sách các directive
Event handling (xử lý xự kiện) trong angularJS
Cơ chế Data binding trong AngularJS
Expressions (biểu thức) trong AngularJS
Views trong AngularJS

THÊM BÌNH LUẬN Cancel reply

Dịch vụ thiết kế Wesbite

NỘI DUNG MỚI CẬP NHẬT

4. KIỂM THỬ VÀ TRIỂN KHAI HỆ THỐNG

2. PHÂN TÍCH VÀ ĐẶC TẢ HỆ THỐNG

3. THIẾT KẾ HỆ THỐNG

1. TỔNG QUAN KIẾN THỨC THỰC HÀNH TRIỂN KHAI DỰ ÁN CÔNG NGHỆ THÔNG TIN

Hướng dẫn tự cài đặt n8n comunity trên CyberPanel, trỏ tên miền

Giới thiệu

hocvietcode.com là website chia sẻ và cập nhật tin tức công nghệ, chia sẻ kiến thức, kỹ năng. Chúng tôi rất cảm ơn và mong muốn nhận được nhiều phản hồi để có thể phục vụ quý bạn đọc tốt hơn !

Liên hệ quảng cáo: [email protected]

Kết nối với HỌC VIẾT CODE

© hocvietcode.com - Tech888 Co .Ltd since 2019

Đăng nhập

Trở thành một phần của cộng đồng của chúng tôi!
Registration complete. Please check your email.
Đăng nhập bằng google
Đăng kýBạn quên mật khẩu?

Create an account

Welcome! Register for an account
The user name or email address is not correct.
Registration confirmation will be emailed to you.
Log in Lost your password?

Reset password

Recover your password
Password reset email has been sent.
The email could not be sent. Possible reason: your host may have disabled the mail function.
A password will be e-mailed to you.
Log in Register
×