2012-09-07 59 views
18

在D3.js中工作時,我想選擇與選擇器匹配的所有元素,但當前元素的除外。在D3.js中jQuery的'不'選擇器的等價物?

原因是我想要將鼠標懸停在一個圓圈上,並將所有其他圓圈與同一班級變成淡藍色,但是當前圓圈保持相同的陰影。

這是我目前:

vis.selectAll('circle.prospect') 
.on("mouseover", function(d) { 
    console.log(d); 
    d3.selectAll('circle.prospect').transition().style('opacity','0.5'); 
    d3.select(this).attr('opacity','1.0'); 
    }); 

在jQuery中,我could do this using not。任何人都知道D3.js等價物?

+2

你試過'd3.selectAll('circle.prospect:not(this)')'? –

+0

@ZoltanToth - 是的,這恐怕不起作用。 – Richard

+1

你也可以使用普通的CSS,而不是JavaScript。例如,當將鼠標懸停在外部SVG元素的任何圓上時淡出其他圓:'svg:hover circle:not(:hover){opacity:.5; }'。 – mbostock

回答

14

一種解決這個更簡單的方法將使用D3的運營商的力量:

vis.selectAll('circle.prospect').on("mouseover", function(d) { 
    var circleUnderMouse = this; 
    d3.selectAll('circle.prospect').transition().style('opacity',function() { 
     return (this === circleUnderMouse) ? 1.0 : 0.5; 
    }); 
}); 

有在這裏是一個區別是,不像你的原代碼,該circleUnderMouse元素的不透明度將順利動畫也。如果它已經完全不透明,那麼可能不是什麼大不了的,否則你可以用類似的方式使用.duration()運算符來加快circleUnderMouse時間到0,其他時間更長。

17

您可以filter選擇:

vis.selectAll('circle.prospect') 
.on("mouseover", function(d) { 
    console.log(d); 
    var circleUnderMouse = this; 
    d3.selectAll('circle.prospect').filter(function(d,i) { 
     return (this !== circleUnderMouse); 
    }).transition().style('opacity','0.5'); 
    d3.select(this).attr('opacity','1.0'); 
    }); 
20

如果你的元素有一個獨特的CSS-訪問標識符,您可以使用:not()選擇。一些潛在的例子:

d3.selectAll("circle.prospect:not(#" + this.id + ")"); 
d3.selectAll("circle.prospect:not(." + someUniqueClassFrom(d) + ")"); 
d3.selectAll("circle.prospect:not([uniqueAttr=" + this.getAttribute('uniqueAttr') + "])"); 

原因d3.selectAll('circle.prospect:not(this)')不起作用,因爲它只是從字面上說,過濾掉任何<this></this>元素 - 這顯然不是你的意圖,因爲它已經選擇只<circle></circle>元素將無效而不管。

即使你不一般適用於一些獨特的DOM屬性沒有理由你不能設置一個臨時:

vis.selectAll('circle.prospect') 
.on("mouseover", function(d) { 
    this.id = 'temp-' + Math.random(); 
    d3.selectAll('circle.prospect:not(#' + this.id + ')').transition().style('opacity','0.5'); 
    d3.select(this).attr('opacity','1.0'); 
    this.id = ''; 
    }); 

但是,儘管如此,如果你的元素不已經有一個ID我認爲伊恩羅伯茨的解決方案可能是我會做的,而不是這個臨時標識符破解。

+0

與不選擇器的最佳答案... – Juan