dポイントプレゼントキャンペーン実施中!

javascript初心者です。
やりたいことは、下記の通りなのですが、どなたか対処方法を教えて頂けないでしょうか?

透過PNGの画像を重ね合わせ、レイヤーのように表示した状態で、各画像の透明部分以外のオンクリックで画像を入れ替え、さらに上の階層の画像を消して下の階層の画像のオンクリックでも画像を入れ替えたいのですが、上手くいきません。。
たとえば、余白部分が透明な丸と四角のPNGを、丸が上になるように重ね、丸をクリックすると丸の色だけが、四角をクリックすると四角の色だけが変わり、さらに丸を非表示にして下の四角をクリックしすると、四角の色が変わるようにしたいのです。

四角PNG + 丸PNG + 透明PNGを重ね合わせ、透明PNGに丸と四角のクリッカブルマップを重ねて持たせることで、両方見えた状態でそれぞれの色を変えることはできたのですが、丸を非表示にする時に丸のクリッカブルマップだけを消すことができず、丸があったところだけクリックが効かなくなってしまいます。
根本的なやり方がまずいのでしょうか?
よろしくお願いします。

ソース抜粋
<script type = "text/javascript">
<!--
function remove(){
document.layer2.style.display='none';
document.getElementById('map2').style.display='none';
}
//-->
</script>


<map name="Map" id="Map">
<area name="map2" id="map2" shape="circle" coords="丸の座標" onClick="document.layer2.src='丸の画像2'" />
<area name="map1" id="map1" shape="rect" coords="四角の座標" onClick="document.layer1.src='四角の画像2'" />
</map>

<div style="position:absolute;top:30px; left:0px">
<img src="四角の画像1" alt ="" name="layer1" id="layer1" />
</div>
<div style="position:absolute;top:30px; left:0px">
<img src="丸の画像1" alt ="" name="layer2" id="layer2" />
</div>
<div style="position:absolute;top:30px; left:0px">
<img src="透明な画像" alt ="" usemap="#Map" />
</div>

<input type="button" value="丸消す" onClick="remove()" />

A 回答 (4件)

No1、No3です。



実験してみましたら、仰る通り下の画像のonclickイベントが発生しませんね。
重なった図形の場合、両方のイベントが発生したような記憶があったので、まとはずれな回答をしてしまったようです。 大変失礼いたしました。

…ということで、再考いたしましたが、どうやら、最初のご質問の通りの方法のほうがよさそうですね。
画像を変える部分は問題なくできているようなので、画像を消して同時にマップを消す部分の例を…

DOMでMapの<area>要素を削除しています。(coordsの座標を無効化することでもいけそうですが、きちんと確認していません。=コメントアウトしている部分。)
とりあえず、クリックすると、その画像を消すと同時に対応するマップ(AREA要素)を削除するという例です。(番号で対応をとっています)
マップを再度有効にする場合は、createElementなどで再作成する必要があります。
<html>
<head>
<style type="text/css">
#shape img { position:absolute; }
#shape #layer0 { top:0; left:0; width:200px; height:200px; border:1px solid gray; }
#shape #layer2 { top:30px; left:0px; }
#shape #layer1 { top:50px; left:50px; }
</style>
<script type="text/javascript">
function test(n) {
var e = document.getElementById('map' + n);
e.parentNode.removeChild(e); //←AREA要素を削除
//e.coords='0,0'; //←座標定義を無効化
document.getElementById('layer' + n).style.display = 'none';
}
</script>
</head>

<body>
<map name="Map" id="Map">
<area id="map1" shape="circle" coords="125,125,75" onclick="test(1);" />
<area id="map2" shape="rect" coords="0,0,150,150" onclick="test(2);" />
</map>

<div id="shape">
<img src="img/rect1.gif" alt ="" name="layer2" id="layer2" />
<img src="img/circle.gif" alt ="" name="layer1" id="layer1" />
<img src="img/rect2.gif" alt ="" name="layer0" id="layer0" usemap="#Map" />
</div>
</body>
</html>

画像の数が多くて、その重なり順が変わるような場合は、画像のz-indexとマップの定義順などをコントロールしてやる必要がありますね。
    • good
    • 0
この回答へのお礼

おおお!できました!
Nodeを使えばできるようになるんですね。大変勉強になりました。
コードまで書いていただき感激です。
大変助かりました。ありがとうございました。

お礼日時:2009/06/03 10:57

No1です



クリッカブルマップの書き換えは可能だったと思いますが、少々面倒そうな気がします。(座標がcsvみたいな記述だったかな?よく覚えていない。)

今回のご質問の場合は、その面倒さにトライしなくても、画像を表示/非表示するのですから、そちらの画像の方にクリックイベントもセットで定義しておく案の方が簡単ではないかというのが、No1の回答の意図です。

そうすれば、クリッカブルマップを書き換えなくても、画像を表示/非表示するだけで、(自動的に)クリック用のマッピングも切り替えることができますし、例えば、表示する画像の位置を移動させたりしても、マップを変更する必要はなくなりますよね。
要は、マップと画像を分けるようなことはせずに(クリッカブルマップはそうですが)、画像とマップを一致させておくことで、処理が簡単になるのではということをいいたかっただけ。

どうしてもマップの書き換えを行いたければ、DOMで選択してcoordsを取ればよいのだけれど、座標が配列ではなくてcsvのようなデータになっていたと記憶しています。(記憶が曖昧なので、違うかも)

この回答への補足

fujillin様 重ね重ねありがとうございます。
マップを書き換える方法はあるにはあるのですね。やはりstyle.display="none"ではだめなんでしょうね。もう少しやり方を探してみます。

「表示/非表示する画像の方にクリックイベントもセットで定義しておく」ということは、各画像にマップを持たせるということですよね。
やり方が悪いのかもしれませんが、下記のコードの場合、PNGを重ねて表示した場合に、下の階層のPNGに触れなくなってしまいます。
(たとえば、四角が下、丸が上になるように重ねた場合、丸の透明部分が邪魔で下の四角のonClickが動かない)

<map name="Map1" id="Map1">
<area shape="rect" coords="四角の座標" onClick="document.layer2.src='四角の画像2'” />
</map>
<map name="Map2" id="Map2">
<area shape="circle" coords="丸の座標" onClick="document.layer2.src='丸の画像2'” />
</map>

<div style="position:absolute;top:30px; left:0px">
<img src="四角の画像" alt ="" name="layer1" id="layer1" usemap="#Map1" /></div>
<div style="position:absolute;top:30px; left:0px">
<img src="丸の画像" alt ="" name="layer2" id="layer2" usemap="#Map2" /></div>

これを解消するためにはどのようにするのが良いのでしょうか?
お手数をおかけしますがよろしくお願いします。

補足日時:2009/06/01 16:39
    • good
    • 0

id="map2"は常に表示させた状態(クリックできる状態)にしておき、


(document.getElementById('map2').style.display='none'; を削除)
クリックされたときに、
layer2の状態を判断して、layer2.style.displayを表示したり非表示にするような動作をしてみてはいかがでしょうか。

if(document.layer2.style.display=='none'){
// ここにlayer2が消えてるときの動作を記述
}else{
// ここにlayer2が表示されているときの動作を記述
}

この回答への補足

返事が遅くなり申し訳ありません。ご回答ありがとうございます。
たしかにこれは一つの解決方法ですね。
map2に割り当てられた動作を、その下にあるmap1の動作に切り替えてみたらできました。

ただこの方法だとクリッカブルマップで指定したAREAの一部を消すことにはなっていないので、根本的な解決になっておらず、数百枚の画像を重ねて行う場合にはかなり複雑になってしまう気がします。

AREAで指定した範囲は、javascriptでは消す方法はないのでしょうか?

補足日時:2009/05/31 18:40
    • good
    • 0

四角と丸の画像が別にあるのなら透明画像にマップを設定する必要はないのでは?



四角はそのままアンカーまたはonclickイベントでも良いし。
丸の画像だけにクリッカブルマップを設定しておけば良いのでは?
そうしておけば、画像を非表示にするだけで、クリックイベントも発生しなくなると思うけど…

試してはいないので、確認してみてください。

この回答への補足

ご回答ありがとうございます。
少し説明が足りなかったです。
実際には、数百枚の背景が透明なPNGを重ねて一枚の絵にし、各PNGを出したり消したりしたいと思っています。
そして現在表示されている絵をクリックすると、該当PNGの色が変わればいいなあと。
上記の四角と丸の例では、分かりやすくするために単純化しています。
2枚でできれば数百枚あってもできるだろうと思いまして。。

ですので、透明画像を使う方法でなくてもいいのですが、クリッカブルマップの一部が消せる必要があるのです。
お手数おかけしますが、解決方法お分かりになりますでしょうか?

補足日時:2009/05/29 19:00
    • good
    • 0

お探しのQ&Aが見つからない時は、教えて!gooで質問しましょう!