Canvas 文字碰撞检测并抽稀的方法


Posted in HTML / CSS onMay 27, 2019

需求背景

一般在做地图相关的需求是才会用到文字抽稀,我也是在为公司的地图引擎实现一个功能时才实现了该方法,在这里将其简化了,就在普通的 Canvas 上进行操作,并没有引入地图概念

效果

Canvas 文字碰撞检测并抽稀的方法

碰撞检测

计算文字在 canvas 中所占据的范围

// 计算文字所需的宽度
var p = {
  x: 10,
  y: 10,
  name: "测试文字"
};
var measure = ctx.measureText(p.name);
// 求出文字在 canvas 画板中占据的最大 y 坐标
var maxX = measure.width + p.x;
// 求出文字在 canvas 画板中占据的最大 y 坐标
// canvas 只能计算文字的宽度,并不能计算出文字的高度。所以就利用文字的宽度除以文字个数计算个大概
var maxY = measure.width / p.name.length + p.y;

var min = { x: p.x, y: p.y };
var max = { x: maxX, y: maxY };
// bounds 为该文字在 canvas 中所占据的范围。
// 在取点位坐标作为最小范围时,textAlign、textBaseline 按照以下方式设置会比较准确。
// 如设置在不同的位置展示,范围最大、最小点也需进行调整
// ctx.textAlign = "left";
// ctx.textBaseline = "top";
var bounds = new Bounds(min, max);

Bounds 范围对象

/**
 * 定义范围对象
 */
function Bounds(min, max) {
  this.min = min;
  this.max = max;
}

/**
 * 判断范围是否与另外一个范围有交集
 */
Bounds.prototype.intersects = function(bounds) {
  var min = this.min,
    max = this.max,
    min2 = bounds.min,
    max2 = bounds.max,
    xIntersects = max2.x >= min.x && min2.x <= max.x,
    yIntersects = max2.y >= min.y && min2.y <= max.y;

  return xIntersects && yIntersects;
};

检测

// 每次绘制之前先与已绘制的文字进行范围交叉检测
// 如发现有交叉,则放弃绘制当前文字,否则绘制并存入已绘制文字列表
for (var index in _textBounds) {
  // 循环所有已绘制的文字范围,检测是否和当前文字范围有交集,如果有交集说明会碰撞,则跳过该文字
  var pointBounds = _textBounds[index];
  if (pointBounds.intersects(bounds)) {
    return;
  }
}

_textBounds.push(bounds);
ctx.fillStyle = "red";
ctx.textAlign = "left";
ctx.textBaseline = "top";
ctx.fillText(p.name, p.x, p.y);

示例、代码地址

示例地址:示例

具体可查看完整代码:Github 地址

以上就是本文的全部内容,希望对大家的学习有所帮助,也希望大家多多支持三水点靠木。

HTML / CSS 相关文章推荐
前端制作动画的几种方式(css3,js)
Dec 12 HTML / CSS
一款纯css3实现的tab选项卡的实列教程
Dec 11 HTML / CSS
CSS3 3D旋转rotate效果实例介绍
May 03 HTML / CSS
基于 HTML5 Canvas实现 的交互式地铁线路图
Mar 05 HTML / CSS
HTML5离线缓存在tomcat下部署可实现图片flash等离线浏览
Dec 13 HTML / CSS
html5贪吃蛇游戏使用63行代码完美实现
Jun 25 HTML / CSS
html5弹跳球示例代码
Jul 23 HTML / CSS
使用jTopo给Html5 Canva中绘制的元素添加鼠标事件
May 15 HTML / CSS
HTML 5.1来了 9月份正式发布 更新内容预览
Apr 26 HTML / CSS
html5开发三八女王节表白神器
Mar 07 HTML / CSS
css height属性中的calc方法详解
Jun 03 HTML / CSS
HTML5 语义化标签(移动端必备)
Aug 23 HTML / CSS
利用canvas实现图片下载功能来实现浏览器兼容问题
May 31 #HTML / CSS
HTML5印章绘制电子签章图片(中文英文椭圆章、中文英文椭圆印章)
Jun 03 #HTML / CSS
详解利用canvas实现环形进度条的方法
Jun 12 #HTML / CSS
Html5 实现微信分享及自定义内容的流程
Aug 20 #HTML / CSS
前端canvas动画如何转成mp4视频的方法
Jun 17 #HTML / CSS
详解FireFox下Canvas使用图像合成绘制SVG的Bug
Jul 10 #HTML / CSS
canvas实现有递增动画的环形进度条的实现方法
Jul 10 #HTML / CSS
You might like
文件上传类
2006/10/09 PHP
PHP获取远程图片并保存到本地的方法
2015/05/12 PHP
一张表搞清楚php is_null、empty、isset的区别
2015/07/07 PHP
yii2学习教程之5种内置行为类详解
2017/08/03 PHP
广告显示判断
2006/08/31 Javascript
jQuery 白痴级入门教程
2009/11/11 Javascript
js实现的仿新浪微博完美的时间组件升级版
2011/12/20 Javascript
js动态拼接正则表达式的两种方法
2014/03/04 Javascript
jquery中的ajax方法怎样通过JSONP进行远程调用
2014/05/04 Javascript
DOM操作一些常用的属性汇总
2015/03/13 Javascript
微信小程序 UI布局常用技巧整理总结
2016/12/05 Javascript
文件上传的几个示例分享【推荐】
2016/12/16 Javascript
jsonp跨域请求实现示例
2017/03/13 Javascript
javascript编写简易计算器
2017/05/06 Javascript
ajax请求data遇到的问题分析
2018/01/18 Javascript
bootstrap table支持高度百分比的实例代码
2018/02/28 Javascript
ng-alain表单使用方式详解
2018/07/10 Javascript
使用Phantomjs和Node完成网页的截屏快照的方法
2019/07/16 Javascript
使用js实现一个简单的滚动条过程解析
2019/09/10 Javascript
JS如何把字符串转换成json
2020/02/21 Javascript
python3模拟百度登录并实现百度贴吧签到示例分享(百度贴吧自动签到)
2014/02/24 Python
Python人脸识别第三方库face_recognition接口说明文档
2019/05/03 Python
python logging日志模块原理及操作解析
2019/10/12 Python
python中的线程threading.Thread()使用详解
2019/12/17 Python
Python 实现 T00ls 自动签到脚本代码(邮件+钉钉通知)
2020/07/06 Python
大学生家政服务项目创业计划书
2014/01/30 职场文书
环境建设实施方案
2014/03/14 职场文书
教师对学生的寄语
2014/04/03 职场文书
团拜会策划方案
2014/06/07 职场文书
高职教师先进事迹材料
2014/08/24 职场文书
学生上课看漫画的检讨书
2014/09/26 职场文书
公司承诺函范文
2015/01/21 职场文书
2015党建工作简报
2015/07/21 职场文书
学生早退检讨书(范文)
2019/08/19 职场文书
JavaScript 原型与原型链详情
2021/11/02 Javascript
Java 超详细讲解ThreadLocal类的使用
2022/04/07 Java/Android