Skip to content

Instantly share code, notes, and snippets.

@ficapy
Last active September 19, 2017 13:35
Show Gist options
  • Star 0 You must be signed in to star a gist
  • Fork 0 You must be signed in to fork a gist
  • Save ficapy/d0c93a941fd4abf0bde3343eeac4d27d to your computer and use it in GitHub Desktop.
Save ficapy/d0c93a941fd4abf0bde3343eeac4d27d to your computer and use it in GitHub Desktop.
https://www.v2ex.com/t/303711 基于微信显示png图片 缩略图背景为白色,放大后背景图为黑色的Bug
package main
import (
"image"
"image/color"
"image/png"
_ "image/png"
"log"
"os"
)
func main() {
black_file, ok := os.Open("black.png")
if ok != nil {
log.Fatal(ok)
}
defer black_file.Close()
front_file, ok := os.Open("front.png")
if ok != nil {
log.Fatal(ok)
}
defer front_file.Close()
resultFile, err := os.Create("result.png")
if err != nil {
log.Fatal(err)
}
defer resultFile.Close()
black, format, ok := image.Decode(black_file)
if ok != nil || format != "png" {
log.Fatal(ok)
}
front, format, ok := image.Decode(front_file)
if ok != nil || format != "png" {
log.Fatal(ok)
}
if black.Bounds().Size() != front.Bounds().Size() {
log.Fatal("image size not equal")
}
result := image.NewRGBA(image.Rect(0, 0, black.Bounds().Size().X, black.Bounds().Size().Y))
var alpha, value uint8
for x := 0; x < black.Bounds().Size().X; x++ {
for y := 0; y < black.Bounds().Size().Y; y++ {
frontValue, _, _, _ := front.At(x, y).RGBA()
blackValue, _, _, _ := black.At(x, y).RGBA()
frontValue, blackValue = frontValue>>8, blackValue>>8
if frontValue <= blackValue {
alpha = 255
value = uint8(frontValue)
} else {
alpha = uint8(255 - frontValue + blackValue)
value = uint8(float64(blackValue) / (float64(alpha) / 255))
// 在存在透明通道的时候RGB算法和python不一致
value = uint8(uint32(alpha) * uint32(value) >> 8)
}
result.SetRGBA(x, y, color.RGBA{value, value, value, alpha})
}
}
png.Encode(resultFile, result)
}
#!/usr/bin/env python
#-*- coding: utf-8 -*-
# Author: ficapy
# Create: '9/18/16'
#########################################################
# 将2张灰度图合并成一张,在白底和黑底分部显示不同的部分
# 完美匹配的要求是:对于相同位置白底总比黑底的像素值大
# 方程式如下(其中y为合成后的像素值,α为alpha值,取值范围0-1)
# 白底: yα + 255(1-α) = 白底像素值
# 黑底: yα = 黑底像素值
# 从以上就能看出为啥白色的像素值必须必黑底大
# 如何使用PS制作黑白底图片呢,变亮就用柔光那一种,变暗就用正片叠底
# 然后两张图差值,查看直方图,看靠0的多不多
# ######################################################
from __future__ import division
from math import ceil
from PIL import Image
front = Image.open('front.png')
black = Image.open('black.png')
assert front.size == black.size
target = front.copy()
img_x,img_y = front.size
front_pix = front.load()
black_pix = black.load()
target_pix = target.load()
for i in range(img_x):
for j in range(img_y):
front_value = front_pix[i,j][0]
black_value = black_pix[i,j][0]
# 0 为全透明 255为不透明
if front_value <= black_value:
alpha = 255
value = front_value
else:
alpha = 255 - front_value + black_value
value = black_value/(alpha/255) if alpha != 0 else black_value
alpha,value = ceil(alpha),ceil(value)
target_pix[i,j] = (value,value,value,alpha)
target.save('result.png')
# 测试查看黑白底效果
# test = Image.open('result.png').convert('RGBA')
# black_background = Image.new( 'RGBA', test.size, 'black')
# white_background = Image.new( 'RGBA', test.size, 'white')
# Image.alpha_composite(black_background, test).save('black_result.png')
# Image.alpha_composite(white_background, test).save('white_result.png')
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment