前端常用代碼片段(五)

前端常用代碼片段(一) 點這裏
前端常用代碼片段(二) 點這裏
前端常用代碼片段(三) 點這裏
前端常用代碼片段(四) 點這裏

1.tap事件點透問題?

問題點擊穿透問題:點擊蒙層(mask)上的關閉按鈕,蒙層消失後發現觸發了按鈕下面元素的click事件

zepto的tap事件是綁定到document的,所以一般點擊tap事件都會冒泡到document纔會觸發。當點擊隱藏蒙層的時候默認也會手指觸發到蒙層下面的元素 執行事件

1. github上有個fastclick插件,用來規避click事件的延時執行

2. 用touchend代替tap事件並阻止掉touchend的默認行爲preventDefault()

//tap事件出現點透問題
$("#id").on("tap", function (event) {
    //很多處理比如隱藏什麼的
    event.preventDefault();
});

//touchend事件解決點頭問題
$("#id").on("touchend", function (event) {
    //很多處理比如隱藏什麼的
    event.preventDefault();
});

3:給tap事件裏面的隱藏蒙層方法執行的方法300毫秒延遲

$("#id").on('tap',function(ev){
    setTimeout(function(){
        $("#id").hide();
    },320)
})

2.固定定位佈局 鍵盤擋住輸入框內容?

1.通過綁定窗口改變事件,監聽鍵盤的彈出。

然後去改變固定定位元素的位置。默認鍵盤的寬度應該是頁面的2分之一。所以我們位移的距離改成鍵盤的二分之一就可以

window.onresize = function(){
    //$(".mian")就是固定定位的元素
    if($(".mian").css('top').replace('px','') != 0){
        $(".mian").css('top',0);
    }else{
        var winHeight = $(window).height();
        $(".mian").css('top',-(winHeight/4));
    }
}

2.通過定時器實時監聽是否觸發input。

如果觸發input框 就把固定定位,改變成靜態定位。這樣就會瀏覽器會總動把內容頂上去。

function fixedWatch(el) {
    //activeElement 獲取焦點元素
    if(document.activeElement.nodeName == 'INPUT') {
        el.css('position', 'static');
    } else {
        el.css('position', 'fixed');
    }
}

setInterval(function() {
    fixedWatch($('.mian'));
}, 500);

3.去掉字符左右空格

export const trimLeOrRi=(str)=>{
   //刪除左右兩端的空格  
   return str.replace(/(^\s*)|(\s*$)/g, ""); 
}

4.通過JS判斷一個數組

4.1 instanceof方法

instanceof 運算符是用來測試一個對象是否在其原型鏈原型構造函數的屬性

var arr = []; 
arr instanceof Array; // true

4.2.constructor方法

constructor屬性返回對創建此對象的數組函數的引用,就是返回對象相對應的構造函數

var arr = []; 
arr.constructor == Array; //true

4.3.toString.call

這種寫法,是 jQuery 正在使用的

Object.prototype.toString.call(obj).slice(8,-1) == Array

4.4.ES5新增方法isArray()

var a = new Array(123);
var b = new Date();
console.log(Array.isArray(a)); //true
console.log(Array.isArray(b)); //false

字符串也是有length屬性的

我們知道所有的Array都是有length屬性的,就算是空數組,那麼length 爲0,那麼字符串有沒有呢?接下來我們來驗證一下。

var str="sdfsd5565s6dfsd65sd6+d5fd5";
console.log(str.length)      // 26

結果是有的,所以我們在判斷類型時,不能單純拿有沒有length屬性來判斷是不是數組了,我們可以用下面的方法來判斷是否是數組:

var obj=[1,2] ;
console.log(toString.call(obj) === '[object Array]');

5. 刪除數組尾部元素

一個簡單的用來清空或則刪除數組尾部元素的簡單方法就是改變數組的length屬性值。

const arr = [11, 22, 33, 44, 55, 66];
// truncanting
arr.length = 3;
console.log(arr); //=> [11, 22, 33]
// clearing
arr.length = 0;
console.log(arr); //=> []
console.log(arr[2]); //=> undefined

6.使用對象解構來處理數組

可以使用對象解構的語法來獲取數組的元素:

const csvFileLine = '1997,John Doe,US,[email protected],New York';
const { 2: country, 4: state } = csvFileLine.split(',');

7.在switch語句中用範圍值

可以使用下面的技巧來寫滿足範圍值的switch語句:

//不推薦使用,只開闊眼界
function getWaterState(tempInCelsius) {
  let state;
  
  switch (true) {
    case (tempInCelsius <= 0): 
      state = 'Solid';
      break;
    case (tempInCelsius > 0 && tempInCelsius < 100): 
      state = 'Liquid';
      break;
    default: 
      state = 'Gas';
  }
  return state;
}
//推薦
function getWaterState2(tempInCelsius) {
  if (tempInCelsius <= 0) {
    return 'Solid';
  }
  if (tempInCelsius < 100) {
    return 'Liquid';
  }
  return 'Gas';
}

8.平鋪多維數組

方法1:es6
使用Spread操作,可以很容易去平鋪嵌套多維數組:

const arr = [11, [22, 33], [44, 55], 66];
const flatArr = [].concat(...arr); //=> [11, 22, 33, 44, 55, 66]
可惜,上面的方法僅僅適用於二維數組。不過,通過遞歸,我們可以平鋪任意維度的嵌套數組。

unction flattenArray(arr) {
  const flattened = [].concat(...arr);
  return flattened.some(item => Array.isArray(item)) ? 
    flattenArray(flattened) : flattened;
}

const arr = [11, [22, 33], [44, [55, 66, [77, [88]], 99]]];
const flatArr = flattenArray(arr); 
//=> [11, 22, 33, 44, 55, 66, 77, 88, 99]

方法2:遞歸

function flatten(arr){
  var res = [];
  for(var i=0;i<arr.length;i++){
    if(Array.isArray(arr[i])){
      res = res.concat(flatten(arr[i]));
    }else{
      res.push(arr[i]);
    }
  }
  return res;
}

方法3:reduce

function flatten(arr){
  return arr.reduce(function(prev,item){
    return prev.concat(Array.isArray(item)?flatten(item):item);
  },[]);
}

本節參考文章:5分鐘掌握JavaScript小技巧

9.如果數組列表太大,以下遞歸代碼將導致堆棧溢出。你如何解決這個問題,仍然保留遞歸模式?

var list = readHugeList();

var nextListItem = function() {
    var item = list.pop();

    if (item) {
        // process the list item...
        nextListItem();
    }
};

通過修改nextListItem函數可以避免潛在的堆棧溢出,如下所示:

var list = readHugeList();

var nextListItem = function() {
    var item = list.pop();

    if (item) {
        // process the list item...
        setTimeout( nextListItem, 0);
    }
};

堆棧溢出被消除,因爲事件循環處理遞歸,而不是調用堆棧。當nextListItem運行時,如果item不爲null,則將超時函數(nextListItem)推送到事件隊列,並且函數退出,從而使調用堆棧清零。當事件隊列運行超時事件時,將處理下一個項目,並設置一個計時器以再次調用nextListItem。因此,該方法從頭到尾不經過直接遞歸調用即可處理,因此調用堆棧保持清晰,無論迭代次數如何。

10.10!

function f(n){
    return (n > 1) ? n * f(n-1) : n
}

11.移動端底部input被彈出的鍵盤遮擋

Element.scrollIntoView():方法讓當前的元素滾動到瀏覽器窗口的可視區域內。

document.querySelector('#inputId').scrollIntoView();
//只要在input的點擊事件,或者獲取焦點的事件中,加入這個api就好了

這個api還可以設置對齊方法,選擇將input放在屏幕的上方/下方,類似的api還有: Element.scrollIntoViewIfNeeded(),這兩個是解決同一個問題的,選擇一個用就可以了。

window.addEventListener('resize', function() {
  if(
    document.activeElement.tagName === 'INPUT' ||
    document.activeElement.tagName === 'TEXTAREA'
  ) {
    window.setTimeout(function() {
      if('scrollIntoView' in document.activeElement) {
        document.activeElement.scrollIntoView();
      } else {
        document.activeElement.scrollIntoViewIfNeeded();
      }
    }, 0);
  }
});

本節參考文章:關於input的一些問題解決方法分享及評論

12.控制input顯/隱密碼

這個就很簡單了,只需更改input的type屬性值就可以了。可以看一下codepen的demo

//點擊函數,獲取dom,判斷更改屬性。
show(){
    let input=document.getElementById("inputId");  
    if(input.type=="password"){ 
      input.type='text';
    }else{
      input.type='password';
    } 
}

本節參考文章:關於input的一些問題解決方法分享

13.input多行輸入顯示換行

在使用textarea標籤輸入多行文本的時候,如果沒有對多行文本顯示處理,會導致沒有換行的情況,如果用戶需要換行...

解決方法:
只要在顯示內容的地方將該屬性設置爲 white-space: pre-line 或者 white-space:pre-wrap,多行文本就可以換行了。

備註:white-space 屬性用於設置如何處理元素內的空白,其中包括空白符和換行符。

clipboard.png

14.輸入框首尾清除空格-trim()

輸入框清除首尾空格是input較爲常見的需求,通常在上傳的時候將首尾空格去除掉。

原生清除方法:

//原生方法獲取值,清除首尾空格返回一個新的字符串
var str2 = document.getElementById("inputId").trim();

Vue清除方法:

<input v-model.trim="msg">

15.在input中監聽鍵盤事件

在用戶登錄或者搜索框的時候,一般都會監聽鍵盤事件綁定回車按鍵,來執行登錄/搜索 等操作。

原生綁定:

<input onkeydown="keydownMsg(event)" type="text" />
function keydownMsg(key) {
    keyCode = key.keyCode; //獲取按鍵代碼
    if (keyCode == 13) {  //判斷按下的是否爲回車鍵
        // 在input上監聽到回車 do something
    }
}

Vue按鍵修飾符
Vue爲監聽鍵盤事件,提供了按鍵修飾符,並且爲常用的按鍵提供了別名,使用方法如下:當回車按鍵在input中被按下的時候,會觸發裏面的函數。

<input @keyup.enter="enterActive">

16.元素滾動到瀏覽器窗口的可視區域

Element.scrollIntoView()方法讓當前的元素滾動到瀏覽器窗口的可視區域內。
Element.scrollIntoViewIfNeeded()方法也是用來將不在瀏覽器窗口的可見區域內的元素滾動到瀏覽器窗口的可見區域。但如果該元素已經在瀏覽器窗口的可見區域內,則不會發生滾動。

因而再有什麼回到頂部、去到置頂位置和鍵盤彈出擋住輸入框之類的需求,都可以簡單解決了。

scrollIntoView

scrollIntoView只接受一個參數,但接受兩種類型的參數,分別是Boolean型參數和Object型參數。

  • 先說Boolean型參數,參數可以使true和false。如果爲true,元素的頂端將和其所在滾動區的可視區域的頂端對齊。若爲false,元素的底端將和其所在滾動區的可視區域的底端對齊。

    <body>
        <div class="chunk"></div>
        <div class="btn-top">up</div>
        <div class="btn-bottom">down</div>
        <script>
        const up = document.querySelector('.btn-top');
        const down = document.querySelector('.btn-bottom');
        const test = document.querySelector('.chunk');
        up.addEventListener('click', function() {
          test.scrollIntoView(true);
        });
        down.addEventListener('click', function() {
          test.scrollIntoView(false);
        });
        </script>
    </body>
  • Object型參數,這個對象有兩個屬性,屬性block 值可以是start和end;屬性behaviorautoinstantsmooth

    up.addEventListener('click', function() {
      test.scrollIntoView({
        block: 'start',
        behavior: 'smooth'
      });
    });
    down.addEventListener('click', function() {
      test.scrollIntoView({
        block: 'end',
        behavior: 'smooth'
      });
    });

scrollIntoViewIfNeeded

scrollIntoViewIfNeeded可以接受一個Boolean型參數,和scrollIntoView不同,true爲默認值,但不是滾動到頂部,而是讓元素在可視區域中居中對齊;false時元素可能頂部或底部對齊,視乎元素靠哪邊更近。

兩者主要區別有兩個。首先是scrollIntoViewIfNeeded是比較懶散的,如果元素在可視區域,那麼調用它的時候,頁面是不會發生滾動的。其次是scrollIntoViewIfNeeded只有Boolean型參數,也就是說,都是瞬間滾動,沒有動畫的可能了。

兼容性的話

scrollIntoView:Boolean型參數幾乎隨便用了
scrollIntoViewIfNeeded:IE和FireFox全紅,移動端基本都OK

詳細見原文

本節參考文章:scrollIntoView...

17.ES6 中的 解構運算符 ...

... 每次只能展開最外層的數組,被 [].concat 後,arr 就扁平化一次。

function flatten(arr){
  while(arr.some(item => Array.isArray(item))){
    arr = [].concat(...arr);
  }
  return arr;
}

const arr = [1, [2, [3, 4]]];
console.log(flatten(arr));

本節參考文章:數組扁平化

18.reverse數組

const reverse = xs => {
  if (xs.length === 1) return xs;
  const [head, ...tail] = xs;
  return reverse(tail).concat(head);
};

reverse([1,2,3,4,5,6]) // [6,5,4,3,2,1]

19.正則實現trim()功能

function myTrim(str) {
  let reg = /^\s+|\s+$/g;
  return str.replace(reg, "");
}
console.log(myTrim('    asdf    '));

本節參考文章:2018前端面試總結...

20.js 數組每一項去除空格

var s = "222 , 3334,         3666    "

s.replace(/\s/g,"") // "222,3334,3666"
發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章