仿淘寶首頁產品分類菜單欄的設計


這幾天一直在給一家電商搞前端開發,首頁做DIV頁面重構的時候自然地做到每個電商平台都會有的部分——產品分類菜單欄,如下圖截的是淘寶的效果:

其實實現鼠標移到左側主分類(我們暫且稱之為A部分)便顯示出右側詳細分類部分(稱之為B部分)的功能並不困難,但這里不得不說主流的電商平台在這個地方都有個很好的用戶體驗,就是B部分的底部總不會被瀏覽器底部遮住,看看下面的圖片分析:

情況⑴——若B底部是不會被瀏覽器遮住的,那么A和B頂部默認在同一水平線上:

情況⑵——若B底部有可能超過瀏覽器底部,導致B下方內容被遮住的話,則采取“摒棄A和B頂部在同水平線上”的顯示方式,以抬高B位置(抬多高呢?嗯,只要B底端剛好貼住瀏覽器底端,或者比瀏覽器低端高一點點就行)來解決問題:

 

下面先說下基礎架構和功能的實現吧。首先架構很簡單,不外乎是寫一層A的DIV(class="maintip"),再寫一層對應的B的DIV(class="tips"),HTML如下:

 

 1   <div class="maintip"><a href="#">服裝類</a></div>
 2   <div class="tips">
 3      <p>
 4      <a href="http://www.baidu.com">各種衣服啊</a>
 5      </p> <br/><br/><br/><br/><br/><br/><br/><br/><br/>
 6      <p>
 7      <a href="http://www.baidu.com">來百度一下找衣服啊</a>
 8      </p>
 9   </div>
10   
11   <div class="maintip">家電數碼</div>
12   <div class="tips">
13      <p>
14      M8賣那么貴,HTC請你繼續flop好么
15      </p>
16   </div>
17   
18   <div class="maintip">美食</div>
19   <div class="tips">
20      <p>
21      葡萄酒,白酒,啤酒 <br/><br/><br/><br/><br/><br/><br/><br/><br/>
22      我特么只是想把這個框拉長
23      </p>
24   </div>
25   
26   <div class="maintip">玩具</div>
27   <div class="tips">
28      <p>
29      <a href="http://www.123.com">智力魔方啊神馬的你要的都有哦</a>
30      </p>
31   </div>
View Code

 

 定義下CSS:

 1 <style type="text/css">
 2 body{
 3     margin:100px;
 4 }
 5 .maintip{
 6     position:relative;
 7     z-index:1;
 8     border:1px solid #E5D1A1;
 9     text-align:center; 
10     width:200px;
11     background:#FFFDD2;  
12     height:35px;
13     line-height:30px;
14 }
15 .tips{
16     position:absolute;
17     z-index:2;
18     width:800px;
19     min-height:100px;
20     border:1px solid #E5D1A1;
21     background:#fff;
22     display:none; 
23 }
24 </style>
View Code

 

注意B部分的position設為absolute。(z-index是為了讓A壓在B上面,A被選中時,其border-right是不上色的,且要確保該邊壓在B上面)

接着寫下JQuery代碼讓鼠標移到A的某行,就顯示出對應的B的那行,且默認A和B等高:

 1 $(function(){
 2  
 3     $(".maintip").each(function(index){   //遍歷A部分,注意這里綁定事件用了index參數
 4         $(this).mouseover(function(){   //鼠標經過A時觸發事件
 5             var obj=$(this).offset();   //獲取被鼠標經過的A的偏移位置,offset()是個好東西,不懂的朋友得去了解下
 6             var xobj=obj.left+200+"px"; //后面要讓B水平偏移的距離,這里的“200”是可自定義的,當然你可以改為$(this).width()來獲得跟A一樣的寬度
 7             var yobj=obj.top+"px";     //后面要讓B垂直偏移的距離
 8             $(this).css({"width":"200px","z-index":"9999","border-right":"none","background":"#fff"});  //A改變樣式,變為選中狀態的效果
 9             $(".tips:eq("+index+")").css({"left":xobj,"top":yobj}).show();   //對應的(這里利用了索引)B改變樣式並顯示出來
10             })
11         .mouseout(function(){     //鼠標離開A時觸發的事件
12             $(".tips").hide();     //B隱藏
13             $(this).css({"width":"200px","z-index":"1","border":"1px solid #E5D1A1","background":"#FFFDD2"})   //A變回原始樣式
14         })
15     })
16     
17          $(".tips").each(function(){  //遍歷B
18             $(this).mouseover(function(){  //鼠標經過B時觸發事件
19             $(this).prev(".maintip").css({"width":"200px","z-index":"9999","border-right":"none","background":"#fff"})  //對應的A變為選中狀態效果
20             $(this).show();  //A不要隱藏了,解決因為上面寫的鼠標離開A導致A隱藏
21         })
22         .mouseout(function(){  //鼠標離開B觸發事件,其實就是讓B隱藏,同時A變為原始狀態
23             $(this).hide();   
24             $(this).prev(".maintip").css({"width":"200px","z-index":"1","border":"1px solid #E5D1A1","background":"#FFFDD2"});
25         }) 
26     })
27 })

 

 現在效果如下:

 但是現在還沒有解決一個問題,就是如果B超過了瀏覽器下方,導致B的部分內容被遮住怎么辦,如下圖所示:

其實問題也不難解決,最終措施不外乎是當B超過瀏覽器底部時,把B往上挪到“B底部與瀏覽器底部齊平”的位置,如下圖:

而具體要挪多高,這個只要獲取瀏覽器當前可視區域的高度就能輕松獲得:

如上圖所示,B的頂部距離瀏覽器頂部的距離只要設為“win_h - b_h”即可解決問題。那么我們着手修改下js代碼:

 1 $(function(){
 2 
 3 $(".maintip").each(function(index){
 4 var tip_height=$(".tips:eq("+index+")").height();
 5 $(this).mouseover(function(){
 6 var win_height=$(window).height();    //獲取瀏覽器當前可視區域高度
 7 var obj=$(this).offset();    
 8 var wobj=$(this).width();
 9 if(obj.top+tip_height<win_height){    //判斷B底部是否超過瀏覽器底部
10     //沒超過,按默認A和B頂端偏移位置一致即可
11     var xobj=obj.left+wobj+"px";
12     var yobj=obj.top+"px";
13 }
14 else{
15     //超過了,那么抬高B頂部位置
16     var tip_top=win_height-tip_height;
17     var xobj=obj.left+wobj+"px";
18     var yobj=tip_top+"px";
19 }
20 $(this).css({"width":"200px","z-index":"9999","border-right":"none","background":"#fff"});
21 $(".tips:eq("+index+")").css({"left":xobj,"top":yobj}).show();
22 }).mouseout(function(){
23 $(".tips").hide();
24 $(this).css({"width":"200px","z-index":"1","border":"1px solid #E5D1A1","background":"#FFFDD2"})
25 })
26 
27  })
28  
29  $(".tips").each(function(){
30 $(this).mouseover(function(){
31 $(this).prev(".maintip").css({"width":"200px","z-index":"9999","border-right":"none","background":"#fff"})
32 $(this).show();  
33 }).mouseout(function(){
34 $(this).hide(); 
35 $(this).prev(".maintip").css({"width":"200px","z-index":"1","border":"1px solid #E5D1A1","background":"#FFFDD2"});
36   }) 
37  
38       })
39 })

在JQ里使用$(window).height()來獲取瀏覽器可視區域高度是解決本章所提問題的關鍵。

最后輕松搞定:

 

我認為一個優秀的前端工程師總會舍得以“更好的體驗”為目標來絞盡腦汁、壓榨自己,雖然我沒達到“優秀前端工程師”的高度,但依舊相信一直強迫自己去實現更多的功能,總會讓我有所建樹,共勉啦 :)

donate


免責聲明!

本站轉載的文章為個人學習借鑒使用,本站對版權不負任何法律責任。如果侵犯了您的隱私權益,請聯系本站郵箱yoyou2525@163.com刪除。



 
粵ICP備18138465號   © 2018-2025 CODEPRJ.COM