intersection 相关问题

交叉点是与描述性几何和函数相关的术语。交点是包含在多个对象中的点。它们是它们所属对象的交叉点。

使用 ASP 或 PHP 检查文件是否存在于 2 个目录中

我正在寻找一种方法来比较两个目录以查看两个目录中是否存在文件。我想要做的是删除其中一个目录中的文件(如果两个目录中都存在该文件)。 我可以使用 ASP 或 PHP。 考试...

回答 5 投票 0

使用 MYSQLI 选择列的一部分与输入的一部分匹配的行

我有一个数据库,其中一列包含有关该行的一系列信息“标签”,这些信息“标签”存储为动态长度的逗号分隔列表(字符串)。我正在使用 mysqli ...

回答 1 投票 0

在 WooCommerce 中禁用优惠券代码列表的“购物车需要付款”

我想禁用“购物车需要付款”以获得折扣代码列表: 优惠券1、优惠券2、优惠券3等。 我发现了 @LoicTheAztec 的这段代码,它工作正常,但仅适用于特定的问题...

回答 1 投票 0

如何在 Codeigniter 视图中检查两个结果数组?

我在控制器中有两个结果数组。我想检查第一个数组中的值是否存在于第二个数组中,并显示两个数组中都存在的值......

回答 1 投票 0

Graphviz:相交但非递归集群

我想知道是否可以在 Graphviz 中做这样的事情: 如您所见,节点“二”位于两个集群内,而集群不是递归的。 注意:图像是用 Dia 制作的。

回答 2 投票 0

TypeScript 中扩展接口和相交接口之间的区别?

假设定义了以下类型: 界面形状{ 颜色: 字符串; } 现在,考虑以下方法来向此类型添加其他属性: 扩大 界面 Square 延伸 Shap...

回答 2 投票 0

计算线段之间的交点

我需要帮助来了解如何计算交叉点。我已经阅读了这里的几个问题并查看了其他网站上的几个示例,但我仍然很困惑并且不明白,而且我......

回答 4 投票 0

Unity3D:检测网格与其他游戏对象相交的三角形

我有平面,包含多个网格(像往常一样)。现在,我向场景中添加了新的游戏对象 - 圆柱体。当圆柱体与平面碰撞时,我需要检测平面中出现的所有三角形...

回答 1 投票 0

检查碰撞圈

我有一些圆圈,我知道它们的 X、Y 和 r。我想检查其中是否有任何一个与其他任何碰撞...... 检查方法很简单: r1+r2 < sqrt((x1-x2) 2 +(y1-y2)2) but do I have to check al...

回答 4 投票 0

此代码如何执行“每像素碰撞检测”?

我目前正在尝试了解每像素碰撞检测。 这是我不明白的代码: static bool IntersectPixels(矩形矩形A,颜色[]数据A,

回答 3 投票 0

这段代码如何执行“每像素碰撞”?

我目前正在尝试了解每像素碰撞检测。 这是我不明白的代码: static bool IntersectPixels(矩形矩形A,颜色[]数据A,

回答 3 投票 0

Shapely找不到肯定存在的交点

在我的代码中,我有两条线(line1,line2)在视觉上肯定彼此相交。它们只是从 yfinance 抓取数据的库存行,但是当运行 line1.intersect(line2) 时,它会...

回答 1 投票 0

前瞻断言可以像正则表达式的交集一样工作,但为什么呢? (JavaScript)

根据堆栈溢出中的这篇文章,前瞻断言可以像正则表达式的交集一样工作,但我真的不知道它为什么起作用。 有人可以向我解释一下吗? 看看...

回答 1 投票 0

如何通过每列中元素的交集来合并两列?

想象我有一个像这样的数据框: 在单个字符串中包含元素列表。 data = {'Col1': ["苹果,香蕉,橙子","狗,猫","python,java,c++"], 'C...

回答 1 投票 0

如何在Java中找到两个数组的交集?

尝试找到 2 个数组 a 和 b 的交集并将其存储到新数组 c 中。 预期结果:数组 c,值为:3、10、4、8。 公共静态无效主(字符串[] args){ int[] a = {3, 10...

回答 6 投票 0

opencv python中查找矩形交集的意外结果

希望你今天一切顺利。我试图在 opencv 中找到两个矩形的交集,但结果不是我期望看到的。简而言之: 在: 相交 = obj_1 & obj_2 print('相交:', 相交...

回答 1 投票 0

JSXGraph:直线与一般圆锥曲线的交点和其他交点?

简短版本:如果 E 是一般圆锥曲线,L 是穿过它的线,我想要类似的东西: P = board.create('交叉点',[L,E,0]); Q = board.create('otherintersection',[L,E,P]); 除了...

回答 1 投票 0

该函数无法检测两条曲线的交点

下面的源代码应该找到两条曲线之间的交点。 但是,该函数无法检测交点。 我该如何修复它? 使用 MathNet.Numerics.Interpolati...

回答 1 投票 0

获取SVG路径的边界框

我想要这个页面的功能 http://codepen.io/netsi1964/full/vNoemp/ 我有路径,需要知道它的边界框作为矩形元素,它是 x、y、宽度和高度 给定代码 我想要这个页面的功能 http://codepen.io/netsi1964/full/vNoemp/ 我有路径,需要知道它的边界框作为矩形元素,它是 x,y,宽度和高度 给定代码 <path d="M147.5 55.8c-5.8-7.2-13.6-14.4-25.5-14.4-8.4 0-15.4 8.2-27 8.2-9 0-13-7.8-23-7.8C51.4 41.8 31 60.4 31 84.5c0 12.8 4.2 32.5 13.6 49.7C51 146.7 59.4 155 69 155c6.7 0 14.7-6.3 24.2-6.3 8.4 0 16.2 5.6 23.8 5.6 18 0 35-23.5 35-39.3 0-.8-.3-1.4-.3-2v-1c-11.8-6.3-18.2-15.7-18.2-29.3 0-11 4.8-20.5 13.6-26.7l.5-.2zm-53-8.8c13.7-4.2 26.3-14.4 26.3-32 0-1.5-.2-3.3-.4-5.3l-.2-.8C106.4 12.6 94 23.4 94 40.3c0 1.6.2 3.6.6 5.8v.8z" style="translate(0px,-212.47488403320312px) scale(1,1)" > 并了解 rect 属性 使用纯 JavaScript:为您的路径提供一个 ID,并使用 getBBox() 获取其边界框。 var myPathBox = document.getElementById("myPath").getBBox(); console.log(myPathBox); 这是一个演示: var myPathBox = document.getElementById("myPath").getBBox(); console.log(myPathBox); <svg width="400" height="400"> <path id="myPath" d="M147.5 55.8c-5.8-7.2-13.6-14.4-25.5-14.4-8.4 0-15.4 8.2-27 8.2-9 0-13-7.8-23-7.8C51.4 41.8 31 60.4 31 84.5c0 12.8 4.2 32.5 13.6 49.7C51 146.7 59.4 155 69 155c6.7 0 14.7-6.3 24.2-6.3 8.4 0 16.2 5.6 23.8 5.6 18 0 35-23.5 35-39.3 0-.8-.3-1.4-.3-2v-1c-11.8-6.3-18.2-15.7-18.2-29.3 0-11 4.8-20.5 13.6-26.7l.5-.2zm-53-8.8c13.7-4.2 26.3-14.4 26.3-32 0-1.5-.2-3.3-.4-5.3l-.2-.8C106.4 12.6 94 23.4 94 40.3c0 1.6.2 3.6.6 5.8v.8z" style="translate(0px,-212.47488403320312px) scale(1,1)" > </svg> getBBox() 要求将您的元素附加到 DOM。 如果您无法使用本机支持的 getBBox() 方法,例如因为您在虚拟 DOM 环境中工作,您还可以根据原始路径数据d字符串计算边界框。 要求 您需要一个路径数据解析器,将 d 路径数据属性字符串转换为可计算命令值的数组。我正在使用基于 SVGPathData 接口方法的 w3c 工作草案的独立解析器,但您也可以使用 Jarek Foksa 的 getPathData polyfill。 将这些命令转换为所有绝对命令和“普通”命令(速记/反射命令,如 h 、 v、s、t 需要标准化为其对应的普通命令) 计算二次和三次贝塞尔命令中极值点的 x/y t 值 – 然后计算这些 t 值处的实际点坐标。参见崔西平的回答“计算三次贝塞尔曲线的边界框” 计算 A 弧线命令的 x/y 极值点 - 需要对弧线命令值进行参数化(rx、ry、角度、largearc、sweep、finalX、finalY) - 基于这篇文章 “如何计算轴-椭圆的对齐边界框?” // wrapper function to calculate boundaries for aeach segment type function getPathBBox(pathData) { let M = { x: pathData[0].values[0], y: pathData[0].values[1] } let xArr = [M.x]; let yArr = [M.y]; for (let i = 1; i < pathData.length; i++) { let com = pathData[i] let { type, values } = com; let valuesL = values.length; let comPrev = pathData[i - 1] let valuesPrev = comPrev.values; let valuesPrevL = valuesPrev.length; if (valuesL) { let p0 = { x: valuesPrev[valuesPrevL - 2], y: valuesPrev[valuesPrevL - 1] }; let p = { x: values[valuesL - 2], y: values[valuesL - 1] }; // add final on path point xArr.push(p.x) yArr.push(p.y) if (type === 'C' || type === 'Q') { let cp1 = { x: values[0], y: values[1] }; let cp2 = type === 'C' ? { x: values[2], y: values[3] } : cp1; let pts = type === 'C' ? [p0, cp1, cp2, p] : [p0, cp1, p]; let bezierExtremesT = getBezierExtremeT(pts) bezierExtremesT.forEach(t => { let pt = getPointAtBezierT(pts, t); xArr.push(pt.x); yArr.push(pt.y); }) } else if (type === 'A') { let arcExtremes = getArcExtemes(p0, values) arcExtremes.forEach(pt => { xArr.push(pt.x); yArr.push(pt.y); }) } } } let xMin = Math.min(...xArr) let xMax = Math.max(...xArr) let yMin = Math.min(...yArr) let yMax = Math.max(...yArr) let bbox = { x: xMin, y: yMin, width: xMax - xMin, height: yMax - yMin } return bbox } // wrapper functions for quadratic or cubic bezier point calculation function getPointAtBezierT(pts, t) { let pt = pts.length === 4 ? getPointAtCubicSegmentT(pts[0], pts[1], pts[2], pts[3], t) : getPointAtQuadraticSegmentT(pts[0], pts[1], pts[2], t) return pt } function getBezierExtremeT(pts) { let tArr = pts.length === 4 ? cubicBezierExtremeT(pts[0], pts[1], pts[2], pts[3]) : quadraticBezierExtremeT(pts[0], pts[1], pts[2]); return tArr; } /** * based on Nikos M.'s answer * how-do-you-calculate-the-axis-aligned-bounding-box-of-an-ellipse * https://stackoverflow.com/questions/87734/#75031511 */ function getArcExtemes(p0, values) { // compute point on ellipse from angle around ellipse (theta) const arc = (theta, cx, cy, rx, ry, alpha) => { // theta is angle in radians around arc // alpha is angle of rotation of ellipse in radians var cos = Math.cos(alpha), sin = Math.sin(alpha), x = rx * Math.cos(theta), y = ry * Math.sin(theta); return { x: cx + cos * x - sin * y, y: cy + sin * x + cos * y }; } //parametrize arcto data let arcData = svgArcToCenterParam(p0.x, p0.y, values[0], values[1], values[2], values[3], values[4], values[5], values[6]); let { rx, ry, pt, endAngle, deltaAngle } = arcData; // arc rotation let deg = values[2]; // final on path point let p = { x: values[5], y: values[6] } // circle/elipse center coordinates let [cx, cy] = [pt.x, pt.y]; // collect extreme points – add end point let extremes = [p] // rotation to radians let alpha = deg * Math.PI / 180; let tan = Math.tan(alpha), p1, p2, p3, p4, theta; // find min/max from zeroes of directional derivative along x and y // along x axis theta = Math.atan2(-ry * tan, rx); let angle1 = theta; let angle2 = theta + Math.PI; let angle3 = Math.atan2(ry, rx * tan); let angle4 = angle3 + Math.PI; // get point for this theta p1 = arc(angle1, cx, cy, rx, ry, alpha); // get anti-symmetric point p2 = arc(angle2, cx, cy, rx, ry, alpha); // get point for this theta p3 = arc(angle3, cx, cy, rx, ry, alpha); // get anti-symmetric point p4 = arc(angle4, cx, cy, rx, ry, alpha); // inner bounding box let xArr = [p0.x, p.x] let yArr = [p0.y, p.y] let xMin = Math.min(...xArr) let xMax = Math.max(...xArr) let yMin = Math.min(...yArr) let yMax = Math.max(...yArr) // on path point close after start let angleAfterStart = endAngle - deltaAngle * 0.001 let pP2 = arc(angleAfterStart, cx, cy, rx, ry, alpha); // on path point close before end let angleBeforeEnd = endAngle - deltaAngle * 0.999 let pP3 = arc(angleBeforeEnd, cx, cy, rx, ry, alpha); /** * expected extremes * if leaving inner bounding box * (between segment start and end point) * otherwise exclude elliptic extreme points */ // left if (pP2.x < xMin || pP3.x < xMin) { extremes.push(p2) } // top if (pP2.y < yMin || pP3.y < yMin) { extremes.push(p4) } // right if (pP2.x > xMax || pP3.x > xMax) { extremes.push(p1) } // bottom if (pP2.y > yMax || pP3.y > yMax) { extremes.push(p3) } return extremes; } // wrapper functions for quadratic or cubic bezier point calculation function getPointAtBezierT(pts, t) { let pt = pts.length === 4 ? getPointAtCubicSegmentT(pts[0], pts[1], pts[2], pts[3], t) : getPointAtQuadraticSegmentT(pts[0], pts[1], pts[2], t) return pt } function getBezierExtremeT(pts) { let tArr = pts.length === 4 ? cubicBezierExtremeT(pts[0], pts[1], pts[2], pts[3]) : quadraticBezierExtremeT(pts[0], pts[1], pts[2]); return tArr; } // cubic bezier function cubicBezierExtremeT(p0, cp1, cp2, p) { let [x0, y0, x1, y1, x2, y2, x3, y3] = [p0.x, p0.y, cp1.x, cp1.y, cp2.x, cp2.y, p.x, p.y]; let extemeT = [], a, b, c, t, t1, t2, b2ac, sqrt_b2ac; for (let i = 0; i < 2; ++i) { if (i == 0) { b = 6 * x0 - 12 * x1 + 6 * x2; a = -3 * x0 + 9 * x1 - 9 * x2 + 3 * x3; c = 3 * x1 - 3 * x0; } else { b = 6 * y0 - 12 * y1 + 6 * y2; a = -3 * y0 + 9 * y1 - 9 * y2 + 3 * y3; c = 3 * y1 - 3 * y0; } if (Math.abs(a) < 1e-12) { if (Math.abs(b) < 1e-12) { continue; } t = -c / b; if (0 < t && t < 1) { extemeT.push(t); } continue; } b2ac = b * b - 4 * c * a; if (b2ac < 0) { if (Math.abs(b2ac) < 1e-12) { t = -b / (2 * a); if (0 < t && t < 1) { extemeT.push(t); } } continue; } sqrt_b2ac = Math.sqrt(b2ac); t1 = (-b + sqrt_b2ac) / (2 * a); if (0 < t1 && t1 < 1) { extemeT.push(t1); } t2 = (-b - sqrt_b2ac) / (2 * a); if (0 < t2 && t2 < 1) { extemeT.push(t2); } } var j = extemeT.length; while (j--) { t = extemeT[j]; } return extemeT; } // quadratic bezier. function quadraticBezierExtremeT(p0, cp1, p) { let [x0, y0, x1, y1, x2, y2] = [p0.x, p0.y, cp1.x, cp1.y, p.x, p.y]; let extemeT = []; for (var i = 0; i < 2; ++i) { a = i == 0 ? x0 - 2 * x1 + x2 : y0 - 2 * y1 + y2; b = i == 0 ? -2 * x0 + 2 * x1 : -2 * y0 + 2 * y1; c = i == 0 ? x0 : y0; if (Math.abs(a) > 1e-12) { t = -b / (2 * a); if (t > 0 && t < 1) { extemeT.push(t); } } } return extemeT } /** * parse pathData from d attribute * the core function to parse the pathData array from a d string **/ function parseDtoPathData(d) { let dClean = d // remove new lines and tabs .replace(/[\n\r\t]/g, "") // replace comma with space .replace(/,/g, " ") // add space before minus sign .replace(/(\d+)(\-)/g, "$1 $2") // decompose multiple adjacent decimal delimiters like 0.5.5.5 => 0.5 0.5 0.5 .replace(/(\.)(?=(\d+\.\d+)+)(\d+)/g, "$1$3 ") // add new lines before valid command letters .replace(/([mlcsqtahvz])/gi, "\n$1 ") // remove duplicate whitespace .replace(/\ {2,}/g, " ") // remove whitespace from right and left .trim(); // split commands let commands = dClean.split("\n").map((val) => { return val.trim(); }); // compile pathData let pathData = []; let comLengths = { m: 2, a: 7, c: 6, h: 1, l: 2, q: 4, s: 4, t: 2, v: 1, z: 0 }; let errors = []; // normalize convatenated larceArc and sweep flags const unravelArcValues = (values) => { let chunksize = 7, n = 0, arcComs = [] for (let i = 0; i < values.length; i++) { let com = values[i] // reset counter if (n >= chunksize) { n = 0 } // if 3. or 4. parameter longer than 1 if ((n === 3 || n === 4) && com.length > 1) { let largeArc = n === 3 ? com.substring(0, 1) : '' let sweep = n === 3 ? com.substring(1, 2) : com.substring(0, 1) let finalX = n === 3 ? com.substring(2) : com.substring(1) let comN = [largeArc, sweep, finalX].filter(Boolean) arcComs.push(comN) n += comN.length } else { // regular arcComs.push(com) n++ } } return arcComs.flat().filter(Boolean); } for (let i = 0; i < commands.length; i++) { let com = commands[i].split(" "); let type = com.shift(); let typeRel = type.toLowerCase(); let isRel = type === typeRel; /** * large arc and sweep flags * are boolean and can be concatenated like * 11 or 01 * or be concatenated with the final on path points like * 1110 10 => 1 1 10 10 */ if (typeRel === "a") { com = unravelArcValues(com) } // convert to numbers let values = com.map((val) => { return parseFloat(val); }); // if string contains repeated shorthand commands - split them let chunkSize = comLengths[typeRel]; let chunk = values.slice(0, chunkSize); pathData.push({ type: type, values: chunk }); // too few values if (chunk.length < chunkSize) { errors.push( `${i}. command (${type}) has ${chunk.length}/${chunkSize} values - ${chunkSize - chunk.length} too few` ); } // has implicit commands if (values.length > chunkSize) { let typeImplicit = typeRel === "m" ? (isRel ? "l" : "L") : type; for (let i = chunkSize; i < values.length; i += chunkSize) { let chunk = values.slice(i, i + chunkSize); pathData.push({ type: typeImplicit, values: chunk }); if (chunk.length !== chunkSize) { errors.push( `${i}. command (${type}) has ${chunk.length + chunkSize}/${chunkSize} - ${chunk.length} values too many ` ); } } } } if (errors.length) { console.log(errors); } /** * first M is always absolute/uppercase - * unless it adds relative linetos * (facilitates d concatenating) */ pathData[0].type = 'M' return pathData; } /** * converts all commands to absolute */ function pathDataToLonghands(pathData) { let pathDataAbs = []; let offX = pathData[0].values[0]; let offY = pathData[0].values[1]; let lastX = offX; let lastY = offY; // analyze pathdata let commandTokens = pathData.map(com => { return com.type }).join('') let hasShorthands = /[hstv]/gi.test(commandTokens); pathData.forEach((com, i) => { let { type, values } = com; let typeRel = type.toLowerCase(); let typeAbs = type.toUpperCase(); let valuesL = values.length; let isRelative = type === typeRel; let comPrev = i > 0 ? pathData[i - 1] : pathData[0]; let valuesPrev = comPrev.values; let valuesPrevL = valuesPrev.length; if (isRelative) { com.type = typeAbs; switch (typeRel) { case "a": com.values = [ values[0], values[1], values[2], values[3], values[4], values[5] + offX, values[6] + offY ]; break; case "h": case "v": com.values = type === 'h' ? [values[0] + offX] : [values[0] + offY]; break; case 'm': case 'l': case 't': com.values = [values[0] + offX, values[1] + offY] break; case "c": com.values = [ values[0] + offX, values[1] + offY, values[2] + offX, values[3] + offY, values[4] + offX, values[5] + offY ]; break; case "q": case "s": com.values = [ values[0] + offX, values[1] + offY, values[2] + offX, values[3] + offY, ]; break; } } // is absolute else { offX = 0; offY = 0; } /** * convert shorthands */ if (hasShorthands) { let cp1X, cp1Y, cpN1X, cpN1Y, cp2X, cp2Y; if (com.type === 'H' || com.type === 'V') { com.values = com.type === 'H' ? [com.values[0], lastY] : [lastX, com.values[0]]; com.type = 'L'; } else if (com.type === 'T' || com.type === 'S') { [cp1X, cp1Y] = [valuesPrev[0], valuesPrev[1]]; [cp2X, cp2Y] = valuesPrevL > 2 ? [valuesPrev[2], valuesPrev[3]] : [valuesPrev[0], valuesPrev[1]]; // new control point cpN1X = com.type === 'T' ? lastX + (lastX - cp1X) : 2 * lastX - cp2X; cpN1Y = com.type === 'T' ? lastY + (lastY - cp1Y) : 2 * lastY - cp2Y; com.values = [cpN1X, cpN1Y, com.values].flat(); com.type = com.type === 'T' ? 'Q' : 'C'; } } // add command pathDataAbs.push(com) // update offsets lastX = valuesL > 1 ? values[valuesL - 2] + offX : (typeRel === 'h' ? values[0] + offX : lastX); lastY = valuesL > 1 ? values[valuesL - 1] + offY : (typeRel === 'v' ? values[0] + offY : lastY); offX = lastX; offY = lastY; }); return pathDataAbs; } /** * Linear interpolation (LERP) helper */ function interpolatedPoint(p1, p2, t = 0.5) { return { x: (p2.x - p1.x) * t + p1.x, y: (p2.y - p1.y) * t + p1.y }; } /** * calculate single points on segments */ function getPointAtCubicSegmentT(p0, cp1, cp2, p, t = 0.5) { let t1 = 1 - t; return { x: t1 ** 3 * p0.x + 3 * t1 ** 2 * t * cp1.x + 3 * t1 * t ** 2 * cp2.x + t ** 3 * p.x, y: t1 ** 3 * p0.y + 3 * t1 ** 2 * t * cp1.y + 3 * t1 * t ** 2 * cp2.y + t ** 3 * p.y }; } function getPointAtQuadraticSegmentT(p0, cp1, p, t = 0.5) { let t1 = 1 - t; return { x: t1 * t1 * p0.x + 2 * t1 * t * cp1.x + t ** 2 * p.x, y: t1 * t1 * p0.y + 2 * t1 * t * cp1.y + t ** 2 * p.y }; } /** * based on @cuixiping; * https://stackoverflow.com/questions/9017100/calculate-center-of-svg-arc/12329083#12329083 */ function svgArcToCenterParam(x1, y1, rx, ry, degree, fA, fS, x2, y2) { const radian = (ux, uy, vx, vy) => { let dot = ux * vx + uy * vy; let mod = Math.sqrt((ux * ux + uy * uy) * (vx * vx + vy * vy)); let rad = Math.acos(dot / mod); if (ux * vy - uy * vx < 0) { rad = -rad; } return rad; }; // degree to radian let phi = (degree * Math.PI) / 180; let cx, cy, startAngle, deltaAngle, endAngle; let PI = Math.PI; let PIx2 = PI * 2; if (rx < 0) { rx = -rx; } if (ry < 0) { ry = -ry; } if (rx == 0 || ry == 0) { // invalid arguments throw Error("rx and ry can not be 0"); } let s_phi = Math.sin(phi); let c_phi = Math.cos(phi); let hd_x = (x1 - x2) / 2; // half diff of x let hd_y = (y1 - y2) / 2; // half diff of y let hs_x = (x1 + x2) / 2; // half sum of x let hs_y = (y1 + y2) / 2; // half sum of y // F6.5.1 let x1_ = c_phi * hd_x + s_phi * hd_y; let y1_ = c_phi * hd_y - s_phi * hd_x; // F.6.6 Correction of out-of-range radii // Step 3: Ensure radii are large enough let lambda = (x1_ * x1_) / (rx * rx) + (y1_ * y1_) / (ry * ry); if (lambda > 1) { rx = rx * Math.sqrt(lambda); ry = ry * Math.sqrt(lambda); } let rxry = rx * ry; let rxy1_ = rx * y1_; let ryx1_ = ry * x1_; let sum_of_sq = rxy1_ * rxy1_ + ryx1_ * ryx1_; // sum of square if (!sum_of_sq) { throw Error("start point can not be same as end point"); } let coe = Math.sqrt(Math.abs((rxry * rxry - sum_of_sq) / sum_of_sq)); if (fA == fS) { coe = -coe; } // F6.5.2 let cx_ = (coe * rxy1_) / ry; let cy_ = (-coe * ryx1_) / rx; // F6.5.3 cx = c_phi * cx_ - s_phi * cy_ + hs_x; cy = s_phi * cx_ + c_phi * cy_ + hs_y; let xcr1 = (x1_ - cx_) / rx; let xcr2 = (x1_ + cx_) / rx; let ycr1 = (y1_ - cy_) / ry; let ycr2 = (y1_ + cy_) / ry; // F6.5.5 startAngle = radian(1.0, 0, xcr1, ycr1); // F6.5.6 deltaAngle = radian(xcr1, ycr1, -xcr2, -ycr2); while (deltaAngle > PIx2) { deltaAngle -= PIx2; } while (deltaAngle < 0) { deltaAngle += PIx2; } if (fS == false || fS == 0) { deltaAngle -= PIx2; } endAngle = startAngle + deltaAngle; while (endAngle > PIx2) { endAngle -= PIx2; } while (endAngle < 0) { endAngle += PIx2; } let toDegFactor = 180 / PI; let outputObj = { pt: { x: cx, y: cy }, rx: rx, ry: ry, startAngle_deg: startAngle * toDegFactor, startAngle: startAngle, deltaAngle_deg: deltaAngle * toDegFactor, deltaAngle: deltaAngle, endAngle_deg: endAngle * toDegFactor, endAngle: endAngle, clockwise: fS == true || fS == 1 }; return outputObj; } <svg id="svg" width="400" height="400"> <path id="path" d="M147.5 55.8c-5.8-7.2-13.6-14.4-25.5-14.4-8.4 0-15.4 8.2-27 8.2-9 0-13-7.8-23-7.8C51.4 41.8 31 60.4 31 84.5c0 12.8 4.2 32.5 13.6 49.7C51 146.7 59.4 155 69 155c6.7 0 14.7-6.3 24.2-6.3 8.4 0 16.2 5.6 23.8 5.6 18 0 35-23.5 35-39.3 0-.8-.3-1.4-.3-2v-1c-11.8-6.3-18.2-15.7-18.2-29.3 0-11 4.8-20.5 13.6-26.7l.5-.2zm-53-8.8c13.7-4.2 26.3-14.4 26.3-32 0-1.5-.2-3.3-.4-5.3l-.2-.8C106.4 12.6 94 23.4 94 40.3c0 1.6.2 3.6.6 5.8v.8z"> </svg> <script> window.addEventListener('DOMContentLoaded', e => { let d = path.getAttribute('d') let pathData = parseDtoPathData(d) // normalize to all absolute and longhands pathData = pathDataToLonghands(pathData) // calculate bounding box let bbPath = getPathBBox(pathData); // render bounding box let { x, y, width, height } = bbPath; let rect = document.createElementNS('http://www.w3.org/2000/svg', 'rect') rect.setAttribute('x', x) rect.setAttribute('y', y) rect.setAttribute('width', width) rect.setAttribute('height', height) rect.setAttribute('fill', 'none') rect.setAttribute('stroke', 'red') svg.append(rect) }) </script> 我知道这是一个老问题,但我想我会把这个变体放到 Furtado 的答案中以供参考。 获取路径边界框的简单方法。 确保路径(或任何其他 SVG 元素上有一个 id。 在 Chrome(或 FF 或可能 IE)中打开 svg 文件。 检查图像 打开检查工具中的控制台。 输入JS:document.getElementById("myPath").getBBox(); (在哪里 myPath 是 id) 边界框信息将显示在控制台中。 同样的方法,只是不需要自定义代码。

回答 3 投票 0

使用JFrame开发java游戏时的碰撞(交叉)问题

我正在制作一个2d java游戏,玩家需要射击瓷砖。 我在代码中遇到了一个错误,子弹会摧毁附近的瓷砖,但并不总是而且不正确。 问题视频记录 你看,我想要

回答 1 投票 0

© www.soinside.com 2019 - 2024. All rights reserved.