POPSブログ

jQuery HoverMenu/10

168

  Category:  jquery2012/11/14 pops 

前ページ掲載の jquery.backgroundpos.js 使用の、HoverMenu 9 のサンプル同様「サブメニュー」を加えた構造にして「サブメニュー」を伸縮表示します。多少の不具合があったので改良をしたものです。(IE6非対応)

 

jQuery HoverMenu 10

新たに「CSS3陰影」を加えました。違いはサンプルを操作してください。JS自体は単純で短いのですが設定が面倒である。これもお病気系の方向けなんでしょうネ。


▼ IE9で閲覧の方に、サンプルの陰影を解除ください

図に示すように、IE9のバグのために文字に陰影をつけた部分が黒くなります。「タイトル陰影の切替」で陰影(shadow)を解除ください。「互換表示」にはしないで操作ください。


 

標準的な、li リストの中に配置の例 (サブメニュー付き)、サンプル11


下のサンプルを「HOVER」ください。メニュー背景を移動変化させます。(IE6非対応)

jquery.backgroundpos.js v1.1.0、jquery-1.6.4.js、を使用。

原則、CSS3の装飾の有効な、(IE9) Safari Firefox Chrome Opera、対応です。「IE7.8」は角丸無しです。

1. 高さ60 CSS3角丸 Shadow処理、固定幅、中央表示、(hover-menu11.js)



ベース背景色の切替 :                   / ベース背景画像 : N A X

要素背景画像の切替 :        

要素背景色の切替 : 指定色1 指定色2 指定色3 指定色4 指定色5 指定色6 複数色1 複数色2

サブメニュー背景色切替 : 白色 灰色 黒色 / 透明度 : 透明度0.5 透明度1

アクティブ背景色の切替 :                 / アクティブ文字 :        

タイトル陰影の切替 : SHADOW 有り SHADOW 無し (初期はSHADOW有り)

原則、CSS3の装飾の有効な、(IE9) Safari Firefox Chrome Opera、対応です。「IE7.8」は角丸無しです。
IE10 は正常に表示されるものとおもいます。但し未確認です。



HTML JS CSS について


HTML CSSは前のページのものに「CSS3で陰影」をいれ、アニメ箇所を減らして改良したものです。少しデザインも多くしてあります。「CSS3で陰影」を削除すればほぼ同じものと言えるでしょう。基本的には、CSS、JSともほぼ同様な構成です。

IE9でバグが出たため大変複雑な説明になります。それでも興味のある方はお読みください。私ならやめます。
【追記】2012/11/17: 多少簡単なものを用意します。


HTML

li要素に「main-menuクラス」入れ子のul要素に「sub-menuクラス」を設定しています。構造は同じにしてください。


<div id="hover-menu">
	<ul>
	<li class="main-menu active">
		<a href="リンクURL"><h3>メインリンク名</h3><br /><p>文字</p></a>
	</li>
	<li class="main-menu">
		<a href="リンクURL"><h3>メインリンク名</h3><br /><p>文字</p></a>
		<ul class="sub-menu">
		<li><a href="リンクURL">サブリンク</a></li>
		<li><a href="リンクURL">サブリンク</a></li>
		<li><a href="リンクURL">サブリンク</a></li>
		<li><a href="リンクURL">サブリンク</a></li>
		<li><a href="リンクURL">サブリンク</a></li>
		</ul>
	</li>
	<li class="main-menu">
		<a href="リンクURL"><h3>メインリンク名</h3><br /><p>文字</p></a>
		<ul class="sub-menu">
		<li><a href="リンクURL">サブリンク</a></li>
		<li><a href="リンクURL">サブリンク</a></li>
		<li><a href="リンクURL">サブリンク</a></li>
		<li><a href="リンクURL">サブリンク</a></li>
		<li><a href="リンクURL">サブリンク</a></li>
		</ul>
	</li>
	<li class="main-menu">
		<a href="リンクURL"><h3>メインリンク名</h3><br /><p>文字</p></a>
	</li>
	<li class="main-menu">
		<a href="リンクURL"><h3>メインリンク名</h3><br /><p>文字</p></a>
	</li>
	</ul>
</div>

注意、事前にjquery.jsの読み込みのあとで、プラグイン jquery.backgroundpos.js を読み込んでおく必要があります。
JS名、ID名、クラス名、activeクラス、などを変更の場合は、JS、CSSの該当の箇所を修正の必要があります。


JS 標準 (上のサンプルの動作と同じもの、IE6では動作しません)

hover-menu11.js、(簡易記述です、読み込んだら実行します)

アニメ部分の設定が jquery.backgroundpos.js 用です。


//hover-menu11.js
//日本語
//プラグインjquery.backgroundpos.js 1.1.0を使用
//sub-menuのアニメを削除/IE78も動作する

(function($){

	$(function(){

		//背景画像中央合わせの x値=(アイテム幅-画像幅)/2
		//現在の計算値、x=(200-110)/2=-45

		//menuの高さ
		var menu_H=60;
		//sub-menuの配置位置position-y/CSSとあわせる
		var sub_pos_X=50;
		//サブメニュー下のスペース 5-10
		var bottom_sps=10;

		//中央揃えの幅を取得して自動で幅などのCSSを決める
		var center_set="set";//set none

		//色データ
		var active_color="#AAAAAA";
		var active_txcolor="#FFFFFF";
		var active_bordercolor="#FFFFFF";//ベースの色に注意
		//複数色データ
		var colordata=["#DB7093","#F4A460","#BC8F8F","#FF69B4","#778899","#00CED1","#9370DB","#6496ED","#CCCCCC",'#EEEEEE'];

		var item=[];
		var subitem_H=[];
		var menu_base=$("#hover-menu");

		//ul要素の幅を決定して設定を実行する
		if (center_set=='set') {
			var ul_W=menu_base.children("ul").width();
			menu_base.children("ul").css({'float':'none'});//追加
			menu_base.css({'text-align':'center'});
			menu_base.children("ul").css({'width':ul_W,'margin':'0 auto'});
		}

		//色データで背景着色などの処理
		$(".main-menu").each(function(i){

			item[i]=$(this);

			//要素を個別に複数色に着色
			item[i].css({'background-color':colordata[i]});

			//高さの取得/無ければnull
			subitem_H[i]=item[i].find('.sub-menu').height();

			//sub-menuのある場所に▼を挿入する
			if (item[i].find('ul').hasClass('sub-menu')) {
				var ti_elm=item[i].find('h3');
				ti_elm.text(ti_elm.text() + ' ▼');
			}

			//activeの処理、activeクラスがあるか
			if (item[i].hasClass('active')) {

				//active 背景着色
				//item[i].css({'background-color':active_color});

				//サブメニューが無い場合、高さがnull
				if (!subitem_H[i]) {

					//active 背景ポジションの変更
					//item[i].css({'background-position':'-45px -80px'});

					//active-arrowクラスを与える
					item[i].addClass("active-arrow");

				}

				//active 文字の色を変える
				item[i].find('h3').css({'color':active_txcolor});

				//active ボーダーを設定/高さボーダー分修正
				item[i].css({'height':menu_H-2,'border-top':'2px ' + active_bordercolor + ' solid'});

			}

			//サブメニュー一旦けす
			item[i].find('.sub-menu').css({'display':'none'});

			//hover-action
			item[i].hover(
				//over
				function() {

					//activeでサブメニューが無い、何もしないで戻る
					if (item[i].hasClass('active') && !subitem_H[i]) {return}

					//一旦消す
					item[i].find('.sub-menu').css({'display':'block'});

					//処理
					item[i].addClass("hovered");

					//伸ばす高さを計算
					var h=0;//初期値0
					if (subitem_H[i]) {h=subitem_H[i]+(sub_pos_X-menu_H)+bottom_sps;}


					//プラグインアニメ実行/基準変更
					item[i].find('.sub-menu').css({'display':'block'});
					item[i].animate({backgroundPosition:'-45px -60px','height':menu_H+h},600,function (){
						//
					});
				},
				//out
				function() {

					//activeでサブメニューが無い、何もしないで戻る
					if (item[i].hasClass('active') && !subitem_H[i]) {return}

					//処理
					item[i].removeClass("hovered");

					//sub-menuがあれば
					if (subitem_H[i]) {

						//アイテム高さを戻す
						item[i].animate({'height':menu_H},300,function (){

							//sub-menu消す
							item[i].find('.sub-menu').css({'display':'none'});
							//プラグインアニメ実行
							item[i].animate({backgroundPosition:'-45px 0px'},400);
								//
							});

						//});
					} else {
						//sub-menuが無ければ
						//プラグインアニメ実行
						item[i].animate({backgroundPosition:'-45px 0px'},400,function (){
							//
						});

					}

				}

			);

		});

	});
})(jQuery);

JS中の説明など削除する、インデントなども少なくすれば、若干早くなります。


使用jqueryバージョンなどの注意点

動作の関係で、jquery バージョン 1.7 1.8系を、プラグイン jquery.backgroundpos.js バージョン v1.1.0、の組み合わせを推奨します。組み合わせを違わせますと「IE7 8」で正常な動作をしません。
プラグインの組み合わせ詳細は、前のページを参照ください。

【参考】当方の記事: jQuery HoverMenu 8


JSの簡単な説明

従来どおり「main-menuクラス」は背景画像を「プラグイン」でアニメ、「sub-menuクラス」の高さを通常のアニメ処理しているだけです。背景画像の動きに合わせて、out処理での順序を変更しています。
初期設定などはJS上部を読んでください。


説明図


● JSの設定

1.要素の高さ及びサブメニューの位置の値を入力します。CSSの値とあわせること。
2.中央配置にする場合は set を入力する。初期はIE7も含み、set 状態です。IE7は説明を読んでください。
3.メニュー要素の着色、active時のデザインなどの変更は、図参照の上に、下記の説明を読んでください。


● メニューを中央配置にする。

この記載のJSは当初から「IE6.7」「中央配置」になっています。

JS上部の設定を set にして下さい。「IE67」を除き中央にセットされます。
「IE67」をも「中央配置」にしたい場合は、下の「JSでの自動で中央揃えにする設定の補正と追加説明」を参照ください。


center_set="";//set none


● メニューを右配置にする。

中央配置の set を解除してください。左配置になります。右配置の場合は float:rightをCSSで記述ください。他のCSSの影響で、左配置にならない場合はfloat:leftを明示すれば直るとおもいます。


#hover-menu ul {
list-style:none;
float:right;
}


● メニューの色、active時のデザイン変更

初期設定は、複数色で染めるようになっています。解除すれば「main-menuクラスであるli要素」のCSSの色が反映されます。
active時の変更は、図のように色々な変更が可能です。但し文字がありますのでいかに読み易くするかが問題です。


解除する場合は//を記入してください、実行しません、反対の場合は//を削除ください

//要素を個別に複数色に着色します、解除すればCSSの色が反映される
item[i].css({'background-color':colordata[i]});

---------------------------------------------

//sub-menuのある場所に▼を挿入する、必要でなければ削除するか、//を入れる
if (item[i].find('ul').hasClass('sub-menu')) {
	var ti_elm=item[i].find('h3');
	ti_elm.text(ti_elm.text() + ' ▼');
}

---------------------------------------------

//active 背景着色、登録の色でそめます、初期では設定していません
//item[i].css({'background-color':active_color});

---------------------------------------------

//active 背景ポジションの変更、背景画像の位置変更してデザインを変える方法です
//item[i].css({'background-position':'-45px -80px'});

---------------------------------------------

//active-arrowクラスを与える、別の背景画像を読み込んでセットします、CSSで変更します

item[i].addClass("active-arrow");

この場合、上のactive 背景ポジションの変更は強制的に無効になります
active要素はアニメしませんので初期設定の位置のままです

#hover-menu .main-menu.active-arrow {
background:url('/main/images/arrow_8b.png') no-repeat;
background-position:center bottom;
}

サブメニューのある要素にはアニメの関係で設定なりません

---------------------------------------------

//active 文字の色を変える、登録の色でそめます、初期では白色
item[i].find('h3').css({'color':active_txcolor});

---------------------------------------------

//active ボーダーを設定、要素上部のボーダーです、登録の色でそめます
item[i].css({'height':menu_H-2,'border-top':'2px ' + active_bordercolor + ' solid'});

常時設定しておいたほうが良い、
border-bottomでボトム設定は可能です、要素の大きさが下に大きくなります

---------------------------------------------

//プラグインアニメ実行、変更は可能です
item[i].animate({backgroundPosition:'-45px 0px'},400);

X値は -45px になっています、次ぎの式で計算しました
背景画像中央合わせの x値=(アイテム幅-画像幅)/2

サンプル背景画像の幅は 200 ですので、要素の最大幅は 200 までです
プラグインアニメでは%等も使用できますが思い道理には行きません、px単位で動かしたほうが賢明

以上設定などの説明でした、変更は自己責任で行ってください。


● active要素の構成とアニメ

active要素の構成は上の説明のように、修飾が可能ですが、原則アニメはしません。但しサブメニューのある要素では active であってもアニメを実行します。


● サブメニューの構成

説明図


1. サブメニューの幅は要素の幅と同じが標準です。(アニメの関係で、overflow:hidden が設定されていますので広げられません)
2. 背景色及び、透明度などで少々加工できますが、白色、透明度なしがリンク文字が見やすくなります。
3. 内部デザインなどは使用者の自由です。サブメニューは position:absolute であることに注意ください。


● 背景画像アニメ位置の変更

背景画像の種類、デザインなどによりアニメ位置の変更をしたい場合があります。



プラグインアニメの書式
$('アニメ対象').animate({backgroundPosition:'X方向値 Y方向値'});

記述例
item[i].animate({backgroundPosition:'-45px -60px','height':menu_H+h},600,function (){
	//
});

X方向値 -45px は現在の要素の大きさと画像大きさから算出した中央値です
Y方向値 -60px は上方に移動させています、変更可能です
600 はアニメのスピードです、変更可能です

px単位で移動したほうが良い、他に% topなどと使用できるが、組み合わせたりすると思い通りに動かない
要素の高さを変更しても、Y方向値の変更で同じアニメを実行可能です


● 要素幅の変更

現在110pxの幅になっている要素幅の変更をする場合は、CSSで「幅110px」部分を希望の幅に合わせてください。「クラス sub-menu li」が少し幅が狭いので注意。
背景画像の形状により X位置が 0 又は中央にあったほうがキレイなものもあります。中央の場合は計算によりX位置を算出して、JS及びCSSのポジションX位置を修正します。
X位置が 0 であっても良いものは全て X位置 0 に修正してかまいません。CSSでいつでも幅の変更ができます。


中央あわせの場合

背景画像のX位置
item[i].animate({backgroundPosition:'-45px -60px',..................

新たに計算する
item[i].animate({backgroundPosition:'新値px -60px',..................

-------------------------------------------

画像によっては原点 0 に有っても良いものもある

item[i].animate({backgroundPosition:'0px -60px',..................


● 要素高さの変更

初期値は60pxです、CSSの60pxの部分を希望の高さにします。サブメニューは position:absoluteですから調整します。タイトル文字などのバランスは好みで変更する。
JS先頭部分の高さの値を変更します。
伴いアニメ及びCSSの、Y位置をアニメ状態を確認しながら好みの位置に調整します。


アニメの状態をみながらY位置を調整
item[i].animate({backgroundPosition:'0px 好みの位置',..................

タイトルが読めるようにも考慮する
タイトルの陰影は黒ですが、場合によっては白のほうが良いかも知れない
IEは陰影はつけていないので無視する


かなり繁雑で面倒な作業になります。変更は、使用者の自己責任で行ってください。


CSS (IE78にも対応した場合のものです)

IE7でも「中央配置」の設定になっています。「中央配置」にしない場合は下記の「JSでの自動で中央揃えにする設定の補正と追加説明」を参照ください。

hover-menu11.css

li要素の幅は「サブメニュー」が有りますので「固定」にするが原則です。中央配置はJSで行ったほうが便利です。


/* hover-menu11.css 動作簡略形、日本語 */

#hover-menu {
display:block;
width:640px;
height:60px;
background-color:transparent;
}

/* 幅を取得のためinline-blockにしている */
#hover-menu ul {
list-style:none;
display:inline-block;
width:auto;
height:60px;
padding:0;
margin:0;
/float:left;/* IE7 */
}
#hover-menu ul li {
list-style:none;
position:relative;
display:inline-block;
width:110px;
height:60px;
margin:0 2px;
padding:0;
text-align:center;
background:url('/main/images/block_alpha8h.png') no-repeat;
background-color:#EEEEEE;
background-position:-45px 0px;
float:left;
overflow:hidden;
}


#hover-menu .main-menu {
border-radius:5px;
-moz-border-radius:5px;
-webkit-border-radius:5px;
box-shadow: 0 0 6px #333;
-moz-box-shadow: 0 0 8px #333;
-webkit-box-shadow: 0 0 8px #333;
}

/* IE8 hack */
#hover-menu .main-menu {
filter:progid:DXImageTransform.Microsoft.Shadow(color=#555555,direction=135,strength=3,enabled=true)\9;
}

/* active-arrowクラス */
#hover-menu .main-menu.active-arrow {
background:url('/main/images/arrow_8b.png') no-repeat;
background-position:center bottom;
}


#hover-menu ul li a {
text-decoration:none;
margin:0
padding:0;
}

#hover-menu ul li h3 {
width:auto;
height:20px;
margin-top:10px;
padding:0 10px;
line-height:20px;
font-size:12px;
font-weight:bold;
color:#CCCCCC;
text-shadow:1px 1px 4px #000000;
cursor:pointer;/*default*/
}

/* IE8 hack */
#hover-menu ul li h3{
filter:progid:DXImageTransform.Microsoft.Shadow(color=#000000,direction=135,strength=3,enabled=true)\9;
}
/* shadowクラス */
#hover-menu ul li h3.shadow {
filter:progid:DXImageTransform.Microsoft.Shadow(color=#000000,direction=135,strength=3,enabled=true)\9;
}


#hover-menu ul li p {
margin-top:-20px;
line-height:12px;
font-size:10px;
color:#CCCCCC;
cursor:pointer;/*default*/
}

/* hovered */
#hover-menu ul li.hovered h3 {
color:#FFFFFF;
}



/* sub-menu */
/* 幅は広げられないabsolute */
#hover-menu .sub-menu {
position:absolute;
top:50px;left:0;
display:inline-block;
width:110px;
height:auto;
margin:0;
padding:0;
background-color:#000000;
opacity:0.5;
filter:alpha(opacity=50);/* IE */
}

#hover-menu .sub-menu li {
clear:both;
list-style:none;
display:inline;
width:110px;
height:auto;
margin-bottom:2px;
padding:0 2px;
line-height:16px;
font-size:11px;
text-align:left;
background-color:transparent;
background-image:none;/* 重要 */
overflow:hidden;
}
#hover-menu .sub-menu li a {
text-decoration:underline;
height:100%;
}
#hover-menu .sub-menu li a:hover {
color:#FFFFFF;
}


IE9のフィルター破壊とIE7.8の対応

下の図に示すように。IE9の場合にメニュータイトルに陰影をつけた場合に「フィルター破壊」をおこします。原因を調べてみました。(”IE様”は何年たっても健在です。雇用を生み出す世界経済の牽引”厄”です。)

説明図


● 「フィルター破壊」

「フィルター破壊」の原因は様々です。驚くに値しない IE の通常の現象です。

1.フィルターが2重になっている。
2.アルファフィルターの影響。
3.その外「原因不明」もある(これ困るぜ)。


上のサンプルの場合は、フィルターが2重、階層は別だが、アルファフィルターも使用している。またAリンクの部分でもある。思わぬところが影響していました。原因はCSSの角丸処理の「border-radius」でした(角丸では無く、overflow:hidden が根本原因)。
IE9では「角丸処理」をしなければテキストに陰影を付けることができます。このレイアウトではIE7.8では問題は起きません。(レイアウトなどの構造次第ではどうなるかは不明、IEでのフイルターの使用はバグに繋がる)


【追記】2012/11/17:もう一度調べてみたら、原因は 「角丸処理」階層の overflow:hidden でした。結果的には同じことですが、複数の階層(DIV)を入れて処理を分散しなければ直すことが出来ないと言うわけです。色々ためしてみましたが難しい様です。hiddenを処理できないほうが事は重大です。アニメの場合結構hiddenを使用しながら組み立てますから。
この記事は繁雑すぎますから、簡単なものに作りなおしました。明日にでもUPします。
間違いを訂正して、お詫びいたします。ああ「IE9」には困った、、、。


● IE9で「ハック」が効かない?

角丸の処理はどうしても行いたいために、IE7.8もあるので、テキストに陰影を付ける処理を「ハック」で制御してみましたが旨くゆきません。
IE9に陰影をつけないように、IE7.8に陰影処理しようと試みました。



通常は下記のハックを使用しているようです

IE7, IE8
#help_me {color/*\**/: blue\9; }

#help_me {
color: green\9; /* IE8 */
*color: yellow; /* IE7 */
}

通常理屈からゆけば下記のようにすれば良い訳ですが、、、IE9に陰影処理してバグがでる?


IE78のハックで
#hover-menu ul li h3 {
filter/*\**/:progid:DXImageTransform.Microsoft.Shadow(color=#000000,direction=135,strength=3,enabled=true)\9;
}

あるいは
#hover-menu ul li h3 {
filter:progid:DXImageTransform.Microsoft.Shadow(color=#000000,direction=135,strength=3,enabled=true)\9;
}

どれも効かない、IE9に陰影処理してしまう。「ワカラン」の一言です。IE9の「互換表示」の準備としてCSSを読み込んでいるのでしょうか?、季節の変わり目か?、アタマのバグか?。。


JSで「ブラウザ判別」して処理すれば別に困りませんが、現在はここも「ワカラン」状態である。


上記のハックは複数の専門のひとがHPで書いてあるものであるが、、少し調べたらこんな記事があった。

【参考】コリスさんの記事: IE9対応、IEの各バージョンごとに異なるスタイルシートを適用する方法のまとめ


「¥9」ハックは疑わしいようだ。しかし方法があとない。考えるにハックを使用せずに、JSで判定したほうが無難のようでもある。私自身はほとんどハックは使用しないのであるが、今回は困った末の処置で、そんでツマズイタが「其の内ナントカなるだろう」。
解決した訳ではないが、今は余り考えずにパスしとこう。


● JSで処理する。


IE9にも陰影がつくので、この部分は削除する
IE9のバグが出ても差し支えなければこのままでも良い

/* IE8 hack */
#hover-menu ul li h3{
filter:progid:DXImageTransform.Microsoft.Shadow(color=#000000,direction=135,strength=3,enabled=true)\9;
}

フィルターをクラスにしてしまう、IE9以外に処理
クラスをあたえなければ有効にはならない

#hover-menu ul li h3.shadow {
filter:progid:DXImageTransform.Microsoft.Shadow(color=#000000,direction=135,strength=3,enabled=true);
}

ブラウザ判別して、JSで addClass('shadow') なりの処理をすれば自由に陰影を制御できる
以下のスクリプトでIE9以外に陰影をつける

(function($){

	$(function(){

		//ブラウザ判別、最初に挿入
		var userAgent = window.navigator.userAgent.toLowerCase();
		var browserIE = 0;//IE判定
		var browser_v = 0;//IEバージョン番号
		var browser_nm = "";//browser名

		if (/*@cc_on!@*/false) {
			browserIE = 1;
			browser_nm = "IE";
			if (navigator.userAgent.match(/MSIE (¥d¥.¥d+)/)) {browser_v = parseFloat(RegExp.$1);}//IE6.7.8.9
		}

		//背景画像中央合わせの x値=(アイテム幅-画像幅)/2

		途中略す

		//色データで背景着色などの処理
		$(".main-menu").each(function(i){

			item[i]=$(this);

			//IE9以外で陰影処理のクラスを付加する、適当なところで処理
			if (browser_v !=9) {
				item[i].find('h3').addClass('shadow');
			}

			途中略す

		});

		途中略す

	});
})(jQuery);

IE9 以外は陰影処理をする、IE以外は filter は機能しない。JSでブラウザ判別分岐するとスクリプトが長くなる。長いスクリプトは嫌われる。


JS (修正したもの)


//hover-menu11.js
//日本語
//プラグインjquery.backgroundpos.js 1.1.0を使用
//sub-menuのアニメを削除/IE78も動作する、IE9でタイトルの陰影をつけない

(function($){

	$(function(){

		//ブラウザ判別、最初に挿入
		var userAgent = window.navigator.userAgent.toLowerCase();
		var browserIE = 0;//IE判定
		var browser_v = 0;//IEバージョン番号
		var browser_nm = "";//browser名

		if (/*@cc_on!@*/false) {
			browserIE = 1;
			browser_nm = "IE";
			if (navigator.userAgent.match(/MSIE (¥d¥.¥d+)/)) {browser_v = parseFloat(RegExp.$1);}//IE6.7.8.9
		}

		//背景画像中央合わせの x値=(アイテム幅-画像幅)/2
		//現在の計算値、x=(200-110)/2=-45

		//menuの高さ
		var menu_H=60;
		//sub-menuの配置位置position-y/CSSとあわせる
		var sub_pos_X=50;
		//サブメニュー下のスペース 5-10
		var bottom_sps=10;

		//中央揃えの幅を取得して自動で幅などのCSSを決める
		var center_set="set";//set none

		//色データ
		var active_color="#AAAAAA";
		var active_txcolor="#FFFFFF";
		var active_bordercolor="#FFFFFF";//ベースの色に注意
		//複数色データ
		var colordata=["#DB7093","#F4A460","#BC8F8F","#FF69B4","#778899","#00CED1","#9370DB","#6496ED","#CCCCCC",'#EEEEEE'];

		var item=[];
		var subitem_H=[];
		var menu_base=$("#hover-menu");

		//ul要素の幅を決定して設定を実行する
		if (center_set=='set') {
			var ul_W=menu_base.children("ul").width();
			menu_base.children("ul").css({'float':'none'});//追加
			menu_base.css({'text-align':'center'});
			menu_base.children("ul").css({'width':ul_W,'margin':'0 auto'});
		}

		//色データで背景着色などの処理
		$(".main-menu").each(function(i){

			item[i]=$(this);

			//要素を個別に複数色に着色
			item[i].css({'background-color':colordata[i]});

			//高さの取得/無ければnull
			subitem_H[i]=item[i].find('.sub-menu').height();

			//sub-menuのある場所に▼を挿入する
			if (item[i].find('ul').hasClass('sub-menu')) {
				var ti_elm=item[i].find('h3');
				ti_elm.text(ti_elm.text() + ' ▼');
			}

			//IE9以外で陰影処理のクラスを付加する、適当なところで処理
			if (browser_v !=9) {
				item[i].find('h3').addClass('shadow');
			}

			//activeの処理、activeクラスがあるか
			if (item[i].hasClass('active')) {

				//active 背景着色
				//item[i].css({'background-color':active_color});

				//サブメニューが無い場合、高さがnull
				if (!subitem_H[i]) {

					//active 背景ポジションの変更
					//item[i].css({'background-position':'-45px -80px'});

					//active-arrowクラスを与える
					item[i].addClass("active-arrow");

				}

				//active 文字の色を変える
				item[i].find('h3').css({'color':active_txcolor});

				//active ボーダーを設定/高さボーダー分修正
				item[i].css({'height':menu_H-2,'border-top':'2px ' + active_bordercolor + ' solid'});

			}

			//サブメニュー一旦けす
			item[i].find('.sub-menu').css({'display':'none'});

			//hover-action
			item[i].hover(
				//over
				function() {

					//activeでサブメニューが無い、何もしないで戻る
					if (item[i].hasClass('active') && !subitem_H[i]) {return}

					//一旦消す
					item[i].find('.sub-menu').css({'display':'block'});

					//処理
					item[i].addClass("hovered");

					//伸ばす高さを計算
					var h=0;//初期値0
					if (subitem_H[i]) {h=subitem_H[i]+(sub_pos_X-menu_H)+bottom_sps;}


					//プラグインアニメ実行/基準変更
					item[i].find('.sub-menu').css({'display':'block'});
					item[i].animate({backgroundPosition:'-45px -60px','height':menu_H+h},600,function (){
						//
					});
				},
				//out
				function() {

					//activeでサブメニューが無い、何もしないで戻る
					if (item[i].hasClass('active') && !subitem_H[i]) {return}

					//処理
					item[i].removeClass("hovered");

					//sub-menuがあれば
					if (subitem_H[i]) {

						//アイテム高さを戻す
						item[i].animate({'height':menu_H},300,function (){

							//sub-menu消す
							item[i].find('.sub-menu').css({'display':'none'});
							//プラグインアニメ実行
							item[i].animate({backgroundPosition:'-45px 0px'},400);
								//
							});

						//});
					} else {
						//sub-menuが無ければ
						//プラグインアニメ実行
						item[i].animate({backgroundPosition:'-45px 0px'},400,function (){
							//
						});

					}

				}

			);

		});

	});
})(jQuery);


● そんなの「関係ない」。

そんなの「関係ない」。かえってデザインになっていいんじゃ無い?、という見方の人もいるかと思います。面倒な処理をしないで、全部にフィルター処理をすればよい。


text-shadowの後に陰影filterを全部にする
他のfilterのshadowクラスなどは削除する

#hover-menu ul li h3 {
width:auto;
height:20px;
margin-top:10px;
padding:0 10px;
line-height:20px;
font-size:12px;
font-weight:bold;
color:#CCCCCC;
text-shadow:1px 1px 4px #000000;
filter:progid:DXImageTransform.Microsoft.Shadow(color=#000000,direction=135,strength=3,enabled=true);
cursor:pointer;/*default*/
}

目の前に相手が居る訳でもない、所詮インターネットである、「バグなど知らん。それはキッとお天気のせいでショウ」を決め込むのも良い。


● 角丸処理をしない場合 (バグは出ない)

CSS3角丸処理をしない場合は、IE9の場合でも「タイトルに陰影を通常の方式で処理」してもバグは出ませんので、上の例と同じ処理で結構です。JSも普通のものでよい。
角丸処理しただけでかなり面倒になっています。(IE9を除外すれば簡単です)


● タイトルに陰影をつけない場合

該当の陰影処理の部分を削除します。JSは標準のものです。


#hover-menu ul li h3に関するtext-shadow、及びフィルター部分を削除する

#hover-menu ul li h3 {

2箇所削除
text-shadow:1px 1px 4px #000000;
filter:progid:DXImageTransform.Microsoft.Shadow(color=#000000,direction=135,strength=3,enabled=true);

}

その外、下のようになっている部分があっても削除
filter:progid:DXImageTransform.Microsoft.Shadow(color=#000000,direction=135,strength=3,enabled=true)\9;


● IE7.8の BOX-SHADOW処理 (通常のフィルター)

IE7.8の場合でも角丸には出来ませんが、BOX要素に陰影処理できますので、下記のようにCSSで設定します。このケースの場合にテキストの陰影とのバグは無いようです。処理する場所によってはどうなるかは予測は出来ません。
IE9がCSS3で処理なっていても影響はないようです。


/* IE8 hack */
#hover-menu .main-menu {
filter:progid:DXImageTransform.Microsoft.Shadow(color=#555555,direction=135,strength=3,enabled=true)\9;
}

但し、陰影処理で大きさが広がりますので注意が必要になります(修正処理はしていません)。また要素にHOVERした時にサブメニューが無くとも若干の伸縮があります。無理して陰影処理をしない方が良いようにも思います。尚、このことがIE9を「互換表示」に切り替えた場合に返ってデザイン崩れの原因になるかも知れません。


参考、ブラウザ判別(IE以外の判定もしたい場合)


var userAgent = window.navigator.userAgent.toLowerCase();
var browserIE = 0;//IE判定
var browser_v = 0;//IEバージョン番号
var browser_nm = "";//browser名

if (/*@cc_on!@*/false) {

	browserIE = 1;
	browser_nm = "IE";

	if (navigator.userAgent.match(/MSIE (¥d¥.¥d+)/)) {browser_v = parseFloat(RegExp.$1);}//IE6.7.8.9

	}
	else if (userAgent.indexOf("firefox") > -1) {browser_nm = "Firefox";}
	else if (userAgent.indexOf("opera") > -1) {browser_nm = "Opera";}
	else if (userAgent.indexOf("chrome") > -1) {browser_nm = "Chrome";}
	else if (userAgent.indexOf("safari") > -1) {browser_nm = "Safari";}
	else {
	browser_nm = "Unknown";
}

中央配置の変更について

初期段階では、中央配置になっています。解除するには JS先頭部分のcenter_setを解除して、CSSの下記部分を削除ください。左揃えになります。


JS

//中央揃えの幅を取得して自動で幅などのCSSを決める
var center_set="";//set none

-------------------------------------------

CSS

/float:leftを削除する、IE6.7での幅取得のためにフロート

#hover-menu ul {
list-style:none;
display:inline-block;
width:auto;
height:60px;
padding:0;
margin:0;
}

右にそろえるならば、JSの中央配置設定解除して
float:right


使用画像

このサンプルでは、アルファチャンネル画像 block_alpha8h.png (200x120)、arrow画像arrow_8b.png (200x20) を使用しています。青色のものは、背景画像のX位置が 0 であっても良いものです。

block_alpha8.png block_alpha8b.png block_alpha8c.png
block_alpha8d.png block_alpha8e.png block_alpha8f.png
block_alpha8g.png block_alpha8h.png 追加交換用画像

arrow_8.png / arrow_8b.png




動作ブラウザを、CSS3対応の、(IE9) Safari Firefox Chrome Opera、に限定したほうが容易です。IE9でこの通りですから、IE10であってもまた問題が出るのでは無いでしょうか。

IE以外のブラウザ対象ならば、説明は書く必要はありません。


もうこんなもの「ドウでも良い」というくらい面倒ですね。書いてる私も面倒ですから、「こんなもん使いません」。ここでみんなで笑いましょう!

大変簡単、無責任説明ですが、以上です。

 


[ この記事のURL ]


タグ:series , memo , Effect , jquery

[ jQuery HoverMenu シリーズ記事 ]

jQuery HoverMenu/112012.11.18
jQuery HoverMenu/102012.11.14
jQuery HoverMenu/92012.11.08
jQuery HoverMenu/82012.11.06
jQuery HoverMenu/72012.11.04
jQuery HoverMenu/62012.11.01
jQuery HoverMenu/52012.10.30
jQuery HoverMenu/42012.10.29
jQuery HoverMenu/32012.10.28
jQuery HoverMenu/22012.10.27
jQuery HoverMenu/12012.10.26

 

ブログ記事一覧



[1]