使用 javaScript 解析 SVG 路径字符串以提取初始 x,y 坐标的最简单方法


path[1].innerHTML 

返回

  <path d="M 5,10 l0,0 l 15 ,0l0,15l-15,0l0,-15 z" ....

M 之后的前 2 位数字是 SVG 路径起点的 x,y 坐标。

path[1].innerHTML.substr(10,2)

返回 x cordinate (5( 和

path[1].innerHTML.substr(13,2) 

返回正确的 y 坐标。问题是这些值可能是一位数、两位数或三位数字,这将破坏 substr(( 的执行方式。

浏览器内置了一个解析器,使用它,否则你只会把你的一生花在轮子重塑和错误修复上。

注意 对于 Chrome,您需要使用填充代码

var path = document.getElementById("p");
var item1 = path.pathSegList[0];
alert("first co-ordinate is " + item1.x + ", " + item1.y);
<svg>
    <path id="p" d="M 5,10 l0,0 l 15 ,0l0,15l-15,0l0,-15 z"/>
</svg>

getPathData()

您还可以将getPathData()方法与 polyfill 一起使用(目前仍然是本机不支持的草稿(。

let path = document.querySelector('#path');
let pathData = path.getPathData();
let M = pathData[0]; //first M command
let [Mx, My] = M.values;
console.log('M coordinates:', Mx, My);
<svg width="20px" height="20px" viewBox="5 10 15 15">
  <path id="path" d="M5 10l0 0l15 0l0 15l-15 0l0-15z" />
</svg>
<script src="https://cdn.jsdelivr.net/npm/path-data-polyfill@latest/path-data-polyfill.min.js"></script>

规范化属性d路径并拆分为数组

svg d 属性允许许多速记符号,例如

  • 命令字母和值之间的可选空格:M1 1M 1 1
  • 逗号、空格或减号(仅适用于负值(作为分隔符M -1,-1M -1 -1M-1-1
  • 串联浮点值,如 M.5.5M 0.5 0.5
  • 和其他像重复的隐式命令m.5.5 0 0M 0.5 0.5 l0 0

这就是为什么我们需要在拆分之前对其进行规范化/消毒的原因

let d = path1.getAttribute('d');
let M = getMCoordinates(d);
console.log(M);

function getMCoordinates(d){
  
  let dArray = d
  // remove new lines and tabs
  .replace(/[nrt]/g, "")
  // replace comma with space
  .replace(/,/g, " ")
  // add space before minus sign
  .replace(/-/g, " -")
  // decompose multiple decimal delimiters like 0.5.5 => 0.5 0.5
  .replace(/(.)(d+)(.)(d+)/g, "$1$2 $3$4")
  // split multiple zero valuues like 0 05 => 0 0 5
  .replace(/( )(0)(d+)/g, "$1 $2 $3")
  // add space between command letter and values
  .replace(/([mlcsqtahvz])/gi, "|$1 ")
  .trim()
  .split(" ")
  .filter(Boolean);
  
  let M = {x: +dArray[1], y: +dArray[2]}
  return M;
  
}
<svg viewBox="0 0 100 100">
<!-- what a mess, but perfectly valid ... -->
  <path id="path1" d="
  m.5.5 0 0 l 15    0l0,15l-15,0 l0,-15 z
"/>
</svg>

一个简单的方法是根据字符串的已知格式拆分字符串,并将 x,y 放在您期望的位置:

const path = "M 5,10 l0,0 l 15 ,0l0,15l-15,0l0,-15 z",
      splitted = path.split(" ")[1].split(","),
      x = splitted[0],
      y = splitted[1];
console.log(x,y);

您也可以使用正则表达式,但它可能并不简单。

使用pathSegList接口:

var path = document.querySelector('path');
var moveto =  path.pathSegList[0]; // always the first movoto command
var x = movoto.x, y = moveto.y

最新更新