在最近的工作中要求使用go去生成乙份pdf文件。一開始是選擇的這家的,但是在測試的時候發現這貨不支援中文。因此換成了gopdf。
在生成的pdf的過程中感覺比較煩的就是座標的計算,gopdf框架的座標軸使用左上角開始的,向左為x軸的正方向,向下為y軸的正方向。這的座標軸的設定倒是和android的座標軸設定類似(聽說傳統pdf的座標軸是從右下角開始的?)。這樣的座標設計不需要我倒著計算座標了。
我們寫pdf時一般都是使用a4紙的大小,如何設定成a4紙大小官方文件上有說明,對於這個大小,我在使用的時候弄出了一些小小的問題。
設定成a4紙大小:
pdf.start(gopdf.config})
如圖:
可以從上圖看出繪製的有一部分超出了繪製區域。
在出現這個問題後,我google到了如下資訊:
解析度是72畫素/英吋時,a4紙的尺寸的影象的畫素是595×842;那我就想用解析度是120畫素 / 英吋的w和h進行嘗試,在進行嘗試後發現生成的pdf已經不是a4紙的大小了。解析度是96畫素/英吋時,a4紙的尺寸的影象的畫素是794×1123;(預設)
解析度是120畫素/英吋時,a4紙的尺寸的影象的畫素是1487×2105;
解析度是150畫素/英吋時,a4紙的尺寸的影象的畫素是1240×1754;
解析度是300畫素/英吋時,a4紙的尺寸的影象的畫素是2480×3508;
func (gp *gopdf) image(picpath string, x float64, y float64, rect *rect) error
第乙個引數是的路徑,第二和第三個引數是要繪製的座標,那最後乙個引數是做什麼的呢?在之前的方法中我直接設定了nil,後面通過測試,這個引數就是要繪製的區域。通過在這個引數中指定繪製的區域大小,就能夠把這張完整的繪製出來。
注:如果要繪製中文內容,請找乙個可靠一定的中文字庫。不然會出現明明在**中設定了文字的內容,但是生成的pdf中沒有乙個現實的中文內容。在這個框架中使用的字型檔檔案只能是ttf檔案,不能是ttc檔案,如果使用ttc檔案會報錯。
繪製文字使用的一般方法是:
func (gp *gopdf) cell(rectangle *rect, text string) error
這個rectangle引數一般設定為nil,這個引數具體是做什麼的我並沒有進行嘗試。
在呼叫這個方法之前需要對字型,字型大小進行設定:
新增字型:
func (gp *gopdf) addttffont(family string, ttfpath string) error
設定使用的字型和大小:
func (gp *gopdf) setfont(family string, style string, size int) error
其中family為之前新增的字型名稱,style為使用的風格,size是字型的大小。style支援「」和u兩種,一般使用「」。畫文字和畫不同,cell()方法並沒有設設定座標,因此需要在畫文字前使用func (gp *gopdf) setx(x float64)
和func (gp *gopdf) sety(y float64)
兩個方法來設定文字的起始座標。把乙個文字所佔的區域想象成乙個矩形區域,設定的x
和y
值也是該矩形區域的左上座標。因此在計算下一行文字的起始位置,不要忘記了在y軸方向上加上文字的大小。
如果要設定文字的顏色就使用:
func (gp *gopdf) settextcolor(r uint8, g uint8, b uint8)
rgb就是指三原色,例如#a8a8a8(灰色,隨便舉個栗子),那麼就可以這樣呼叫:settextcoolor(0xa8,0xa8,0xa8)
。
畫直線使用的方法是:
func (gp *gopdf) line(x1 float64, y1 float64, x2 float64, y2 float64)
(x1,y1)為起始座標,(x2,y2)為結束位置。
設定線的顏色可以使用:
func (gp *gopdf) setstrokecolor(r uint8, g uint8, b uint8)
設定線的寬度:
func (gp *gopdf) setlinewidth(width float64))
但是線的寬度是從基準線向兩邊擴充套件。
func (gp *gopdf) oval(x1 float64, y1 float64, x2 float64, y2 float64)
這是畫橢圓的方法和我我們在學校裡的橢圓方程不同,經過測試,是畫乙個矩形中的內切矩形。因此只有兩個座標就可以了,乙個是左上角座標,乙個是右下角座標。
先上效果:
我實現的思路是先畫綠色背景。然後在寫文字內容。文字和邊框周圍有一定的間距,為了能夠復用我定義了如下的結構體:
type border struct
因為線的長度和文字的長度有關,因此需要先計算文字的長度:
func (gp *gopdf) measuretextwidth(text string) (float64, error)
在得到文字的長度後,加上leftpadding
和rightpadding
就是背景的寬度。背景的高度需要在文字的大小基礎上新增上toppadding
和bottompadding
。
func (h *helper) drawborder(border *border, x, y float64) (currentx, currenty float64, err error)
linewidth := border.leftpadding + contentlen + border.rightpadding
h.pdf.line(x, y+lineheight/2, x+linewidth, y+lineheight/2)
//寫文字內容
h.pdf.setx(x + border.leftpadding)
h.pdf.sety(y + border.toppadding)
h.pdf.cell(nil, border.content)
currentx = x
currenty = y + lineheight
return
}
在繪製pdf的時候需要注意使用func (gp *gopdf) addpage()
來進行新增新頁,不然生成的pdf檔案是無法開啟的。
gopdf這個開源框架中還提供了大量的使用方法,比如畫貝塞爾曲線(func (gp *gopdf) curve(x0 float64, y0 float64, x1 float64, y1 float64, x2 float64, y2 float64, x3 float64, y3 float64, style string)
),設定線的型別(func (gp *gopdf) setlinetype(linetype string)
)等等。
使用該框架給我最大的感受就是:要實現什麼效果,最重要的還是對效果進行分析,選擇正確的方法,計算出正確座標(這個我感覺比較重要)
vcbuild的簡單使用
vcbuild 命令列 更新 2007 年 11 月 vcbuild 工具使用以下命令列語法來生成 visual c 專案和解決方案。複製 vcbuild options project solution config all 標誌 options生成選項。有關更多資訊,請參見 vcbuild 選項...
QList的簡單使用
qlistlist list 1 2 3 4 5 6 7 8 qlist的插入 voidinsert int i,const t value 在qlist其中某個位置插入value,假如沒 宣告i i 預設size 及在最後插入value iteratorinsert iterator before...
QTreeWidget的簡單使用
qtreewidget是一種樹形的部件,它以樹的形式顯示各個項,它的每個項使用qtreewidgetitem來表示。qtreewidgetitem的值的表示都是用qstringlist來表示的。簡單的說明一下 for int i 0 i 3 i for int i 0 i 3 i treewidge...