image_ 写入多个文字

package main

import (
	"flag"
	"fmt"
	"github.com/golang/freetype"
	"github.com/golang/freetype/truetype"
	"image"
	"image/color"
	"image/jpeg"
	"image/png"
	"io/ioutil"
	"log"
	"os"
	"path/filepath"
	"strings"
)

var (
	imageFile     = flag.String("image_file", "/Users/cpenny/go/src/local/picture_draw_tp/image.png", "image_path")
	fontFile      = flag.String("font_file", "/Users/cpenny/go/src/local/picture_draw_tp/SourceHanSansCN-Medium.ttf", "font path")
	destImageFile = flag.String("dest_image_file", "new_file.jpg", "dest_image_path")
	fontDpi       = flag.Float64("font_dpi", 80, "font_dpi")
	fontSize      = flag.Float64("font_size", 59, "font_size")
)

// 字体内容及坐标
type TextPt struct {
	Value string `json:"value"`
	X     int    `json:"x"`
	Y     int    `json:"y"`
}

// 字体路径 像素 尺码 颜色
type TextFont struct {
	FontPath string      `json:"font_path"`
	FontDpi  float64     `json:"font_dpi"`
	FontSize float64     `json:"font_size"`
	Cr       color.Color `json:"cr"`
}

// 字体综合
type Texts struct {
	TextFont
	Tps []TextPt `json:"tps"`
}

func main() {
	// 默认颜色
	cr := color.Color(
		color.RGBA{
			R: 0,
			G: 255,
			B: 255,
			A: 255,
		})
	// 写入内容1
	var ts []Texts
	var tps1 []TextPt
	tp1 := TextPt{
		Value: "hafaskljf",
		X:     710,
		Y:     1000,
	}
	tps1 = append(tps1, tp1)
	tp2 := TextPt{
		Value: "isafhhfdhh",
		X:     610,
		Y:     900,
	}
	tps1 = append(tps1, tp2)
	tt1 := Texts{
		TextFont: TextFont{
			FontPath: *fontFile,
			FontDpi:  *fontDpi,
			FontSize: *fontSize,
			Cr:       cr,
		},
		Tps: tps1,
	}
	ts = append(ts, tt1)
	// 写入内容2
	var tps2 []TextPt
	tp3 := TextPt{
		Value: "hafaskljf",
		X:     1110,
		Y:     1000,
	}
	tps2 = append(tps2, tp3)
	tp4 := TextPt{
		Value: "isafhhfdhh",
		X:     1410,
		Y:     900,
	}
	tps2 = append(tps2, tp4)
	cr = color.NRGBA{
		R: 0,
		G: 255,
		B: 0,
		A: 255,
	}
	tt2 := Texts{
		TextFont: TextFont{
			FontPath: *fontFile,
			FontDpi:  *fontDpi,
			FontSize: *fontSize,
			Cr:       cr,
		},
		Tps: tps2,
	}
	ts = append(ts, tt2)
	// 生成新的图片
	var quality int
	quality = 100 // 图片质量
	err := GenerateNewImage(*imageFile, *fontFile, *destImageFile, ts, quality)
	if err != nil {
		fmt.Println(err)
	}
}

// 读取图片信息
func readImage(iPath string) (img *image.NRGBA, err error) {
	var imgFile *os.File
	var jpgImg image.Image
	// 打开文件
	imgFile, err = os.Open(iPath)
	if err != nil {
		log.Println("打开文件")
		return img, err
	}
	fSuffix := filepath.Ext(iPath)
	fSuffix = strings.ToLower(fSuffix)
	if fSuffix == ".png" {
		// 解析png图片
		jpgImg, err = png.Decode(imgFile)
		if err != nil {
			log.Println("解析png图片")
			return img, err
		}
	} else if fSuffix == ".jpg" || fSuffix == ".jpeg" {
		// 解析jpeg图片
		jpgImg, err = jpeg.Decode(imgFile)
		if err != nil {
			log.Println("解析jpeg图片")
			return img, err
		}
	}
	defer imgFile.Close()
	img = image.NewNRGBA(jpgImg.Bounds())
	for y := 0; y < img.Bounds().Dy(); y++ {
		for x := 0; x < img.Bounds().Dx(); x++ {
			img.Set(x, y, jpgImg.At(x, y))
		}
	}
	return img, nil
}

// 读取字体
func readFont(fPath string) (font *truetype.Font, err error) {
	// 读取字体数据
	var fontBytes []byte
	fontBytes, err = ioutil.ReadFile(fPath)
	if err != nil {
		log.Println("读取字体数据")
		return font, err
	}
	// 载入字体数据
	font, err = freetype.ParseFont(fontBytes)
	if err != nil {
		log.Println("载入字体数据")
		return font, err
	}
	return font, nil
}

// 设置文字格式
func setTextType(font *truetype.Font, img *image.NRGBA, dpi, fontSize float64, cr color.Color) (*freetype.Context) {
	f := freetype.NewContext()
	//设置分辨率
	f.SetDPI(dpi)
	//设置字体
	f.SetFont(font)
	//设置尺寸
	f.SetFontSize(fontSize)
	f.SetClip(img.Bounds())
	//设置输出的图片
	f.SetDst(img)
	//设置字体颜色(红色)
	f.SetSrc(image.NewUniform(cr))
	return f
}

// 写入文字
func writeText(fontPath string, img *image.NRGBA, fontDpi, fontSize float64, cr color.Color, tps []TextPt) (err error) {
	// 1. 读取字体信息
	var font *truetype.Font
	font, err = readFont(fontPath)
	if err != nil {
		log.Println("读取字体信息")
		panic(err)
	}
	// 2. 设置文字格式
	var f *freetype.Context
	f = setTextType(font, img, fontDpi, fontSize, cr)
	if len(tps) > 0 {
		for _, tp := range tps {
			pt := freetype.Pt(tp.X, tp.Y)
			_, err = f.DrawString(tp.Value, pt)
			if err != nil {
				log.Println("设置文字格式")
				return err
			}
		}
	}
	return err
}

// 写入新文件
func writeNew(fPath string, img *image.NRGBA, quality int) (err error) {
	//保存到新文件中
	var newFile *os.File
	if fPath == "" {
		fPath = "new_file.jpg"
	}
	newFile, err = os.Create(fPath)
	if err != nil {
		return err
	}

	err = jpeg.Encode(newFile, img, &jpeg.Options{quality})
	if err != nil {
		return err
	}
	return nil
}

// 生成新图片
func GenerateNewImage(imagePath, fontPath, destImagePath string, ts []Texts, quality int) error {
	// 1. 读取图片信息
	var img *image.NRGBA
	var err error
	img, err = readImage(imagePath)
	if err != nil {
		panic(err)
	}
	// 2. 写入文字
	if len(ts) > 0 {
		for _, tt := range ts {
			err = writeText(fontPath, img, tt.FontDpi, tt.FontSize, tt.Cr, tt.Tps)
			if err != nil {
				panic(err)
			}
		}
	}
	// 3. 保存到新文件中
	err = writeNew(destImagePath, img, quality)
	if err != nil {
		panic(err)
	}
	return nil
}

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

原创文章 2 获赞 1 访问量 3663

猜你喜欢

转载自blog.csdn.net/q320036715/article/details/106117530
今日推荐