2017-04-04 52 views
0

取消流我想要做的背後的想法是打破/完成一個功能,一旦我再次運行相同的功能,但具有不同的參數。當onClick,javascript

現在我有一串隨機字符被髮送到端點。

一個類獲取此端點並允許流填充內容視圖。

我有一個標籤,每次點擊它時都會調用這個填充函數。

我喜歡這樣,當我點擊另一個選項卡或同一個選項卡時,函數結束,停止使用先前的參數,然後再次使用新參數運行該函數。在點擊同一個標籤的情況下,它什麼也不做。

下面我有HTML正文,CSS,客戶端的JS腳本和發送流的node.js服務器端。你應該能夠或多或少的複製粘貼這個,它會運行。

不要忘記爲節點安裝npm。只需運行節點代碼即可啓動服務器。

HTML:

<div class="tab-bar"> 
     <button class="tab" onclick="getStreamNContentLocale('stream_1')">London</button> 
     <button class="tab" onclick="getStreamNContentLocale('stream_2')">Paris</button> 
     <button class="tab" onclick="getStreamNContentLocale('stream_3')">Tokyo</button> 
    </div> 
    <div class="content"> 
     <div id="stream_1"> 
     </div> 
     <div id="stream_2"> 
     </div> 
     <div id="stream_3"> 
     </div> 
    </div> 
    <script src="js/index.js"></script> 

CSS:

.tab-bar { 
    height: 40px; 
    width: 100%; 
    background-color: black; 
} 

.tab { 
    color: white; 
    font-size: 100%; 
    float: left; 
    padding: 9px 16px; 
    vertical-align: middle; 
    background-color: inherit; 
} 

.content { 
    border: 1px solid #ccc; 
    overflow: auto; 
    height: 200px; 
    width: 100%; 
} 

JS:

console.log((new Date()).toLocaleString()); 

function getStreamNContentLocale(contentID) { 
    let xhr = new XMLHttpRequest(), 
     streamArray = [], 
     snapshotsSent = 0; 

    xhr.open('GET', `/stream`); 
    xhr.seenBytes = 0; 
    xhr.onreadystatechange =() => { 
     if (xhr.readyState > 2) { 
      if (snapshotsSent < 30) { 
       streamArray.push("Snapshot sent " + (new Date()).toLocaleString() + "\n" + xhr.responseText.substring(xhr.seenBytes, xhr.responseText.length)); 
       document.querySelector(`#${contentID}`).innerText = streamArray; 
      } else if (snapshotsSent >= 30) { 
       streamArray.shift(); 
       streamArray.push("Snapshot sent " + (new Date()).toLocaleString() + "\n" + xhr.responseText.substring(xhr.seenBytes, xhr.responseText.length)); 
       document.querySelector(`#${contentID}`).innerText = streamArray; 
      } 
      xhr.seenBytes = xhr.responseText.length; 
     } 
     snapshotsSent++; 
     /********************************************************************************************** 
     * xhr.responseText.substring(xhr.seenBytes, xhr.responseText.length) is each snapshot we GET * 
     * snapshotsSent is the number of snapshots we have actually gotten so far in this session * 
     **********************************************************************************************/ 
    }; 
    xhr.send(); 
} 

SERV ER:

let express = require('express'), 
    app = express(), 
    bodyParser = require('body-parser'), 
    path = require('path'); 

init(function() { 
     callback(null); 
    }); 

function init(callback) { 
    app.use(bodyParser.json()); 

    app.use(bodyParser.urlencoded({ 
     extended: true 
    })); 

    app.use(express.static(path.join(__dirname, "../../views"))); 

    app.get('/', function(req, res) { 
     res.sendFile(path.join(__dirname, "../../views/index.html")); 
    }); 

    app.get('/stream', (req, res) => { 
     console.log('sending stream to /stream'); 
     setInterval(() => { 
      res.write(Math.random(16).toString(36).substring(2) + "\n"); 
     }, 200); 
    }); 

    app.listen(8000,() => { 
     console.log("Listening on port 8000"); 
    }); 

    callback(); 
} 

回答

1

可以存儲在函數本身的XMLHttpRequest xhr並在每次運行函數時終止它。像這樣(在你的JS文件):

function getStreamNContentLocale(contentID) { 

    if(getStreamNContentLocale.xhr !== undefined) 
     getStreamNContentLocale.xhr.abort(); 

    getStreamNContentLocale.xhr = new XMLHttpRequest(), 
     streamArray = [], 
     snapshotsSent = 0; 

    // the rest of your code goes here 
} 

abort()方法:https://developer.mozilla.org/en-US/docs/Web/API/XMLHttpRequest/abort

編輯:也是在你的回調添加getStreamNContentLocale.xhr = undefined;,否則中止完成的請求時,它可能會返回一個錯誤。

+0

啊,每當我運行該函數時,它都會檢查流是否已經在運行,通過檢查是否定義了「getStreamNContentLocale.xhr」。對? –

+0

確切地說:) 如果這是您需要的,請不要忘記驗證此答案。 –

+0

我們將會看到,我現在正在測試這個。 –