You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

Python实现视频帧类iOS/Figma平滑圆角(解决粗糙问题)

实现iOS/Figma风格平滑圆角的视频帧处理方案

问题根源分析

你之前的两种方案存在以下导致圆角粗糙的问题:

  • PIL基础方案:直接用小尺寸圆形裁剪拼接alpha通道,无抗锯齿处理,边缘是硬像素过渡,自然会像素化。
  • 超采样方案:未按超采样比例放大圆角半径,降采样后圆角精度不足;同时存在变量名错误(如im.width应为im_pil.width),且转换回OpenCV时丢失了alpha通道的平滑过渡信息。

正确实现方案

采用超采样抗锯齿+高精度alpha通道合成的方式,复刻iOS/Figma的平滑圆角效果,步骤如下:

  1. 对视频帧进行4-8倍超采样,放大画布尺寸
  2. 在超采样后的画布上绘制等比例放大的圆角矩形alpha通道
  3. 使用LANCZOS高质量降采样还原到原帧尺寸,得到带平滑边缘的alpha通道
  4. 将alpha通道合并到原帧,转换为OpenCV格式写入视频

完整代码实现

import cv2
import numpy as np
from PIL import Image, ImageDraw, ImageResampling

def add_smooth_rounded_corners(frame, radius, supersample=4):
    # 转换OpenCV帧为PIL RGBA图像
    img_rgb = cv2.cvtColor(frame, cv2.COLOR_BGR2RGB)
    im_pil = Image.fromarray(img_rgb).convert("RGBA")
    w, h = im_pil.size

    # 超采样参数计算
    ss_w, ss_h = w * supersample, h * supersample
    ss_radius = radius * supersample

    # 创建超采样后的alpha通道
    alpha = Image.new('L', (ss_w, ss_h), 0)
    draw = ImageDraw.Draw(alpha)
    # 绘制圆角矩形,填充白色(255为完全不透明)
    draw.rounded_rectangle(
        [0, 0, ss_w - 1, ss_h - 1],
        radius=ss_radius,
        fill=255
    )

    # 降采样回原尺寸,使用LANCZOS保证平滑
    alpha = alpha.resize((w, h), resample=ImageResampling.LANCZOS)

    # 将alpha通道合并到原图像
    im_pil.putalpha(alpha)

    # 转换回OpenCV BGR格式
    im_np = np.array(im_pil)
    return cv2.cvtColor(im_np, cv2.COLOR_RGBA2BGR)

# 视频处理主流程
if __name__ == "__main__":
    input_path = "input_video.mp4"
    output_path = "output_rounded.mp4"

    cap = cv2.VideoCapture(input_path)
    if not cap.isOpened():
        raise ValueError("无法打开输入视频")

    fps = cap.get(cv2.CAP_PROP_FPS)
    width = int(cap.get(cv2.CAP_PROP_FRAME_WIDTH))
    height = int(cap.get(cv2.CAP_PROP_FRAME_HEIGHT))
    fourcc = cv2.VideoWriter_fourcc(*'mp4v')

    out = cv2.VideoWriter(output_path, fourcc, fps, (width, height))

    while cap.isOpened():
        ret, frame = cap.read()
        if not ret:
            break

        # 添加圆角,radius根据需求调整(比如iOS常用的20-40)
        rounded_frame = add_smooth_rounded_corners(frame, radius=30, supersample=6)
        out.write(rounded_frame)

    cap.release()
    out.release()
    cv2.destroyAllWindows()

关键细节说明

  • 超采样比例:推荐用4-6倍,平衡平滑度和处理速度;追求极致效果可以用8倍,但会增加计算时间。
  • 圆角半径:直接设置实际像素半径,代码会自动按超采样比例放大,确保降采样后边缘平滑。
  • LANCZOS降采样:这是PIL中最适合图像缩小的算法,能最大程度保留边缘的平滑过渡,避免锯齿。
  • RGBA格式处理:全程保留RGBA通道,确保alpha的半透明过渡信息不丢失,这是圆角平滑的核心。

内容的提问来源于stack exchange,提问作者Aviato

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.07.03 05:23:14