<ruby id="bdb3f"></ruby>

    <p id="bdb3f"><cite id="bdb3f"></cite></p>

      <p id="bdb3f"><cite id="bdb3f"><th id="bdb3f"></th></cite></p><p id="bdb3f"></p>
        <p id="bdb3f"><cite id="bdb3f"></cite></p>

          <pre id="bdb3f"></pre>
          <pre id="bdb3f"><del id="bdb3f"><thead id="bdb3f"></thead></del></pre>

          <ruby id="bdb3f"><mark id="bdb3f"></mark></ruby><ruby id="bdb3f"></ruby>
          <pre id="bdb3f"><pre id="bdb3f"><mark id="bdb3f"></mark></pre></pre><output id="bdb3f"></output><p id="bdb3f"></p><p id="bdb3f"></p>

          <pre id="bdb3f"><del id="bdb3f"><progress id="bdb3f"></progress></del></pre>

                <ruby id="bdb3f"></ruby>

                企業??AI智能體構建引擎,智能編排和調試,一鍵部署,支持知識庫和私有化部署方案 廣告
                # 在 JavaScript 中實現 MVC 和 PubSub > 原文: [https://howtodoinjava.com/javascript/implement-mvc-and-pubsub-in-javascript/](https://howtodoinjava.com/javascript/implement-mvc-and-pubsub-in-javascript/) 我們知道什么是 MVC? MVC 代表[**模型 - 視圖 - 控制器**](https://en.wikipedia.org/wiki/Model%E2%80%93view%E2%80%93controller "MVC")。 簡而言之,MVC 是一種設計技術,其中將應用組件分為 3 組,以便可以獨立開發它們而無需考慮它們將如何交互。 如果構建正確,則很少有配置代碼可以綁定它們,并且可以立即使用。 [**PubSub(發布者訂閱者)**](https://en.wikipedia.org/wiki/Publish%E2%80%93subscribe_pattern "pubsub") 模型是設計范式,其中多個訂閱者正在監聽源上的更改事件,并且一旦發生任何更改,便會立即通知監聽器。 在用戶交互影響屏幕上多個部分的大型系統中,此模式消除了許多硬編碼,并提供了設計靈活性。 ![PubSub + MVC in JavaScript](https://img.kancloud.cn/3b/fb/3bfb467a7889b504e810730487c4d4f9_591x165.png) JavaScript 中的 PubSub + MVC 在本教程中,我們將學習以下概念: ```java Building Model-View-Controller components Building Publisher Subscriber infrastructure Understanding Event Notification mechanism Demo application ``` 讓我們從構建 MVC 組件開始。 ## 構建模型視圖控制器組件 在 JavaScript 中,如果必須開發 MVC 結構,則至少需要編寫 3 個對象。 我只花 3 個使例子更加關注概念。 例如,我以媒體播放器為例。 此媒體播放器附有一個播放列表,用戶可以使用按鍵事件在此播放列表上向前和向后移動。 **模型**:存儲當前視圖狀態 `playlist` – 數組對象將所有曲目存儲在當前可用的播放列表中。 `currentIndex` – 當前播放的曲目 模型還包含幫助用戶在用戶交互后保持其當前狀態更改的函數。 ```java var Model = { playlist: new Array(), currentIndex : 0, reLoad: function() { currentIndex = 0; var tracks = document.getElementById("playListSelector").options; for(var i=0; i<tracks.length; i++) { this.playlist&#91;i&#93; = tracks&#91;i&#93;.value; } }, next: function () { if(this.currentIndex < (this.playlist.length-1)) this.currentIndex++; publish(this); }, prev: function () { if(this.currentIndex > 0) this.currentIndex--; publish(this); }, current: function () { publish(this); } }; ``` **視圖**:表示用戶與之交互的屏幕 該對象只有一種方法可以在屏幕上呈現用戶事件的結果。 ```java var View = { notify: function(model) { document.getElementById("playListSelector").selectedIndex = model.currentIndex; } }; ``` **控制器**:視圖調用控制器以更改模型 控制器具有在用戶交互期間將被調用的函數。 ```java var Controller = { model: Model, moveNext: function () { this.model.next(); return this; }, movePrev: function () { this.model.prev(); return this; }, getCurrent: function () { this.model.current(); return this; } }; ``` ## 構建發布者訂閱服務器基礎結構 到目前為止,一切都很好。 現在,我們將添加一些 pub-sub 邏輯,以便無論何時觸發任何用戶事件,都會通知所有已注冊的視圖,并且它們可以進行所需的視覺更改。 ```java //All subscribers for a event var subscribers = []; function publish(event) { for (i in subscribers) { subscribers[i].notify(event); } }; ``` 上面的代碼聲明了一個數組,該數組可用于存儲所有感興趣的視圖以將其自身注冊為事件監聽器。 每當任何事件作為用戶交互觸發時,都會通知他們該事件。 要將視圖注冊為事件監聽器,將使用以下代碼: ```java //Subscribe for updates subscribers.push(View); ``` ### 了解事件通知機制 事件處理按以下順序執行: 視圖觸發事件 -> 控制器觸發模型更新 -> 模型將通知發送到 pubsub -> pubsub 通知所有有關事件的視圖,以便它們可以更新用戶屏幕 在上面的代碼段中,假設用戶按下了播放列表中的下一首曲目。 這是控制流: 1. 用戶按下“下一首”按鈕 2. 控制器的`moveNext()`方法調用 3. `moveNext()`觸發模型的`next()`方法 4. `next()`方法增加當前正在播放曲目的`currentIndex` 5. `next()`方法使用`publish()`方法發布事件 6. `publish()`方法調用`notify()`方法是所有注冊的訂戶 7. 視圖`notify()`方法根據模型的當前狀態更新用戶屏幕 這樣,所有可能的事件都將從控制器處理到視圖層。 最后,我們一直都處于模型的當前狀態。 ## 演示應用 我已經在一個文件中使用了上述所有代碼段,并使用 HTML `select`元素進行了虛擬播放列表行為。 `select`的當前選定選項代表媒體播放器中當前播放的曲目。 讓我們看一下完整的演示代碼: ```java <html> <head> <meta charset="utf-8"> <script language="javascript"> // PubSub var subscribers = []; function publish(event) { for (i in subscribers) { subscribers[i].notify(event); } }; // MVC var Model = { playlist: new Array(), currentIndex : 0, reLoad: function() { currentIndex = 0; var tracks = document.getElementById("playListSelector").options; for(var i=0; i<tracks.length; i++) { this.playlist&#91;i&#93; = tracks&#91;i&#93;.value; } }, next: function () { if(this.currentIndex < (this.playlist.length-1)) this.currentIndex++; publish(this); }, prev: function () { if(this.currentIndex > 0) this.currentIndex--; publish(this); }, current: function () { publish(this); } }; var View = { notify: function(model) { document.getElementById("output").innerHTML = JSON.stringify(model); document.getElementById("playListSelector").selectedIndex = model.currentIndex; } }; var Controller = { model: Model, moveNext: function () { this.model.next(); return this; }, movePrev: function () { this.model.prev(); return this; }, getCurrent: function () { this.model.current(); return this; } }; subscribers.push(View); // Subscribe for updates function initializeModel() { Model.reLoad(); } </script> </head> <body onload="initializeModel()"> <input type="button" onclick="Controller.getCurrent();" value="Current Track"> <input type="button" onclick="Controller.moveNext();" value="Next Track"> <input type="button" onclick="Controller.movePrev();" value="Previous Track"> <select id="playListSelector" multiple readonly> <option value="0">Track 1</option> <option value="1">Track 2</option> <option value="2">Track 3</option> <option value="3">Track 4</option> </select> <span id="output" /> </body> </html> ``` 上面的代碼還有另外一個方法`initializeModel()`,該方法用于在頁面加載時使用播放列表項初始化模型對象。 現在,當我們按“下一個曲目”時,選擇元素中的下一個選項被選中。 同樣,按下“上一曲目”按鈕,則在選擇列表中選擇了上一個選項。 您將看到如下運行代碼: ![Demo Screen of MVC + PubSub w2ith JavaScript](https://img.kancloud.cn/d9/ba/d9ba16fa42941bd0f11216f9f22be5a0_733x124.png) JavaScript 中的 MVC + PubSub 的示例界面 如果不清楚或您有任何建議/查詢,請發表評論。 ———————————————————————————————————— **更新:** 經過簡短的郵件討論后,Brook Monroe 向我發送了類似示例的更好的代碼示例。 盡管本教程的目的不是更好的代碼實踐,而是詳細介紹了概念。 我在下面共享更新的代碼以供參考。 它可能會幫助您。 ```java <html> <head> <meta charset="utf-8"> <script src="./pubsub.js"></script> </head> <body> <button id="btnCurrent">Current Track</button> <button id="btnNext">Next Track</button> <button id="btnPrev">Previous Track</button> <select id="playListSelector" multiple readonly> <option value="0" selected>Track 1</option> <option value="1">Track 2</option> <option value="2">Track 3</option> <option value="3">Track 4</option> </select> <span id="output"></span> </body> </html> //pubsub.js // PubSub ( function () { "use strict"; var subscribers = [], elCache = {}, Model = { playlist : [], currentIndex : 0, reLoad : function() { var tracks = Array.prototype.slice.call(elCache.get("playListSelector").options); this.playlist = []; tracks.forEach( function (e,i) { this.playlist.push(tracks[i].value); }, Model); this.currentIndex = 0; }, next : function () { if (this.currentIndex < (this.playlist.length-1)) { this.currentIndex++; } subscribers.publish(this); }, prev : function () { if (this.currentIndex > 0) { this.currentIndex--; } subscribers.publish(this); }, current : function () { subscribers.publish(this); } }, // MVC View = { notify : function(model) { elCache.get("output").innerHTML = JSON.stringify(model); elCache.get("playListSelector").selectedIndex = model.currentIndex; } }, Controller = { moveNext: function () { Model.next(); return this; }, movePrev: function () { Model.prev(); return this; }, getCurrent: function () { Model.current(); return this; } }; function start() { elCache.get = function (elId) { return this[elId] || ( this[elId] = document.getElementById(elId) ); }; subscribers.publish = function (event) { this.forEach( function (e) { e.notify(event); } ); }; subscribers.push(View); // Subscribe for updates elCache.get("btnCurrent").addEventListener("click", Controller.getCurrent.bind(Model)); elCache.get("btnNext").addEventListener("click", Controller.moveNext.bind(Model)); elCache.get("btnPrev").addEventListener("click", Controller.movePrev.bind(Model)); Model.reLoad.bind(Model)(); } window.addEventListener("load",start,false); } )(); ``` **祝您學習愉快!**
                  <ruby id="bdb3f"></ruby>

                  <p id="bdb3f"><cite id="bdb3f"></cite></p>

                    <p id="bdb3f"><cite id="bdb3f"><th id="bdb3f"></th></cite></p><p id="bdb3f"></p>
                      <p id="bdb3f"><cite id="bdb3f"></cite></p>

                        <pre id="bdb3f"></pre>
                        <pre id="bdb3f"><del id="bdb3f"><thead id="bdb3f"></thead></del></pre>

                        <ruby id="bdb3f"><mark id="bdb3f"></mark></ruby><ruby id="bdb3f"></ruby>
                        <pre id="bdb3f"><pre id="bdb3f"><mark id="bdb3f"></mark></pre></pre><output id="bdb3f"></output><p id="bdb3f"></p><p id="bdb3f"></p>

                        <pre id="bdb3f"><del id="bdb3f"><progress id="bdb3f"></progress></del></pre>

                              <ruby id="bdb3f"></ruby>

                              哎呀哎呀视频在线观看