按配置数据绘制配置型地图marker的icon,自定义marker

news2024/11/16 19:24:00

一、需求

需要自定义配置数据的marker,其中图片内容要灵活可配置自动生成。此处项目用的百度地图。

效果图:

二、思路

用背景图+canvas绘制数字的方式生成icon的图片资源。

再将icon生成对应地图marker。

三、代码

canvasImg.js
<!--
* @description canvasImg.js 背景图+绘制内容生成图片资源
* @author xw
!-->

export function addFontWithBgImg(file, params, callback) {
    var ready = new FileReader()
    /* 开始读取指定的Blob对象或File对象中的内容. 当读取操作完成时,readyState属性的值会成为DONE,如果设置了onloadend事件处理程序,则调用之.同时,result属性中将包含一个data: URL格式的字符串以表示所读取文件的内容.*/
    ready.readAsDataURL(file) // 调用reader.readAsDataURL()方法,把图片转成base64
    ready.onload = function () {
        var re = this.result
        canvasDataURL(re, params, callback)
    }
}

/**
 * path 背景图资源路径
 * params:{ bgImgStyle: 'no-repeat', bgWidth: 35, bgHeight: 48, fontText: 1, fontWidth: 35, fontHeight: 35, font: 'bold 20px PingFangSC', bgc: '#0081FF', fontColor: '#fff' }
 * callback
 *      bgImgStyle = [
            "no-repeat", // 不平铺
            "repeat-x", // 横向平铺
            "repeat-y", // 纵向平铺
            "repeat" // 全画布平铺
        ];
 * */
export function canvasDataURL(path, params, callback) {
    const defaultOptions = {
        bgImgStyle: 'no-repeat',
        bgWidth: 45,
        bgHeight: 48,
        bgc: '#0081FF',
        fontText: 1, // 图片正中 大数字
        font: 'bold 20px PingFangSC',
        fontWidth: 34,
        fontHeight: 39,
        fontColor: '#0081FF',
        fontTwoText: 1, // 右上角 小数字
        fontTwo: 'bold 10px PingFangSC',
        fontTwoColor: '#fff',
        fontTwoPositionX: 35,
        fontTwoPositionY: 10,
    }
    const options = Object.assign(defaultOptions, params)
    const { bgImgStyle, bgWidth, bgHeight, fontText, fontWidth, fontHeight, font, bgc, fontColor, fontTwoText, fontTwo, fontTwoColor, fontTwoPositionX, fontTwoPositionY } = options
    // console.log('createNumberImg()-options', options)
    const img = new Image()
    img.src = path
    img.onload = function () {
        const canvas = document.createElement('canvas');
        // document.body.appendChild(canvas); //将画布添加到页面上
        // 设置画布大小
        canvas.width = bgWidth;
        canvas.height = bgHeight;
        // context 获取2D上下文
        const ctx = canvas.getContext('2d');
        // 清空画布内容
        ctx.clearRect(0, 0, canvas.width, canvas.height);
        // ctx.fillStyle = ctx.createPattern(img, bgImgStyle);
        // ctx.fillRect(0, 0, canvas.width, canvas.height);
        // ctx.fill();
        ctx.drawImage(img, 0, 0, canvas.width, canvas.height)  //绘制背景图片

        // 背景色 部分,会覆盖背景图, 背景色做背景 和 背景图做背景 二选一
        // ctx.fillStyle = bgc
        // 背景画布设置完后,绘制第2层内容, 覆盖在背景上的 内容---ctxTwo--fillText
        // const ctxTwo = canvas.getContext('2d');
        ctx.font = font
        ctx.fillStyle = fontColor
        ctx.textAlign = 'center' // 水平居中 left center right ,positionX = fontWidth / 2
        const positionX = fontWidth / 2
        ctx.textBaseline = 'middle' // 垂直居中 top  middle bottom,  positionY = fontHeight / 2
        const positionY = fontHeight / 2
        ctx.fillText(String(fontText), positionX, positionY)

        ctx.font = fontTwo
        ctx.fillStyle = fontTwoColor
        ctx.fillText(String(fontTwoText), fontTwoPositionX, fontTwoPositionY)
        // 导出为图片数据URL
        const imageDataUrl = canvas.toDataURL('image/png', 1); // canvas.toDataURL('image/png', 1)
        // console.log("生成的图像资源链接:", imageDataUrl);
        callback(imageDataUrl)
    }

}


/**
 * 将以base64的图片url数据转换为Blob
 * @param urlData
 * 用url方式表示的base64图片数据
 */
export function convertBase64UrlToBlob(urlData) {
    const arr = urlData.split(',')
    const mime = arr[0].match(/:(.*?);/)[1]
    const bstr = atob(arr[1])
    let n = bstr.length
    const u8arr = new Uint8Array(n)
    while (n--) {
        u8arr[n] = bstr.charCodeAt(n)
    }
    return new Blob([u8arr], { type: mime })
}
具体使用
createIconImg() {
                // 图片资源 自己找几个bg 在项目里本地引用
                const iconNormal = require('@/assets/image/bg/normal.png');
                const iconDanger = require('@/assets/image/bg/danger.png'); 
                const iconInfo = require('@/assets/image/bg/info.png'); 
                const userImgMap = {
                    '0': iconInfo,
                    '1': iconNormal,
                    '2': iconNormal,
                    '3': iconDanger,
                }
                const fontColorMap = {
                    '0': '#666',
                    '1': '#0081FF',
                    '2': '#0081FF',
                    '3': 'red',
                }
const pointList = [
                    { lng: '113.939435', lat: '22.522226', completeStatus: '0', frequency: 1 },
                    { lng: '113.947254', lat: '22.524549', completeStatus: '1', frequency: 3 },
                    { lng: '113.945889',  lat: '22.520798', completeStatus: '2',  frequency: 4 },
                ]
                // 设置地图 marker ---此处用的百度地图--BMap--使用 canvasDataURL方法
                const markers = []
                if (BMap && pointList && pointList.length > 0) {
                    const mapRef = this.$refs.map
                    mapRef?.clearOverlays()
                    // 生成的icon图片bgWidth背景宽高 要和 canvas画布宽高保持一致
                    const bgWidth = 45
                    const bgHeight = 48
                    const iconSize = new BMap.Size(bgWidth, bgHeight)
                    const iconOptions = { offset: new BMap.Size(25, 50) }
                    pointList.forEach((em, idx) => {
                        const userImg = userImgMap[String(em.completeStatus) || '0']
                        const fontColor = fontColorMap[String(em.completeStatus) || '0']
                        const params = { bgWidth, bgHeight, fontText: String(idx+1), fontColor, fontTwoText: String(em.frequency)} 
                        // 生成图片资源
                        canvasDataURL(userImg, params, function (imgUrl) {
                            const siteMarker = this.createMarker(mapRef, imgUrl, iconSize, iconOptions, item, index)
                            markers.push(siteMarker)
                        })
                    })
                    setTimeout(() => { 
                        const centerPoint = new BMap.Point(Number(selectRow.pointList[0]?.lng), Number(selectRow.pointList[0]?.lat));
                        mapRef.centerAndZoom(centerPoint, 15)
                    }, 300)
                }
            },
            createMarker(mapRef, iconImg, item, index) {
                const siteIcon = new BMap.Icon(
                    iconImg,
                    iconSize,
                    iconOptions,
                )
                const sitePoint = new BMap.Point(Number(item.lng), Number(item.lat));
                const siteMarker = new BMap.Marker(sitePoint, {
                    icon: siteIcon
                })
                // siteMarker.lisaSiteInfo = item // lisaSiteInfo自定义字段 主要装item信息,在InfoWindow的innerHtml时使用
                // const newHtml = '<div class="">我是innerHtml</div>'
                // console.log('newHtml', newHtml)
                // const infoWindow = new BMap.InfoWindow({
                //     content: newHtml,
                //     InfoWindowOptions: {
                //         width: 400,
                //         height: 300,
                //         enableAutoPan: true,
                //     }
                // })
                siteMarker.on('click', function () {
                    alert("carText模拟触发了地图click事件!");
                    // console.log('mapRef', mapRef)
                    // mapRef.openInfoWindow(infoWindow, sitePoint); //开启信息窗口
                })
                mapRef.addOverlay(siteMarker)
                return siteMarker
            },

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.coloradmin.cn/o/1415135.html

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈,一经查实,立即删除!

相关文章

【misc | CTF】攻防世界 适合作为桌面

天命&#xff1a;这题还挺繁琐的&#xff0c;知识点还不少 目录 步骤1&#xff1a;图片隐写 步骤2&#xff1a;Winhex查看ascii码 步骤1&#xff1a;图片隐写 拿到这张图片&#xff0c;不可能扔进ps会有多图层&#xff0c;普通图片也就一个图层而已 但居然可以有隐写图片这…

数据结构之生成树及最小生成树

数据结构之生成树及最小生成树 1、生成树概念2、最小生成树 数据结构是程序设计的重要基础&#xff0c;它所讨论的内容和技术对从事软件项目的开发有重要作用。学习数据结构要达到的目标是学会从问题出发&#xff0c;分析和研究计算机加工的数据的特性&#xff0c;以便为应用所…

Linux-ROS学习之旅-话题编程(二)

##承接上一篇文章的知识&#xff0c;有下面的实例操作 通过代码新生一个海龟&#xff0c;放置在(5,5)点&#xff0c;命名为turtle2&#xff0c;通过代码订阅turtle2的实时位置并打印在终端&#xff0c;控制turtle2实现旋转运动 步骤&#xff1a; 1.创建一个工作空间和一个功…

可以实时监控电脑的软件有哪些?好用的四款电脑监控软件【高人气收藏分享】

在当今数字化时代&#xff0c;电脑已经成为我们工作和生活中不可或缺的工具。然而&#xff0c;有时候我们需要对电脑进行监控&#xff0c;以确保工作效率和保护个人隐私。因此&#xff0c;选择一款好的电脑监控软件非常重要。本文将介绍四款好用的电脑监控软件&#xff0c;并探…

行测-资料:1. 速算技巧、基期与现期

1、速算技巧 1.1 截位直除 1.1.1 截位 1.1.2 截谁 1.1.3 截几位 选项差距大&#xff1a; 四个选项首位均不同首位相同&#xff0c;第二位差大于首位 选项差距小&#xff1a; 首位相同且第二位差小于等于首位 例子 C&#xff0c;截两位。 C&#xff0c;截两位。 B&#xff0c;截…

第十七讲_HarmonyOS应用开发Stage模型应用组件

HarmonyOS应用开发Stage模型应用组件 1. 应用级配置2. Module级配置3. Stage模型的组件3.1 AbilityStage3.1.1 AbilityStage的创建和配置3.1.2 AbilityStage的生命周期回调3.1.3 AbilityStage的事件回调&#xff1a; 3.2 UIAbility3.2.1 UIAbility生命周期3.2.3 UIAbility启动模…

mysql INSERT数据覆盖现有元素(若存在)

INSERT...ON DUPLICATE KEY UPDATE的使用 如果指定了ON DUPLICATE KEY UPDATE&#xff0c;并且插入行后会导致在一个UNIQUE索引或PRIMARY KEY中出现重复值&#xff0c;则会更新ON DUPLICATE KEY UPDATE关键字后面的字段值。 例如&#xff0c;如果列a被定义为UNIQUE&#xff0…

P1226 【模板】快速幂题解

题目 给你三个整数a,b,p&#xff0c;求 mod p。 输入输出格式 输入格式 输入只有一行三个整数&#xff0c;分别代表a,b,p。 输出格式 输出一行一个字符串a^b mod ps&#xff0c;其中a,b,p分别为题目给定的值&#xff0c;s为运算结果。 输入输出样例 输入样例 2 10 9 …

三角函数、反三角函数

一、三角函数 二、反三角函数&#xff1a;已知三角函数值&#xff0c;反算角度大小 因为严格单调函数才有反函数一个y对应一个x&#xff0c;显然ysinx&#xff0c;ycosx&#xff0c;ytanx在其定义域并不是严格单调&#xff0c;所以需要人为划定范围。 1. 研究yarcsinx、yarcco…

第十六回 花和尚单打二龙山 青面兽双夺宝珠寺-FreeBSD基本操作:查找程序和文件的路径

杨志最终没有跳崖而是怅然下了冈子。那十四个人醒来&#xff0c;后悔没有听杨志的话&#xff0c;现在事情已经发生了&#xff0c;大家只好商量把所有的错推到杨志身上&#xff0c;说他和强盗合伙劫了生辰纲。 杨志到酒店吃酒没钱付账&#xff0c;跟店家打起来&#xff0c;却原…

编写nginx脚本,安装失败

这是我写的nginx脚本-&#xff08;正确的&#xff0c;已经修改过的&#xff09; 这是我在运行脚本是出现的问题 这是我在nginx官网上粘贴的内容&#xff0c;请注意我用红笔画的地方&#xff0c;与第一张我写的脚本图片作对比&#xff0c;会发现多出现两个转义符号\。第二幅图就…

mysql连接查询,备忘

mysql连接查询 在MySQL数据库查询中&#xff0c;经常会使用到多表查询&#xff0c;本篇介绍mysql中的内连接&#xff0c;左连接&#xff0c;右连接。 用作备忘。 使用两个简单的数据表做展现。 表A AidAvalue1a0012a0023a0034a0045a005 表B BidBvalue1b0012b0023b0034b0046b…

Acwing-语法基础练习

目录 1. 非常基础的C (面向程序) 框架 2. 一些基础数据类型 3.变量的输入输出 4.ACWing题库-第1题&#xff1a;AB 5.四则运算(只整理一部分较难的) 6.数据类型转换 寒假自学用,记录Acwing题目。 语言&#xff1a;C 1. 非常基础的C (面向程序) 框架 #include <iostre…

Android13系统导航栏添加隐藏导航栏功能按钮

最近有个项目&#xff0c;客户要求在底部导航栏中添加一个可以隐藏整个导航栏的功能按钮&#xff0c;效果如下图&#xff1a; 具体方法如下&#xff1a; 1. 在frameworks/base做如下修改&#xff1a; diff --git a/packages/SystemUI/res/layout/navigation_bar.xml b/packag…

后端学习:数据库MySQL学习

数据库简介 数据库&#xff1a;英文为 DataBase&#xff0c;简称DB&#xff0c;它是存储和管理数据的仓库。   接下来&#xff0c;我们来学习Mysql的数据模型&#xff0c;数据库是如何来存储和管理数据的。在介绍 Mysql的数据模型之前&#xff0c;需要先了解一个概念&#xf…

YOLO自制数据集及训练

使用 Make Sense 网站进行标注 https://www.makesense.ai/可以让AI帮你先标一下 一定要点一下 + ,不然不会加进去 导出标签

混淆矩阵、准确率、查准率、查全率、DSC、IoU、敏感度的计算

1.背景介绍 在训练的模型的时候&#xff0c;需要评价模型的好坏&#xff0c;就涉及到混淆矩阵、准确率、查准率、查全率、DSC、IoU、敏感度的计算。 2、混淆矩阵的概念 所谓的混淆矩阵如下表所示&#xff1a; TP:真正类&#xff0c;真的正例被预测为正例 FN:假负类&#xf…

OSI七层模型 | TCP/IP模型 | 网络和操作系统的联系 | 网络通信的宏观流程

文章目录 1.OSI七层模型2.TCP/IP五层(或四层)模型3.网络通信的宏观流程3.1.同网段通信3.2.跨网段通信 1.OSI七层模型 在计算机通信诞生之初&#xff0c;不同的厂商都生产自己的设备&#xff0c;都有自己的网络通讯标准&#xff0c;导致了不同厂家之间各种协议不兼容&#xff0…

Linux文本三剑客---grep

grep&#xff08;从文本或字符串种过滤特定内容。&#xff09; 格式&#xff1a;Usage: grep [OPTION]... PATTERNS [FILE]... 常用选项&#xff1a; -E 等价于 egrep 扩展正则 -i 忽略大小写 -w 匹配单词 -o 仅显示匹配内容 -r 递归匹配 -c 统计匹配的行数 -v 取反 -n 行号 -A…

ABAP 状态栏排除某些按钮

ABAP 状态栏排除某些按钮 GUI State状态栏 在状态栏这里有这些按钮&#xff0c;现在在导出界面要排除掉这些按钮&#xff1a; 将要排除的按钮追加到gt_code内表&#xff1a; gt_fcode功能码内表的定义 DATA:gt_fcode TYPE TABLE OF sy-ucomm,完整程序 *&---------…