能夠看到下面兩張圖,圖1搜索框爲fixed固定在頂部,滾動沒有任何問題。javascript
圖2當光標進入搜索框時,ios自做聰明的把光標定位到中間,而且fixed屬性被自動修改爲了absolute。此時注意滾動頁面的話,會發現本來fixed的搜索框跟着文檔一塊兒滾動了。css
再仔細觀察ios下的一些特色,ios爲了讓input垂直居中,甚至還滾動了滾動條,本來看不到的上半段產品的內容也漏出來了。html
在網上搜索事後,大部分都是轉載的這一篇文章,甚至配圖都是拿別人原來的:java
http://efe.baidu.com/blog/mobile-fixed-layout/jquery
這個解決方案,主要用到了一個div包裹了整個能夠滾動的部分,而後不能滾動的部分就固定在底部,不失爲一種不錯的解決方案,惋惜個人搜索框不是一直固定在頂部,頁面滾動到下面的時候纔出現搜索框置頂,頁面回到最頂部時搜索框要消失,而且我須要監控window.onscroll,作自動翻頁的ajax請求等等,最後這個方案就無法使用了。即便要使用的話修改量應該也很大。android
在參考了下面這篇文章後,想到了新的思路:ios
http://www.cnblogs.com/yexiaochai/p/3561939.htmlweb
文章中提到,ajax
咱們想到這麼一個場景,若是咱們能監控到鍵盤的行爲,若是能的話,咱們即可以app
① 鍵盤彈出時候將fixed元素設置爲static(最後我設置成absolute)
② 鍵盤消失時候將fixed元素設置爲fixed
基於這個想法,進行一系列的測試,首先static的意思是迴歸文檔,致使整個搜索框都找不到了,由於可能回到文檔最底部去了。因此static不可用,那麼absolute呢,只要設置成absolute而後設置合適的top就能夠了。思路是,根據滾動條獲取top,而後經過$(window).height()獲取屏幕可見區域的高度,估計虛擬鍵盤大概是一半,那麼就除以2,而後減去搜索框的高度,就得到了偏移量。
最後top=top-偏移量,便可。
想法是不錯的,實現起來效果如何呢。觀察以前的圖2,咱們能夠猜想ios移動了滾動條,始終爲了保證input處於垂直居中的位置,因此哪怕咱們給他設置了top-偏移量,最後ios仍是又往上滾動了一下。真是又愛又恨啊,你這麼聰明你爲何搞這麼個BUG出來呢。
仍是回到圖2去進行測試,當ios經過滾動條將input居中後,ios就不會再繼續監控那個input了,此時咱們隨便拖拉頁面,input都不會再回到中間,基於這個想法,那麼咱們經過js延遲一會來從新設置scroll可不能夠呢?
帶着這樣的想法進行了一些測試,最後解決方案以下
1. 監控input的focus和blur事件,進入時設置搜索框爲absolute;
2. 獲取當前scroll的高度,設置給搜索框的top;
3. 設置延遲函數,從新滾動滾動條到當前的top;
4. 離開input時恢復原來的fixed佈局。
測試iphone6s ios 9.x 沒問題
android 隨便找了一臺同事的vivo測試 沒問題
暫時就測了2臺手機
<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN" "http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd"> <html xmlns="http://www.w3.org/1999/xhtml"> <head > <title></title> <meta name="viewport" content="width=device-width, initial-scale=1.0"> <meta http-equiv="Pragma" content="no-cache"> <meta http-equiv="Cache-Control" content="no-cache"> <meta http-equiv="Expires" content="0"> <meta name="viewport" content="width=device-width, initial-scale=1.0, user-scalable=0, minimum-scale=1.0, maximum-scale=1.0" /> <meta name="viewport" content="initial-scale=1, width=device-width, maximum-scale=1, user-scalable=no" /> <meta name="viewport" content="initial-scale=1.0,user-scalable=no,maximum-scale=1" media="(device-height: 568px)" /> <meta name="apple-mobile-web-app-capable" content="yes" /> <meta name="apple-touch-fullscreen" content="yes" /> <meta name="full-screen" content="yes" /> <meta name="apple-mobile-web-app-status-bar-style" content="black" /> <meta name="format-detection" content="telephone=no" /> <meta name="format-detection" content="address=no" /> <style> #float-search{ height:40px; background:red; position:fixed; top:0; width:100%; } #float-search input{ height:36px; border:1px solid #ccc; width:100px } </style> </head> <body> <div class="warp"> <p>1</p> <p>2</p> <p>3</p> <p>4</p> <p>5</p> <p>6</p> <p>7</p> <p>8</p> <p>9</p> <p>10</p> <p>1</p> <p>2</p> <p>3</p> <p>4</p> <p>5</p> <p>6</p> <p>7</p> <p>8</p> <p>9</p> <p>10</p> <p>1</p> <p>2</p> <p>3</p> <p>4</p> <p>5</p> <p>6</p> <p>7</p> <p>8</p> <p>9</p> <p>10</p> <p>1</p> <p>2</p> <p>3</p> <p>4</p> <p>5</p> <p>6</p> <p>7</p> <p>8</p> <p>9</p> <p>10</p> <p>1</p> <p>2</p> <p>3</p> <p>4</p> <p>5</p> <p>6</p> <p>7</p> <p>8</p> <p>9</p> <p>10</p> <p>1</p> <p>2</p> <p>3</p> <p>4</p> <p>5</p> <p>6</p> <p>7</p> <p>8</p> <p>9</p> <p>10</p> <p>1</p> <p>2</p> <p>3</p> <p>4</p> <p>5</p> <p>6</p> <p>7</p> <p>8</p> <p>9</p> <p>10</p><p>1</p> <p>2</p> <p>3</p> <p>4</p> <p>5</p> <p>6</p> <p>7</p> <p>8</p> <p>9</p> <p>10</p> <p>1</p> <p>2</p> <p>3</p> <p>4</p> <p>5</p> <p>6</p> <p>7</p> <p>8</p> <p>9</p> <p>10</p> <p>1</p> <p>2</p> <p>3</p> <p>4</p> <p>5</p> <p>6</p> <p>7</p> <p>8</p> <p>9</p> <p>10</p> <p>1</p> <p>2</p> <p>3</p> <p>4</p> <p>5</p> <p>6</p> <p>7</p> <p>8</p> <p>9</p> <p>10</p> <p>1</p> <p>2</p> <p>3</p> <p>4</p> <p>5</p> <p>6</p> <p>7</p> <p>8</p> <p>9</p> <p>10</p> </div> <div id="float-search"> <input type="text" id="Text1" name="q" x-webkit-speech="" placeholder="搜索商品" autocomplete="off" value=""> </div> <div id="debugmsg" style="position: fixed; top: 20%; right:100px;width: 100px; height: 100px; border: 1px solid red;"> </div> </body> <script src="http://cdn.bootcss.com/jquery/3.1.0/jquery.js"></script> <script> function printStyles(elem) { var dtop = $(document).scrollTop(); var position = $("#"+elem).css("position"); var top = $("#"+elem).css('top'); var height = $(window).height();//整個窗口高 height = height / 4; var html = 'top:' + dtop + "<br/>" + "bodyTop:" + document.body.scrollTop + "<br/>" + "position:" + position + "<br/>" + "top:" + top + "<br/>" + "height:" + height; return html; } $().ready(function () { window.onscroll = function() { //測試代碼 $("#debugmsg").html(printStyles('float-search')); //end 測試代碼 $("#float-search input").focus(function() { var top = $(document).scrollTop(); var height = $(window).height();//整個窗口高 height = height / 4; $("#float-search").css("position", "absolute"); $("#float-search").css("top",top); setTimeout(function() { $("html,body").animate({scrollTop:top},5);//1000是ms,也能夠用slow代替 },5); //測試代碼 $("#debugmsg").html(printStyles('float-search')); //end 測試代碼 }).blur(function() { $("#float-search").css("position", "fixed"); $("#float-search").css("top","0"); //測試代碼 $("#debugmsg").html(printStyles('float-search')); //end 測試代碼 }); } }); </script> </html>