2012-02-29 71 views
2

我已經寫了一個非常複雜的腳本來創建圖形 - 通過Tkinter模塊。Python - Tkinter保存PS圖像 - 無法打開它們

它可以像我期望的那樣工作,並將畫布保存爲PostScript文件。

只有我無法渲染任何PS文件。完全一樣。

當我決定使用Tkinter時,我非常自信,我會用PS文件做些事情,讓它們進入更加標準的格式。

我看過一些教程,建議將繪圖移植到PIL,這可能會起作用,但將相當多的任務移植到tk到PIL的所有動態對象。

我想知道是否有人有更快/更髒的方式將像素從窗口小部件窗口變成圖像文件。

或任何窗口的方法來查看/光柵化的PS文件?如果有興趣,我可以在某個地方放置一個PS文件示例。 (python的代碼是相當複雜的,需要3代MySQL表拉在一起的數據)

我想從這裏使用screengrab方法:http://mail.python.org/pipermail/image-sig/2003-May/002292.html

和奮鬥把事情按正確順序。

Tkinter的代碼:

def drawCircles(MasterList,buildlist): 
master = Tk() 
w = Canvas(master, width=1000, height=1000) 
w.config(bg='white') 
coordsMain = MasterList[6:] 
textMain = MasterList[0:2] 
w.pack() 
w.create_oval(*coordsMain, width=3, fill = "ivory3") 
masterLabel = "Source PUID\n" + str(MasterList[3]) + "\nFiles = " + str(MasterList[4]) 
w.create_text(*textMain, text=masterLabel, justify = "center", font=("Helvetica", 16)) 
for i in buildlist: 
coordsSet = i[6:10] 
w.create_oval(*coordsSet, width=3, fill = i[5]) 
set_label = i[3] + "\n" + str(i[4]) + "%" 
l=w.create_text(4,4, text=set_label, justify = "center", fill="white", font=("Helvetica", 16)) 
a,b,c,d= (w.bbox(l)) 
bboxArea =(c-a)*(d-b) 
a,b,c,d = i[6:10] 
circleArea = (c-a)*(d-b) 
if bboxArea>circleArea: 
    textSet = i[10:] 
    j=w.create_text(*textSet, text=set_label, justify = "center", font=("Helvetica", 16)) 
    r=w.create_rectangle(w.bbox(j),fill="white", width=0) 
else: 
    textSet = i[:2] 
    j=w.create_text(*textSet, text=set_label, justify = "center", font=("Helvetica", 16)) 
    r=w.create_rectangle(w.bbox(j),fill=i[5], width=0) 
w.tag_lower(r,j) 
PUID = str(MasterList[3]) 
PUID = PUID.replace('/', '-') 
filename = "\images\\" + PUID + ".jpg" 
mainloop() 

屏幕抓取代碼:

x0 =w.winfo_rootx() 
y0 =w.winfo_rooty() 
x1 =x0 + w.winfo_width() 
y1 =y0 + w.winfo_height() 
im =ImageGrab.grab((x0, y0, x1, y1)) 
im.save(filename) 

我可以做一個jpg這種方式,但似乎無法得到組件的內容中的JGP(創建的文件聲明爲jpg,但沒有圖像有效載荷)

如果我在主循環之後放置了屏幕抓取代碼,它說它在mainloop之前銷燬了該對象,它沒有構建obj ect yet ....

回答

1

原來的update()函數之前後記呼叫所需,通過指定tk畫布manpage。

pathName postscript?option value option value ...?

注意:默認情況下,Postscript僅針對屏幕上畫布窗口中顯示的信息生成。如果畫布是新創建的,它可能仍然具有1x1像素的初始大小,因此Postscript中不會顯示任何內容。要解決此問題,請調用「update」命令以等待畫布窗口達到其最終大小,否則使用-width和-height選項指定要打印的畫布區域。

我已經將此標記爲修復程序,因爲PS文件是首選的保存格式,並且質量遠高於screengrab方法。

工作的代碼現在變爲:

def drawCircles(MasterList,buildlist): 
master = Tk() 
w = Canvas(master, width=1000, height=1000) 
w.config(bg='white') 
coordsMain = MasterList[6:] 
textMain = MasterList[0:2] 
w.pack() 
w.create_oval(*coordsMain, width=3, fill = "ivory3") 
masterLabel = "Source PUID\n" + str(MasterList[3]) + "\nFiles = " + str(MasterList[4]) 
w.create_text(*textMain, text=masterLabel, justify = "center", font=("Helvetica", 16)) 
for i in buildlist: 
coordsSet = i[6:10] 
w.create_oval(*coordsSet, width=3, fill = i[5]) 
set_label = i[3] + "\n" + str(i[4]) + "%" 
l=w.create_text(4,4, text=set_label, justify = "center", fill="white", font=("Helvetica", 16)) 
a,b,c,d= (w.bbox(l)) 
bboxArea =(c-a)*(d-b) 
a,b,c,d = i[6:10] 
circleArea = (c-a)*(d-b) 
if bboxArea>circleArea: 
    textSet = i[10:] 
    j=w.create_text(*textSet, text=set_label, justify = "center", font=("Helvetica", 16)) 
    r=w.create_rectangle(w.bbox(j),fill="white", width=0) 
else: 
    textSet = i[:2] 
    j=w.create_text(*textSet, text=set_label, justify = "center", font=("Helvetica", 16)) 
    r=w.create_rectangle(w.bbox(j),fill=i[5], width=0) 
w.tag_lower(r,j) 
PUID = str(MasterList[3]) 
PUID = PUID.replace('/', '-') 
filename = "\images\\" + PUID + ".PS" 
w.update() 
mainloop() 
1

你可以嘗試把它交給ghostscriptsubprocess。這可以使PostScript以幾乎任何位圖格式存在。

+0

我試圖從命令行Ghostscipt打開圖像,他們不呈現在所有 - 我仍然設置擺弄,看看我是否能得到它飛行。 – Jay 2012-02-29 22:28:10

+0

你可以把PostScript文件放在什麼地方嗎?我以前從Python生成過PostScript。這並不困難。 – 2012-02-29 23:05:51

+0

當然 - http://dl.dropbox.com/u/59536414/fmt-15.PS應該是一個1000 x 1000的畫布 – Jay 2012-02-29 23:15:32

1

我認爲可能發生的情況是實際的框架沒有在腳本中得到更新。我可以重現你的症狀 - 文件產生,但無有效載荷 - 通過註釋掉cv.update()調用以下:

import Tkinter as tk 
root = tk.Tk() 
root.title("Simple plot") 
cv = tk.Canvas(width=200, height=200, bg='white') 
cv.pack() 
cv.create_text(100, 100, text="hello world!") 
cv.update() # comment out to make empty postscript! 
cv.postscript(file="my_drawing.ps", colormode='color') 
+0

太棒了 - 我將抓取器代碼分開 - 所以現在可以工作 - 就像這樣。更新,然後得到x,x1,y,y1,然後是主循環,然後是最後兩條im線。謝謝。我錯過了更新電話。你怎麼知道使用它? – Jay 2012-02-29 23:25:59

+0

像這樣:googled「tkinter postscript」。找到[此鏈接](http://www.daniweb.com/software-development/python/code/216929),我從中竊取了上述代碼。試過了,沒有工作。嘗試在ipython下,然後它,確實讓我吃驚。意識到真正的差異是交互性;谷歌搜索「tkinter更新」,其餘的是歷史。 – DSM 2012-02-29 23:31:01

+0

真棒,謝謝。我非常感謝你的時間。我打算稍微打開一會兒,然後再從PS開啓線程中獲得任何有用的東西。 – Jay 2012-02-29 23:34:57