image_写入多张图片

package main

import (
	"errors"
	"flag"
	"image"
	"image/color"
	"image/draw"
	"image/jpeg"
	"image/png"
	"os"
	"path/filepath"
	"strings"
)

var (
	imageFile     = flag.String("image_path", "/Users/cpenny/go/src/local/picture_draw_pp/image.png", "path")
	destImageFile = flag.String("dest_image_path", "new_file.jpg", "path")
)

type ImagePt struct {
	Value      string  `json:"value"`
	X          int     `json:"x"`
	Y          int     `json:"y"`
	Percentage float64 `json:"percentage"`
}

func main() {
	// 读取图片信息
	var err error
	var imageNr *image.NRGBA
	imageNr, err = readImage()
	if err != nil {
		panic(err)
	}
	// 写入图片信息
	ipt := ImagePt{
		Value:      "temp.png",
		X:          0,
		Y:          0,
		Percentage: 0.6,
	}
	imageNr, err = writeImage(imageNr, ipt)
	if err != nil {
		panic(err)
	}
	// 压缩图片

	// 保存图片
	err = genImage(imageNr)
	if err != nil {
		panic(err)
	}
}

func readImage() (imageNR *image.NRGBA, err error) {
	//原始图片是sam.jpg
	var imgI image.Image
	imgI, err = getImage("temp.png")
	if err != nil {
		return imageNR, err
	}
	b := imgI.Bounds()
	m := image.NewNRGBA(b)
	draw.Draw(m, b, imgI, image.ZP, draw.Src)
	return m, nil
}

// 插入图片
func writeImage(imageR *image.NRGBA, ipt ImagePt) (nr *image.NRGBA, err error) {
	var watermark image.Image
	watermark, err = getImage(ipt.Value)
	if err != nil {
		return nr, err
	}
	//把水印写到右下角,并向0坐标各偏移10个像素
	offset := image.Pt(ipt.X, ipt.Y)
	waterRgba := ImageTypeToRGBA64(&watermark)
	waterRgba = OpacityAdjust(waterRgba, ipt.Percentage)
	draw.Draw(imageR, watermark.Bounds().Add(offset), waterRgba, image.ZP, 60)
	return imageR, err
}

//Image转换为image.RGBA64
func ImageTypeToRGBA64(m *image.Image) *image.RGBA64 {
	bounds := (*m).Bounds()
	dx := bounds.Dx()
	dy := bounds.Dy()
	newRgba := image.NewRGBA64(bounds)
	for i := 0; i < dx; i++ {
		for j := 0; j < dy; j++ {
			colorRgb := (*m).At(i, j)
			r, g, b, a := colorRgb.RGBA()
			nR := uint16(r)
			nG := uint16(g)
			nB := uint16(b)
			alpha := uint16(a)
			newRgba.SetRGBA64(i, j, color.RGBA64{R: nR, G: nG, B: nB, A: alpha})
		}
	}
	return newRgba
}

//将输入图像m的透明度变为原来的倍数。若原来为完成全不透明,则percentage = 0.5将变为半透明
func OpacityAdjust(m *image.RGBA64, percentage float64) *image.RGBA64 {
	bounds := m.Bounds()
	dx := bounds.Dx()
	dy := bounds.Dy()
	newRgba := image.NewRGBA64(bounds)
	for i := 0; i < dx; i++ {
		for j := 0; j < dy; j++ {
			colorRgb := m.At(i, j)
			r, g, b, a := colorRgb.RGBA()
			opacity := uint16(float64(a) * percentage)
			//颜色模型转换,至关重要!
			v := newRgba.ColorModel().Convert(color.NRGBA64{R: uint16(r), G: uint16(g), B: uint16(b), A: opacity})
			//Alpha = 0: Full transparent
			rr, gg, bb, aa := v.RGBA()
			newRgba.SetRGBA64(i, j, color.RGBA64{R: uint16(rr), G: uint16(gg), B: uint16(bb), A: uint16(aa)})
		}
	}
	return newRgba
}

// 生成图片
func genImage(imageR *image.NRGBA) (err error) {
	var imgF *os.File
	imgF, err = os.Create(*destImageFile)
	if err != nil {
		return err
	}
	res := getImageSuffix(*destImageFile)
	if res != "" {
		if res == "jpg" {
			err = jpeg.Encode(imgF, imageR, &jpeg.Options{100})
			if err != nil {
				return err
			}
		} else if res == "png" {
			err = png.Encode(imgF, imageR)
			if err != nil {
				return err
			}
		}
	}

	return nil
}

// 获取图片
func getImage(iPath string) (img image.Image, err error) {
	var imgF *os.File
	imgF, err = os.Open(iPath)
	if err != nil {
		return img, err
	}
	res := getImageSuffix(iPath)
	if res != "" {
		if res == "png" {
			img, err = png.Decode(imgF)
			if err != nil {
				return img, err
			}
		} else if res == "jpg" {
			img, err = jpeg.Decode(imgF)
			if err != nil {
				return img, err
			}
		} else {
			return img, errors.New("无法解析该图片")
		}
	}

	return img, err
}

// 获取图片后缀
func getImageSuffix(iPath string) (res string) {
	suffix := filepath.Ext(iPath)
	suffix = strings.ToLower(suffix)
	if suffix == ".jpg" || suffix == ".jpeg" {
		res = "jpg"
	} else if suffix == ".png" {
		res = "png"
	} else {
		res = ""
	}
	return res
}

  参考链接:https://www.cnblogs.com/wangjunqiao/p/10985397.html

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值