### Python port of W5GFE's Wires Perl/Tk Script
### Barry Newberger W5KH
### 23 Nov 03
### Version 1.0

### Python derivative work copyright Barry S. Newberger

# Original Perl/Tk script:
# copyright July 23, 1999, Bill Walker W5GFE, bw@cs.ecok.edu
# This software is available under the terms of the GNU Public License

############################################
from Tkinter import *
import math
import sys
import os
import re
import types
############################################


class Wires_plot:

    def __init__(self, master, color_list, graph_param) :
    
        master.title("Wires")
        self.maxwidth = graph_param[0]
        self.maxaspect = graph_param[1]
        self.centerx = graph_param[2]
        self.centery = graph_param[3]

        self.colors = color_list
        self.counter = 0
        self.colorindex = 0

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


# set up the frames

        self.topframe = Frame(master)
        self.topframe.pack()
        self.topleft = Frame(self.topframe)
        self.topleft.pack(side = 'left')
	self.topleftlabel = Label(self.topleft, text = 'X-Y View')
        self.topright = Frame(self.topframe)
	self.topright.pack(side = 'right')
	self.toprightlabel = Label(self.topright, text = 'X-Z View')
	
    
        self.bottomframe = Frame(master)
        self.bottomframe.pack()
        
        # Create 'quit' button 
        self.quitter = Button(self.bottomframe, text = 'Quit',\
            command = master.destroy)
        self.quitter.pack(side ='bottom', fill = 'x')
        
        self.bottomleft = Frame(self.bottomframe)
        self.bottomleft.pack(side = 'left')
        self.bottomright = Frame(self.bottomframe)
        self.bottomright.pack(side = 'right')
	self.bottomleftlabel = Label(self.bottomleft, text = 'Y-Z View')

	self.topleftlabel.pack()
	self.toprightlabel.pack()
	self.bottomleftlabel.pack()

        self.xygraph = Canvas(self.topleft, background = 'yellow',\
            relief = 'sunken', borderwidth = 2)               
        self.xygraph_sb_horiz = Scrollbar(self.topleft, orient = "horizontal", command = self.xygraph.xview)
        self.xygraph_sb_horiz.pack(side = 'bottom', fill = 'x')
        self.xygraph_sb_vert = Scrollbar(self.topleft, orient = "vertical", command = self.xygraph.yview)  
        self.xygraph_sb_vert.pack(side = 'right', fill = 'y')
        self.xygraph.pack(side = 'left', fill = 'x')
        self.xygraph.configure(yscrollcommand = self.xygraph_sb_vert.set)
        self.xygraph.configure(xscrollcommand = self.xygraph_sb_horiz.set)

        self.xzgraph = Canvas(self.topright, background = 'yellow',\
            relief = 'sunken', borderwidth = 2)               
        self.xzgraph_sb_horiz = Scrollbar(self.topright, orient = "horizontal", command = self.xzgraph.xview)
        self.xzgraph_sb_horiz.pack(side = 'bottom', fill = 'x')
        self.xzgraph_sb_vert = Scrollbar(self.topright, orient = "vertical", command = self.xzgraph.yview)  
        self.xzgraph_sb_vert.pack(side = 'right', fill = 'y')
        self.xzgraph.pack(side = 'left')
        self.xzgraph.configure(yscrollcommand = self.xzgraph_sb_vert.set)
        self.xzgraph.configure(xscrollcommand = self.xzgraph_sb_horiz.set)

        self.yzgraph = Canvas(self.bottomleft, background = 'yellow',\
            relief = 'sunken', borderwidth = 2)               
        self.yzgraph_sb_horiz = Scrollbar(self.bottomleft, orient = "horizontal", command = self.yzgraph.xview)
        self.yzgraph_sb_horiz.pack(side = 'bottom', fill = 'x')
        self.yzgraph_sb_vert = Scrollbar(self.bottomleft, orient = "vertical", command = self.yzgraph.yview)  
        self.yzgraph_sb_vert.pack(side = 'right', fill = 'y')
        self.yzgraph.pack(side = 'right', fill = 'x')
        self.yzgraph.configure(yscrollcommand = self.yzgraph_sb_vert.set)
        self.yzgraph.configure(xscrollcommand = self.yzgraph_sb_horiz.set)
        
        self.filebox = Listbox(self.bottomright, setgrid = 1)
        self.filebox_sb = Scrollbar(self.bottomright, orient = 'vertical',\
            command = self.filebox.yview)
        self.filebox_sb.pack(side = 'right', fill = 'y')
        self.filebox.pack(side = 'right', fill = 'x', ipadx = 64, anchor = 's',\
            ipady = 18)        
        self.filebox.configure(background = 'pink')
        self.filebox.configure(yscrollcommand = self.filebox_sb.set)

	self.topleftlabel.pack()
	self.toprightlabel.pack()
	self.bottomleftlabel.pack()
        

#################### a button

        self.filebox.bind ('<Double-1>', self.button_handler);



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


    def readdata (self, in_file) :
        
        self.X0 = []
        self.X1 = []
        
        self.Y0 = []
        self.Y1 = []
        
        self.Z0 = []
        self.Z1 = []
        
        RADIUS = []
        
        done = 0
        self.counter = 0
        
        patt1obj = re.compile("^GW")
        patt2obj = re.compile(",")
        patt3obj = re.compile("^[ \t][ \t]*")
        patt4obj = re.compile("[ \t][ \t]*")
        
        input = open(in_file)
        while(not done):
            line = input.readline()    
            line.rstrip()
            m = patt1obj.search(line)
            if m != None :
 # next two for somnec input            
                line = patt1obj.sub("GW ", line)
                line = patt2obj.sub(" ",line)
                line = patt3obj.sub('', line)
                line = patt4obj.sub('|',line)
                    
                self.X0.insert(self.counter, 0.)
                self.X1.insert(self.counter, 0.)
        
                self.Y0.insert(self.counter, 0.)
                self.Y1.insert(self.counter, 0.)
        
                self.Z0.insert(self.counter, 0.)
                self.Z1.insert(self.counter, 0.)
                
                RADIUS.insert(self.counter, 0.)
                    
                (GW,tag,segments,self.X0[self.counter], self.Y0[self.counter], self.Z0[self.counter],\
                    self.X1[self.counter], self.Y1[self.counter], self.Z1[self.counter],\
                    RADIUS[self.counter]) = re.split('\|',line)
                self.counter += 1
                  	                                                                   
            if (line == ''):
                done = 1
                
    # End of loop over antenna file
    	               
        input.close()
        
        (MAXSCALE, MINSCALE) = maxmin (flatten_tuple((maxmin(self.X0), maxmin(self.Y0), maxmin(self.Z0),\
            maxmin(self.X1), maxmin(self.Y1), maxmin(self.Z1))))
        
        MAXSCALE = float(MAXSCALE)
        MINSCALE = float(MINSCALE)
        
        if (MAXSCALE == MINSCALE) :
            SCALE = self.maxaspect
        else :
            SCALE = self.maxaspect/(MAXSCALE - MINSCALE)

#scale it
        i = 0
        colorindex = 0
        while (i < self.counter) :
#scale it and put it on the graphs
            colorindex = (colorindex + 1) % (len(self.colors))
            usecolor = self.colors[colorindex]

            self.xygraph.create_line(self.translate([SCALE * float(self.X0[i]),\
             SCALE *float(self.Y0[i]),\
             SCALE *float(self.X1[i]),\
             SCALE *float(self.Y1[i])]),\
             tags = "line",fill = usecolor, width = '3')

            self.yzgraph.create_line(self.translate([SCALE*float(self.Y0[i]),\
             SCALE*float(self.Z0[i]),\
             SCALE*float(self.Y1[ i]),\
             SCALE*float(self.Z1[i])]),\
             tags = "line", fill = usecolor, width = '3')

            self.xzgraph.create_line(self.translate([SCALE*float(self.X0[i]),\
             SCALE*float(self.Z0[i]),\
             SCALE*float(self.X1[i]),\
             SCALE*float(self.Z1[i])]),\
             tags = "line", fill = usecolor, width = '3')
            
            i += 1
      
# -- end of subroutine readdata -- #

    def button_handler (self, event):
        self.xygraph.delete('lines')
        self.yzgraph.delete('lines')
        self.xzgraph.delete('lines')
# put origins on the graphs
        self.xygraph.create_text(self.centerx, self.centery, text = '0')
        self.yzgraph.create_text(self.centerx, self.centery, text = '0')
        self.xzgraph.create_text(self.centerx, self.centery, text = '0')
        self.readdata(self.filebox.get('active'));
        self.xygraph.configure(scrollregion = self.xygraph.bbox('all'))
        self.yzgraph.configure(scrollregion = self.yzgraph.bbox('all'))
        self.xzgraph.configure(scrollregion = self.xzgraph.bbox('all'))

# -- end of subroutine button_handler -- #

##########################
## translate coordinates to new origin, and flip the y axis
## if one of these lengths is 0, we add a fudge factor to make
## a "blob" of color

    def translate (self, In_Vect) :
 # takes a set of (x0,y0,x1,y1) and does the translation and flip
        if (((In_Vect[0] - In_Vect[2]) == 0) and ((In_Vect[1] - In_Vect[3] ) == 0  )): # it is a point
            In_Vect[2] = In_Vect[2] + 3
            In_Vect[3] = In_Vect[3] + 3
        In_Vect[0] = In_Vect[0] + self.centerx
        In_Vect[1] = self.centery - In_Vect[1]
        In_Vect[2] = In_Vect[2] + self.centerx
        In_Vect[3] = self.centery - In_Vect[3]
        return (In_Vect)

# -- end of class Necview_plot -- #


########### some subprograms

def maxmin (vect) :
  # returns (maximum, minimum) of a vector
    max = vect[0]
    min = vect[0]
    i = 0
    while (i < len(vect) ) :
        if max < vect[i] :
            max = vect[i]
        if min > vect[i] :
            min = vect[i]
        i = i + 1
    return (max, min)
  
# -- end of subroutine maxmin -- #

def isTuple(x): return type(x) == types.TupleType

# -- end of subroutine isTuple -- #
 
# -- subroutine flatten_tuple due to David Yoo(dyoo@hkn.eecs.berkeley.edu) -- #

def flatten_tuple(T):
	if not isTuple(T) : return (T,)
	elif len(T) == 0: return ()
	else: return flatten_tuple(T[0]) + flatten_tuple(T[1:])

# -- end of subroutine flatten_tuple -- #

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

def main() :

    maxwidth = 400; # pixels
    maxaspect = maxwidth * 7 / 8
    centerx = maxwidth/2
    centery = maxwidth/2

    colors = ( 'green',  'cyan', 'PeachPuff3', \
        'RosyBrown1', 'IndianRed1', 'PaleVioletRed1', \
        'MediumOrchid1','pink','blue')

    colorindex = 0 # IS THIS USED?
    graph_param = (maxwidth, maxaspect, centerx, centery)

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

    root = Tk()
    views = Wires_plot(root, colors, graph_param)
    
################################

# populate the file box

    for file in os.listdir(os.getcwd()) :
        views.filebox.insert('end', file)

#   Interact...

    root.mainloop()

# -- end of main -- #

if __name__ == '__main__': 
    main()










