1. 程式人生 > >前端每週學習分享--第12期

前端每週學習分享--第12期

1.VuePress

大家看過不少Vue.js及其子專案的文件,一定發現了它們風格完全一致,介面清爽,讀起來很舒服,它們都使用了vuepress。

VuePress是尤大為了支援 Vue 及其子專案的文件需求而寫的一個靜態網站生成工具,廣泛用於編寫技術文件 ,可以部署在github上做個人部落格。

原理:

在構建過程中,會建立應用程式的伺服器渲染版本,通過訪問每個路由,來渲染相應的 HTML。

其中, 每個 markdown 檔案都使用 markdown-it 編譯為 HTML,然後作為 Vue 元件的模板進行處理。這允許你直接在 markdown 檔案中使用 Vue,在需要嵌入動態內容時,這種使用方式非常有用。

十分實用的特性:

  • md檔案可內嵌vue程式碼
  • 可自定義主題
  • 利用service worker做離線快取
  • 多語言支援
  • 基於git的最近更新

官方文件: https://vuepress.docschina.org/guide/#%E8%BF%90%E8%A1%8C%E5%8E%9F%E7%90%86-how-it-works

快速搭建: https://segmentfault.com/a/1190000016333850#articleHeader1

2.WebWorker

web worker是執行在後臺的jacvascript,利用類似執行緒的訊息傳遞實現並行,獨立於其他指令碼,不會影響頁面的效能。

web worker能夠長時間執行,有理想的啟動效能以及理想的記憶體消耗。

worker 建立後,它可以向它的建立者指定的事件監聽函式傳遞訊息,這樣該worker生成的所有任務都會接收到這些訊息。

webworker有專用執行緒dedicated worker(單視窗專用),sharedWorker(可多視窗共享),以及後來的service worker(目前瀏覽器支援程度還不高)。

2.1.dedicated worker

使用方法:

worker執行緒裡監聽onmessage,

頁面執行緒裡建立worker物件:const myworker = new Worker("worker.js")

傳送訊息:postMessage(msg)

接受訊息:onmessage = function(e){const msg = e.data}

msg的資料格式自行定義。

終止worker:myworker.terminate()

例如下面的示例,worker會接收頁面上輸入的兩個數字,計算出乘積後返回結果。

worker.js

onmessage = function(e) {
  console.log('Worker: Message received from main script');
  let result = e.data[0] * e.data[1];
  if (isNaN(result)) {
    postMessage('Please write two numbers');
  } else {
    let workerResult = 'Result: ' + result;
    console.log('Worker: Posting message back to main script');
    postMessage(workerResult);
  }
}

index.html裡

const first = document.querySelector('#number1');
const second = document.querySelector('#number2');
const result = document.querySelector('.result');
if (window.Worker) {
    const myWorker = new Worker("worker.js");

    first.onchange = function() {
      myWorker.postMessage([first.value, second.value]);
      console.log('Message posted to worker');
    }

    second.onchange = function() {
      myWorker.postMessage([first.value, second.value]);
      console.log('Message posted to worker');
    }

    myWorker.onmessage = function(e) {
        result.textContent = e.data;
        console.log('Message received from worker');
    }
} else {
    console.log('Your browser doesn\'t support web workers.')
}

2.2.shared worker

共享程序可以連線到多個不同的頁面,這些頁面必須屬於相同的域(相同的協議,主機以及埠)

在火狐中,共享程序不能在私有與公共文件間進行共享。

SharedWorker.port返回一個MessagePort物件,用來進行通訊和對共享程序進行控制。

建立共享程序物件:const myWorker = new SharedWorker("worker.js");

獲取埠:

傳送訊息:myWorker.port.postMessage(msg)

接收訊息:myWorker.port.onmessage = function(e) {const msg = e.data}

worker執行緒獲取埠:onconnect = function(e) {const port = e.ports[0]}

啟動埠:port.start()

2.3.service worker

Service Worker 可以理解為一個介於客戶端和伺服器之間的一個代理伺服器 ,常用於做離線資源快取

出於對安全問題的考慮,Service Worker 只能被使用在 https 或者本地的 localhost 環境下。

暫時沒有仔細學這塊,可以閱讀Service Worker —這應該是一個挺全面的整理。

參考文章:

WebWorker簡介

MDN Web Workers API

3.程式碼相關

3.1.元素內文字垂直居中

已知元素高度的話,可以設定line-height:元素高度.

如果元素高度未知,就不能使用line-height了。

有人會想使用line-height:100%,會發現這是不行的,這個百分比是相對當前字型尺寸,而不是元素高度。

我使用了flex佈局實現

    display: flex;
    align-items:center;
    justify-content:center;

還可以設定padding來使文字看起來垂直居中

padding: 50px 20px;

3.2.微信小程式自定義placeholder的隱藏時機

在一個searchBar元件中,有一個自定的placeholder如下:

<!-- <view
​        wx:if="{{!inputValue.length}}"
​        class="placeholder" >
​        {{placeholder}}
​     </view> -->

原生的placeholder不是在觸發bindinput時隱藏,而是在輸入鍵盤按鈕點選時。使用inputValue.length來判斷顯示自定義的placeholder會在某些輸入法中導致拼音預覽和自定義placeholder重疊(因為拼音顯示的時候value值還沒變)

最後選擇棄用這個自定義placeholder,使用input元件的placeholder屬性,並使用placeholder-class來設定它的樣式。

3.3.關於微信小程式原生元件的坑

微信小程式原生元件文件

原生元件有camera、canvas、input (僅在focus時表現為原生元件) 、live-player、live-pusher、map、textarea、video、cover-view、cover-image。

所以當你用canvas畫圖表、使用地圖、播放視訊甚至做文字輸入時,都是可能遇到相關坑點的。

  1. 關於原生元件、元件之間的層級關係、

​ 原生元件的層級始終高於普通元件,不論普通元件的z-index設定了多少。

​ 後插入的原生元件可以覆蓋之前的原生元件。

​ 原生元件之間的相對層級關係可以通過z-index來調整。

​ 原生元件會遮擋vconsole彈出的除錯面板。

​ cover-view和cover-image可以覆蓋在部分原生元件上。

  1. cover-view的使用

​ cover-view在做地圖、畫布、視訊上的彈出層時是會用到的,但它有很多使用限制。

​ cover-view只能內嵌cover-view、cover-image、button,其他元素在真機上就會被cover-view給覆蓋住,如果想內嵌radio、picker等就只能自己用這3個可內嵌的元素來實現。

​ cover-view不支援iconfont,也不支援單邊border、background-imageshadowoverflow: visible等。

  1. input的使用

​ input在不聚焦時是佔位元素,會被原生元件遮擋,聚焦時才使用原生元件渲染。這就會出現input設定了更高的z-index,不聚焦時仍會被其他原生元件遮住。

​ 要解決這個問題,可以使用textarea來代替input。

​ 我的一個解決方案是,加一個標誌位來記錄input是否聚焦,當不聚焦時,顯示一個承載value值的cover-view(它需要繫結一個觸發聚焦的點選事件),聚焦時,就顯示input元件。

3.4.多個標籤頁之間的通訊方案

  1. 使用websocket

    WebSocket 教程 | 阮一峰

    https://juejin.im/post/5bcad1326fb9a05cda779d0b#heading-6

  2. 使用localstorage或者cookie

  3. 使用sharedworker

我遇到的問題是需要在新視窗開啟當前網站的新視窗時,能繼承上一個視窗的vuex的狀態樹裡的某些資料。這不需要和伺服器打交道,最好就在本地。

最後使用localstorage來做,在跳轉新視窗前更新localstorage,在新視窗根元件掛載時取出資料