2010-04-16 55 views
1

我有一个函数可以获取经度和纬度并将其转换为x和y进行绘图。转换到X和Y工作正常,这不是我遇到的问题。绘制点,以便它们不重叠,如果它们具有相同的坐标

我想确保两点不绘制在同一个地方。在一组结果中,大约有30个在另一个之上(因为它们具有相同的经度和纬度),这个数字可能会大得多。

目前,我试图通过移动点至点的左侧,右侧,顶部或底部,使一个正方形来实现这一目标。一旦绘制了由点组成的正方形,然后移动到下一行并在前一个正方形周围绘制另一个点的平方。

的代码是Javascript支持,但是它是非常通用的,所以我想这是稍微无关。

我的代码如下:

var prevLong, prevLat, rand = 1, line = 1, spread = 8, i = 0; 

function plot_points(long, lat){ 

    // CODE HERE TO CONVERT long and lat into x and y 

    // System to not overlap the points 
    if((prevLat == lat) && (prevLong == long)) { 

     if(rand==1) { 
      x += spread*line; 
     } else if(rand==2) { 
      x -= spread*line; 
     } else if(rand==3) { 
      y += spread*line; 
     } else if(rand==4) { 
      y -= spread*line; 
     } else if(rand==5) { 
      x += spread*line; 
      y += spread*line; 
     } else if(rand==6) { 
      x -= spread*line; 
      y -= spread*line; 
     } else if(rand==7) { 
      x += spread*line; 
      y -= spread*line; 
     } else if(rand==8) { 
      x -= spread*line; 
      y += spread*line; 
     // x = double 
     } else if(rand==9) { 
      x += spread*line; 
      y += spread; 
     } else if(rand==10) { 
      x += spread; 
      y += spread*line; 
     } else if(rand==11) { 
      x -= spread*line; 
      y -= spread; 
     } else if(rand==12) { 
      x -= spread; 
      y -= spread*line; 
     } else if(rand==13) { 
      x += spread*line; 
      y -= spread; 
     } else if(rand==14) { 
      x += spread; 
      y -= spread*line; 
     } else if(rand==15) { 
      x += spread*line; 
      y -= spread; 
     } else if(rand==16) { 
      x += spread; 
      y -= spread*line; 
     } else if(rand==17) { 
      x -= spread*line; 
      y += spread; 
     } else if(rand==18) { 
      x -= spread; 
      y += spread*line; 
     } else if(rand==19) { 
      x -= spread*line; 
      y += spread; 
     } else if(rand==20) { 
      x -= spread; 
      y += spread*line; 
     } 

     if(rand == 20) {rand = 1; line++; } else { rand++; } 
     i++ 
    } else { 

     line = 1; 
     i = 0; 

    } 

    prevLat = latitude; 
    prevLong = longitude; 

    return [x,y]; 

} 

这是输出:output

它不能正常工作,我甚至不知道如果我以正确的方式接近问题在所有。

有没有人需要这样做?你会建议什么方法?

+1

你是否打开到密度表示的备选implmentations?要么通过直径,颜色或其他变体? – 2010-04-16 18:04:37

+0

您的意思是,例如,将具有相同坐标的点合并为一个点,然后使用大小/颜色来显示密度?每个点代表一个不同的数据,因此他们需要分开识别。 IE浏览器。从一个角度来看,有许多不同的值是独特的。 – betamax 2010-04-16 18:11:11

+0

关于您的评论,我的解决方案假定所有的点都以相同的颜色呈现。我仍然认为用相同的坐标来计算点的数量比较容易,然后根据总数来排列点。这些点当然可以根据其他标准进行着色,但是可以根据计数进行排列。 – Ernelli 2010-04-16 18:31:34

回答

1

通过对坐标进行分组开始。直到最后一步,您的long,lat - > x,y转换可能不是必需的。一种方法是创建一个散列图,您可以在其中存储每个长/经位置和每个位置的计数。

然后你转换每个长,纬度位置为X,Y坐标和使用次数来决定如何呈现围绕x,y位置但按点数大小为中心的点。

一个工作算法,以呈现一个正方形是:

var count = 30; // example 
result = []; 

var width = count/Math.sqrt(count); 
width = Math.floor(width); 
height = Math.floor(count/width); 
var remain = count % width; 

var i,j; 

for(i = 0; i < width; i++) 
    for(j = 0; j < height; j++) 
    result.push([x-Math.floor(width/2)+i, y-Math.floor(height/2)+j]; 
for(i = 0; i < remain; i++) 
    result.push([x-Math.floor(width/2)+i, y-Math.floor(height/2)+j]; 

输入是点,X,Y的中心坐标计数,输出是点呈现的阵列。

最后一行是剩下的点,e.g 15点多呈现:

OOOO 
OOOO 
OOOO 
OOO 
+0

这种方法似乎有效。我目前无法测试,但明天我会明白发生了什么。谢谢! – betamax 2010-04-16 18:33:49

1

使用Ernelli的解决方案作为一个例子,我设法让绘图工作正常。这似乎有点冗长,但有效,并且不慢。

Ernelli的解决方案有一个错误在第二个for循环:

for(j = 0; i < height; i++) 

应该是:

for(j = 0; j < height; j++) 

无论如何,这是我的代码,我使用和工作。 pointArray是所有要被绘制的元件的阵列:

var countArray = new Array(); 

// Go through every point and group same co-ordinates together 
for (var i = pointArray.length-1; i > -1; i--) { 
    if(pointArray[i] != undefined) 
    { 
     var found = 0; 

     // Check if this point is already in array 
     for (var j = countArray.length-1; j > -1; j--) 
     { 
      if(countArray[j] != undefined) 
      { 
       if((pointArray[i].getBBox().x == countArray[j]["x"]) && (pointArray[i].getBBox().y == countArray[j]["y"])) 
       { 
        countArray[j]["points"].push(pointArray[i]); 
        found = 1; 
       } 
      } 
     } 

     // The point is not in the array, so add it 
     if(found != 1) 
     { 
      var index = countArray.length; 
      countArray[index] = new Array(); 
      countArray[index]["x"] = pointArray[i].getBBox().x; 
      countArray[index]["y"] = pointArray[i].getBBox().y; 
      countArray[index]["points"] = new Array(); 
      countArray[index]["points"].push(pointArray[i]); 
     } 

    } 
} 

// For each co-ordinate 
for (var j = countArray.length-1; j > -1; j--) 
{ 
    if(countArray[j] != undefined) 
    { 
     // If there is more than one point 
     if(countArray[j]["points"].length > 1) { 

      // Calculate the square points 
      var count = countArray[j]["points"].length; 
      var x = countArray[j]["x"]; 
      var y = countArray[j]["x"]; 
      result = []; 

      var width = count/Math.sqrt(count); 
      width = Math.floor(width); 
      height = Math.floor(count/width); 
      var remain = count % width; 


      var i2,j2, xx, yy; 
      var space = 8; 
      for(i2 = 0; i2 < width*space; i2+=space) 
      { 
       for(j2 = 0; j2 < height*space; j2+=space) 
       { 
       result.push([(Math.floor(width/2)+i2), (Math.floor(height/2)+j2)]); 
       } 
      } 
      for(i2 = 0; i2 < remain*space; i2+=space) 
      { 
       result.push([(Math.floor(width/2)+i2), (Math.floor(height/2)+j2)]); 
      } 

      // Go through each point and then translate it to it's new position 
      for (var jj = countArray[j]["points"].length-1; jj > -1; jj--) 
      { 
       if(countArray[j]["points"][jj] != undefined) 
       { 
        if(result[jj] != undefined) 
        { 
         countArray[j]["points"][jj].translate(result[jj][0]-((width*8)/2), result[jj][1]-((height*8)/2)) 
        } 
       } 
      } 
     } // End if count more than 1 
    } // End if undefined 
} 

注意,此使用许多raphael.js功能(如getBBox和平移)

+0

感谢您发现错误,我更新了示例代码。 – Ernelli 2010-04-20 07:14:15

相关问题