在工作的途中,很多时候会发现一些特别使用的组件。我们需要把我们有用的组件分享给大家,如果大家都这么做,何愁国家的科技实力不强。(也可能导致行业更加内卷)
本次手把手记录的是一个vue3的给dom生成水印的指令,这里把他封装成一个组件,下一次直接拉下来就可以使用。这个可以用在移动端或者是pc端上防止数据被人截屏。效果如下:
源码仓库:github.com/cll123456/v…
这里我们可以思考下,写一个组件的步骤是啥?
配置环境,在这个组件中,要做的是项目如何打包,使用的语言等?
在开发环境需要把代码进行打包,测试。这里使用rollup进行打包,如果对rollup有疑问的,可以查看往期的文章
"@types/jest": "^27.0.2", ### jest的类型检查库
"@vue/test-utils": "^2.0.0-rc.16", ### vue官方的测试工具
"eslint": "^8.1.0", ### 代码检查
"jest": "^27.3.1", ### jest 是一个令人愉快的 JavaScript 测试框架
"prettier": "^2.4.1", ### 代码格式的检查工具,和esline类似
"rollup": "^2.59.0", ### 代码进行打包的工具
"rollup-plugin-typescript2": "^0.30.0", ### rollup 转义typescript 的插件
"ts-jest": "^27.0.3", ### jest在测试ts代码的预处理库
"typescript": "^4.3.5", ### 强大的类型检查库
"vue": "^3.2.16", ### vue3
"@vue/vue3-jest": "^27.0.0-alpha.3" ### jest 测试vue的代码
"rollup-plugin-dts": "^4.0.0" ### rollup 自动生成类型文件
"rollup-plugin-terser": "^7.0.2" ### rollup 对代码进行压缩
复制代码
安装完成上面的依赖后,咋们就需要开始进行配置文件了。
新建tsconfig.json
用于编写ts的规则
{
"compilerOptions": {
"target": "es6", // 编译的模板是es6,
"moduleResolution": "node", // 模块解析策略是node
"strict": true, // 启动严格模式
"importHelpers": true, // 开启模块导入助手
"esModuleInterop": true, // 开启模块的相互转换
"allowSyntheticDefaultImports": true, // 允许异步导入
"noImplicitThis": false, // 允许隐士的this
"declaration": true, // 需要生成.d.ts的类型文件
"baseUrl": "./", // 根路径
"lib": ["esnext", "dom", "dom.iterable", "scripthost"], // 需要使用的资源库
"paths": {
"@/*": ["src/*"] // 相对路径的指向
}
},
"include": ["src/**/*.ts", "tests/**/*.ts"], // 检查这里包含的文件
"exclude": ["node_modules","dist"] // 这里包含的文件不进行检查
}
复制代码
有了类型检查,接下来配置一下rollup
的默认配置
这里只说明几个关键的点,在rollup
中使用插件的顺序需要注意,不然容易报错,在本项目中, 插件的顺序应该是先进行 ts的转换
, 然后进行代码压缩
,最后是生成声明文件
,具体的文件配置文件内容查看: github.com/cll123456/v…
接下来就是eslint,prettier,jest
的配置了,这两个配置也是比较简单的,一个是配置代码的检查规则,另一个是配置测试代码的规则。
eslint
配置请查看:github.com/cll123456/v…prettier
的配置请查看: github.com/cll123456/v…jest
的配置请查看: github.com/cll123456/v…如果看到这里的话。恭喜你,你的环境就好了,接下来请尽情的撸代码吧!
需要在dom中生成水印,无非就是在dom中加入一张背景图片,然后在背景图片中加入想要的内容。
/**
* 添加水印
* @param str 水印的内容
* @param parentNode 父节点
* @param font 水印文字大小
* @param textColor 水印颜色
* @param rowLength 一个水印的宽度是多少
* @param colLength 一个水印的长度是多少
*/
function addWaterMarker(str: string, parentNode: HTMLDivElement, font: string, textColor: string, rowLength: number, colLength: number) {// 水印文字,父元素,字体,文字颜色
let can = document.createElement('canvas');
parentNode.appendChild(can);
can.width = parentNode.offsetWidth;
can.height = parentNode.offsetHeight;
can.style.display = 'none';
let cans = can.getContext('2d');
cans?.rotate(-10 * Math.PI / 180);
cans!.font = font || "16px Microsoft JhengHei";
cans!.fillStyle = textColor || "rgba(180, 180, 180, 0.3)";
cans!.textAlign = 'left';
cans!.textBaseline = 'middle';
// 需要遍历添加文字
for (let row = 0; row < can.height / rowLength; row++) {
for (let col = 0; col < can.width / colLength; col++) {
cans?.fillText(str, col * colLength, row * rowLength);
}
}
// 在节点中添加内容
parentNode.style.backgroundImage = "url(" + can.toDataURL("image/png") + ")";
}
复制代码
上面是生成水印的核心代码,就看你放在哪里了
代码写好后,测试也是很关键的、本项目使用了两种测试方法
jest
测试: 这个测试过程也是很简单,只是简单测试,属性存在与否。测试的结果如下:
当测试完成时候,就需要发布了。发布流程如下:
npm login
登录