vis.py :  » Business-Application » ThanCad » thancad-0.0.9 » p_gchart » Python Open Source

Home
Python Open Source
1.3.1.2 Python
2.Ajax
3.Aspect Oriented
4.Blog
5.Build
6.Business Application
7.Chart Report
8.Content Management Systems
9.Cryptographic
10.Database
11.Development
12.Editor
13.Email
14.ERP
15.Game 2D 3D
16.GIS
17.GUI
18.IDE
19.Installer
20.IRC
21.Issue Tracker
22.Language Interface
23.Log
24.Math
25.Media Sound Audio
26.Mobile
27.Network
28.Parser
29.PDF
30.Project Management
31.RSS
32.Search
33.Security
34.Template Engines
35.Test
36.UML
37.USB Serial
38.Web Frameworks
39.Web Server
40.Web Services
41.Web Unit
42.Wiki
43.Windows
44.XML
Python Open Source » Business Application » ThanCad 
ThanCad » thancad 0.0.9 » p_gchart » vis.py
from math import fabs
from Tkinter import *
import Image as Imagepil
from p_gtkuti import *
from p_gtkwid import thanicon
from p_gtecqm import dxfinter
from thanopt import ThanOptions
from vistrans import T

##############################################################################
##############################################################################

class WinCoor:
    "Provides coordinate systems as windows."
    
    def __init__(self, *args):
        if len(args) == 4:
      self.win = [float(x) for x in args]
  elif len(args) == 1:
      self.win = list(args[0].win)
        else:
            raise TypeError, "1 or 4 arguments expected"
        if self.win[2] == self.win[0]: self.win[2] = self.win[0] + 1   #Thanasis2009_02_15:empty lines
        if self.win[3] == self.win[1]: self.win[3] = self.win[1] + 1   #Thanasis2009_02_15:empty lines


    def middle(self):
        return (self.win[0]+self.win[2])*0.5, (self.win[1]+self.win[3])*0.5
  
    def coor(self, other, otherpoint):
        dother = otherpoint[0]-other.win[0], otherpoint[1]-other.win[1]
  dother = dother[0]/(other.win[2]-other.win[0]), dother[1]/(other.win[3]-other.win[1])
  dother = dother[0]*(self.win[2]-self.win[0]), dother[1]*(self.win[3]-self.win[1])
        dother = dother[0]+self.win[0], dother[1]+self.win[1]
  return dother

    def rcoor(self, other, dother):
  dother = dother[0]/(other.win[2]-other.win[0]), dother[1]/(other.win[3]-other.win[1])
  dother = dother[0]*(self.win[2]-self.win[0]), dother[1]*(self.win[3]-self.win[1])
  return dother
  
    def resize(self, factx, facty):
        w = self.win; factx *= 0.5; facty *= 0.5
        d = (w[2]-w[0])*factx, (w[3]-w[1])*facty
  self.win = w[0]-d[0], w[1]-d[1], w[2]+d[0], w[3]+d[1]

    def reratio(self, other):
        t = other.win; w = self.win
  factx, facty = fabs((t[2]-t[0])/(w[2]-w[0])), fabs((t[3]-t[1])/(w[3]-w[1]))
        fact = min((factx, facty))
  self.resize(factx/fact-1, facty/fact-1)  

    def recenter(self, ce):
        d = (self.win[2]-self.win[0])*0.5, (self.win[3]-self.win[1])*0.5
  self.win = ce[0]-d[0], ce[1]-d[1], ce[0]+d[0], ce[1]+d[1]

    
##############################################################################
##############################################################################

class ThanZoomPanCoor:
    "Represents three coordinate systems for use in zoom and pan (Tkinter canvas)."

    def __init__(self, dc):
        dc.update()
  px = dc.winfo_width()
  py = dc.winfo_height()
  
  self.margin = 0.02
  
  self.pix = WinCoor(0, py-1, px-1, 0)
#  self.can = WinCoor(0, py, px, 0)
  self.wor = WinCoor(0, 0, px-1, py-1)

    def onSize(self, dc, zoom, regen):
        dc.update()
  px = dc.winfo_width()
  py = dc.winfo_height()
  w = self.pix.win 
  if px == w[2]+1 and py == w[1]+1: return
  worp = self.wor
  w1 = self.wor.coor(self.pix, (0, py-1))
  w2 = self.wor.coor(self.pix, (px-1, 0))
  self.pix = WinCoor(0, py-1, px-1, 0)
  self.wor = WinCoor(w1[0], w1[1], w2[0], w2[1])
  if zoom: self.zoomwin(worp, dc, regen)

#=============================================================================

    def zoomwin(self, worn, dc, regen):
        "Redraws the curves into canvas dc."
  
  worn = WinCoor(worn)
        worn.reratio(self.pix)
  worn.resize(self.margin, self.margin)
  wcen = worn.middle()
  wce = self.wor.middle()
  dx, dy = self.pix.rcoor(self.wor, (wcen[0]-wce[0], wcen[1]-wce[1]))
  dc.move(ALL, -dx, -dy)
        wcen = self.pix.coor(self.wor, wcen)
  wcen = wcen[0]-dx, wcen[1]-dy
  
  w = self.wor.win; dx,  dy  = w[2]-w[0], w[3]-w[1]
  w = worn.win;     dxn, dyn = w[2]-w[0], w[3]-w[1]
  if dx > dy: sc = dx/dxn
  else:       sc = dy/dyn
  dc.scale(ALL, wcen[0], wcen[1], sc, sc)
  
  self.wor = worn
  if regen: self.thanRegen()

#=============================================================================

    def zoompix(self, ce, fact, dc, regen, center1):
        "Zooms with center at ce; ce is in pixels."
  
        if center1: ce = self.wor.coor(self.pix, ce)
  else: ce = self.wor.middle()
  w = self.wor.win; dx, dy = (w[2]-w[0])*0.5/fact, (w[3]-w[1])*0.5/fact
  self.zoomwin(WinCoor(ce[0]-dx, ce[1]-dy, ce[0]+dx, ce[1]+dy), dc, regen)

#=============================================================================

    def transeq(self):
        "Returns the coefs of the transformation equations world->canvas (which coincides with pixel."

  ww = self.wor.win; dx,  dy  = ww[2]-ww[0], ww[3]-ww[1]
  pw = self.pix.win; dxp, dyp = pw[2]-pw[0], pw[3]-pw[1]
  xsc = dxp/dx
  ysc = dyp/dy

#  x = pw[0] + (x-ww[0])*sc
  dx = pw[0] - ww[0]*xsc
  dy = pw[1] - ww[1]*ysc
  return dx, dy, xsc, ysc

  
##############################################################################
##############################################################################

class ChartWinx:
    def thanInit(self, toplevel, thanZoomPanCoor, thanOptions, chart, title, *args, **kw):
        bg = kw.pop("bg")
        toplevel.__init__(self, *args, **kw)
  thanOptions.__init__(self, "p_gchart")

        self.thanState = STATE_NONE
  self.__chart = chart

  self.title(title)
        self.thanCanvas = Canvas(self, bg=bg)
  self.thanCur = self.thanCanvas["cursor"]
  self.thanCanvas.grid(row=1, sticky="snwe")
  self.rowconfigure(1, weight=1)
  self.columnconfigure(0, weight=1)
        self.thanCanvas.bind("<Button-3>", self.__onClickr)
        self.thanCanvas.bind("<Button-1>", self.__onClick)
  self.bind("<Escape>", self.__onEscape) 
  thanZoomPanCoor.__init__(self, self.thanCanvas)
  
  self.thanFloatMenu = self.__createFloatMenu()
  self.thanMenubar = self.__createMenubar()
  self.showMenubar.trace("w", self.__showMenubar)
  self.__showMenubar()
  self.thanToolbar = self.__createToolbar()
  self.showToolbar.trace("w", self.__showToolbar)
        self.__showToolbar()
  
        self.__chart.minmax()
  self.__zoomall()
  if not self.regenWhenZoomall.get(): self.thanRegen()
        self.bind("<Configure>", self.__onSize)
  
  self.thanImundo = []
  self.thanImredo = []
        self.thanResetModified()
  self.thanFileDefined = False
  self.protocol("WM_DELETE_WINDOW", self.thanMnuFileExit)


    def __createFloatMenu(self):
        m = Menu(self, tearoff=False)

  m1 = Menu(m, tearoff=False)
  m1.add_command(label="Rotate  90 deg", command=lambda f=90.0:  self.__rot(f))
  m1.add_command(label="Rotate 180 deg", command=lambda f=180.0: self.__rot(f))
  m1.add_command(label="Rotate 270 deg", command=lambda f=270.0: self.__rot(f))
#  m1.add_command(lable="Rotate arbitrary", command=lambda f=90.0: self.__rot(f))
  m1.add_separator()
  m1.add_command(label="convert to b/w", command=lambda c="2": self.__convert(c))
  m1.add_command(label="convert to b/w inverted", command=lambda c="3": self.__convert(c))
  m1.add_separator()
  m1.add_command(label="Undo", command=self.__undo)
  m1.add_command(label="Redo", command=self.__redo)
  m1.add_separator()
  m1.add_command(label="Open", command=self.thanMnuFileOpen)
  m1.add_command(label="Save", command=self.thanMnuFileSave)
  m1.add_command(label="Save As", command=self.thanMnuFileSaveas)
  m.add_cascade(label="image", menu=m1)

  m.add_command(label="zoom in",  command=self.__zoomin)
  m.add_command(label="zoom out", command=self.__zoomout)
  m.add_command(label="zoom all", command=self.__zoomall)
  m.add_separator()
  m.add_command(label="center to", command=self.__centerto)
  m.add_separator()
  m.add_command(label="regen", command=self.thanRegen)
  m.add_command(label="cancel", command=self.__cancel)
  m.add_separator()
  
  m1 = Menu(m, tearoff=False)
  m1.add_checkbutton(label="zoom  when window changes", variable=self.zoomWhenConf)
  m1.add_checkbutton(label="regen when window changes", variable=self.regenWhenConf)
  m1.add_separator()
  m1.add_checkbutton(label="regen when zoom", variable=self.regenWhenZoom)
  m1.add_checkbutton(label="regen when zoom all", variable=self.regenWhenZoomall)
  m1.add_checkbutton(label="center when zoom", variable=self.centerWhenZoom)
  m1.add_separator()
  m1.add_checkbutton(label="show menu bar", variable=self.showMenubar)
  m1.add_checkbutton(label="show tool bar", variable=self.showToolbar)

  m.add_cascade(label="options", menu=m1)
  
  m1 = Menu(m, tearoff=False)
  m1.add_command(label="save current options as defaults", command=self.thanOptSave)
  m1.add_separator()
  m1.add_command(label="reload saved   default options", command=self.thanOptGet)
  m1.add_command(label="reload factory default options", command=self.thanOptFactory)

  m.add_cascade(label="defaults", menu=m1)
  return m

    def __createMenubar(self):
        m = Menu(self, tearoff=False)

  m1 = Menu(m, tearoff=False)
  m1.add_command(label="Exit",  command=self.thanMnuFileExit)
  m.add_cascade(label="File", menu=m1)

  m1 = Menu(m, tearoff=False)
  m1.add_command(label="zoom in",  command=self.__zoomin)
  m1.add_command(label="zoom out", command=self.__zoomout)
  m1.add_command(label="zoom all", command=self.__zoomall)
  m1.add_separator()
  m1.add_command(label="center to", command=self.__centerto)
  m1.add_separator()
  m1.add_command(label="regen", command=self.thanRegen)
  m1.add_command(label="cancel", command=self.__cancel)
  m.add_cascade(label="View", menu=m1)
  
  m1 = Menu(m, tearoff=False)
  m1.add_checkbutton(label="zoom  when window changes", variable=self.zoomWhenConf)
  m1.add_checkbutton(label="regen when window changes", variable=self.regenWhenConf)
  m1.add_separator()
  m1.add_checkbutton(label="regen when zoom", variable=self.regenWhenZoom)
  m1.add_checkbutton(label="regen when zoom all", variable=self.regenWhenZoomall)
  m1.add_checkbutton(label="center when zoom", variable=self.centerWhenZoom)
  m1.add_separator()
  m1.add_checkbutton(label="show menu bar", variable=self.showMenubar)
  m1.add_checkbutton(label="show tool bar", variable=self.showToolbar)
  m.add_cascade(label="Options", menu=m1)
  
  m1 = Menu(m, tearoff=False)
  m1.add_command(label="save current options as defaults", command=self.thanOptSave)
  m1.add_separator()
  m1.add_command(label="reload saved   default options", command=self.thanOptGet)
  m1.add_command(label="reload factory default options", command=self.thanOptFactory)
  m.add_cascade(label="Defaults", menu=m1)

  return m

    def __createToolbar(self):
        t = Frame(self, relief=GROOVE, bd=2)
  buttons = \
  ( ("zoomin",  self.__zoomin),
    ("zoomout", self.__zoomout),
    ("zoomall", self.__zoomall),
    ("move",    self.__centerto),
    ("regen",   self.thanRegen),
    ("cancel",  self.__cancel),
  )
        c = 0
        for icon, callback in buttons:
#            iconfun = getattr(thanicon, icon)
#      ph = PhotoImage(data=iconfun())
#      setattr(t, icon, ph)                         # Save a reference of the icon
      but = Button(t, image=thanicon.get(icon), command=callback)
      but.grid(row=0, column=c)
      c += 1

      t.grid(row=0, sticky="wn")
  t.grid_forget()
  return t
  
    def __onSize(self, evt):
        self.onSize(self.thanCanvas, self.zoomWhenConf.get(), self.regenWhenConf.get() or self.regenWhenZoom.get())
  
    def __showMenubar(self, *args):
  if self.showMenubar.get(): self["menu"] = self.thanMenubar
        else: self["menu"] = Menu(self)

    def __showToolbar(self, *args):
  if self.showToolbar.get(): self.thanToolbar.grid(row=0, sticky="wn")
        else: self.thanToolbar.grid_forget()

#============================================================================

    def __onClickr(self, event):
        "Well, here is what should be done when right mouse clicks."

  self.thanFloatMenu.post(event.x_root, event.y_root)

    def __onEscape(self, event):
        "Well, here is what should be done when user presses escape."

        if self.thanFloatMenu.winfo_ismapped():
      self.thanFloatMenu.unpost()
  else:
      self.__cancel()

#============================================================================

    def __onClick(self, event):
        "Well, here is what should be done when right mouse clicks."

#-------Initial values

  if self.thanState == STATE_NONE: return
  elif self.thanState == STATE_ZOOMIN:
      self.zoompix((event.x, event.y), self.zoomFact, self.thanCanvas, self.regenWhenZoom.get(), self.centerWhenZoom.get())
  elif self.thanState == STATE_ZOOMOUT:
      self.zoompix((event.x, event.y), 1.0/self.zoomFact, self.thanCanvas, self.regenWhenZoom.get(), self.centerWhenZoom.get())
  elif self.thanState == STATE_CENTER:
      self.zoompix((event.x, event.y), 1.0+self.margin, self.thanCanvas, False, True)
      
#============================================================================

    def __zoomin(self):
        self.thanCanvas.config(cursor="circle")
  self.thanState = STATE_ZOOMIN
    def __zoomout(self):
        self.thanCanvas.config(cursor="dot")
  self.thanState = STATE_ZOOMOUT
    def __zoomall(self):
        c = self.__chart
        self.zoomwin(WinCoor(c.xmin, c.ymin, c.xmax, c.ymax), self.thanCanvas, self.regenWhenZoom.get() or self.regenWhenZoomall.get())
    def __centerto(self):
        self.thanCanvas.config(cursor="hand1")
  self.thanState = STATE_CENTER
    def __cancel(self):
        self.thanCanvas.config(cursor=self.thanCur)
  self.thanState = STATE_NONE
    def thanRegen(self):
        dx, dy, xsc, ysc = self.transeq()
  self.__chart.regen(self.thanCanvas, dx, dy, xsc, ysc)
    def __rot(self, f):
        "Rotates f degress all images int the chart."
  self.__chart.thanRot(f)
  self.thanImundo.append((self.__chart.thanRot, (-f,), self.__chart.thanRot, (f,)))
  self.thanImredo = []
  self.thanRegen()
  self.thanSetModified()
    def __convert(self, c):
        "Rotates f degress all images int the chart."
  self.__chart.thanConv(c)
  self.thanImundo = []
  self.thanImredo = []
  self.thanRegen()
  self.thanSetModified()
    def __undo(self):
        "Undoes previous alteration."
  if len(self.thanImundo) <= 0: return
  unfun, unargs, refun, reargs = self.thanImundo.pop()
  unfun(*unargs)
  self.thanImredo.append((unfun, unargs, refun, reargs))
  self.thanRegen()
    def __redo(self):
        "Redoes previous undo alteration."
  if len(self.thanImredo) <= 0: return
  unfun, unargs, refun, reargs = self.thanImredo.pop()
  refun(*reargs)
  self.thanImundo.append((unfun, unargs, refun, reargs))
  self.thanRegen()

    def thanMnuFileOpen(self, evt=None):
        "Opens an existing file and corresponding window."
  while True:
      if self.thanMnuFileClose() == "break": return "break"
            filnam, fr = thanGudOpenReadFile(self, "*", "Open image file", mode="rb")
      if filnam.strip() == "": return
            try:
          print "Image=", Image
          im = Imagepil.open(fr)
            except IOError, why:
          thanGudModalMessage(self, why, "Image file open failed")   # (Gu)i (d)ependent
    continue
      break
  self.thanFilnam = filnam
  self.thanFileDefined = True
  self.thanResetModified()
  self.thanFocus()
  self.__chart.imageAdd(im, 0.0, 0.0, 100.0)
  self.thanRegen()

    def thanMnuFileClose(self, evt=None):
        if self.thanIsModified():
      a = thanGudAskOkCancel(self, T["File modified. Ok to quit?"], T["FILE MODIFIED"])
      if not a: self.thanFocus(); return "break"
        import chart
  self.__chart = chart.ThanChart()
  self.thanResetModified()

    def thanMnuFileSave(self, evt=None):
        if not self.thanFileDefined: return self.thanMnuFileSaveas()
  im = self.__chart.thanGetImage()
  if im == None: return
  try: im.save(self.thanFilnam)
  except IOError, why: thanGudModalMessage(self, why, T["Error opening file"])
  else:
      self.thanFileDefined = 1
      self.thanResetModified()
        self.thanFocus()

    def thanMnuFileSaveas(self, evt=None):
  im = self.__chart.thanGetImage()
  if im == None: return
        filnam = thanGudGetSaveFile(self, "*", "Saves to a File") 
  if filnam.strip() == "": return
  try: im.save(filnam)
  except IOError, why: thanGudModalMessage(self, why, T["Error opening file"])
  else:
      self.thanFilnam = filnam
      self.thanFileDefined = 1
      self.thanResetModified()
        self.thanFocus()

    def thanMnuFileExit(self, evt=None):
  if self.thanMnuFileClose() == "break": return "break"
  self.destroy()
  
    def thanResetModified(self): self.__modified = False
    def thanSetModified(self): self.__modified = True
    def thanIsModified(self): return self.__modified
    def thanFocus(self): self.focus_set()

class ChartWin1(Toplevel, ThanZoomPanCoor, ThanOptions, ChartWinx):
    def __init__(self, chart, title, *args, **kw):
        self.thanInit(Toplevel, ThanZoomPanCoor, ThanOptions, chart, title, *args, **kw)

class ChartWin(Tk, ThanZoomPanCoor, ThanOptions, ChartWinx):
    def __init__(self, chart, title, *args, **kw):
        self.thanInit(Tk, ThanZoomPanCoor, ThanOptions, chart, title, *args, **kw)

class ChartDxf(dxfinter.Tk, ThanZoomPanCoor):
    def __init__(self, chart, title, *args, **kw):
        c = self.__chart = chart
  self.pix = WinCoor(0.0, 0.0, 19.0, 29.0)
        self.wor = WinCoor(c.xmin, c.ymin, c.xmax, c.ymax)
  self.wor.reratio(self.pix)
  dxfinter.Tk.__init__(self)
  self.thanCanvas = dxfinter.Canvas(self, "white")
  self.thanRegen()
    def thanRegen(self):
        dx, dy, xsc, ysc = self.transeq()
  self.__chart.regen(self.thanCanvas, dx, dy, xsc, ysc)
    def transeq(self):
        "Returns the coefs of the transformation equations world->canvas (which coincides with pixel."
  ww = self.wor.win; dx,  dy  = ww[2]-ww[0], ww[3]-ww[1]
  pw = self.pix.win; dxp, dyp = pw[2]-pw[0], pw[3]-pw[1]
  xsc = dxp/dx
  ysc = dyp/dy

#  x = pw[0] + (x-ww[0])*sc
  dx = pw[0] - ww[0]*xsc
  dy = pw[1] - ww[1]*ysc
  return dx, dy, xsc, ysc

#############################################################################
#############################################################################

def vis(*charts, **kw):
    bg = kw.pop("bg", "black")
    root = ChartWin(charts[0], charts[0].title+" (Main)", bg=bg)
    for ch in charts[1:]:
        c = ChartWin1(ch, ch.title, root, bg=bg)
    root.mainloop()

def viswin(root, *charts, **kw):    
    "The caller has already started tk."
    bg = kw.pop("bg", "black")
    for ch in charts:
        c = ChartWin1(ch, ch.title, root, bg=bg)
    c.wait_window()

def visdxf(*charts):
    root = ChartDxf(charts[0], "Main Chart")
#    for ch in charts[1:]:
#        c = ChartWin1(ch, "Chart", root)
    root.mainloop()

STATE_NONE = 0
STATE_ZOOMIN = 1
STATE_ZOOMOUT = 2
STATE_CENTER = 3

if __name__ == "__main__":
    import chart
    im = Imagepil.new("L", (100, 100))
    ch = chart.ThanChart()
    ch.imageAdd(im, 0.0, 0.0, 100.0)
    del im
    root = ChartWin(ch, "Main Chart")
    root.mainloop()
www.java2java.com | Contact Us
Copyright 2009 - 12 Demo Source and Support. All rights reserved.
All other trademarks are property of their respective owners.