canvas绘制圆形头像的核心是先用arc()绘制圆形路径并调用clip()定义裁剪区域,再drawimage绘制图片,且需配合save()/restore()保护绘图状态,clip仅影响后续绘制,不支持羽化边缘。

Canvas 绘制带遮罩的圆形头像,核心就是用 clip() 把画布“框”出一个圆,之后所有绘制只在圆内生效——图片自然被裁成圆形,不依赖 CSS 或额外图层。
先画圆路径,再调用 clip()
clip 不是直接画图,而是定义一个“可见区域”。必须分两步:先用 arc() 描绘圆形路径(不填充、不描边),再调用 ctx.clip() 将该路径设为裁剪边界。注意:clip() 只作用于后续绘制,对之前已画内容无效。
- 路径必须用
beginPath()开启,且建议紧跟closePath()(虽然圆自动闭合,但养成习惯防误) - 圆心坐标和半径要与后续
drawImage()的位置匹配,否则头像会偏移或被截断 - clip 后的绘制(如 drawImage)仍需指定完整坐标和尺寸,只是超出圆的部分会被自动丢弃
记得 save() 和 restore() 保护绘图状态
clip 会影响整个绘图上下文,一旦设置,后续所有操作(包括文字、其他图形)都会受限。若页面还需在同个 canvas 上画其他内容,必须用 save() 提前保存状态,用 restore() 恢复。
- 不 save/restore 容易导致后续绘图“莫名其妙消失”,尤其在复杂 UI 或动画中
- 微信小程序、uni-app 等环境也遵循这一规则,不能省略
- 即使只画一个头像,也建议包裹 save/restore,避免未来扩展时踩坑
clip 和 globalCompositeOperation 的区别
clip 是“物理裁剪”,真正限制像素输出区域;而 globalCompositeOperation = 'destination-in' 是图像合成模式,靠颜色混合实现视觉裁剪。两者都能得圆形头像,但机制不同:
- clip 更轻量,性能好,适合纯裁剪场景
- destination-in 需要先画图、再画白色圆并设合成模式,多一步且依赖 fill 颜色(透明色无效)
- clip 无法实现羽化边缘,如需柔和过渡,得配合
createRadialGradient+globalCompositeOperation实现渐变遮罩
常见问题与调试要点
实际写代码时,头像“没裁圆”或“完全空白”,往往卡在这几个点:
- 忘记在
clip()前调用beginPath(),导致路径未重置,裁剪区域错乱 - 图片加载完成前就执行 drawImage,结果什么都没画出来——务必等
img.onload再触发裁剪绘制 - canvas 宽高设得太小,或圆心坐标超出画布范围,导致裁剪区为空
- 多个 clip 连续调用时,新裁剪区会与旧区域取交集(不是覆盖),容易越裁越小,需 restore 或 resetClip(兼容性差,慎用)
大量免费API接口:立即使用
涵盖生活服务API、金融科技API、企业工商API、等相关的API接口服务。免费API接口可安全、合规地连接上下游,为数据API应用能力赋能!











