2016-11-06 15 views
2

私はいつでも6つのバブルを持っているバブル行のようです。配列には6つのjsonオブジェクトがあります。コードは、読み込み時に最初に追加されたサークルのみを表示しています。しかし、配列を変更すると、最初のバブルを削除し、その行の右端に1つのバブルを追加します。私はそれをテストするために配列に要素を挿入するためにsetIntervalを使用しています。私は配列の状態を記録しているので、配列は正しく変更されていますが、svgグラフィックは更新されません。私は問題がcreateElementGroup()を再利用しているかどうか、またはこのケースでノードを削除する方法(通常のケースではexit()d3メソッドを使用していますが、どこで実装するのかはわかりません)この特定の場合)。D3.js:配列に追加された要素がsvgグラフィックをリフレッシュしていません

さらに、要素を削除して追加すると、どこをスムーズにする必要がありますか。ライブデモはここにある:

//listener that will be executed on setIntervalCheck to update the graphic 
setInterval(function(){ 
    moveForwardOnBubbleList(); 
    createElementGroup(); 
    }, 100000); 



var profile_pic_url="https://scontent.fsst1-2.fna.fbcdn.net/v/t1.0-9/13680856_103268503450198_1479797031996897052_n.jpg?oh=f43bced91822fb210c8be8a410825da9&oe=58D46460"; 

var dataset = [{unique_followers: 5, profile_pic:profile_pic_url}, {unique_followers: 10, profile_pic:profile_pic_url},{ unique_followers: 15, profile_pic:profile_pic_url}, { unique_followers: 20, profile_pic:profile_pic_url}, { unique_followers: 25, profile_pic:profile_pic_url}, {unique_followers: 40, profile_pic:profile_pic_url} ]; 

var w=600,h=600; 

var svg=d3.select("body").append("svg") 
            .attr("width",w) 
            .attr("height",h); 

//1st level:All circles group 
var circlesGroup = svg.append("g").classed("general-group",true); 
//2nd level: Group of circle and text 
var elementGroup; 

var circle; 

var circleAttributes; 
//create g's of existing data 
createElementGroup(); 

elementGroup.on('click', function(d,i){ 
    var that=this; 

    d3.selectAll('.element-group').each(function(d,i) { 
    if(this.id!==that.id){ 
     d3.select(this).classed("selected",false); 
    } 
    }); 

    d3.select(this).classed("selected", !d3.select(this).classed("selected")); 

    }); 

//adding circular background image to the circles 
//var circlesSelection=svg.selectAll('circle'); 


function createElementGroup(){ 
    elementGroup = circlesGroup 
    .selectAll('circle') 
    .data(dataset) 
    .enter() 
    .append("g").classed("element-group",true); 

    circle=elementGroup.append('circle'); 

    circleAttributes = circle 
    .attr("r", 20) 
    .attr("stroke","black") 
    .attr("fill", "white") 
    .classed("circle",true); 

    //text to show 
    elementGroup.append("text") 
     .attr("text-anchor", "middle") 
    .text(function(d) { 
    return parseInt(d.unique_followers); 
    }) 
    .style("pointer-events","none") 
    .classed('tweet-number', true); 

    //image to show as background 

    //element group positioning for the text to be inside circle 
    elementGroup.attr("transform", function(d,i){ 
    return "translate(" + (i*80+45) + "," + h/2 + ")"; 
}); 

    elementGroup.attr("fill-opacity", 0).transition().duration(500).attr("fill-opacity", 1); 
    elementGroup.attr("id", function(d, i) { return "c"+i; }); 


} 

function addBubbleLast(){ 
    dataset.push({unique_followers: 40, profile_pic:profile_pic_url}); 
} 

function removeFirstBubble(){ 
    dataset.shift(); 

} 

function moveForwardOnBubbleList(){ 
    addBubbleLast(); 
    removeFirstBubble(); 
} 



/*CSS*/ 
body 
     { 
      /*padding-top: 50px;*/ 
      padding-left: 100px; 
     } 

     .tweet-number{ 
     opacity:0.25; 
     } 

     .circle{ 

     } 


     .selected *{ 
      transform: scale(2); 
      transition: all 0.5s ease, opacity 0.5s ease; 
      opacity:1.0; 
    } 

http://codepen.io/juanf03/pen/BQyYBq

コード(あなたはそれがそのように私はそれが正しいノードで確認し、拡張し、データを表示し確認するために泡をクリックすることができます)

EDIT:Gerardo Furtadoの素晴らしい提案の後のコード修正。

//listener that will be executed on setIntervalCheck to update the graphic 
setInterval(function(){ 
    moveForwardOnBubbleList(); 
    createElementGroup(); 
    }, 6000); 



var profile_pic_url="https://scontent.fsst1-2.fna.fbcdn.net/v/t1.0-9/13680856_103268503450198_1479797031996897052_n.jpg?oh=f43bced91822fb210c8be8a410825da9&oe=58D46460"; 

var dataset = [{unique_followers: 5, profile_pic:profile_pic_url}, {unique_followers: 10, profile_pic:profile_pic_url},{ unique_followers: 15, profile_pic:profile_pic_url}, { unique_followers: 20, profile_pic:profile_pic_url}, { unique_followers: 25, profile_pic:profile_pic_url}, {unique_followers: 40, profile_pic:profile_pic_url} ]; 

var w=900,h=600; 

var svg=d3.select("body").append("svg") 
            .attr("width",w) 
            .attr("height",h); 

//1st level:All circles group 
var circlesGroup = svg.append("g").classed("general-group",true); 
//2nd level: Group of circle and text 
var elementGroup; 

var circle; 

var circleAttributes; 
//create g's of existing data 
createElementGroup(); 



//adding circular background image to the circles 
//var circlesSelection=svg.selectAll('circle'); 


function createElementGroup(){ 
    elementGroup = circlesGroup 
    .selectAll('.element-group') 
    .data(dataset, function(d){ return d.unique_followers}); 
//doesn't work the exit transition 
    var elementExit = elementGroup.exit().transition().duration(1000).style("opacity", 0).remove(); 

    var elementEnter = elementGroup.enter() 
    .append("g").classed("element-group",true).style("opacity",0); 

    elementEnter.merge(elementGroup).attr("transform", function(d,i){ 

    //option 1 generation by mod 
    if(i%2===0){ 
    return "translate(" + (i*80+45) + "," + h/1.55 + ")"; 
    }else{ 
    return "translate(" + (i*80+45) + "," + h/1.45 + ")"; 

    } 

    /* 
    //option 2 random 
    var random= (Math.random() * (1.6 - 1.45) + 1.45).toFixed(4); 

     return "translate(" + (i*80+45) + "," + h/random + ")";*/ 


}).transition().duration(2000).style("opacity", 1.0); 

    circle=elementEnter.append('circle'); 



    circleAttributes = circle 
    .attr("r", 20) 
    .attr("stroke","black") 
    .attr("fill", "white") 
    .classed("circle",true); 

    d3.selectAll('.element-group').on('click', function(d,i){ 
    var that=this; 
    d3.selectAll('.element-group').each(function(d,i) { 
    if(this.id!==that.id){ 
     d3.select(this).classed("selected",false); 
    } 
    }); 

    d3.select(this).classed("selected", !d3.select(this).classed("selected")); 

    }); 

    //text to show 
    var texts = elementEnter.append("text") 
     .attr("text-anchor", "middle") 
    .text(function(d) { 
    return parseInt(d.unique_followers); 
    }) 
    .style("pointer-events","none") 
    .classed('tweet-number', true); 

    //image to show as background 

    //element group positioning for the text to be inside circle 



} 

function addBubbleLast(){ 

    var random=Math.floor(Math.random() * (40)) + 1; 


    dataset.push({unique_followers: random, profile_pic:profile_pic_url}); 
} 

function removeFirstBubble(){ 
    dataset.shift(); 

} 

function moveForwardOnBubbleList(){ 
    addBubbleLast(); 
    removeFirstBubble(); 
} 

//CSS 

    body 
    { 
     /*padding-top: 50px;*/ 
     padding-left: 100px; 
    } 

    .tweet-number{ 
    opacity:0.25; 
    } 

    .circle{ 

    } 

.selected *{ 
     transform: scale(2); 
     transition: all 0.5s ease; 
     opacity:1.0; 
} 

.element-group *{ 
    transition: all 0.5s ease; 
} 

circle + text{ 
} 

答えて

2

"入力"、 "終了"、 "更新"の選択が必要です。

まず、我々は(キー機能付き)のデータをバインドします

var elementEnter = elementGroup.enter() 
    .append("g").classed("element-group",true); 

今重要な注意:これはD3のV4であるとして

elementGroup = circlesGroup 
    .selectAll('.element-group') 
    .data(dataset, function(d){ return d.unique_followers}); 

その後、我々は選択を入力して設定します。 X、あなたが作業更新の選択持つように選択をmergeする必要があります。最後に

elementEnter.merge(elementGroup).attr("transform", function(d,i){ 
    return "translate(" + (i*80+45) + "," + h/2 + ")"; 
}); 

を、元それが選択:ここで

var elementExit = elementGroup.exit().remove(); 

はあなたCodePenです:http://codepen.io/anon/pen/Wobyem

+0

2質問:私のクリックイベントが死んだ理由1)あなたは知っています?。それは気泡を2倍に拡大していましたが、変更後はうまくいきませんでした。 2)なぜデータセットに「キー機能」を使用しましたか?なぜあなたはその番号に要素をバインドしましたか? – Juan

+0

キー機能は「データポイントを入力として受け取り、対応するキーを返します。名前などの文字列で、データポイントを一意に識別します。」クリックイベントについて:私はあなたのコードの他の部分を変更しませんでした。それは今あなたの仕事です。私はあなたに選択肢に対処する方法を示しました。それに応じてコード全体を書き直す必要があります。 –

+0

ありがとう、私は何が間違っているか見る必要がありますが、私はもう一つ質問があります、ここで毎回rerenderedされているかhttp://codepen.io/juanf03/pen/ZBYRNK?.....私はちょうどwan't正しい方法を知るために...私は、再作成する関数に作成終了と更新を入れます...クリックイベントは、jqueryで以前に起こったような、動的に生成された要素に問題がありますか?だから私は尋ねているのです – Juan

関連する問題