背景
我需要为学校制作一个分层地图,但是我发现市面上的分层地图制作流程极其麻烦(关键是花费颇高),常见思路有以下几中
- HTML Canvas硬画,如题,就是硬生生用css在原有图像(常见png等)上面绘制一层画布,然后添加n多区域,所有的区域都需要手动指定位置、大小等参数
- 优点:简单,但是麻烦,呈现效果直观
- 缺点:我要画700多个房间,不如直接让我死;此外,难以修改,修改不能直接看,改点东西费时费力还容易出错
- 借助cad等已有的原始分层稿件转换
- 优点:特别简单易行
- 缺点:我不会cad、我的垃圾电脑带不动cad、cad绘图也不是很简单……
- 借助在线分层地图制作平台
- 优点:简单易行
- 缺点:往往需要大量金钱、都是些小平台,一倒闭就完蛋了
- WebGL
- 优点:适合超大规模场景
- 缺点:也只适合超大规模场景了,小项目简直就是杀鸡焉用牛刀,并且从字体显示到交互,一切都需要手动实现……
所以,我最终自己想了个邪门办法,即—— SVG+CSS !(我真不知道前人有没有人用过,反正我没搜到相关公开资料……)
原理与实现简介
- svg本质上是 DOM 节点,可以像 HTML 一样被操作
- 通过
<g>标签可以自然地对图形元素进行分组,每个组、每个元素可以分别设置不同格式与样式 - 可以直接在任意元素上绑定 click、hover 等事件
- 可以通过 CSS 类来控制不同层级的显示/隐藏状态、或更改其显示效果等
- SVG在不选择“以曲线形式保存文字”时,文字是原样储存在svg源码中的,比如以下svg图片是一个无框线、填充为纯红色的、名字叫做“测试矩形”的矩形
<?xml version="1.0" encoding="UTF-8" standalone="no"?><!DOCTYPE svg PUBLIC "-//W3C//DTD SVG 1.1//EN" "http://www.w3.org/Graphics/SVG/1.1/DTD/svg11.dtd"><svg width="2481px" height="3508px" version="1.1" xmlns="http://www.w3.org/2000/svg" xmlns:xlink="http://www.w3.org/1999/xlink" xml:space="preserve" xmlns:serif="http://www.serif.com/" style="fill-rule:evenodd;clip-rule:evenodd;stroke-linejoin:round;stroke-miterlimit:2;"><rect id="测试矩形" x="226.961" y="1078.47" width="1203.35" height="788.988" style="fill:#f00;"/></svg> - 因此,我们可以借助上述的原理,以相同的底图,但是不同的矩形或其它路径色块实现多张svg图片的制作,再把他们作为分层地图的底稿。接下来,便只需要处理路径的显示了(个人推荐分别为各楼层导出多张图片,当然你也可以显示全部图层,然后通过css控制各楼层的显示隐藏(优点太费工夫了,反而不如第一种简单粗暴更有效))
- 路径显示的做法也很简单
- 读取图片
- 解析DOM
- 提取楼层信息并进行对应
- 建立映射关系
- 用响应式变量(如
currentFloor)记录当前楼层 - 根据当前楼层状态,应用不同的 CSS 类(比如改变透明度等)
- 监听搜索按钮点击(或其它交互,原理一样),更新
currentFloor状态
最终效果
搜索该区域后,将高亮显示搜索区域并持续闪烁。
门牌号示例:21212,31313,12121,22021,11104等