2

右を指す単純な矢印記号をレンダリングするこの HTML があります。

<!DOCTYPE html>
<html>
<head>
<style>
div { width: 0px; height: 0px; border-left: 20px solid black; border-top: 20px solid transparent; border-bottom: 20px solid transparent; border-right: 20px solid transparent; position: absolute; left: 35px; top: 53px; cursor: pointer; }
</style>
<body>
<div></div>
</body>
</html>

ホバーすると、カーソルがポインタに変わります。しかし、それは実際には正方形divであるため、 の周囲内で矢印のすぐ外側にいる場合でも、カーソルはポインターに変わりますdiv

そこで、マウスがその矢印の上にあるときにのみカーソルがポインターに変わるように、このJavascriptの追加を書きました。この目的のために、Firebug から三角形の 3 つの頂点の座標を計算しました ( (35,53)(55,73)(35,93)上から時計回り)。次に、問題の点がこれらの 3 つの頂点によって形成される三角形の内側にあるかどうかを確認します。これは、各エッジの点と反対側の頂点がそのエッジの同じ側にあるかどうかを確認することによって行います (もしそうであれば、その点の座標を と に代入して得られた値の積xy 、ポジティブ)。

<!DOCTYPE html>
<html>
<head>
<style>
div { width: 0px; height: 0px; border-left: 20px solid black; border-top: 20px solid transparent; border-bottom: 20px solid transparent; border-right: 20px solid transparent; position: absolute; left: 35px; top: 53px;  }
.hoverclass { cursor: pointer; }
</style>
<script src="jquery.js">
</script>
<script>
$(document).ready(function(){
$("div").click(function(e) { alert(e.pageX + " " + e.pageY); });
function l1(x,y) { return y - x - 18; }
function l2(x,y) { return x+y-128; }
function l3(x,y) { return x-35; }
$("div").hover(function(e) {
var x = e.pageX;
var y = e.pageY;
if (l1(x,y)*l1(35,93) >= 0 && l1(x,y)*l1(35,93) >= 0 && l1(x,y)*l1(35,93) >= 0 ) {
$(this).addClass('hoverclass');
}
else { $(this).removeClass('hoverclass'); }
},
function() {
$(this).removeClass('hoverclass');
});
});
</script>
<body>
<div></div>
</body>
</html>

ただし、結果は予測できません。カーソルが三角形の内側だけでポインターを変えることもあれば、(以前と同じように) 外側も変えることもあれば、まったく動かないこともあります。hoverこれはおそらく、スクリプトが一時的にハングしている可能性がある、時間外に機能する機能によるものだと思われます。これを達成する他の方法はありますか?

4

3 に答える 3

3

これは、HTML5 キャンバスを使用して実行できます。基本的な考え方は、canvas 要素の mousemove でピクセルの色をチェックすることです。このようにして、要素を任意の形式にすることができます。もちろん、次のコードを最適化する必要があります。

実際のデモを見る

 function findPos(obj) {
    var curleft = 0, curtop = 0;
    if (obj.offsetParent) {
        do {
            curleft += obj.offsetLeft;
            curtop += obj.offsetTop;
        } while (obj = obj.offsetParent);
        return { x: curleft, y: curtop };
    }
    return undefined;
}

// set up triangle
var example = document.getElementById('example');
var context = example.getContext('2d');
context.fillStyle   = '#000';
context.strokeStyle = '#f00';
context.lineWidth   = 1;

context.beginPath();
// Start from the top-left point.
context.moveTo(10, 10); // give the (x,y) coordinates
context.lineTo(60, 60);
context.lineTo(10, 120);
context.lineTo(10, 10);

// Done! Now fill the shape, and draw the stroke.
// Note: your shape will not be visible until you call any of the two methods.
context.fill();
context.stroke();
context.closePath();

$('#example').mousemove(function(e) {
    var pos = findPos(this);
    var x = e.pageX - pos.x;
    var y = e.pageY - pos.y;
    var coord = "x=" + x + ", y=" + y;
    var c = this.getContext('2d');
    var p = c.getImageData(x, y, 1, 1).data;
    if(p[3]!='0') $(this).css({cursor:'pointer'});
    else $(this).css({cursor:'default'});
});
于 2013-01-14T09:50:09.647 に答える
2

代わりに CSS を使用することをお勧めします。:before および :after 疑似クラスを使用すると、魔法を行うことができます。Nicolas Gallagher によるこのPure CSS GUI アイコンをチェックしてください。

CSS プリプロセッサを使用する場合、これらのアイコンを mixin としてラップできます。このようにして、必要なプロパティを次のように割り当てることができます。

#icon > .close(16px, #fff, #E83921);

結果

于 2013-01-14T09:39:29.003 に答える
2

CSSのみで任意の形状にカーソルポインターを持たせることができます。overflow: hiddenアイデアは、 (必要な形状に応じていくつかのものを持つことができます)を持つラッパーコンテナを回転させることです. OPの問題の場合、このコードはトリックを行います:

<div class="arrow"><i></i></div>

.arrow {
  margin: 100px;
  border_: 1px red solid;
  width: 40px;
  height: 40px;
  overflow: hidden;
  -webkit-transform: rotate(45deg);
  transform: rotate(45deg);
}
.arrow i {
  height: 65px;
  width: 65px;
  background-color: green;
  content: '';
  display: block;
  cursor: pointer;
  margin: -35px 0 0 11px;
  -webkit-transform: rotate(45deg);
  transform: rotate(45deg);
}

このデモを参照してください: http://cssdesk.com/PaB5n

これには CSS 変換のサポートが必要であるため、クロスブラウザーではありません。

于 2013-01-14T10:26:00.243 に答える