Python 透明背景 PNG 处理 去白底/改透明度教程
用 Pillow 把图片白底变透明、调整整体不透明度、把透明 PNG 合成到背景上,支持按容差去除指定颜色,适合抠图标、做贴纸、合成海报。
场景痛点
下载的图标、截图、贴纸都是白底,想叠到深色海报上,白底方块特别难看。用 PS 魔棒去底色差,边缘还有白边。用 Python 按颜色容差把白色(或指定色)变透明,再整体调透明度,一次批量处理一整图标文件夹。
用到的库
pip install Pillow
完整代码
# -*- coding: utf-8 -*-
# 1) 把图片白底变透明 2) 整体调不透明度 3) 透明 PNG 合成到底图上
import os
from PIL import Image
import numpy as np
IMG_EXTS = {".jpg", ".jpeg", ".png", ".bmp", ".webp"}
def white_to_transparent(im, tolerance=30):
"""把接近白色的像素变透明,tolerance 越大去除范围越广"""
im = im.convert("RGBA")
arr = np.array(im)
# R/G/B 都大于 255-tolerance 视为白色
white_mask = (arr[:, :, 0] > 255 - tolerance) & \
(arr[:, :, 1] > 255 - tolerance) & \
(arr[:, :, 2] > 255 - tolerance)
arr[white_mask, 3] = 0 # alpha 通道设为 0
return Image.fromarray(arr)
def set_opacity(im, opacity=0.8):
"""整体不透明度 0~1"""
im = im.convert("RGBA")
alpha = im.split()[3]
alpha = alpha.point(lambda p: int(p * opacity))
im.putalpha(alpha)
return im
def paste_on_background(fg_path, bg_path, out_path, position=(50, 50)):
"""把透明 PNG 前景贴到底图指定位置"""
fg = Image.open(fg_path).convert("RGBA")
bg = Image.open(bg_path).convert("RGBA")
bg.paste(fg, position, fg) # 第三个参数是 mask,用 fg 自己的 alpha
bg.convert("RGB").save(out_path, quality=92)
print(f"合成完成 {out_path}")
def batch_white_to_transparent(input_dir, output_dir, tolerance=30):
os.makedirs(output_dir, exist_ok=True)
for name in sorted(os.listdir(input_dir)):
if os.path.splitext(name)[1].lower() not in IMG_EXTS:
continue
with Image.open(os.path.join(input_dir, name)) as im:
out = white_to_transparent(im, tolerance)
base, _ = os.path.splitext(name)
out.save(os.path.join(output_dir, base + ".png"))
print(f"去白底 {name}")
if __name__ == "__main__":
# 1) 批量去白底
batch_white_to_transparent("./icons", "./icons_transparent", tolerance=30)
# 2) 单张调透明度
im = Image.open("./logo.png")
set_opacity(im, 0.6).save("./logo_60.png")
# 3) 合成到底图
paste_on_background("./logo_60.png", "./poster_bg.jpg",
"./poster_final.jpg", position=(100, 100))
代码讲解
RGBA是四个通道:R/G/B 颜色 + A 透明度。Pillow 里im.convert("RGBA")就把图转成带 alpha 的模式。- 去白底用 numpy:把图转成数组,找出 R/G/B 都接近 255 的像素,把它们的 alpha 通道(第 3 列)设成 0,就变透明了。
tolerance控制容差,30 适合纯白,50 适合带一点灰边的截图。 set_opacity用alpha.point(lambda p: int(p*opacity))把整张图的 alpha 曲线乘个系数,实现半透明。- 合成时
bg.paste(fg, position, fg)的第三个参数把 fg 自己的 alpha 当蒙版,透明区域就不会盖住底图。
运行结果
把带白底的图标放进 ./icons,运行后 ./icons_transparent 里得到同名透明 PNG。再用 paste_on_background 把 logo 贴到海报背景上,输出最终合成图。
注意事项
- 去白底只对"纯底图"有效,图本身有白色花纹会一起被去掉,这种情况要手抠。
- JPG 不支持透明,去白底后必须存成 PNG 或 WebP。
- 容差开太大,图里的浅灰阴影也会变透明;建议 20~40 之间调。
- 合成时若前景图比底图大,会被裁掉,先用
thumbnail缩到合适尺寸。

更新时间:2026-09-14 20:20:18
上一篇:Python Excel 自动生成图表:一键生成柱状图 / 折线图