h5实现毛笔
实现毛笔效果的技术方案
在H5中实现毛笔效果通常涉及Canvas绘图、SVG路径或WebGL技术,结合笔触动态变化和压力感应模拟。以下是几种常见方法:

使用Canvas绘制毛笔笔触
通过Canvas的lineTo和quadraticCurveTo方法模拟毛笔笔触的粗细变化:

const canvas = document.getElementById('brushCanvas');
const ctx = canvas.getContext('2d');
let isDrawing = false;
canvas.addEventListener('mousedown', startDrawing);
canvas.addEventListener('mousemove', draw);
canvas.addEventListener('mouseup', stopDrawing);
function startDrawing(e) {
isDrawing = true;
ctx.beginPath();
ctx.moveTo(e.offsetX, e.offsetY);
ctx.lineWidth = 10 + Math.random() * 10; // 模拟压力变化
}
function draw(e) {
if (!isDrawing) return;
ctx.lineTo(e.offsetX, e.offsetY);
ctx.strokeStyle = '#000';
ctx.lineCap = 'round';
ctx.lineJoin = 'round';
ctx.stroke();
}
function stopDrawing() {
isDrawing = false;
}
SVG路径动态生成
通过SVG的<path>元素实时更新d属性,结合CSS滤镜模拟墨迹扩散:
<svg id="brushSvg" width="500" height="300"></svg>
<script>
const svg = document.getElementById('brushSvg');
let path = document.createElementNS('http://www.w3.org/2000/svg', 'path');
path.setAttribute('stroke', 'black');
path.setAttribute('fill', 'none');
path.setAttribute('stroke-width', '8');
svg.appendChild(path);
let points = [];
svg.addEventListener('mousemove', (e) => {
points.push([e.offsetX, e.offsetY]);
if(points.length > 3) {
let d = `M ${points[0][0]} ${points[0][1]} Q`;
for(let i=1; i<points.length; i++) {
d += ` ${points[i][0]} ${points[i][1]}`;
}
path.setAttribute('d', d);
}
});
</script>
WebGL实现水墨效果
使用Three.js等库实现更真实的毛笔渲染:
import * as THREE from 'three';
const renderer = new THREE.WebGLRenderer({ alpha: true });
renderer.setSize(window.innerWidth, window.innerHeight);
document.body.appendChild(renderer.domElement);
const scene = new THREE.Scene();
const camera = new THREE.PerspectiveCamera(75, window.innerWidth/window.innerHeight, 0.1, 1000);
camera.position.z = 5;
const brushGeometry = new THREE.BufferGeometry();
const brushMaterial = new THREE.MeshBasicMaterial({ color: 0x000000 });
const brush = new THREE.Mesh(brushGeometry, brushMaterial);
scene.add(brush);
function animate() {
requestAnimationFrame(animate);
renderer.render(scene, camera);
}
animate();
性能优化建议
- 对于移动端使用
requestAnimationFrame替代直接事件监听 - 采用离屏Canvas预渲染常用笔触
- 使用Web Worker处理复杂的路径计算
- 实现笔触数据压缩算法减少内存占用
第三方库推荐
- Paper.js:矢量图形库适合毛笔路径处理
- Fabric.js:提供交互式Canvas绘制
- Konva.js:高性能Canvas库支持压力感应
- InkBrush.js:专为毛笔效果优化的轻量库
以上方法可根据项目需求组合使用,Canvas方案适合简单实现,WebGL适合高质量渲染,SVG适合需要后期编辑的场景。
