Welcome To Our Shell

Mister Spy & Souheyl Bypass Shell

Current Path : /home/ift/52_procpy/dataninja/

Linux ift1.ift-informatik.de 5.4.0-216-generic #236-Ubuntu SMP Fri Apr 11 19:53:21 UTC 2025 x86_64
Upload File :
Current File : //home/ift/52_procpy/dataninja/gui_file.py

import os,re,sys,time,math,tkinter,codecs,procpy

import procpy.block
import procpy.arrow
import procpy.rearr_grid


# import procpy.procobj

try:
    import tkinter.ttk,Pmw,xmltodict,json,svgwrite   #   ,tkintertable
except:
    import pip
    pip.main(["install","pyttk"])
    pip.main(["install","Pmw"])
    pip.main(["install","tkintertable"])
    pip.main(["install","xmltodict"])
    pip.main(["install","json"])
    pip.main(["install","svgwrite"])
    import tkinter.ttk,Pmw,xmltodict,json,svgwrite   #   ,tkintertable

import tkinter.filedialog

#**************************************************************************

class Gui_file (tkinter.Frame):


    def init (self,filename,gui):

        self.filename            = filename
        self.gui                 = gui
        self.loopobj             = gui.loopobj
        self.db                  = procpy.mysqlite.DBConn({'type':'sqlite','name':':memory:'})
        self.saved_yet           = 0

        self.current_zoom_factor = 1.0
        self.moffset             = 1
        self.fontsize_buttons    = 8
        self.griddata            = { "SHOW": False, "SNAP": False,"OFFSETX": 0.0,"OFFSETY": 0.0,
                                     "X": procpy.config.STARTGRIDX,
                                     "Y": procpy.config.STARTGRIDY  }   #  the grid for blocks
        self.hl_block_0          = None
        self.hl_block            = None
        self.hl1                 = None
        self.hl2                 = None

        self.color_blocks           = "#96C7E8"# light blue          #  wenn leer, Farbe aus dem gml-File
        self.color_startbl          = "#ff00ff"# rosa 
        self.color_endbl            = "#00ffff"# cyan 
        self.color_highlight_column = "#0069AF"# navy blue
        self.color_reportbar        = "#6DA5D5"# light blue

        self.snap = { 'OBJX': 0, 'OBJY': 0, 'GRIDX': 0, 'GRIDY': 0 }

        self.groupby   = "PATH"
        self.sortfield = "COUNT"
        self.sortupper = 0

        self.blocks     = []   #  key-values:  function : block
        self.colors     = {}

        self.loopobj.app.bind("<Delete>",self.delete_highlighted_element)

        self.mainframe  = tkinter.PanedWindow(self,orient=tkinter.VERTICAL)
        self.mainframe.pack(expand=tkinter.TRUE,fill=tkinter.BOTH)

        self.main_h = self.mainframe.winfo_height()
        self.main_w = self.mainframe.winfo_width()

        self.upperframe = tkinter.Frame(self.mainframe,height=self.main_h*0.672,    width=self.main_w)
        self.lowerframe = tkinter.Frame(self.mainframe,height=self.main_h*(1-0.672),width=self.main_w)
        self.upperframe.pack()
        self.lowerframe.pack()
        
        return()
		
#        self.mainframe.add(self.upperframe)
#        self.mainframe.add(self.lowerframe)




        self.buttonframe        = tkinter.Frame(self.upperframe,width=120)
        self.buttonframe_top    = tkinter.Frame(self.buttonframe)
        self.buttonframe_bottom = tkinter.Frame(self.buttonframe)
        self.buttonframe_top.pack(side=tkinter.TOP,expand=tkinter.TRUE,fill=tkinter.Y)
        self.buttonframe_bottom.pack(side=tkinter.BOTTOM)
        self.buttonframe_left   = tkinter.Frame(self.buttonframe_top)
        self.buttonframe_right  = tkinter.Frame(self.buttonframe_top)
        self.buttonframe_left.pack(side=tkinter.LEFT,expand=tkinter.TRUE,fill=tkinter.Y)
        self.buttonframe_right.pack(side=tkinter.LEFT,expand=tkinter.TRUE,fill=tkinter.Y)

        self.runcounter    = tkinter.Entry(self.buttonframe_left,width=6)
        self.runcounter.insert(0,"1")
        self.runcounter.pack()
        self.startbutton   = tkinter.Button(self.buttonframe_left,text="Start",width=6,
                                        command=self.start_process,font=("Arial",self.fontsize_buttons))
        self.startbutton.pack()
        self.stopbutton    = tkinter.Button(self.buttonframe_left,text="Stop",width=6,
                                        command=self.stop_process,font=("Arial",self.fontsize_buttons))
        self.stopbutton.pack()
        self.resetbutton   = tkinter.Button(self.buttonframe_left,text="0",width=6,bg="yellow",
                                        command=self.reset_process_data,font=("Arial",self.fontsize_buttons))
        self.resetbutton.pack()
        tkinter.Frame(self.buttonframe_left).pack(expand=tkinter.TRUE,fill=tkinter.Y)
        self.speedbutton   = tkinter.Button(self.buttonframe_left,text="Speed",width=6,
                                        command=self.reset_speed,font=("Arial",self.fontsize_buttons))
        self.speedbutton.pack()

        self.miniview_w    = 120
        self.miniview_h    = 100
        self.miniview      = tkinter.Canvas(self.buttonframe_bottom,width=self.miniview_w,height=self.miniview_h)
        self.miniview.pack()

        self.speedruler_h  = 200
        self.speedruler    = tkinter.Scale(self.buttonframe_right,from_=1000,to=1,length=self.speedruler_h)
        self.reset_speed()
        self.speedruler.pack(expand=tkinter.TRUE,fill=tkinter.Y)

        self.graphframe    = tkinter.Frame(self.upperframe)
        self.graphframe.pack(side=tkinter.LEFT,expand=tkinter.TRUE,fill=tkinter.BOTH)
        self.buttonframe.pack(side=tkinter.LEFT,fill=tkinter.Y)

        self.width_scrollbars = 8
        self.graphcanvas   = tkinter.Canvas(self.graphframe, width=self.gui.app_w-120, height=self.main_h*0.672, bg="white")
        self.xscroll = tkinter.Scrollbar(self.graphframe,orient=tkinter.HORIZONTAL)
        self.yscroll = tkinter.Scrollbar(self.graphframe,orient=tkinter.VERTICAL)
        self.xscroll.config(command=self.graphcanvas.xview,width=self.width_scrollbars)
        self.yscroll.config(command=self.graphcanvas.yview,width=self.width_scrollbars)
        self.graphcanvas.config(xscrollcommand=self.xscroll.set)
        self.graphcanvas.config(yscrollcommand=self.yscroll.set)
        self.xscroll.pack(side=tkinter.BOTTOM,fill=tkinter.X)
        self.yscroll.pack(side=tkinter.RIGHT,fill=tkinter.Y)
        self.graphcanvas.pack(side=tkinter.LEFT,expand=tkinter.TRUE,fill=tkinter.BOTH)
        
#        self.blockeditframe = Tkinter.Frame(self.upperframe,width=120)

        self.reportcanvas = tkinter.Canvas(self.lowerframe)
        self.uscroll      = tkinter.Scrollbar(self.lowerframe,orient=tkinter.HORIZONTAL)
        self.vscroll      = tkinter.Scrollbar(self.lowerframe,orient=tkinter.VERTICAL)
        self.uscroll.config(command=self.reportcanvas.xview,width=self.width_scrollbars)
        self.vscroll.config(command=self.reportcanvas.yview,width=self.width_scrollbars)
        self.reportcanvas.config(xscrollcommand=self.uscroll.set)
        self.reportcanvas.config(yscrollcommand=self.vscroll.set)
        self.uscroll.pack(side=tkinter.BOTTOM,fill=tkinter.X)
        self.vscroll.pack(side=tkinter.RIGHT,fill=tkinter.Y)
        self.reportcanvas.pack(side=tkinter.LEFT,expand=True,fill=tkinter.BOTH)

#        self.reportcanvas.config(scrollregion=(0,0,100,800)) # len(self.header_comboboxes)*200))

        self.actual_report_columns = []
        self.header_comboboxes     = []

        self.click_target = None
        def set_click_target(type):
            self.click_target = type

        text = ""
        if os.path.isfile(self.filename):
            text = open(self.filename).read()
        else:
            text = self.save_graphics()
        self.load_graphics(text,0)
        self.reset_drawdata()

        self.mouse_x = 0  # mouse event coords
        self.mouse_y = 0

        self.allow_context_menu = True

        self.current_zoom_level = 1.0

        self.graphcanvas.pack()
        self.fit_scrollbar()
        return(self.mainframe)

#************************************************************************************

	#Task: swim lanes ovelapping with blocks
	# Issue and Solution
    def load_graphics (self,text,mode):


        #self.graphcanvas.delete("all")

        self.saved_yet  = 1
		#-------------------------------
		#Issue: The mouse events to create swim lanes and blocks was bound on the background
		#of the rectangle item/tag inside the Canvas. Therefore the swin lanes was moved
		#behind rectangle rather than behind the blocks, when the method tag_lower was use on them inside the module Block.
		#--------------------------------
        #self.background = self.graphcanvas.create_rectangle(0,0,999999,999999,fill='white')
        #self.background="yellow"
        #self.graphcanvas.create_rectangle(0,0,99,99,fill='white')
        #self.graphcanvas.tag_bind(self.background,"<ButtonRelease-1>", self.release_button)
        #self.graphcanvas.tag_bind(self.background,"<Double-Button-1>", self.create_block)
        #self.graphcanvas.tag_bind(self.background,"<B1-Motion>",       self.move_mouse)
		#----------------------------------
		#Solution part 1: I have bound the mouse events on the Canvas, Part 2 in the module Block.
        self.graphcanvas.config(background="white")
        self.graphcanvas.bind("<ButtonRelease-1>", self.release_button)
        self.graphcanvas.bind("<Double-Button-1>", self.create_block)
        self.graphcanvas.bind("<B1-Motion>",       self.move_mouse)
		#---------------------------------------------------------------

        exec(text)     #  here the program code of the process file is read
        exec(self.__module__ + ".PROC = PROC")  #  new definition of the class PROC in gui_file
        obj       = PROC()  #  generate an object of the new class
        self.vars = {}
        funcs     = {}
        jumps     = {}

        for fkt in PROC.__dict__:    #   draw blocks

            try: 
                obj.__dict__ = { '_FKT_': fkt } #  make a new obj.__dict__ , and store the fkt in _FKT_
                PROC.__dict__[fkt](obj)         #  execution of the next funtion in the __dict__ of the class
                obj.BLOCK                       #  check whether BLOCK variable exists
            except Exception as e:              #  otherwise do not proceed
                continue
            
            
            block     = procpy.block.Block(mode,self,obj)
            block.fit_content()
            self.blocks.append(block)
            


            for var in block.vars:
                self.vars[var] = 1

#   Standard format for JUMP: {  'fkt1' :  [ 'condition', bend1_x, bend1_y, bend2_x, .... ] }

            if not 'JUMP' in vars(obj) or obj.JUMP == '':    #   conversions to the JUMP-variable
                obj.JUMP = {}   #  no jump                   #   to enable lazy coding of the process files
            elif type(obj.JUMP) == type(''):    #  JUMP = 'fkt1'  -> { 'fkt1' : [0] }
                obj.JUMP = { obj.JUMP : [0] }   
            elif type(obj.JUMP) == type([]):
                obj.JUMP = { obj.JUMP[0] : [0] + obj.JUMP[1:] }   #  JUMP = ['fkt1',x1,y1,...]  -> 
            jumps[block] = obj.__dict__                           #  { 'fkt1' : [0,x1,y1,....] }
            funcs[fkt]   = block

        for block in jumps:    #   draw arrows
            for jump in jumps[block]['JUMP']:
                arrdata = jumps[block]['JUMP'][jump]
                if not type(arrdata) == type([]):   #  'lazy' issue: see above
                    arrdata = [ arrdata ]
                procpy.arrow.Arrow(mode,self,block,funcs[jump],arrdata)

        self.vars = list(self.vars.keys())  #  all variables for reporting section
        self.vars.sort()

        for block in self.blocks:  #final adjustment of block shape to all the arrows
            if not block.shape == 'a':
                block.fit_content('x')
       
        self.fit_scrollbar() 
#************************************************************************************

    def fit_scrollbar(self): 
    
        '''
        guarantees a minimal size of scrollregion and
        includes all blocks in the scrollregion
        '''

        max_X = 1000      
        max_Y = 300
        
        for block in self.blocks:
            max_X = max(max_X, max(block.bbox[0],block.bbox[2]))
            max_Y = max(max_Y, max(block.bbox[1],block.bbox[3]))


        self.graphcanvas.config(scrollregion = (0,0,max_X+100,max_Y+100))

#************************************************************************************

    def hl_block_ok (self):

        if not self.hl_block == None:
            if self.hl_block.sync_content_to_fkt_and_text() == -1:
                self.hl_block.syntax_error = 1
                return(False)

        return(True)
            
#************************************************************************************

    def save_graphics (self):


        if not self.hl_block_ok():
            return()

        self.saved_yet          = 1


       # text = '''#  -*-  coding: utf-8 -*- this causes problems with exec
        text = '''
    
import procpy

class PROC (object):

    def __init__ (self,*pars):
        self.pars  = list(pars)
        self.JUMP  = ''' + "'---FUNC---'" + '''
        
'''

        blocks_data = []
        max_varlen  = 0

        self.blocks.sort(key=lambda block: block.nr)

        for block in self.blocks:    #  First run through the blocks
            varlen                = block.get_varlen()
            max_varlen            = max(max_varlen,abs(varlen))
            if block.nr == 0 and block.shape is not 'a':   #  if the block has no predecessor, then it is a starting block, dont include swimlanes
                text = re.sub(r"---FUNC---",block.fkt,text)

        for block in self.blocks:    #  Second run through the blocks
            text  = text + '''
    def ''' + block.fkt + ''' (self):
    
'''
            
            block.fit_content()   #  necessary because the content of the blocks have to be written into header and text
            
 
 
            for item in block.get_vars():
                if item[0] == 'JUMP':     #  replace block object refs in arrow to fkt names
                    jumpval = {}
                    for jump in item[1]:
                        jumpval[jump.fkt] = item[1][jump]
                    item[1] = jumpval
                if item[0] == 'JUMP' and not bool(jumpval):  # only write down if jump-block exists
                    text = text+ "\n"
                else:
                    text = text + "        self." + (item[0]+" "*max_varlen)[0:max_varlen] + " = " + json.dumps(item[1]) + "\n"
                        
        text = re.sub(r"\"([\d\.]+)\"","\\1",text,999999)
        
        exec(text)
        exec(self.__module__ + ".PROC = PROC")

#        self.gui.filemenu.entryconfig("Save",state="disabled")

        return(text)
                 

#************************************************************************************

    def check_whether_point_is_inside_of_a_block (self,x=-1,y=-1):
    
        '''
        Returns the maximal width and height of all blocks,
        if the point (x,y) is not inside of any block.
        Otherwise it returns the fkt of the block.
        '''
        
        bbox_w = 0
        bbox_h = 0
        
        for block in self.blocks:
            if block.bbox[0] < x and x < block.bbox[2] and block.bbox[1] < y and y < block.bbox[3]:
                return(None,block)
            bbox_w = max(bbox_w,block.bbox[2]-block.bbox[0])
            bbox_h = max(bbox_h,block.bbox[3]-block.bbox[1])

        return(bbox_w,bbox_h)        

#************************************************************************************

    def create_block (self,event):
        

        ### get the real canvas position, not the window position of the event
        try:
            x = self.graphcanvas.canvasx(event.x)
            y = self.graphcanvas.canvasy(event.y)
        except: # for testing, event is only a list object
            x = event[0]
            y = event[1]

      

        self.saved_yet = 0
        if not self.hl_block_ok():
            return()


        self.after(250,self.create_block_1)
        (bbox_w,bbox_h) = procpy.config.CREATE_BLOCK_SIZE

        bbox_w = bbox_w * self.current_zoom_factor
        bbox_h = bbox_h * self.current_zoom_factor

        obj      = PROC()
        obj.JUMP = {}

        zaehler = -1 
        for block in self.blocks:
            
            m = re.search(r"^t(\d+)$",block.fkt)
            if m:
                zaehler = max(zaehler,int(m.group(1)))
        newfkt = "t" + ("%02u" % (zaehler+1)) # commented in prod2 -> error: global name 'newfkt' is not defined, newfkt replaced with t00; switched back in task_runprocess
        
        if type(event) == type([]):   #  Test-Interface
            if len(event) == 2:
                event.append(bbox_w) 
            if len(event) == 3:
                event.append(bbox_h) 
            obj.BLOCK  = [newfkt, event[0],event[1],event[2],event[3]]
        else:
            obj.BLOCK  = [newfkt,x,y,bbox_w,bbox_h]
        
        obj._FKT_  =  newfkt                      # 't00'
        if obj.BLOCK[1] < obj.BLOCK[3]/2:
            obj._FKT_ = "LANE0"

        block      = procpy.block.Block(0,self,obj)
        if 'not_valid' in vars(block):
            return()
        self.blocks.append(block)

        self.graphcanvas.pack()
        self.fit_scrollbar()
        if self.griddata['SNAP']:
#            self.rearr_sugiyama(0.5)
            self.rearr_grid(0.2)
        self.last_event = None
        
#***************************************************************************************        
        
    def create_block_1 (self):

        if self.hl2:
            self.hl_block = self.hl2
            self.hl2      = None
            self.hl_block.highlight_block(0)


#************************************************************************************

    def create_arrow (self):
        

        self.saved_yet          = 0

        if not self.hl_block_ok():   #  highlighted block has to carry valid python code
            return()

        if self.hl_block and self.hl_block.shape == "a" or self.hl_block_0 and self.hl_block_0.shape == "a":
            return()                 #  do not draw arrows to and from swimlane blocks
        
        fkt  = None
        jump = None
        for block in self.blocks:
            if not fkt  and block == self.hl_block_0:
                fkt  = block
            if not jump and block == self.hl_block:
                jump = block
            if fkt and jump:
                break
        
        if not fkt:
            fkt = jump
        if jump:
            if fkt:
                create_the_arrow = True
                if fkt == jump:    #   don t create the arrow if source and target are identical
                    create_the_arrow = False
            #    count = 1
                for arrow in fkt.arrows_out:        #  check all the out arrows from fkt whether there
                    if arrow.target_block == jump:  #  is already an arrow between fkt and jump. in case
                        create_the_arrow = False    #  don t provide any new arrow
                        break
            #        count +=1 # count the arrows of this block for calculation of condition-string for creating the arrow
            #                  # this is not needed anymore as soon as the user can chose the condition manually (editable arrows)
                if create_the_arrow:
                    condition = 50               #round(100/count)
                    jump.hl_arrow = procpy.arrow.Arrow(0,self,fkt,jump,[condition])
                    fkt.fit_content("x")
                    jump.fit_content("x")
                else:
                    self.hl_block_0 = self.hl_block
                    self.hl_block   = None
                    return()

        self.rearr_grid(0.2,1)


#************************************************************************************

    def press_button (self,event):

        self.x0 = event.x
        self.y0 = event.y
        self.i0 = int((self.x0-self.griddata['OFFSETX']+3)/self.griddata['X'])
        self.j0 = int((self.y0-self.griddata['OFFSETY']+3)/self.griddata['Y'])
        if self.i0 == 0 or self.j0 == 0:
            self.i0 = 0
            self.j0 = 0

#************************************************************************************

    def move_mouse (self,event):
        
        if 'x0' in vars(self):

            (dx,dy) = (event.x-self.x0,event.y-self.y0)
            if self.i0 > 0:  #  changing of the grid dimensions
                (xquot,yquot) = (1.0/(self.x0-self.griddata['OFFSETX']),1.0/(self.y0-self.griddata['OFFSETY']))
            else:    #   changing of the offstes
                (dx_rel,dy_rel) = (dx,dy)
                
            for line in self.grid_lines:
                coords = self.graphcanvas.coords(line)
                if   coords[0] == coords[2]:  #  vertical line
                    if self.i0 > 0:
                        dx_rel = dx * (coords[2]-self.griddata['OFFSETX']) * xquot
                    self.graphcanvas.coords(line,coords[0]+dx_rel,coords[1],coords[2]+dx_rel,coords[3])
                elif coords[1] == coords[3]:  #  horizontal line
                    if self.j0 > 0:
                        dy_rel = dy * (coords[3]-self.griddata['OFFSETY']) * yquot
                    self.graphcanvas.coords(line,coords[0],coords[1]+dy_rel,coords[2],coords[3]+dy_rel)

            (self.x0,self.y0) = (event.x,event.y)

#************************************************************************************

    def release_button (self,event):

        if not self.hl_block_ok():
            return()

        self.hl2              = self.hl1
        self.hl1              = self.hl_block
        self.hl_block         = None
        self.hl_block_0       = None

#************************************************************************************

    def release_line (self,event):

        if self.i0 == 0:
            self.griddata['OFFSETX'] = event.x
            self.griddata['OFFSETY'] = event.y
        else:
            self.griddata['X'] = (event.x - self.griddata['OFFSETX'])/self.i0
            self.griddata['Y'] = (event.y - self.griddata['OFFSETY'])/self.j0
        del self.x0
        del self.i0
        del self.y0
        del self.j0

#************************************************************************************

    def delete_highlighted_element (self,event):



        if not self.hl_block_ok():
            return()



        self.saved_yet          = 0


        if self.hl_block:

            arrow = self.hl_block.hl_arrow
            
            if arrow:   #  delete arrow
                block = arrow.source_block
                jump  = arrow.target_block
                block.arrows_out.remove(arrow)
                jump.arrows_in.remove(arrow)
                arrow.destroy()
                self.hl_block.hl_arrow = None
                self.num_blocks(jump)
                self.hl_block   = None
                self.hl_block_0 = None
            else:       #  delete block
                self.hl_block.destroy()
                for arrow in self.hl_block.arrows_out:
                    self.num_blocks(arrow.target_block)
                self.blocks.remove(self.hl_block)
                self.hl_block   = None
                self.hl_block_0 = None

#************************************************************************************

    def num_blocks (self,jump):    #   numerate a block

        self.num_blocks_0(jump,999999)   #  1.  set the block and all ancestors to highest level
        self.num_blocks_0(jump,0)        #  2.  now compute lower levels by arrows
        if jump.nr == 999999:
            self.num_blocks_0(jump,1)    #  3.  if jump.nr remains highest level, then number it with 1.

#************************************************************************************

    def num_blocks_0 (self,block,nr,touched_blocks=None):   #   determines the minimum level of a block

        if touched_blocks == None:
            touched_blocks = {}
            
        for arrow in block.arrows_in:
            if nr == 0:
                nr = 999999
            nr = min(arrow.source_block.nr+1,nr)

        if not block in touched_blocks:
            touched_blocks[block] = block.nr
            block.nr              = nr
            block.fit_content("x")
            for arrow in block.arrows_out:
                jump = arrow.target_block
                self.num_blocks_0(jump,min(nr+1,999999),touched_blocks)
                
#************************************************************************************


    def toggle_show_grid (self):
    
        if self.griddata['SHOW']:
        
            for line in self.grid_lines:
                self.graphcanvas.delete(line)
            self.grid_lines       = []
            self.griddata['SHOW'] = False
        
        else:

            bbox = self.get_bounding_box()
            maxx = max(bbox[2],self.graphcanvas.winfo_width())
            maxy = max(bbox[3],self.graphcanvas.winfo_width())
            self.grid_lines = []
        
            x = self.griddata['X']
            while x < maxx:
                self.grid_lines.append(self.graphcanvas.create_line(x,0,x,maxy,width=1,fill="magenta",dash=(2,5)))
                x = x + self.griddata['X']
        
            y = self.griddata['Y']
            while y < maxy:
                self.grid_lines.append(self.graphcanvas.create_line(0,y,maxx,y,width=1,fill="magenta",dash=(2,5)))
                y = y + self.griddata['Y']

            for line in self.grid_lines:
                self.graphcanvas.tag_bind(line,"<ButtonPress-1>",   self.press_button)
                self.graphcanvas.tag_bind(line,"<B1-Motion>",       self.move_mouse)
                self.graphcanvas.tag_bind(line,"<ButtonRelease-1>", self.release_line)
            
            self.griddata['SHOW'] = True

        self.gui.switch_tab()        
        

#************************************************************************************

    def grid_select (self,l,event):

        (x,y) = self.check_whether_point_is_inside_of_a_block()
        if x:
            (self.gx,self.gy) = (event.x,event.y)
        else:
            self.gx = None    


#************************************************************************************

    def grid_move (self,event):

        dx = event.x - self.gx
        dy = event.y - self.gy


#************************************************************************************

    def toggle_snap_grid (self):
        if self.griddata['SNAP']:
            self.griddata['SNAP'] = False
        else:
            self.griddata['SNAP'] = True
        self.gui.switch_tab()        
                    
#************************************************************************************

    def fit_blocks_to_grid (self):

        g = self.griddata
        for block in self.blocks:
            x  = g['X'] * int((block.bbox[0] - g['OFFSETX'] + 0.5*g['X'])/g['X'])
            y  = g['Y'] * int((block.bbox[1] - g['OFFSETY'] + 0.5*g['Y'])/g['Y'])
            dx = block.bbox[0] - x - g['OFFSETX']
            dy = block.bbox[1] - y - g['OFFSETY'] 
            block.newbbox = [ block.bbox[0] - dx, block.bbox[1] - dy,
                              block.bbox[2] - dx, block.bbox[3] - dy ]


#************************************************************************************
    def rearrange_blocks(self): # arranges block without overlap
        block_coordinates = []
        for block in self.blocks:
            i,j = block.gridpos()
            while self.check_gridpos_empty(i,j,block_coordinates)==False:
                i,j = block.gridpos(i,j+1)
            block_coordinates.append([i,j])
            
#************************************************************************************
    def check_gridpos_empty(self,coord1,coord2,block_coordinates):
        i = coord1
        j = coord2
        return not([i,j] in block_coordinates or [i+1,j] in block_coordinates or [i-1,j] in block_coordinates)
        
#************************************************************************************


    def rearr_grid (self,move_interval,b=0):

        self.rearrange_blocks() 

        procpy.rearr_grid.Rearr_grid(self).newbends_for_arrows()
        self.positioning(move_interval)
        self.fit_scrollbar()

#************************************************************************************

    def rearr_grid_arrows_with_sugiyama (self,move_interval):

        for block in self.blocks:
            block.gridpos()
        procpy.rearr_sugiyama.Rearr_sugiyama(self,0).arrows_sugiyama_fit()
        self.positioning(move_interval)

#************************************************************************************

    def rearr_sugiyama (self,move_interval):

        procpy.rearr_sugiyama.Rearr_sugiyama(self,0).blocks_sugiyama_fit()
        procpy.rearr_sugiyama.Rearr_sugiyama(self,0).arrows_sugiyama_fit()
        self.positioning(move_interval)

#************************************************************************************

    def rearr_circle (self,move_interval):

        (maxw,maxh) = (0,0)
        for block in self.blocks:
            (maxw,maxh) = (max(maxw,block.bbox[2]-block.bbox[0]),
                           max(maxh,block.bbox[3]-block.bbox[1]))
        anzahl      = float(len(self.blocks))
        radiusx     = maxw * math.log(anzahl) * 1.5
        radiusy     = maxh * math.log(anzahl) * 1.5
        zaehler     = anzahl
               
        self.blocks.sort(key=lambda block: block.nr)
        for block in self.blocks:
            block.newbbox    = [0,0,0,0]
            block.newbbox[0] = radiusx * (1.1+math.cos(math.pi*zaehler/anzahl))
            block.newbbox[1] = radiusy * (1.1+math.sin(math.pi*zaehler/anzahl))
            block.newbbox[2] = block.newbbox[0] + block.bbox[2] - block.bbox[0]
            block.newbbox[3] = block.newbbox[1] + block.bbox[3] - block.bbox[1]
            zaehler          = zaehler + 2
            for arrow in block.arrows_out:
                arrow.newbends   = []
                arrow.anchorline = 0
        self.positioning(move_interval)

#************************************************************************************

    def rearr_swimlane (self,move_interval):

        swimlanes = {}           #  Collecting and sorting the swimlanes
        for swimlane in self.blocks:
            if swimlane.shape == "a":
                swimlanes[ ("%09.4f" % swimlane.bbox[1]) + "-" + ("%09.4f" % swimlane.bbox[3]) ] = swimlane
        swkeys = list(swimlanes.keys())
        swkeys.sort()
        
        dy   = 0  #  shift to down
        miny = 0  #  limit in height for swimlane
        
        all_arrows = []
        for block in self.blocks:
            block.newbbox = block.bbox[:]
            for arrow in block.arrows_in:
                all_arrows.append(arrow)
                arrow.newbends = []
                for arrowline in arrow.arrowlines[:-1]:
                    coords = self.graphcanvas.coords(arrowline)
                    arrow.newbends.append([coords[2],coords[3]])
                
        for swkey in swkeys:
            swimlane            = swimlanes[swkey]
            dy                  = max(0,miny - swimlane.bbox[1])
            swimlane.newbbox    = [0,0,0,0,0]
            swimlane.newbbox[1] = swimlane.bbox[1] + dy
            swimlane.newbbox[2] = swimlane.bbox[2] - swimlane.bbox[0]
            swimlane.newbbox[3] = swimlane.bbox[3] + dy
            miny                = swimlane.newbbox[3]
#            (blocks,arrows,singlepoints) = swimlane.blocks_and_arrows_in_swimlane()
            (blocks,arrows,singlepoints) = (swimlane.move_blocks,swimlane.move_arrows,swimlane.move_singlepoints)
            for block in blocks:
                block.newbbox[1] = block.bbox[1] + dy
                block.newbbox[3] = block.bbox[3] + dy
            for arrow in arrows:
                all_arrows.remove(arrow)
                zaehler = 0
                for arrowline in arrow.arrowlines[:-1]:
                    arrow.newbends[zaehler][1] = arrow.newbends[zaehler][1] + dy
                    zaehler = zaehler + 1
            for point in singlepoints:
                if point[2] == 0 and point[1] > 0:
                    arrow = point[0]
                    arrow.newbends[point[1]-1][1] = arrow.newbends[point[1]-1][1] + dy

        self.positioning(move_interval)

#************************************************************************************
#************************************************************************************

    def positioning (self,move_interval=3.0,max_rounds=100):

        duetime      = time.clock() + move_interval
        zaehler      = 0
        gesamt_time  = 0
        nr           = max_rounds
        
        if 'semaphore_positioning_in_progress' in vars(self):
            return()
            
        self.semaphore_positioning_in_progress = True

# 1. Preparation: Absolute to relative values, extend arrows if necessary

        maxshift = 0
        for block in self.blocks:   #  shift the absolute coordinates to relative
            fkt  = block.fkt
            bbox = block.bounding_box()   #  and add - if needed - helper bends in arrows
            if 'newbbox' in vars(block):
                block.newbbox = [block.newbbox[0]-block.bbox[0],block.newbbox[1]-block.bbox[1],
                                 block.newbbox[2]-block.bbox[2],block.newbbox[3]-block.bbox[3]]
            else:
                block.newbbox = [0,0,0,0]                                
            maxshift     = max(maxshift,abs(block.newbbox[0]),abs(block.newbbox[1]),
                                        abs(block.newbbox[2]),abs(block.newbbox[3]))
            for arrow in block.arrows_out:
                if not 'newbends' in vars(arrow):
                    continue
#                jump    = arrow.target_block
                bends   = arrow.newbends
                lines   = arrow.arrowlines
                zaehler = 1
                for bend in bends:
                    if len(lines) == 1:   #  if no bend is in arrow
                        (x,y)  = arrow.get_shapes_mid_point()
                        coords = self.graphcanvas.coords(lines[0])
                        self.graphcanvas.coords(lines[0],x,y,coords[2],coords[3])
                        lines.insert(-1,self.graphcanvas.create_line(coords[0],coords[1],x,y,
                                            fill='black',width=procpy.config.ARROWTHICKNESS))
                    while len(lines) < zaehler+1:   #  extend arrow bends to match the count of new bends
                        coords = self.graphcanvas.coords(lines[-1])
                        lines.insert(-1,self.graphcanvas.create_line(coords[0],coords[1],coords[0],coords[1],
                                                fill='black',width=procpy.config.ARROWTHICKNESS))
                    coords   = self.graphcanvas.coords(lines[zaehler])
                    bend[0]  = bend[0] - coords[0]
                    bend[1]  = bend[1] - coords[1]
                    maxshift = max(maxshift,abs(bend[0]),abs(bend[1]))
                    zaehler  = zaehler + 1

#        self.gui.mark("B")

#  2.  Morphing arrows in a loop step by step

        while nr > 0:

            time0 = time.clock()
            
            for block in self.blocks:
                if 'newbbox'in vars(block):
                    (dx0,dy0,dx1,dy1) = ( block.newbbox[0]/nr, block.newbbox[1]/nr, block.newbbox[2]/nr, block.newbbox[3]/nr )
                    block.newbbox = [ block.newbbox[0] - dx0, block.newbbox[1] - dy0,
                                      block.newbbox[2] - dx1, block.newbbox[3] - dy1 ] 
                    block.bbox    = [ block.bbox[0] + dx0, block.bbox[1] + dy0, block.bbox[2] + dx1, block.bbox[3] + dy1 ]
                    block.fit_content()

            for block in self.blocks:
                for arrow in block.arrows_out:
                    if not 'newbends' in vars(arrow):
                        continue
                    zaehler1 = 0
                    while (0 == 0):
                        px       = None
                        try:
                            c_line1 = self.graphcanvas.coords(arrow.arrowlines[zaehler1+1])
                        except:
                            break
                        c_line0  = self.graphcanvas.coords(arrow.arrowlines[zaehler1])
                        try:
                            bend    = arrow.newbends[zaehler1]
                            (dx,dy) = ( bend[0]/nr, bend[1]/nr )
                            bend[0] = bend[0] - dx
                            bend[1] = bend[1] - dy
                            (px,py) = ( c_line1[0], c_line1[1] )
                        except Exception as e:   #  if no new bend definition is available anymore
                            if not px:
                                (px,py) = arrow.get_shapes_mid_point()
                            (dx,dy) = ( (px-c_line0[2])/nr, (py-c_line0[3])/nr ) 
                        self.graphcanvas.coords(arrow.arrowlines[zaehler1],
                                                c_line0[0],    c_line0[1],    c_line0[2]+dx, c_line0[3]+dy)
                        self.graphcanvas.coords(arrow.arrowlines[zaehler1+1],
                                                c_line1[0]+dx, c_line1[1]+dy, c_line1[2],     c_line1[3]  )
                        zaehler1 = zaehler1 + 1
                    bbox = self.get_bounding_box()
                    arrow.fit_block_connections()
                    arrow.fit_description()  #  self.griddata)
            
            self.graphcanvas.update()
            bbox = self.get_bounding_box()
            xdim = self.graphcanvas.winfo_width()
            ydim = self.graphcanvas.winfo_height()

#            self.gui.mark(str(nr))
            zaehler      = zaehler + 1              #   count runs
            time0        = time.clock() - time0      #   time for this loop run
            gesamt_time  = gesamt_time + time0      
            rest_time    = duetime - time.clock()    #   Computing runs /waittime to match
            avg_time     = gesamt_time/zaehler      #   the interval for this action
            if rest_time > 0 :
                wait_time = rest_time/nr - avg_time
                if wait_time > 0:
                    time.sleep(wait_time)
                    nr = nr-1
                else:
                    nr = min( int(rest_time/avg_time), nr-1 )
                    nr = max(1,nr)
            else:
                nr = min(2,nr-1)

#        self.gui.mark("C")

        bbox = self.get_bounding_box()
        xdim = self.graphcanvas.winfo_width()
        ydim = self.graphcanvas.winfo_height()
        self.graphcanvas.config(scrollregion=(0,0,max(xdim,bbox[2]),max(ydim,bbox[3])))


#  3.  Deleting superfluous bends in arrows at end of moving

        for block in self.blocks:
            for arrow in block.arrows_out:
                if not 'newbends' in vars(arrow):
                    continue
                lines = arrow.arrowlines
                try:
                    soll_len = len(arrow.newbends) + 1
                except:
                    continue
                c_line0  = None
                while soll_len < len(lines):
                    c_line0 = self.graphcanvas.coords(lines[-2])
                    self.graphcanvas.delete(lines.pop(-2))
                if c_line0:
                    c_line1 = self.graphcanvas.coords(lines[-1])
                    self.graphcanvas.coords(lines[-1],c_line0[0],c_line0[1],c_line1[2],c_line1[3])
                arrow.fit_description(self.griddata)
                del arrow.newbends
            try:
                del block.newbbox
            except:
                pass
                

#   4.  now at last a re-fitting is necessary

        for block in self.blocks:
            for arrow in block.arrows_out:
                arrow.fit_block_connections()

        self.graphcanvas.update()
        del self.semaphore_positioning_in_progress
        return(True)

#************************************************************************************

    def reset_speed (self):
        self.speedruler.set(950)

#************************************************************************************

    def get_bounding_box (self):

        bbox = []
        for block in self.blocks:
            block.bounding_box(bbox)
            for jump in block.arrows_in:
                jump.bounding_box(bbox)
        return(bbox)
                    
#************************************************************************************

    def set_zoomfaktor (self,fac):   #   fac: factor to zoom, if = -1/ -2/ -3: fit to width, height resp. canvas


        xdim = self.graphcanvas.winfo_width()
        ydim = self.graphcanvas.winfo_height()
        
        if fac < 0 and fac > -4:  #  fit to page width resp. height resp. canvas

            self.graphcanvas.update()
            
            bbox = self.get_bounding_box()
            fakx = float(xdim) / float(bbox[2]) # - bbox[0])
            faky = float(ydim) / float(bbox[3]) # - bbox[1])
            
            if fac == -3 and fakx < faky:
                fac = -1
            elif fac == -3:
                fac = -2
            fac = 0.96 * [fakx,faky][-fac-1]
    
        elif self.hl_block and not self.hl_block.shape == "a":

            self.hl_block.zoom_text(fac)
            return()

        self.current_zoom_factor = self.current_zoom_factor * fac
        for block in self.blocks:
            block.scale(fac)
        bbox = self.get_bounding_box()
        self.graphcanvas.config(scrollregion=(0,0,max(xdim,bbox[2]/0.96),max(ydim,bbox[3]/0.96)))
        self.griddata['X'] = fac * self.griddata['X']
        self.griddata['Y'] = fac * self.griddata['Y']
        if self.griddata['SHOW']:
            self.toggle_show_grid()
            self.toggle_show_grid()

#************************************************************************************

    def sortcols (self,event):
    
        canvas = event.widget
        x = canvas.canvasx(event.x)
        y = canvas.canvasy(event.y)
        
        fieldnr = int(x)/160
        field   = self.actual_report_columns[fieldnr]
        if self.sortfield == field:
            self.sortupper = (self.sortupper + 1) % 4
        else:
            self.sortupper = 0
            
        self.sortfield = field
        self.draw_report_bars()
        
#**************************************************************************

    def compute_report_data (self,entry):
        
        try:
            group0 = entry.SUMVALUES[self.groupby]
        except:
            pass #group0 =

        try:
            group0 = str(float(group))
        except:	
            pass
        
        for group in [group0,"__gesamt__"]:
            try:
                self.counts[group]   += 1
            except:
                
                self.counts[group]    = 1
                self.sumvalues[group] = {}
            if not group == "__gesamt__":
                self.maxcount = max(self.counts[group],self.maxcount)

            for field in self.report_fields:
                if field == "COUNT":
                    continue
                if field == "":
                    continue
                try:
                    self.sumvalues[group]
                except:
                    self.sumvalues[group] = {}
                try:
                    self.sumvalues[group][field]
                except:
                    self.sumvalues[group][field] = 0
                try:
                    self.maxvalues[field]
                except:
                    self.maxvalues[field] = 0
                try:
                    val = entry.SUMVALUES[field]
                except:
                    val = "0"
                try:
                    val = float(val)
                    self.sumvalues[group][field] += val
                    if not group == "__gesamt__":
                        self.maxvalues[field] = max(self.maxvalues[field],val)
                except:
                    self.sumvalues[group][field]  = val

        self.draw_data = []
        for group in self.sumvalues:
            data_row = {}
            for field in self.report_fields:
                if field == "COUNT":
                    data_row[field] = [self.counts[group],self.maxcount]
                else:
                    val = self.sumvalues[group][field]
                    try:
                        val = float(val) / self.counts[group]
                    except Exception as e:
                        pass
                    data_row[field] = [val,self.maxvalues[field]]
            if group == "__gesamt__":
                self.draw_data_gesamt = data_row
            else:
                self.draw_data.append(data_row)


#****************************************************

    def draw_report_headers (self,reason_for_call=1):
    
        new_columns = []
        for header_combobox in self.header_comboboxes:
            header_text = header_combobox.get()
            if not header_text == "":
                new_columns.append(header_text)
        new_columns.append("")
        
        if not self.actual_report_columns == new_columns:

            o1 = len(self.actual_report_columns)
            o2 = len(new_columns)
            if not o2 == o1:
                if o2 < o1:
                    while o2 < len(self.header_comboboxes):
                        self.header_comboboxes[-1].destroy()
                        del self.header_comboboxes[-1]
                else:
                    newcombo = tkinter.ttk.Combobox(self.reportcanvas,width=12,font=("Arial",8))
                    self.reportcanvas.create_window((o2-1)*160+20,5,anchor=tkinter.NW,window=newcombo)
                    if o1 == 0:
                        newcombo.insert(0,'PATH')
                        newcombo.config(state='readonly')
                    if o1 == 1:
                        newcombo.insert(0,'COUNT')
                        newcombo.config(state='readonly')
                    else:
                        newcombo.config(postcommand=self.draw_report_headers)
#                    newcombo.config(validatecommand=self.draw_report,validate='all')
                    self.header_comboboxes.append(newcombo)
                    self.reportcanvas.config(scrollregion=(0,0,len(self.header_comboboxes)*160,10))

            self.actual_report_columns = new_columns
            zaehler = 0
            option_values = self.vars + [""]
            for column_text in self.actual_report_columns:
                self.header_comboboxes[zaehler].delete(0,9999)
                self.header_comboboxes[zaehler].insert(0,column_text)
                if column_text in ['PATH','COUNT']:
                    self.header_comboboxes[zaehler].config(values=[])
                else:
                    self.header_comboboxes[zaehler].config(values=option_values)
                zaehler = zaehler + 1
            if 'draw_data' in vars(self):
                self.draw_report_bars()

        self.reportcanvas.config(scrollregion=(0,0,len(self.header_comboboxes)*160,10))
        if len(self.actual_report_columns) < 3:
            return(self.draw_report_headers())


#****************************************************

    def draw_report_bars (self):
    
#        nr = self.report_fields_nr[self.sortfield]
        if self.sortfield == 'COUNT':
            self.draw_data.sort(key=lambda x: x['COUNT']+x['PATH'], reverse=(self.sortupper%2==0))
        else:
            self.draw_data.sort(key=lambda x: x[self.sortfield], reverse=(self.sortupper%2==0))
        self.draw_data1 = [self.draw_data_gesamt] + self.draw_data

        self.reportcanvas.delete("reportbar")

        row       = 1
        cellh     = 12
        cellw     = 160

        x0 = 0
        y0 = 2*cellh
        y0 = 3*cellh

        gesamtzeile = True  #  first line is the total/average data line
        for ergrow in self.draw_data1:
            x0 = 0
            y0 = y0 + cellh
            for field in self.actual_report_columns[0:-1]:
                if gesamtzeile and field == self.sortfield:
                    xpos = x0+2
                    ypos = y0-int(2.7*cellh)
                    color_sort = "yellow"
                    if self.sortupper%2 == 0:    #  compute and draw sort marker
                        ypos       = ypos - 10
                        color_sort = "red"
                    self.reportcanvas.create_oval(xpos,ypos,xpos+4,ypos+4,fill=color_sort,tag='reportbar')
                fillcolor = procpy.config.COLOR_REPORTBAR
                val       = ergrow[field][0]
                gval      = ergrow[field][1]
                if gesamtzeile:
                    fillcolor = 'grey'
                    if field == 'PATH':
                        val = "TOTAL / AVERAGE"
                try:
                    val1 = float(val)/float(gval)
                    if not (gesamtzeile and field == "COUNT"):
                        o = self.reportcanvas.create_rectangle(x0+5,
                                                     y0-12,
                                                     x0+5+val1*(cellw-40),
                                                     y0-2,
                                                     fill=fillcolor,tag='reportbar')
                        self.reportcanvas.tag_bind(o,'<ButtonPress-1>',lambda event: self.sortcols(event) )
                    val = int(val)
                except:
                    pass
                if field == 'COUNT' and self.sortupper > 1:
                    if gesamtzeile:
                        relative_val = val
                    else:
                        val = '%3.1f' % (100 * float(val) / float(relative_val) ) + '%'
                o = self.reportcanvas.create_text(x0+6,y0,text=str(val),anchor='sw',font=("Arial",8),
                                       tag=['reportbar',field])
                self.reportcanvas.tag_bind(o,'<ButtonPress-1>',lambda event: self.sortcols(event) )
                x0 = x0 + cellw
            gesamtzeile = False

        self.reportcanvas.config(scrollregion=(0,0,len(self.header_comboboxes)*160,y0+15))

#***************************************************************************************

    def start_process(self):
       
        if self.saved_yet  == 0:
            self.save_graphics()

        self.startbutton.config(state='disable')
        self.hl_block = None
        o = self.runcounter.get()
        self.runcounter.delete(0,10)
        if int(o) < 1:
            self.runcounter.insert(0,"1")
            self.startbutton.config(state='normal')
            return(0)
        self.runcounter.insert(0,str(int(o)-1))

        o = self.resetbutton.config('text')[-1]
        self.resetbutton.config(text=str(int(o)+1))

        self.block_list = {}
        self.hl_blocks  = {}
        self.steps      = {}
        for block in self.blocks:
            self.graphcanvas.itemconfig(block.elems['SHAPE'],fill=self.color_blocks)
            if block.shape == 'a':# swimlanes are not counted in block_list
                pass
            else:
                self.block_list[block.fkt] = block
        
        if not self.block_list: # if there are no blocks, stop process
            self.stop_process()
            return()	
        self.loopobj.after(0,self.proceed_process,self.__module__+".PROC")
        
#***************************************************************************************

    def proceed_process (self,mode="START",pars=[]):
        
        proc_instance = procpy.prcmanager.Prcmanager(self.db).run_process(mode,pars)
        speedfactor   = 5**(int(self.speedruler.get())/100-1)

        if proc_instance:

            self.entry = proc_instance
            obj        = proc_instance.OBJID
            fkt        = proc_instance.__func__
            sleeptime  = str(proc_instance.TIME)

            if obj in self.hl_blocks:
                id = self.hl_blocks[obj]
                self.block_list[id].content.config(bg=self.color_blocks,highlightcolor=self.color_blocks)
                self.block_list[id].contentframe.config(background=self.color_blocks,bg=self.color_blocks,
                highlightcolor=self.color_blocks) 
                self.graphcanvas.itemconfig(self.block_list[id].elems['SHAPE'],fill=self.color_blocks)    #   <----

            try:
                fillcolor1 = "red"
                self.block_list[fkt].content.config(bg=fillcolor1,highlightcolor=fillcolor1)        # color the content
                self.block_list[fkt].contentframe.config(background=fillcolor1,bg=fillcolor1,
                highlightcolor=fillcolor1)                                                          # color the contentframe
                self.graphcanvas.itemconfig(self.block_list[fkt].elems['SHAPE'],fill=fillcolor1)    # color the outer rectangle
                
                self.hl_blocks[obj] = fkt
            except Exception as e:
                pass
                print(str(e))
            if int(sleeptime) < 9999999900:   #   Prozess laeuft weiter
                self.loopobj.after(max( 50,int(sleeptime)*1000/speedfactor),self.proceed_process,'___dryrun___')
                return()


        self.compute_report_data(self.entry)   #  Daten des beendeten Prozesses gehen
        self.draw_report_headers()             #  in das Reporting ein
        self.draw_report_bars()
#        self.runobj = procpy.caller.Scripts()
        self.loopobj.after(max(35,int(1000/speedfactor)),self.del_all_highlighting)
        self.loopobj.after(max(70,int(2000/speedfactor)),self.start_process)
            
#****************************************************

    def stop_process (self):

        o = self.runcounter.get()
        self.runcounter.delete(0,10)
        self.runcounter.insert(0,"1")
        self.del_all_highlighting()
        self.startbutton.config(state='normal')

#****************************************************

    def reset_process_data (self):
    
        self.reset_drawdata()
        self.reportcanvas.delete('reportbar')

#****************************************************

    def reset_drawdata (self):

        self.resetbutton.config(text='0')
        self.report_fields    = ['PATH','COUNT'] + self.vars
        self.counts           = {}
        self.maxcount         = 0
        self.sumvalues        = {}
        self.maxvalues        = {}
        self.draw_report_headers()
#        self.field_expression = {}
#        for field in self.report_fields:
#            if re.search(r"[^A-Za-z0-9\_]",field):
#                self.field_expression[field] = re.sub(r"([A-Z][A-Za-z0-9\_]*)","float(entry.\\1)",field,99999999)
#            else:
#                self.field_expression[field] = "entry." +field
#        

#****************************************************

    def del_all_highlighting (self):

        self.saved_yet          = 0
        fillcolor1 = self.color_blocks

        for block in self.blocks:
            block.content.config(bg=fillcolor1,highlightcolor=fillcolor1)                            # color the content
            block.contentframe.config(background=fillcolor1,bg=fillcolor1,highlightcolor=fillcolor1) # color the contentframe
            self.graphcanvas.itemconfig(block.elems['SHAPE'],fill=fillcolor1)                        # color the outer rectangle
                


#****************************************************

    def show_menu(self, event,):
        if self.allow_context_menu:
            type = self.graphcanvas.type(event.widget.find_withtag("current"))
            if self.click_target == None or type == None:
                background_menu = tkinter.Menu(self.graphcanvas, tearoff=0)
                background_menu.add_command(label="New block", command= lambda :self.create_block(event.x_root, event.y_root))
                background_menu.post(event.x_root, event.y_root)

            elif self.click_target.__class__ is procpy.block.Block:
                block_menu = tkinter.Menu(self.graphcanvas, tearoff=0)
                block_menu.add_command(label="New arrow", command=lambda : self.create_arrow(self.click_target))
                block_menu.post(event.x_root, event.y_root)


#************************************************************************************
#************************************************************************************

    def xxscale_texts (self,fac):    #  scale texts

        for block in self.blocks:
            block.scale_texts(fac)
            for arrow in block.arrows_out:
                arrow.scale_texts(fac)

        self.current_zoom_factor = self.current_zoom_factor * fac

#************************************************************************************

    def xxset_zoomfaktor (self,fac,draw_new=True):

        xdim = self.graphcanvas.winfo_width()
        ydim = self.graphcanvas.winfo_height()
        
        if fac < 0 and fac > -4:  #  fit to page width resp. height resp. canvas

            self.graphcanvas.update()
            
            bbox = self.get_bounding_box()
            fakx = xdim / (bbox[2] - bbox[0])
            faky = ydim / (bbox[3] - bbox[1])
            if   fac == -1:
                fak = fakx
            elif fac == -2:
                fak = faky
            else:
                fak = min(fakx,faky)

            self.graphcanvas.scale("all",0,0,fak,fak)

            """for fkt in self.blocks[fkt]:
                block = self.blocks[fkt]
                old_size = self.graphcanvas.itemcget(block.text,'text')
                new_size = self.graphcanvas.itemconfig(block.text,font=('Arial',old_size*fak)
            for fkt in self.arrows:
                 for jump in self.arrows[fkt][jump]"""
            bbox = self.get_bounding_box()
            self.graphcanvas.config(scrollregion=(bbox[0],bbox[1],max(bbox[2],bbox[0]+xdim)+1,max(bbox[3],bbox[1]+ydim)+1))


#            for fkt in self.blocks[fkt]:
#                block = self.blocks[fkt]
#                old_size = self.graphcanvas.itemcget(block.text,'text')
#                new_size = self.graphcanvas.itemconfig(block.text,font=('Arial',old_size*fak)
#            for fkt in self.arrows:
#                for jump in self.arrows[fkt][jump]

#        elif fac == -5:
#            if self.fak == -1:
#                fac = -7
#            else:
#                fac = -9
##        if fac == -7:           #  toggle back to graph view
#            self.fak = self.fit
#
#        elif fac == -9:           #  presentation as a textfield for the pycode
#            self.fak = -1
#
        elif fac > 0:
            bbox = self.get_bounding_box()
            self.graphcanvas.scale("all",0,0,fac,fac)
            bbox = self.get_bounding_box()
#            bx   = bbox[2] - bbox[0] + 20
#            by   = bbox[3] - bbox[1] + 20
#            bbox = self.get_bounding_box()
#            print (bbox[0],bbox[1],max(bbox[2],bbox[0]+xdim),max(bbox[3],bbox[1]+ydim))
            self.graphcanvas.config(scrollregion=(bbox[0],bbox[1],max(bbox[2],bbox[0]+xdim)-1,max(bbox[3],bbox[1]+ydim)-1))
#            self.graphcanvas.config(scrollregion=(0,0,bbox[2]+20,bbox[3]+15))

#            faknew = self.fak * fac
#            if True:
##            if (faknew > fakx or faknew > faky) and faknew < 10*max(fakx,faky):
#                self.fak = faknew
#                self.fit = faknew
#            else:
#                return()
#
#        try:
#            if self.fak < self.fak0 * (1 + 0.00001) and self.fak > self.fak0 * (1 - 0.00001):
#                return
#        except:
#            pass
#        self.fak0 = self.fak        

#        self.draw_bpm()


#************************************************************************************

    def xxdraw_miniview (self):
    
        fakx = self.miniview_w / (self.pd.w())
        faky = self.miniview_h / (self.pd.h())
        self.draw_graphics(self.miniview,min(fakx,faky),self.moffset,False)

#************************************************************************************

    def xxdraw_bpm (self):

        if self.fak < 0:
            pycode = self.pd.text
        else:
            self.graphcanvas_w  = self.fak * (self.pd.w())
            self.graphcanvas_h  = self.fak * (self.pd.h())
            print(self.graphcanvas_w)
            print(self.graphcanvas_h)
 
        try:
            self.graphcanvas.destroy()
        except:
            pass
        try:
            self.xscroll.destroy()
        except:
            pass
        try:
            self.yscroll.destroy()
        except:
            pass

        if self.fak < 0:
            self.graphcanvas = tkinter.Frame(self.graphframe)
            self.graphcanvas.pack(expand=tkinter.TRUE,fill=tkinter.BOTH)
            self.graphtext   = tkinter.Text(self.graphcanvas,wrap=tkinter.NONE,width=10,height=10)
            self.graphtext.pack(expand=True,fill=tkinter.BOTH)
            self.graphtext.insert(tkinter.END,pycode)
        else:
            self.graphcanvas = tkinter.Canvas(self.graphframe)
            self.graphcanvas.config(scrollregion=(0,0,self.graphcanvas_w,self.graphcanvas_h))
            self.xscroll = tkinter.Scrollbar(self.graphframe,orient=tkinter.HORIZONTAL)
            self.yscroll = tkinter.Scrollbar(self.graphframe,orient=tkinter.VERTICAL)
            self.xscroll.config(command=self.graphcanvas.xview,width=8)
            self.yscroll.config(command=self.graphcanvas.yview,width=8)
            self.graphcanvas.config(xscrollcommand=self.xscroll.set)
            self.graphcanvas.config(yscrollcommand=self.yscroll.set)
            self.xscroll.pack(side=tkinter.BOTTOM,fill=tkinter.X)
            self.yscroll.pack(side=tkinter.RIGHT,fill=tkinter.Y)
            self.graphcanvas.pack(side=tkinter.LEFT,expand=True,fill=tkinter.BOTH)

            # create a menu
            #self.initUI()

            #Moving canvas with mouse not working at the moment with moving with items
            #self.graphcanvas.bind("<ButtonPress-1>", self.move_start)
            #self.graphcanvas.bind("<B1-Motion>", self.move_move)

            #Add zoom function with mousewheel
            # linux
            self.graphcanvas.bind("<Button-4>", self.zoomerP)
            self.graphcanvas.bind("<Button-5>", self.zoomerM)
            # windows
            self.graphcanvas.bind("<MouseWheel>", self.zoomer)

        if self.fak > 0:
            self.draw_graphics(self.graphcanvas,self.fak,self.offset,True)

#************************************************************************************

    def xxdraw_graphics (self,graph_widget,fak,offset,with_text=False):

        graph_widget.config(background='white')

        self.sources = {}  #  The arrow lists of the blocks where the arrows are sources
        self.targets = {}  #  The arrow lists of the blocks where the arrows are targets

        for fkt in self.pd.funcs:  #  process all the blocks
            self.sources[fkt] = []
            self.targets[fkt] = []
            x   = fak * ( self.pd.x(fkt) - self.pd.x0() ) + offset
            y   = fak * ( self.pd.y(fkt) - self.pd.y0() ) + offset
            w   = fak * self.pd.w(fkt)
            h   = fak * self.pd.h(fkt)
           # self.blocks[fkt] = graph_widget.create_rectangle(
           #         int(x-w/2),int(y-h/2),
           #         int(x+w/2),int(y+h/2),fill=self.color_blocks)
            block_size = (int(x-w/2),int(y-h/2),int(x + w / 2),int(y+h/2))
            self.blocks[fkt] = Box(graph_widget,fkt,self.color_blocks,block_size)
            if with_text:
                #o1 = self.graphcanvas.create_text(int(x-w/2),int(y-h/2),anchor=Tkinter.NW,
                #                text=fkt,font=("ARIAL",6))
                #o2 = self.graphcanvas.create_text(int(x),int(y),anchor=Tkinter.CENTER,
                #                text=self.pd.prg(fkt),font=("ARIAL",7))
                self.blocks[fkt].create_text((int(x-w/2),int(y-h/2)),tkinter.NW,fkt,6)
                self.blocks[fkt].create_text((int(x),int(y)), tkinter.CENTER, self.pd.prg(fkt), 7)
#                self.graphcanvas.tag_bind(o,'<ButtonPress-1>',self.make_text_fkt(node) )
            self.colors[fkt] = self.color_blocks


        for fkt in self.pd.funcs:   #   draw the arrows:
            for ziel in self.pd.data[fkt]['JUMP']:  #  process all the edges
                self.pd.data[fkt]['JUMP'][ziel][1:]
                arrow = [self.pd.x(fkt),self.pd.y(fkt)] + self.pd.data[fkt]['JUMP'][ziel][1:] + [self.pd.x(ziel),self.pd.y(ziel)]
                p0    = None
                zaehler = 0
                while (0 == 0):
                    try:
                        p = [ arrow[zaehler], arrow[zaehler+1] ]
                    except:
                        break
                    zaehler = zaehler + 2
                    x   = fak * ( p[0] - self.pd.x0() ) + offset
                    y   = fak * ( p[1] - self.pd.y0() ) + offset
                    if p0:
                        #o = graph_widget.create_line(int(p0[0]),int(p0[1]),int(x),int(y),fill='black')
                        arrow_size = (int(p0[0]),int(p0[1]),int(x),int(y))
                        self.blocks[fkt].create_arrow(arrow_size,"black",ziel)
                        self.blocks[ziel].set_arrow_from(fkt+":"+ziel)
                        #self.sources[fkt].append(o)
                        #self.targets[fkt].append(o)
                    p0  = [x,y]
                #if with_text:
                    #graph_widget.create_oval(x-1.5,y-1.5,x+1.5,y+1.5,fill="black")


bypass 1.0, Devloped By El Moujahidin (the source has been moved and devloped)
Email: contact@elmoujehidin.net bypass 1.0, Devloped By El Moujahidin (the source has been moved and devloped) Email: contact@elmoujehidin.net