分享
  1. 首页
  2. 文章

Go - freetype(因zc原因被锁, 重新发送)

谢秀岳 · · 1429 次点击 · · 开始浏览
这是一个创建于 的文章,其中的信息可能已经有所发展或是发生改变。

文字矢量绘制图形, AND 粘贴到图片上。

如果中文乱码请换字体(字体的TrueType需要是cmap编码)

!! 还有 , 要‘kxsw’。

如果不能‘kxsw’, 这里有曲线救国的方式

cd src
mkdir golang.org && cd golang.org
mkdir x 
git clone https://github.com/golang/image

然后去github. clone github.com/golang/freetype

这个包应该是: code.google.com/p/freetype-go/freetype, 但是'天c'有Q a

完整代码如下。

package main
import (
 "github.com/golang/freetype"
 "image"
 //"image/color"
 // "image/png"
 "image/jpeg"
 "io/ioutil"
 "log"
 "os"
 
 "image/draw"
)
const (
 dx = 590 // 图片的大小 宽度
 dy = 500 // 图片的大小 高度
 fontFile = "C:/www/go/src/study/simsun.ttf"
 fontSize = 20 // 字体尺寸
 fontDPI = 72 // 屏幕每英寸的分辨率
)
func main() {
 // 需要保存的文件
 // imgfile, _ := os.Create("C:/www/go/src/study/out.png")
 // defer imgfile.Close()
 // 新建一个 指定大小的 RGBA位图
 img := image.NewNRGBA(image.Rect(0, 0, dx, dy))
 // 画背景
 /*for y := 0; y < dy; y++ {
 for x := 0; x < dx; x++ {
 // 设置某个点的颜色,依次是 RGBA
 img.Set(x, y, color.RGBA{uint8(x), uint8(y), 0, 255})
 }
 }*/
 // 读字体数据
 fontBytes, err := ioutil.ReadFile(fontFile)
 if err != nil {
 log.Println("读取字体数据出错")
 log.Println(err)
 return
 }
 font, err := freetype.ParseFont(fontBytes)
 if err != nil {
 log.Println("转换字体样式出错")
 log.Println(err)
 return
 }
 c := freetype.NewContext()
 c.SetDPI(fontDPI)
 c.SetFont(font)
 c.SetFontSize(fontSize)
 c.SetClip(img.Bounds())
 c.SetDst(img)
 c.SetSrc(image.Black)
 pt := freetype.Pt(158, 60 * int(c.PointToFixed(fontSize)>>8)) // 字出现的位置
 _, err = c.DrawString("DEBUG", pt)
 if err != nil {
 log.Println("向图片写字体出错")
 log.Println(err)
 return
 }
 //重新第二行的位置
 pt.X += c.PointToFixed(fontSize) * 15
 _, err = c.DrawString("2018年03月06日", pt)
 if err != nil {
 log.Println("向图片写字体出错")
 log.Println(err)
 return
 }
 // 以PNG格式保存文件
 // err = png.Encode(imgfile, img)
 // if err != nil {
 // log.Println("生成图片出错")
 // log.Fatal(err)
 // }
 hc(img)
}
func hc(imgt *image.NRGBA){
 imgb, _ := os.Open("C:/www/go/src/study/certificate.jpg")
 img, _ := jpeg.Decode(imgb)
 defer imgb.Close()
 
 offset := image.Pt(200, 200)
 b := img.Bounds()
 m := image.NewRGBA(b)
 draw.Draw(m, b, img, image.ZP, draw.Src)
 draw.Draw(m, imgt.Bounds().Add(offset), imgt, image.ZP, draw.Over)
 
 imgw, _ := os.Create("C:/www/go/src/study/out.jpg")
 jpeg.Encode(imgw, m, &jpeg.Options{jpeg.DefaultQuality})
 defer imgw.Close()
}

效果

晚安。( ̄o ̄) . z Z

// 早上更新

因为业务需求, 图片是直接输出的

看了又看。很多文章没讲到如何输出图片, 我现在都没搜索到相关文章。

看代码即可, 关键代码如下

 w.Header().Set("content-type", "image/png")
 var b bytes.Buffer
 png.Encode(&b, doneImg)
 w.Write(b.Bytes())

搜索关键字:go content-type输出image图片

又完整代码如下

package imgaddtext
import (
 "net/http"
 "fmt"
 "encoding/json"
 
 "github.com/golang/freetype"
 "image"
 //"image/color"
 "image/png"
 "image/jpeg"
 "io/ioutil"
 "log"
 "os"
 
 "image/draw"
 "bytes"
)
const (
 baseFile = "D:/www/go/src/yhz/router/imgaddtext/"
)
const (
 dx = 1125 // 图片的大小 宽度
 dy = 1400 // 图片的大小 高度
 fontFile = baseFile + "simsun.ttf"
 fontSize = 42 // 字体尺寸
 fontDPI = 72 // 屏幕每英寸的分辨率
)
var errorRequest = struct{
 Code int16
 Msg string
}{}
func Error(msg string) (string){
 errorRequest.Code = 1
 errorRequest.Msg = msg
 re, _ := json.Marshal(errorRequest)
 return string(re)
}
func LackParams(r *http.Request, m []string) (bool, string){
 r.ParseForm()
 for _, val := range m {
 if len(r.Form[val]) == 0 {
 return true, Error("缺少参数")
 }
 }
 return false, ""
}
func Start(w http.ResponseWriter, r *http.Request) {
 r.ParseForm() 
 // 参数缺少验证
 if re, str := LackParams(r, []string{"realName", "wx", "ww", "time"}); re {
 fmt.Fprintf(w, str)
 return
 }
 
 realName := r.Form["realName"][0]
 wxName := r.Form["wx"][0]
 wwName := r.Form["ww"][0]
 timeName := r.Form["time"][0]
 
 // 新建一个 指定大小的 RGBA位图
 img := image.NewNRGBA(image.Rect(0, 0, dx, dy))
 // 画背景
 /*for y := 0; y < dy; y++ {
 for x := 0; x < dx; x++ {
 // 设置某个点的颜色,依次是 RGBA
 img.Set(x, y, color.RGBA{uint8(x), uint8(y), 0, 255})
 }
 }*/
 // 读字体数据
 fontBytes, err := ioutil.ReadFile(fontFile)
 if err != nil {
 log.Println("读取字体数据出错")
 log.Println(err)
 return
 }
 font, err := freetype.ParseFont(fontBytes)
 if err != nil {
 log.Println("转换字体样式出错")
 log.Println(err)
 return
 }
 
 c := freetype.NewContext()
 c.SetDPI(fontDPI)
 c.SetFont(font)
 c.SetFontSize(fontSize)
 c.SetHinting(50)
 c.SetClip(img.Bounds())
 c.SetDst(img)
 c.SetSrc(image.Black)
 
 pt := freetype.Pt(dx / 2 - ((fontSize + 17) * (len([]rune(realName))/2)), dy / 2 + 300) 
 
 _, err = c.DrawString(realName, pt)
 if err != nil {
 log.Println("向图片写字体出错")
 log.Println(err)
 return
 }
 //重新第二行的位置
 // pt.X += c.PointToFixed(fontSize) * 15
 pt = freetype.Pt(358, dy / 2 + 300 + 90)
 c.SetFontSize(30)
 _, err = c.DrawString(wxName, pt)
 if err != nil {
 log.Println("向图片写字体出错")
 log.Println(err)
 return
 }
 
 pt = freetype.Pt(358, dy / 2 + 200 + 280)
 _, err = c.DrawString(wwName, pt)
 if err != nil {
 log.Println("向图片写字体出错")
 log.Println(err)
 return
 }
 pt = freetype.Pt(150, dy - 10)
 c.SetFontSize(23)
 _, err = c.DrawString(timeName, pt)
 if err != nil {
 log.Println("向图片写字体出错")
 log.Println(err)
 return
 }
 
 doneImg := hc(img)
 
 
 w.Header().Set("content-type", "image/png")
 // w.Header().Set("Content-Length", fmt.Sprintf("%d", len(img)))
 // re := []byte(img)
 var b bytes.Buffer
 png.Encode(&b, doneImg)
 w.Write(b.Bytes())
}
func hc(imgt *image.NRGBA) *image.RGBA {
 imgb, _ := os.Open(baseFile + "bookbg.png")
 img, _ := png.Decode(imgb)
 defer imgb.Close()
 offset := image.Pt(0, 0)
 b := img.Bounds()
 m := image.NewRGBA(b)
 draw.Draw(m, b, img, image.ZP, draw.Src)
 draw.Draw(m, imgt.Bounds().Add(offset), imgt, image.ZP, draw.Over)
 imgw, _ := os.Create(baseFile + "out.jpg")
 jpeg.Encode(imgw, m, &jpeg.Options{jpeg.DefaultQuality})
 defer imgw.Close()
 return m
}

效果:

--END--


有疑问加站长微信联系(非本文作者)

本文来自:简书

感谢作者:谢秀岳

查看原文:Go - freetype(因zc原因被锁, 重新发送)

入群交流(和以上内容无关):加入Go大咖交流群,或添加微信:liuxiaoyan-s 备注:入群;或加QQ群:692541889

关注微信
1429 次点击
暂无回复
添加一条新回复 (您需要 后才能回复 没有账号 ?)
  • 请尽量让自己的回复能够对别人有帮助
  • 支持 Markdown 格式, **粗体**、~~删除线~~、`单行代码`
  • 支持 @ 本站用户;支持表情(输入 : 提示),见 Emoji cheat sheet
  • 图片支持拖拽、截图粘贴等方式上传

用户登录

没有账号?注册
(追記) (追記ここまで)

今日阅读排行

    加载中
(追記) (追記ここまで)

一周阅读排行

    加载中

关注我

  • 扫码关注领全套学习资料 关注微信公众号
  • 加入 QQ 群:
    • 192706294(已满)
    • 731990104(已满)
    • 798786647(已满)
    • 729884609(已满)
    • 977810755(已满)
    • 815126783(已满)
    • 812540095(已满)
    • 1006366459(已满)
    • 692541889

  • 关注微信公众号
  • 加入微信群:liuxiaoyan-s,备注入群
  • 也欢迎加入知识星球 Go粉丝们(免费)

给该专栏投稿 写篇新文章

每篇文章有总共有 5 次投稿机会

收入到我管理的专栏 新建专栏