使用SVG构建推文地图

自从IE9宣布支持它以来,SVG已经建议将自己作为一个可靠的解决方案来考虑您的可视化需求。在本文中,我想向您介绍Polymaps,一种创建基于地图的可视化的好方法。这适用于所有识别SVG的浏览器。

使用SVG进行此类可视化的优势很多:文件较小,可视化功能更强,处理能力更低,动画更快。此外,这些将适用于您心爱的iPhone和iPad!在这里,我们将使用Polymaps来绘制基于Twitter公共时间线存档的人们推文的位置。我们将学习:

1.如何在JSON文件中获取地理位置数据
2.如何用几行代码制作世界地图
3.如何使用JavaScript与SVG交互(在jQuery的帮助下)

虽然我们使用推文进行此可视化,但您可以使用您拥有位置信息的任何数据,包括BrightKite,Foursquare,Gowalla签到,CIA世界图书信息或者您的Web应用程序输出的某些数据。

看一眼Twitter.json在教程文件中注意我是如何捕获我们将在SVG地图上呈现的数据。

介绍Polymaps

Polymaps是一个JavaScript库,可生成类似于的地图谷歌地图要么打开图层。除了支持地图(例如谷歌地图)的图像平铺集外,它还支持可以使用SVG渲染的矢量切片。

矢量几何体通过加载以GeoJSON并且对象被渲染为SVG元素 - 圆形,路径等。使用矢量切片时,渲染在性能和速度方面都是微不足道的,因为它不必像图像切片设置那样多次访问服务器。 Polymaps还提供了多种功能,使您可以添加或删除地理位置,并通过JavaScript触发事件。

因为Polymaps使用SVG,所以您可以简单地使用CSS来设置矢量数据的样式(以及SVG中可用的所有强大的滤镜和渐变)。在本教程中,我们将使用一个JSON文件,其中包含世界地图的坐标(此文件位于世界下载Polymaps时的示例文件夹)。

Polymaps有稀疏的文档。但网上有很多例子(见Polymaps.org/ex- 在zip文件中找到完整的源代码),您可以使用它来更好地理解Polymaps。让我们首先使用JSON文件渲染世界地图。

渲染地图

首先,在包含脚本之前,我们应该在我们的HTML文件中包含Polymaps库。我们也在使用jQuery进行小型操作,所以我们也要包含它:

   

我们使用协议相对URL来加载jQuery(paulirish.com/2010/the-protocol-relative-url)。我们还包括一个本地副本,因此即使在很少从Google服务器检索文件的情况下,该演示也能正常运行。然后我们初始化一个地图Polymaps可以使用并识别其父容器的对象:

var map = po.map().container(document.getElementById('map')。appendChild(po.svg('svg')))。centter({lat:51.48,lon:0});

我们创建一个SVG元素并将其附加到#地图然后传递#地图到了容器()所以Polymaps知道需要输出SVG文件的位置。。中央()获取您希望地图居中的地理坐标(在上面的代码中,这些是格林威治皇家天文台的地理坐标)。与其他地图一样,您可以使用10级缩放。您还可以设置缩放范围,该范围设置用户可以使用的最大和最小缩放级别(有关更多功能,请参阅polymaps.org/docs/map.html)。
现在,我们将解析World.json包含每个国家/地区的文件及其位置信息作为对象。我们将其添加为地图上的图层:

map.add(po.geoJson()。url(“world.json”).tile(false).zoom(3).on(“load”,manipulatemap);

Po.geoJson根据通过的模板传递构造GeoJSON图层.URL()功能。您可以传递JSON文件或带有占位符的URL字符串以返回图像切片(请参阅此示例:polymaps.org/ex/pale-dawn.html) 至URL()

如果您从与托管应用程序的位置不同的主机调用JSON或图像切片,请确保该服务器具有合适的访问控制允许来源标头设置为返回的数据可用。

你会得到两个带有地图图层的事件:加载节目。在上面的代码中,Manipulatemap加载地图后将调用函数。我也希望用户放大和缩小但不要平移,因此我指定:

map.add(po.compass()。pan(“none”));

您希望您的国家/地区出现,因此推文的来源更加清晰。一旦将JSON文件解析为SVG Map层,我们就可以这样做,所以我们这样做了Manipulatemap()。当。。。的时候加载事件被触发,它通过了特征用于从中创建地图的对象以GeoJSON文件。中的每个对象特征Object包含关联的SVG元素(在本例中为aSVGPath元素)和来自的相关信息World.json用来创造它。现在只需为每个国家设置正确的颜色。而不是担心颜色选择,如何动态地做它?

我们希望确保颜色具有凝聚力。在这里,使用HSL表示法会有所帮助。我们设置一个色调,只改变饱和度(随机)和亮度(在边界内):

var feature = e.features [i]; var hue = 29; var sat = Math.round(Math.random()* 99 + 1); var lit = Math.round(Math.random()* 60 + 30); feature.element.setAttribute(“fill”,'hsl('+ hue +“,”+ sat +'%,'+ lit +'%)');

我们将色调设置为29,这为我们提供了一个很好的棕色基础。我们改变饱和度水平(的Math.random()提供介于0和1之间的值。但是,我们希望控制亮度不会偏离边缘太远(因此它只在30%到90%之间变化)。现在,我们为所有国家提供了一种平滑的泥土色调,同时它们具有饱和度和亮度。唯一需要注意的是,桌面和移动设备上的Safari不喜欢SVG中的HSLA - 所以你看到的只是深黑色填充。如果您对颜色不太了解,可以使用RGBA甚至是十六进制单位这样颜色在所有浏览器上都可见。

此时,让我们创建将用于呈现推文的SVG元素。我们只会修改内容和坐标,这样我们就不必为每条新推文销毁和创建新元素。

tweetcontainer = po.svg('g'); location = po.svg('circle'); if(document.implementation.hasFeature(“http://www.w3.org/Graphics/SVG/ feature / 1.2 /#TextFlow”,“1.2”)){tweettext = po.svg(“textArea”); tweettext.setAttribute(“width”,300); tweettext.setAttribute(“height”,200); } else {tweettext = po.svg(“text”); } location.setAttribute('r',5); //设置圆圈的半径tweetcontainer.setAttribute('class','tweet-container'); tweetcontainer.appendChild(tweettext); tweetcontainer.appendChild(位置); SVG [0] .appendChild(tweetcontainer);

Po.svg是Polymaps提供的函数,用于初始化SVG名称空间中的SVG元素。我们可以使用它来创建所有SVG元素,包括表示推文文本和位置的元素。

请注意如果声明?我们正在查询浏览器,告诉我们它是否实现了SVG规范的某些功能。我们想要使用的功能被称为TEXTAREA。它使您能够约束文本的宽度,不像文本元素,不做任何自动换行。没有流行的浏览器实现除了Opera之外的这部分规范。对我们来说幸运的是,浏览器也不会对此撒谎,因此我们可以安全地使用此功能来检测(并使用)TEXTAREA如果实施;否则文本元件。

我们之前没有使用jQuery函数,因为jQuery使用的一些方法需要HTML元素可用的函数而不是SVG元素。我们将推文和圆圈附加到我们的分组元素,并将分组元素附加到我们的根SVG元素。

加载Twitter内容

接下来,我们将解析我们的Twitter数据Showtwitter()。我们需要翻译我们的地理位置数据Twitter.json到SVG地图上的像素坐标。这很容易做到的LocationPoint(),由Polymaps提供。这会将地理位置转换为相对于地图容器的SVG像素坐标:

var mappos = map.locationPoint({lat:tweet.location.x,lon:tweet.location.y});

现在,我们使用我们设置推文和圆圈的坐标Mappos宾语:

location.setAttribute('cx',mappos.x); location.setAttribute('cy',mappos.y); tweettext.setAttribute(“x”,(+ mappos.x + 10)); tweettext.setAttribute(“y”,(+ mappos.y + 5));

然后我们需要用新的推文替换之前的推文:

tweettext.firstChild && tweettext.removeChild(tweettext.firstChild); //如果有一个tweettext.appendChild(document.createTextNode(tweet ['tweet'])),则删除旧的推文; //添加下一条推文

我们终于打电话了Showtwitter定期在地图上显示新的推文。

在流行的浏览器中,只有IE8及以下版本不支持SVG。此演示不适用于这些浏览器。你可以使用这个脚本(来自diveintohtml5.org/everything.html#svg)检测对SVG的支持,如果没有支持,则渲染图形或嵌入Flash文件:

if(!!(document.createElementNS && document.createElementNS('http:// www.w3.org/2000/svg','svg')。createSVGRect)){  } else {  }

你也可以通过添加可动画的SVG元素来扩展它。要了解SVG动画的可能性,请查看这些动画迷幻演示。



翻译字数超限