Exemple #1
2
class per():
    def __init__(self,data,y,v='план'):
        
        w=Toplevel()
        w.wm_title('Доп')
        w.columnconfigure(0,weight=1)
        w.rowconfigure(0,weight=1)
        
        years=sorted(data.keys())
        cols=data['2013']['degurs']  # ЗАГЛУШКА : список дежурных

        self.t=Treeview(w,columns=cols)
        for c in cols:
            self.t.heading(c,text=c)
            self.t.column(c,width=65,anchor='center')
        self.t.tag_configure('табель',background='green')
        self.t.tag_configure('ош',background='red')
        #self.t.tag_configure('табель',background='green')
        self.scrX=Scrollbar(w,orient='horizontal',command=self.t.xview)
        self.scrY=Scrollbar(w,orient='vertical',command=self.t.yview)
        self.t['xscrollcommand']=self.scrX.set
        self.t['yscrollcommand']=self.scrY.set
        self.t.grid(row=0,column=0,sticky=N+S+E+W)
        self.scrX.grid(row=1,column=0,sticky=E+W)
        self.scrY.grid(row=0,column=1,sticky=N+S)

        for y in years:
            x=self.t.insert('','end',text=y)
            eeY=[]
            for m in ['01','02','03','04','05','06','07','08','09','10','11','12']:
                d0=data[y]
                if m not in d0: continue
                d=d0[m]
                rez=dict()
                tag=''
                if v=='авто':
                    if 'табель' in d['degur']:
                        vv='табель'
                        tag=vv
                    else:
                        vv='план'
                elif v=='табель':
                    if 'табель' not in d['degur']:
                        vv='план'
                        tag='ош'
                    else:
                        vv=v
                        tag=vv
                else:
                    vv=v
                for j,s in d['degur'][vv].items():
                    rez[j]=analyse2(s,d)
                NUL=(0,0,0,0,0,0,0)
                ee=[rez.get(j,NUL)[0]-rez.get(j,NUL)[3]+rez.get(j,NUL)[4] for j in cols]
                eeY.append(ee)
                self.t.insert(x,'end',text=m,values=[x or '-' for x in ee],tag=tag)
            eeY=[sum(x) for x in zip(*eeY)]
            self.t.insert(x,'end',text='итого',values=eeY,tag='Y')
def Mk_Book_display(book, name):
    w = book.page(name)
    disp = Frame(w)

    tree_columns = ('book_no', 'book_name', 'book_author', 'book_publisher', 'in_out_status')
    Entries=Treeview(   disp,
                        columns=tree_columns,
                        show="headings"
                    )


    global_bucket['book_shelf'] = Entries

    vsb = Scrollbar (   disp,
                        orient="vertical",
                        command=Entries.yview)
    Entries.configure(yscrollcommand=vsb.set)
    for col,width in zip(tree_columns,(4,20,10,5,6)):
        Entries.heading(col, text=col.title(), anchor='w')
        Entries.column(col, width=1)

    vsb.pack(side=RIGHT,fill=Y)
    Entries.pack(fill=BOTH, expand=1)
    disp.pack(fill=BOTH, expand=1)

    update()
Exemple #3
0
class MainWindow(Frame):
    """
    Macro class for the main program window
    """
    def __init__(self, parent):

        Frame.__init__(self, parent)

        self.parent = parent
        self.parent.title('PyNBTx %s' % __version__)

        self.style = Style()
        self.style.theme_use('default')
        self.style.configure('TButton', padding=0)

        self.pack(fill=BOTH, expand=1)

        self.menu = MainMenu(root)
        self.toolbar = ToolBar(self)
        self.tree = Treeview(self, height=20)
        self.tree_display = TreeDisplay(self.tree)

        self.ui_init()

    def ui_init(self):
        root['menu'] = self.menu
        self.toolbar.pack(anchor=NW, padx=4, pady=4)
        self.tree.column('#0', width=300)
        self.tree.pack(fill=BOTH, anchor=NW, padx=4, pady=4)
Exemple #4
0
	def CreateUI(self, classInstance):

		self.headers = [ 
			"Customers", 
			"Inter-arrival time", 
			"Arrival time", 
			"Service time",
			"Waiting time in queue", 
			"Time when service begins", 
			"Time when service ends", 
			"Time customer spends in system",
			"Idle time of server"
		]

		self.contents =[]

		# populates the table from other class to generate the tkinter table
		def compilelist(classInstance):
			self.contents.append(classInstance.intarrival())
			self.contents.append(classInstance.arrival())
			self.contents.append(classInstance.service())
			self.contents.append(classInstance.queuewait())
			self.contents.append(classInstance.servbegin())
			self.contents.append(classInstance.servend())
			self.contents.append(classInstance.custspend())
			self.contents.append(classInstance.idle())

			return self.contents

		# Calling the function
		compilelist(classInstance)

		self.rearrange = []
		for row in zip(*self.contents):
			self.rearrange.append(row)

		self.headdata = []
		for x in range(len(self.contents[0])):
			self.headdata.append(x+1)

		header_lists = []
		tv = Treeview(self)
		tv['columns'] = (self.headers)

		for x in range(len(self.headers)):
			tv.heading("#%s"%x, text=self.headers[x], anchor='center')
			tv.column ("#%s"%x, anchor='center', width="150")

		tv.grid(sticky = (N,S,W,E))
		self.treeview = tv
		self.grid_rowconfigure(0, weight = 1)
		self.grid_columnconfigure(0, weight = 1)
def Mk_Status_display(book, name):
    w = book.page(name)
    disp = Frame(w)

    tree_columns = ('book_no', 'book_name', 'date', 'staff_id', 'staff_name', 'note')
    Entries=Treeview(   disp,
                        columns=tree_columns,
                        show="headings",
                    )

    global_bucket['status_register'] = Entries

    vsb = Scrollbar (   disp,
                        orient="vertical",
                        command=Entries.yview)
    Entries.configure(yscrollcommand=vsb.set)
    for col in tree_columns:
        Entries.heading(col, text=col.title(), anchor='w')
        Entries.column(col, width=0)
    vsb.pack(side=RIGHT,fill=Y)
    Entries.pack(fill=BOTH, expand=1)
    disp.pack(fill=BOTH, expand=1)

    update()
Exemple #6
0
class BioInfo(Tk):
    def __init__(self):
        Tk.__init__(self)
        self.wm_title("BioInfo : comparaison des listes")
        self.resizable(width=FALSE, height=FALSE)
        self.SortDir = False

        # Lists Types
        self.typeList1 = None
        self.typeList2 = None

        # Frame content
        self.frameContent = Frame(self)
        self.frameContent.pack(side=TOP, fill=X)

        # ScrollBar
        scrollbar = Scrollbar(self.frameContent, orient=VERTICAL)
        scrollbar.pack(side=RIGHT, fill=Y)

        # Result Content
        self.dataCols = ('microArn_A', 'microArn_B', 'FoldC', 'p-Value', 'Note')
        self.tree = Treeview(self.frameContent, columns=self.dataCols, show = 'headings', yscrollcommand=scrollbar.set)

        # configure column headings
        for c in self.dataCols:
            self.tree.heading(c, text=c, command=lambda c=c: self.columnSort(c, self.SortDir))
            self.tree.column(c, width=10)

        self.tree.pack(side=LEFT, fill=X, expand="yes")

        scrollbar.config(command=self.tree.yview)

        # Frame Lists
        self.frameLists = Frame(self)
        self.frameLists.pack(side=LEFT)

        # Frame Forms
        self.frameForms = Frame(self)
        self.frameForms.pack(side=LEFT, padx=20)

        #Liste n°1 selection
        self.frameList1 = Frame(self.frameLists)
        self.frameList1.pack()

        self.typeListStr1 = StringVar(self.frameList1)
        self.typeListStr1.set(str(ListBioType.TypeA))

        self.buttonTypeList1 = OptionMenu(self.frameList1, self.typeListStr1, str(ListBioType.TypeA), str(ListBioType.TypeB)).pack(side=LEFT)

        self.entrylist1 = Entry(self.frameList1, width=30)
        self.entrylist1.pack(side=LEFT)

        self.buttonBrowseList1 = Button(self.frameList1, text="Parcourir", command=self.load_fileList1, width=10)
        self.buttonBrowseList1.pack(side=LEFT, padx=5)

        # List n°2 selection
        self.frameList2 = Frame(self.frameLists)
        self.frameList2.pack(side=BOTTOM)

        self.typeListStr2 = StringVar(self.frameList2)
        self.typeListStr2.set(str(ListBioType.TypeB))

        self.buttonTypeList2 = OptionMenu(self.frameList2, self.typeListStr2, str(ListBioType.TypeA), str(ListBioType.TypeB)).pack(side=LEFT)

        self.entrylist2 = Entry(self.frameList2, width=30)
        self.entrylist2.pack(side=LEFT)

        self.buttonBrowseList2 = Button(self.frameList2, text="Parcourir", command=self.load_fileList2, width=10)
        self.buttonBrowseList2.pack(side=LEFT, padx=5)

        # Form pValue
        self.framePVal = Frame(self.frameForms)
        self.framePVal.pack()

        Label(self.framePVal, text="pValue").pack(side=LEFT)
        self.entryPVal = Entry(self.framePVal, width=6)
        self.entryPVal.pack(side=LEFT)

        # Form foldC
        self.frameFoldC = Frame(self.frameForms)
        self.frameFoldC.pack()

        Label(self.frameFoldC, text="foldCh").pack(side=LEFT)
        self.entryFoldC = Entry(self.frameFoldC, width=6)
        self.entryFoldC.pack(side=LEFT)

        # Form note
        self.frameNote = Frame(self.frameForms)
        self.frameNote.pack()

        Label(self.frameNote, text="note    ").pack(side=LEFT)
        self.entryNote = Entry(self.frameNote, width=6)
        self.entryNote.pack(side=LEFT)

        # Bouton comparer
        self.buttonComparer = Button(self, text="Comparer", command=self.compare, width=10, state=DISABLED)
        self.buttonComparer.pack(fill= X, expand="yes", padx=20, pady=(10,0))

        #Bouton exporter
        self.buttonExport = Button(self, text="Exporter", command=self.export, width=10, state=DISABLED)
        self.buttonExport.pack(fill= X, expand="yes", padx=20)

        # Réinitialiser
        self.buttonReset = Button(self, text="Réinitialiser", command=self.reset, width=10)
        self.buttonReset.pack(fill= X, expand="yes", padx=20, pady=(0,10))

        # file members
        self.list1 = None
        self.list2 = None

    def load_fileList1(self):
        fname = askopenfilename(filetypes=(("CSV files", "*.csv"),
                                           ("All files", "*.*") ))
        if fname:
            self.entrylist1.delete(0, END)
            self.list1 = fname
            self.entrylist1.insert(0,fname)

            self.buttonComparer.config(state=NORMAL)


    def load_fileList2(self):
        fname = askopenfilename(filetypes=(("CSV files", "*.csv"),
                                           ("All files", "*.*") ))
        if fname:
            self.entrylist2.delete(0, END)
            self.list2 = fname
            self.entrylist2.insert(0,fname)

            self.buttonComparer.config(state=NORMAL)

        else:
            showerror("Erreur : fichier B", "La liste B est introuvable")


    def resetTree (self):
        for i in self.tree.get_children():
            self.tree.delete(i)

    def reset(self):
        self.list1 = None
        self.entrylist1.delete(0, END)

        self.list2 = None
        self.entrylist2.delete(0, END)

        self.entryPVal.delete(0,END)
        self.entryFoldC.delete(0, END)
        self.entryNote.delete(0, END)

        self.typeList1 = None
        self.typeList2 = None

        self.buttonExport.config(state=DISABLED)
        self.buttonComparer.config(state=DISABLED)

        self.resetTree()

    def isValidfoldC(self, s):
        try:
            float(s)
            return True
        except ValueError:
            return False

    def isValidPValue(self, s):
        try:
            f = float(s)
            if f >= 0 and f <= 1:
                return True
            else:
                return False
        except:
            return False

    def isValidNote (self, s):
        try:
            f = int(s)
            return True
        except:
            return False

    def compare(self):
        self.buttonExport.config(state=NORMAL)

        # Détermination type Listes

        # List 1

        if self.typeListStr1.get() == str(ListBioType.TypeA):
            self.typeList1 = ListBioType.TypeA
        elif self.typeListStr1.get() == str(ListBioType.TypeB):
            self.typeList1 = ListBioType.TypeB
        else:
            self.typeList1 = None

        # List 2
        if self.typeListStr2.get() == str(ListBioType.TypeA):
            self.typeList2 = ListBioType.TypeA
        elif self.typeListStr2.get() == str(ListBioType.TypeB):
            self.typeList2 = ListBioType.TypeB
        else:
            self.typeList2 = None


        if not self.isValidfoldC(self.entryFoldC.get()) and not self.entryFoldC.get() == "":
            showerror("Erreur : foldC","La valeur fold Change n'est pas un nombre")

        elif not self.isValidPValue(self.entryPVal.get()) and not self.entryPVal.get() == "":
            showerror("Erreur : pValue","La valeur pValue n'est pas un nombre compris entre 0 et 1")

        elif not self.isValidNote(self.entryNote.get()) and not self.entryNote.get() == "":
            showerror("Erreur : note", "La valeur note n'est pas un nombre entier")

        # (List A and No List) or (No List and List A)
        elif ((self.list1 is not None and self.typeList1 == ListBioType.TypeA) and (self.list2 is None)) or\
             ((self.list2 is not None and self.typeList2 == ListBioType.TypeA) and (self.list1 is None)):

            self.resetTree()

            try:
                listComp = ListComparator(self.list1, self.list2, self.entryPVal.get(), self.entryFoldC.get(), self.entryNote.get())
                for e in listComp.getFilterListA():
                    self.tree.insert('', 'end', values=e)

            except IndexError:
                showerror("Erreur : liste A invalide", "Le fichier liste A n'est pas un fichier valide")


        # (List B and No List) or (No List and List B)
        elif ((self.list1 is not None and self.typeList1 == ListBioType.TypeB) and (self.list2 is None)) or\
             ((self.list2 is not None and self.typeList2 == ListBioType.TypeB) and (self.list1 is None)):

            self.resetTree()

            try:
                listComp = ListComparator(self.list1, self.list2, self.entryPVal.get(), self.entryFoldC.get())
                for e in listComp.getFilterListB():
                    self.tree.insert('', 'end', values=e)
            
            except IndexError:
                showerror("Erreur : liste A invalide", "Le fichier liste A n'est pas un fichier valide")

        # (List A and List B) or (List B and List A)
        elif ((self.list1 is not None and self.typeList1 == ListBioType.TypeA) and \
             (self.list2 is not None and self.typeList2 == ListBioType.TypeB)) or \
             ((self.list1 is not None and self.typeList1 == ListBioType.TypeB) and \
             (self.list2 is not None and self.typeList2 == ListBioType.TypeA)):

            self.resetTree()

            listA = ""
            listB = ""
            if self.typeList1 == ListBioType.TypeA:
                listA = self.list1
            else:
                listA = self.list2

            if self.typeList1 == ListBioType.TypeB:
                listB = self.list1
            else:
                listB = self.list2
            try:
                listComp = ListComparator(listA, listB, self.entryPVal.get(), self.entryFoldC.get(), self.entryNote.get())
                for e in listComp.getDiffAandB():
                    self.tree.insert('', 'end', values=e)

            except IndexError:
                showerror("Erreur : liste A ou B invalide", "Le fichier liste A ou B n'est pas un fichier valide")

        # (List A and List A)
        elif ((self.list1 is not None and self.typeList1 == ListBioType.TypeA) and \
             (self.list2 is not None and self.typeList2 == ListBioType.TypeA)):

            self.resetTree()

            try:
                listComp = ListComparator(self.list1, self.list2, self.entryPVal.get(), self.entryFoldC.get(), self.entryNote.get())
                for e in listComp.getDiffAandA():
                    self.tree.insert('', 'end', values=e)

            except IndexError:
                showerror("Erreur : liste A ou B invalide", "Le fichier liste A ou B n'est pas un fichier valide")

        # (List B and List B)
        elif ((self.list1 is not None and self.typeList1 == ListBioType.TypeB) and \
             (self.list2 is not None and self.typeList2 == ListBioType.TypeB)):

            self.resetTree()

            try:
                listComp = ListComparator(self.list1, self.list2, self.entryPVal.get(), self.entryFoldC.get())
                for e in listComp.getDiffBandB():
                    self.tree.insert('', 'end', values=e)

            except IndexError:
                showerror("Erreur : liste A ou B invalide", "Le fichier liste A ou B n'est pas un fichier valide")
        else:
            showerror("Erreur : Combinaisons de listes invalides", "Votre choix de types de listes ne correspond à aucune combinaison possible, contacter le developpeur")


    def export(self):
        if len(self.tree.get_children()) == 0:
            showinfo("Export", "Il n'y a rien à exporter")
            return

        fname = asksaveasfilename(filetypes=(("CSV files", "*.csv"),
                                             ("All files", "*.*") ))

        if fname:
            resExp = []
            for it in self.tree.get_children():
                resExp.append(self.tree.item(it)["values"])

            expTabToCSV = TreeExportator(resExp, fname)
            expTabToCSV.export()

            showinfo("Export", "Exportation au format CSV réussi")

    def columnSort (self, col, descending=False):
        data = [(self.tree.set(child, col), child) for child in self.tree.get_children('')]

        data.sort(reverse=descending)
        for indx, item in enumerate(data):
            self.tree.move(item[1], '', indx)

        # reverse sort direction for next sort operation
        self.SortDir = not descending
Exemple #7
0
class Configurator(tk.Tk):
    """
    The main Tk window representing the main app.
    
    Attributes
    ---------- 
    treeview :  :py:class:`~tkinter.Treeview`
        The treeview widget.
    treeview_popup_target_id : `int`
        The pop target id relating to the id of the selected element.
    treeview_popup : :py:class:`~tkinter.Widget`
        The treeview popup widget.
    cfg_file_name : `str`
        The file name of the current configuration.
    element_dict : `dict`
        The dictionary of elements. Keys are the element ids.
    root_element : :py:class:`~enrich2.base.storemanager.StoreManager`
        An instance inheriting from storemanager that acts as a root object.
    force_recalculate :py:class:`tkinter.BooleanVar`
        The tkinter boolean variable for this option.
    component_outliers :py:class:`tkinter.BooleanVar`
        The tkinter boolean variable for this option.
    tsv_requested : :py:class:`tkinter.BooleanVar`
        The tkinter boolean variable for this option.
    treeview_buttons : `list`
        The ``new``, ``edit`` and ``delete`` buttons.
    go_button : :py:class`~tkinter.ttk.Button`
        The button that begins the analysis
    scorer_widget : :py:class:`~enrich2.gui.options_frame.ScorerScriptsDropDown`
        The ScorerScriptsDropDown instance associated with this app.
    scorer : :py:class:`~enrich2.plugins.scoring.BaseScorerPlugin`
        The scorer class loaded from a plugin
    scorer_attrs : `dict`
        The scoring attributes for the plugin.
    scorer_path : `str`
        The path to the currently selected scoring plugin.
    analysis_thread : :py:class:`~threading.Thread`
        The thread object that runs the computation method to prevent 
        GUI blocking.
    
    Methods
    -------
    create_main_frame
    create_menubar
    create_treeview_context_menu
    create_new_element
    
    menu_open
    menu_save
    menu_saveas
    menu_selectall
    
    refresh_treeview
    treeview_context_menu
    set_treeview_properties
    populate_tree
    go_button_press
    new_button_press
    edit_button_press
    delete_button_press
    delete_element
    apply_seqlib_fastq
    
    get_element
    get_focused_element
    get_selected_elements
    get_selected_scorer_class
    get_selected_scorer_attrs
    get_selected_scorer_path
    
    run_analysis
    set_gui_state
    configure_analysis
    
    refresh_plugins
    show_plugin_source_window

    See Also
    --------
    :py:class:`~tkinter.Tk`
    
    """
    def __init__(self):
        tk.Tk.__init__(self)
        self.title("Enrich 2")

        # Main app variables
        self.cfg_file_name = tk.StringVar()
        self.element_dict = dict()
        self.root_element = None
        self.analysis_thread = None
        self.plugin_source_window = None
        self.queue = queue.Queue()

        # Treeview variables
        self.treeview = None
        self.treeview_popup_target_id = None
        self.treeview_popup = None

        # analysis options
        self.force_recalculate = tk.BooleanVar()
        self.component_outliers = tk.BooleanVar()
        self.tsv_requested = tk.BooleanVar()

        # allow resizing
        self.rowconfigure(0, weight=1)
        self.columnconfigure(0, weight=1)

        # create UI elements
        self.treeview_buttons = []
        self.go_button = None
        self.scorer_widget = None
        self.scorer = None
        self.scorer_attrs = None
        self.scorer_path = None
        self.create_main_frame()
        self.create_menubar()
        self.create_treeview_context_menu()
        self.after(10, self.poll_logging_queue)

        self.plugin_source_window = SourceWindow(master=self)
        self.plugin_source_window.hide()
        self.refresh_plugins()

    # ---------------------------------------------------------------------- #
    #                           Creation Methods
    # ---------------------------------------------------------------------- #
    def create_treeview_context_menu(self):
        """
        This creates the tree-like view rendering the experiment heirachy.
        """
        self.treeview_popup = tk.Menu(self, tearoff=0)
        self.treeview_popup.add_command(label="Apply FASTQ...",
                                        command=self.apply_seqlib_fastq)

    def create_main_frame(self):
        """
        Large function creating all the basic elements of the main app frame.
        Creates the treeview and associated buttons, the scoring plugin frame
        and the go button.
        """
        # Frame for the Treeview and New/Edit/Delete buttons
        main = Frame(self, padding=(3, 3, 12, 12))
        main.rowconfigure(0, weight=1)
        main.columnconfigure(0, weight=1)
        main.columnconfigure(1, weight=0)
        main.grid(row=0, column=0, sticky="nsew")

        # ------------------------------------------------------- #
        # Frame for the Treeview and its scrollbars
        tree_frame = Frame(main, padding=(3, 3, 12, 12))
        tree_frame.rowconfigure(0, weight=1)
        tree_frame.rowconfigure(1, weight=0)
        tree_frame.columnconfigure(0, weight=1)
        tree_frame.columnconfigure(1, weight=0)
        tree_frame.grid(row=0, column=0, sticky="nsew")

        # ------------------------------------------------------- #
        # Treeview with column headings
        self.treeview = Treeview(tree_frame)
        self.treeview["columns"] = ("class", "barcodes", "variants")
        self.treeview.column("class", width=120)
        self.treeview.heading("class", text="Type")
        self.treeview.column("barcodes",
                             width=25,
                             stretch=tk.NO,
                             anchor=tk.CENTER)
        self.treeview.heading("barcodes", text="BC")
        self.treeview.column("variants",
                             width=25,
                             stretch=tk.NO,
                             anchor=tk.CENTER)
        self.treeview.heading("variants", text="V")
        self.treeview.grid(row=0, column=0, sticky="nsew")

        # Treeview context menu bindings
        self.treeview.bind("<Button-2>", self.treeview_context_menu)

        # Treeview scrollbars
        tree_ysb = tk.Scrollbar(tree_frame,
                                orient="vertical",
                                command=self.treeview.yview)
        tree_xsb = tk.Scrollbar(tree_frame,
                                orient="horizontal",
                                command=self.treeview.xview)
        tree_ysb.grid(row=0, column=1, sticky="nsw")
        tree_xsb.grid(row=1, column=0, sticky="ewn")
        self.treeview.config(yscroll=tree_ysb.set, xscroll=tree_xsb.set)

        # ------------------------------------------------------- #
        # Frame for New/Edit/Delete buttons
        button_frame = Frame(main, padding=(3, 3, 12, 12))
        button_frame.grid(row=1, column=0)
        new_button = Button(button_frame,
                            text="New...",
                            command=self.new_button_press)
        new_button.grid(row=0, column=0)
        edit_button = Button(button_frame,
                             text="Edit...",
                             command=self.edit_button_press)
        edit_button.grid(row=0, column=1)
        delete_button = Button(button_frame,
                               text="Delete",
                               command=self.delete_button_press)
        delete_button.grid(row=0, column=2)

        self.treeview_buttons = [new_button, delete_button, edit_button]

        # ------------------------------------------------------- #
        # Frame for Plugin and Analysis Options
        right_frame = Frame(main, padding=(3, 3, 12, 12))
        right_frame.rowconfigure(0, weight=1)
        right_frame.rowconfigure(1, weight=0)
        right_frame.columnconfigure(0, weight=1)
        right_frame.columnconfigure(1, weight=0)
        right_frame.grid(row=0, column=1, sticky="new")

        # ------------------------------------------------------- #
        # LabelFrame for plugin and options
        scoring_plugin = ScorerScriptsDropDown(right_frame,
                                               text="Scoring Options",
                                               padding=(3, 3, 12, 12))
        scoring_plugin.grid(row=0, column=0, sticky="new")
        self.scorer_widget = scoring_plugin

        # ------------------------------------------------------- #
        # LabelFrame for Analysis Options
        row = 0
        options_frame = LabelFrame(right_frame,
                                   text="Analysis Options",
                                   padding=(3, 3, 12, 12))
        options_frame.grid(row=1, column=0, sticky="new", pady=4)

        # force recalculate
        force_recalculate = Checkbutton(options_frame,
                                        text="Force Recalculation",
                                        variable=self.force_recalculate)
        force_recalculate.grid(column=0, row=row, sticky="w")
        row += 1

        # component outliers
        component_outliers = Checkbutton(
            options_frame,
            text="Component Outlier Statistics",
            variable=self.component_outliers,
        )
        component_outliers.grid(column=0, row=row, sticky="w")
        row += 1

        # write tsv
        tsv_requested = Checkbutton(options_frame,
                                    text="Write TSV Files",
                                    variable=self.tsv_requested)
        tsv_requested.grid(column=0, row=row, sticky="w")
        tsv_requested.invoke()
        row += 1

        # ------------------------------------------------------- #
        # Run Analysis button frame
        go_button_frame = Frame(main, padding=(3, 3, 12, 12))
        go_button_frame.grid(row=1, column=1)
        go_button = Button(go_button_frame,
                           text="Run Analysis",
                           command=self.go_button_press)
        go_button.grid(column=0, row=0)
        self.go_button = go_button

    def create_new_element(self):
        """
        Create and return a new element based on the current selection.

        This element is not added to the treeview. 
        """
        element = None
        parent_element = self.get_focused_element()
        if isinstance(parent_element, Experiment):
            element = Condition()
            element.parent = parent_element
        elif isinstance(parent_element, Condition):
            element = Selection()
            element.parent = parent_element
        elif isinstance(parent_element, Selection):
            element = CreateSeqLibDialog(self).element_type()
            element.parent = parent_element
        elif isinstance(parent_element, SeqLib):
            # special case: creates a copy of the selected SeqLib as a sibling
            element = type(parent_element)()
            element.configure(parent_element.serialize())
            element.parent = parent_element.parent
            # clear out the seqlib-specific values
            element.name = None
            element.timepoint = None
            element.counts_file = None
            element.reads = None
        else:
            raise ValueError("Unrecognized parent object "
                             "type '{}'".format(type(parent_element)))
        return element

    def create_menubar(self):
        """
        Creates the menubar for the main app, with associated drop down menus.
        """
        # make platform-specific keybinds
        if platform.system() == "Darwin":
            accel_string = "Command+"
            accel_bind = "Command-"
        else:
            accel_string = "Ctrl+"
            accel_bind = "Control-"

        # create the menubar
        menubar = tk.Menu(self)

        # file menu
        filemenu = tk.Menu(menubar, tearoff=0)
        filemenu.add_command(
            label="Open...",
            accelerator="{}O".format(accel_string),
            command=self.menu_open,
        )
        filemenu.add_command(label="Save",
                             accelerator="{}S".format(accel_string),
                             command=self.menu_save)
        filemenu.add_command(
            label="Save As...",
            accelerator="{}Shift+S".format(accel_string),
            command=self.menu_saveas,
        )
        menubar.add_cascade(label="File", menu=filemenu)

        # edit menu
        filemenu = tk.Menu(menubar, tearoff=0)
        filemenu.add_command(
            label="Select All",
            accelerator="{}A".format(accel_string),
            command=self.menu_selectall,
        )
        menubar.add_cascade(label="Edit", menu=filemenu)

        # tools menu
        filemenu = tk.Menu(menubar, tearoff=0)
        filemenu.add_command(
            label="Show Log",
            accelerator="{}L".format(accel_string),
            command=show_log_window,
        )
        filemenu.add_command(
            label="Plugin Sources",
            accelerator="{}P".format(accel_string),
            command=self.show_plugin_source_window,
        )
        filemenu.add_command(
            label="Refresh Plugins",
            accelerator="{}R".format(accel_string),
            command=self.refresh_plugins,
        )
        menubar.add_cascade(label="Tools", menu=filemenu)

        # add the menubar
        self.config(menu=menubar)

        # add file menu keybinds
        self.bind("<{}o>".format(accel_bind), lambda event: self.menu_open())
        self.bind("<{}s>".format(accel_bind), lambda event: self.menu_save())
        self.bind("<{}Shift-s>".format(accel_bind),
                  lambda event: self.menu_saveas())

        # add edit menu keybinds
        self.bind("<{}a>".format(accel_bind),
                  lambda event: self.menu_selectall())

        # add show log menu keybinds
        # add edit menu keybinds
        self.bind("<{}l>".format(accel_bind), lambda event: show_log_window())
        self.bind("<{}p>".format(accel_bind),
                  lambda event: self.show_plugin_source_window())
        self.bind("<{}r>".format(accel_bind),
                  lambda event: self.refresh_plugins())

    # ---------------------------------------------------------------------- #
    #                          Treeview Methods
    # ---------------------------------------------------------------------- #
    def treeview_context_menu(self, click):
        """
        Sets the currently selected treeview object id in the variable
        ``treeview_popup_target_id``.
        
        Parameters
        ----------
        click : 
            tkinter click event
        """
        target = self.treeview.identify_row(click.y)
        if target != "":
            self.treeview_popup_target_id = target
            self.treeview_popup.post(click.x_root, click.y_root)
        self.treeview_popup_target_id = None

    def apply_seqlib_fastq(self):
        """
        Applies settings to the seqlib object by running the configuration
        method.
        """
        SeqLibApplyDialog(self, self, self.treeview_popup_target_id)

    def new_button_press(self):
        """
        Spawns a dialog box depending on the currently selected treeview item
        to create a new element.
        """
        if self.treeview.focus() == "" and self.root_element is not None:
            tkinter.messagebox.showwarning(None, "No parent element selected.")
        else:
            if self.treeview.focus() == "" and self.root_element is None:
                element = CreateRootDialog(self).element
                if isinstance(element, SeqLib):
                    EditDialog(self, self, element)
                self.root_element = element
            else:
                element = self.create_new_element()
                EditDialog(self, self, element)

            # refresh the treeview and re-assign treeview id's
            self.refresh_treeview()

            # select the newly added element if it was successfully added
            if element.treeview_id in list(self.element_dict.keys()):
                self.treeview.focus(element.treeview_id)
                self.treeview.selection_set(element.treeview_id)
            else:
                if element.parent is not None:
                    self.treeview.focus(element.parent.treeview_id)
                    self.treeview.selection_set(element.parent.treeview_id)
                del element

    def edit_button_press(self):
        """
        Spawns a dialog box depending on the currently selected treeview item
        to edit the selected element.
        """
        if self.treeview.focus() == "":
            tkinter.messagebox.showwarning(None, "No element selected.")
        else:
            EditDialog(self, self, self.get_focused_element())

    def delete_button_press(self):
        """
        Deletes the selected treeview element and it's children.
        """
        if self.treeview.focus() == "":
            tkinter.messagebox.showwarning(None, "No element selected.")
        else:
            DeleteDialog(self, self)

    def delete_element(self, tree_id):
        """
        Delete element with Treeview id *tree_id* from the tree, from the 
        element dictionary, and from the associated data structure. Recursively 
        deletes all children of *tree_id*.

        The tree should be refreshed using :py:meth:`refresh_tree` after 
        each deletion. This is the responsibility of the caller.

        Parameters
        ----------
        tree_id : `int`
            The id of the currently selected treeview element.

        """
        if tree_id in self.element_dict:
            # recursively delete children
            if self.element_dict[tree_id].children is not None:
                for child in self.element_dict[tree_id].children:
                    self.delete_element(child.treeview_id)

            # check if deleting the root element
            if self.root_element.treeview_id == tree_id:
                # clear the root element
                print("None {}".format(tree_id))
                self.root_element = None
            else:
                try:
                    # remove the element from its parent's list of children
                    self.element_dict[tree_id].parent.remove_child_id(tree_id)
                except AttributeError:
                    raise AttributeError(
                        "Non-root element lacks proper parent")

            # delete the element from the dictionary
            del self.element_dict[tree_id]

    def refresh_treeview(self):
        """
        Clears the Treeview and repopulates it with the 
        current contents of the tree.
        """
        # clear the entries in the Treeview
        for x in self.treeview.get_children():
            self.treeview.delete(x)

        # clear the id-element dictionary
        # elements may be given new id's after repopulation
        self.element_dict.clear()

        # repopulate
        if self.root_element is not None:
            self.populate_tree(self.root_element)

    def set_treeview_properties(self, element):
        """
        Set the information text for the Treeview *element*.

        Parameters
        ----------
        element : :py:class:`~enrich2.base.storemanager.StoreManager`
            The storemanager object to configure.
        """
        # set class property
        self.treeview.set(element.treeview_id, "class",
                          element.treeview_class_name)

        # add the check marks for barcodes/variants
        if "variants" in element.labels:
            self.treeview.set(element.treeview_id, "variants", u"\u2713")
        else:
            self.treeview.set(element.treeview_id, "variants", "")
        if "barcodes" in element.labels:
            self.treeview.set(element.treeview_id, "barcodes", u"\u2713")
        else:
            self.treeview.set(element.treeview_id, "barcodes", "")

        self.treeview.set(element.treeview_id, "class",
                          element.treeview_class_name)

    def populate_tree(self, element, parent_id=""):
        """
        Recursively populate the Treeview.

        Also populates the *id_cfgstrings*.

        Parameters
        ----------
        element : :py:class:`~enrich2.base.storemanager.StoreManager`
            The storemanager object to configure.
        parent_id : `int`
            ``treeview_id`` of element's parent.
        """
        # insert into the Treeview
        element.treeview_id = self.treeview.insert(parent_id,
                                                   "end",
                                                   text=element.name,
                                                   open=True)
        # add id-element pair to dictionary
        self.element_dict[element.treeview_id] = element
        # set information fields
        self.set_treeview_properties(element)

        # populate for children
        if element.children is not None:
            for child in element.children:
                self.populate_tree(child, parent_id=element.treeview_id)

    # ---------------------------------------------------------------------- #
    #                          Getter Methods
    # ---------------------------------------------------------------------- #
    def get_selected_scorer_class(self):
        """
        Returns the currently selected scoring class object.
        """
        return self.scorer

    def get_selected_scorer_attrs(self):
        """
        Returns the currently selected scoring class attribute `dict`.
        """
        return self.scorer_attrs

    def get_selected_scorer_path(self):
        """
        Returns the currently selected scoring path.
        """
        return self.scorer_path

    def get_element(self, treeview_id):
        """
        Returns the element with *treeview_id*.

        Parameters
        ----------
        treeview_id : `int`
            ``treeview_id`` attribute of element to get.

        Returns
        -------
        :py:class:`~enrich2.base.storemanager.StoreManager`
            The instance with matching ``treeview_id``

        """
        return self.element_dict[treeview_id]

    def get_focused_element(self):
        """
        Gets the focused element in the treeview.

        Returns
        -------
        :py:class:`~enrich2.base.storemanager.StoreManager`
            Returns the element that is currently being focused in the 
            Treeview. ``None`` if nothing is focused.
        """
        if self.treeview.focus() != "":
            return self.get_element(self.treeview.focus())
        else:
            return None

    def get_selected_elements(self):
        """
        Returns a list of currently selected elements in the treeview.

        Returns
        -------
        `list`
            Returns a list of elements that are currently selected in the 
            Treeview. If no elements are selected, it returns an empty list.

        """
        return [self.get_element(x) for x in self.treeview.selection()]

    # ---------------------------------------------------------------------- #
    #                          Menubar Methods
    # ---------------------------------------------------------------------- #
    def menu_open(self):
        """
        Spawns an `askopenfilename` dialog to open a configuration file.
        """
        message_title = "Open Configuration"
        fname = tkinter.filedialog.askopenfilename()
        if len(fname) > 0:  # file was selected
            try:
                with open(fname, "rU") as handle:
                    cfg = json.load(handle)
            except ValueError:
                tkinter.messagebox.showerror(message_title,
                                             "Failed to parse config file.")
            except IOError:
                tkinter.messagebox.showerror(message_title,
                                             "Could not read config file.")
            else:
                if is_experiment(cfg):
                    obj = Experiment()
                elif is_selection(cfg):
                    obj = Selection()
                elif is_seqlib(cfg):
                    sltype = seqlib_type(cfg)
                    obj = globals()[sltype]()
                else:
                    tkinter.messagebox.showerror(
                        message_title, "Unrecognized config format.")
                    return
                obj.output_dir_override = False
                try:
                    if isinstance(obj, Experiment) or isinstance(
                            obj, Selection):
                        obj.configure(cfg, init_from_gui=True)
                    else:
                        obj.configure(cfg)

                    # Try load the scorer into the GUI
                    scorer_path = cfg.get(SCORER, {}).get(SCORER_PATH, "")
                    scorer_attrs = cfg.get(SCORER, {}).get(SCORER_OPTIONS, {})
                    if scorer_path:
                        self.scorer_widget.load_from_cfg_file(
                            scorer_path, scorer_attrs)
                    else:
                        log_message(
                            logging_callback=logging.warning,
                            msg="No plugin could be loaded from configuration.",
                            extra={"oname": self.__class__.__name__},
                        )

                except Exception as e:
                    tkinter.messagebox.showerror(
                        message_title,
                        "Failed to load config file:\n\n{}".format(e))
                else:
                    self.root_element = obj
                    self.cfg_file_name.set(fname)
                    self.refresh_treeview()

    def menu_save(self):
        """
        Asks the user where to save the current configuration.
        """
        if len(self.cfg_file_name.get()) == 0:
            self.menu_saveas()
        elif self.root_element is None:
            tkinter.messagebox.showwarning("Save Configuration",
                                           "Cannot save empty configuration.")
        else:
            save = askyesno("Save Configuration",
                            "Overwrite existing configuration?")
            if not save:
                return
            try:
                with open(self.cfg_file_name.get(), "w") as handle:
                    cfg = self.root_element.serialize()

                    # Get the currently selected scorer
                    if not isinstance(self.root_element,
                                      SeqLib) and not isinstance(
                                          self.root_element, Condition):
                        (
                            _,
                            attrs,
                            scorer_path,
                        ) = self.scorer_widget.get_scorer_class_attrs_path()
                        cfg[SCORER] = {
                            SCORER_PATH: scorer_path,
                            SCORER_OPTIONS: attrs
                        }
                    write_json(cfg, handle)
            except IOError:
                tkinter.messagebox.showerror("Save Configuration",
                                             "Failed to save config file.")
            else:
                tkinter.messagebox.showinfo(
                    "Save Configuration",
                    "Saved file at location:\n\n{}".format(
                        self.cfg_file_name.get()),
                )

    def menu_saveas(self):
        """
        Asks the user where to save the current configuration.
        """
        if self.root_element is None:
            tkinter.messagebox.showwarning("Save Configuration",
                                           "Cannot save empty configuration.")
        else:
            fname = tkinter.filedialog.asksaveasfilename()
            if len(fname) > 0:  # file was selected
                try:
                    with open(fname, "w") as handle:
                        cfg = self.root_element.serialize()

                        # Get the currently selected scorer
                        if not isinstance(self.root_element,
                                          SeqLib) and not isinstance(
                                              self.root_element, Condition):
                            (
                                _,
                                attrs,
                                scorer_path,
                            ) = self.scorer_widget.get_scorer_class_attrs_path(
                            )
                            cfg[SCORER] = {
                                SCORER_PATH: scorer_path,
                                SCORER_OPTIONS: attrs,
                            }
                        write_json(cfg, handle)
                except IOError:
                    tkinter.messagebox.showerror(
                        "Save Configuration", "Failed to save config file.")
                else:
                    self.cfg_file_name.set(fname)
                    tkinter.messagebox.showinfo(
                        "Save Configuration",
                        "Saved file at location:\n\n{}".format(
                            self.cfg_file_name.get()),
                    )

    def menu_selectall(self):
        """
        Add all elements in the Treeview to the selection.
        """
        for k in self.element_dict.keys():
            self.treeview.selection_add(k)

    def show_plugin_source_window(self):
        """
        Show the pop-up window to modify plugin sources
        """
        if not self.plugin_source_window:
            self.plugin_source_window = SourceWindow(master=self)
        else:
            self.plugin_source_window.toggle_show()

    # ---------------------------------------------------------------------- #
    #                         Run Analysis Methods
    # ---------------------------------------------------------------------- #
    def go_button_press(self):
        """
        Starts the analysis if all elements have been properly configured.
        This will run the analysis in a new thread and block out GUI editing 
        to prevent the analysis breaking.
        """
        (
            self.scorer,
            self.scorer_attrs,
            self.scorer_path,
        ) = self.scorer_widget.get_scorer_class_attrs_path()

        if self.scorer is None or self.scorer_attrs is None:
            tkinter.messagebox.showwarning("Incomplete Configuration",
                                           "No scoring plugin selected.")
        elif self.root_element is None:
            tkinter.messagebox.showwarning(
                "Incomplete Configuration",
                "No experimental design specified.")
        else:
            plugin, *_ = self.scorer_widget.get_selected_plugin()
            if plugin.md5_has_changed():
                proceed = askokcancel(
                    "Selected plugin has been modified.",
                    "The selected plugin has been modified on disk. Do you "
                    "want to proceed with the current version? To see changes "
                    "click 'Cancel' and refresh plugins before proceeding.",
                )
                if not proceed:
                    return
            if askyesno(
                    "Save Configuration?",
                    "Would you like to save the confiugration "
                    "file before proceeding?",
            ):
                self.menu_save()
            run = askyesno(
                "Begin Analysis?",
                "Click Yes when you are ready to start.\n\nThis could "
                "take some time so grab a cup of tea, or a beer if that's "
                "your thing, and enjoy the show.",
            )
            if run:
                self.configure_analysis()
                self.set_gui_state(tk.DISABLED)
                thread = threading.Thread(target=self.run_analysis)
                thread.setDaemon(True)
                self.analysis_thread = thread
                self.analysis_thread.start()
                self.after(100, self.poll_analysis_thread)

    def poll_logging_queue(self):
        """
        Polls the logging queue for messages to log.
        """
        try:
            log = get_logging_queue(init=True).get(0)
            log[CALLBACK](log[MESSAGE], **log[KWARGS])
            self.after(10, self.poll_logging_queue)
        except queue.Empty:
            self.after(10, self.poll_logging_queue)

    def poll_analysis_thread(self):
        """
        Polls the thread to check it's state. When it is finished, all stores
        are closed.
        """
        try:
            analysis_result = self.queue.get(0)
            self.handle_analysis_result(analysis_result)
        except queue.Empty:
            self.after(100, self.poll_analysis_thread)

    def handle_analysis_result(self, success):
        """
        Shows the appropriate messagebox and logs exceptions upon analysis
        completing.
        
        Parameters
        ----------
        success : `bool`
            Exception object if an error occured during analysis, otherwise
            None to indicate successful computation.
        """
        log_message(
            logging_callback=logging.info,
            msg="Closing stores...",
            extra={"oname": self.root_element.name},
        )
        self.root_element.store_close(children=True)
        log_message(
            logging_callback=logging.info,
            msg="Stores closed.",
            extra={"oname": self.root_element.name},
        )

        if success:
            showinfo("Analysis completed.",
                     "Analysis has completed successfully!")
            log_message(
                logging_callback=logging.info,
                msg="Completed successfully!",
                extra={"oname": self.root_element.name},
            )
        else:
            showwarning(
                "Error during analysis.",
                "An error occurred during the analysis. See log for details",
            )
            log_message(
                logging_callback=logging.info,
                msg="Completed, but with errors!",
                extra={"oname": self.root_element.name},
            )
        self.set_gui_state(tk.NORMAL)

    def run_analysis(self):
        """
        Runs the storemanager compute method.
        """
        try:
            self.root_element.validate()
            self.root_element.store_open(children=True)
            self.root_element.calculate()
            if self.root_element.tsv_requested:
                self.root_element.write_tsv()
            self.queue.put(True, block=False)
        except Exception as exception:
            log_message(
                logging_callback=logging.exception,
                msg=exception,
                extra={"oname": self.root_element.name},
            )
            self.queue.put(False, block=False)
        finally:
            return

    def configure_analysis(self):
        """
        Configures the attributes of the root_element by querying the GUI
        options.
        """
        try:
            self.root_element.force_recalculate = self.force_recalculate.get()
            self.root_element.component_outliers = self.component_outliers.get(
            )
            self.root_element.tsv_requested = self.tsv_requested.get()

            scorer_class = self.get_selected_scorer_class()
            scorer_class_attrs = self.get_selected_scorer_attrs()
            scorer_path = self.get_selected_scorer_path()
            self.root_element.scorer_class = scorer_class
            self.root_element.scorer_class_attrs = scorer_class_attrs
            self.root_element.scorer_path = scorer_path
        except Exception as e:
            log_message(
                logging_callback=logging.info,
                msg="An error occurred when trying to configure the "
                "root element.",
                extra={"oname": self.root_element.name},
            )
            log_message(
                logging_callback=logging.exception,
                msg=e,
                extra={"oname": self.root_element.name},
            )

    # ---------------------------------------------------------------------- #
    #                         GUI Modifications
    # ---------------------------------------------------------------------- #
    def set_gui_state(self, state):
        """
        Sets the state of the `go_button`, `treeview` and `treeview_buttons`.

        Parameters
        ----------
        state : `str`
            State to set, usually ``'normal'`` or ``'disabled'``

        """
        for btn in self.treeview_buttons:
            btn.config(state=state)
        self.go_button.config(state=state)
        if state == "normal":
            self.treeview.bind("<Button-2>", self.treeview_context_menu)
        else:
            self.treeview.bind("<Button-2>", lambda event: event)

    def refresh_plugins(self):
        """
        Refresh the plugins by re-checking the sources file.
        """
        if self.plugin_source_window:
            sources = self.plugin_source_window.sources
            self.scorer_widget.refresh_sources(sources)
Exemple #8
0
class DialogOpenArchive(Toplevel):
    def __init__(self, mainWin, openType, filesource, filenames, title, colHeader, showAltViewButton=False):
        parent = mainWin.parent
        super(DialogOpenArchive, self).__init__(parent)
        self.parent = parent
        self.showAltViewButton = showAltViewButton
        parentGeometry = re.match("(\d+)x(\d+)[+]?([-]?\d+)[+]?([-]?\d+)", parent.geometry())
        dialogX = int(parentGeometry.group(3))
        dialogY = int(parentGeometry.group(4))
        self.accepted = False

        self.transient(self.parent)
        
        frame = Frame(self)

        treeFrame = Frame(frame, width=500)
        vScrollbar = Scrollbar(treeFrame, orient=VERTICAL)
        hScrollbar = Scrollbar(treeFrame, orient=HORIZONTAL)
        self.treeView = Treeview(treeFrame, xscrollcommand=hScrollbar.set, yscrollcommand=vScrollbar.set)
        self.treeView.grid(row=0, column=0, sticky=(N, S, E, W))
        hScrollbar["command"] = self.treeView.xview
        hScrollbar.grid(row=1, column=0, sticky=(E,W))
        vScrollbar["command"] = self.treeView.yview
        vScrollbar.grid(row=0, column=1, sticky=(N,S))
        treeFrame.columnconfigure(0, weight=1)
        treeFrame.rowconfigure(0, weight=1)
        treeFrame.grid(row=0, column=0, columnspan=4, sticky=(N, S, E, W), padx=3, pady=3)
        self.treeView.focus_set()
        
        mainWin.showStatus(_("loading archive {0}").format(filesource.url))
        self.filesource = filesource
        self.filenames = filenames
        self.selection = filesource.selection
        self.hasToolTip = False
        selectedNode = None

        if openType == ENTRY_POINTS:
            try:
                metadataFiles = filesource.taxonomyPackageMetadataFiles
                ''' take first for now
                if len(metadataFiles) != 1:
                    raise IOError(_("Taxonomy package contained more than one metadata file: {0}.")
                                  .format(', '.join(metadataFiles)))
                '''
                metadataFile = metadataFiles[0]
                metadata = filesource.url + os.sep + metadataFile
                self.metadataFilePrefix = os.sep.join(os.path.split(metadataFile)[:-1])
                if self.metadataFilePrefix:
                    self.metadataFilePrefix += "/"  # zip contents have /, never \ file seps
                self.taxonomyPkgMetaInf = '{}/META-INF/'.format(
                            os.path.splitext(os.path.basename(filesource.url))[0])

        
                self.taxonomyPackage = parsePackage(mainWin, filesource, metadata,
                                                    os.sep.join(os.path.split(metadata)[:-1]) + os.sep)
                
                # may be a catalog file with no entry oint names
                if not self.taxonomyPackage["nameToUrls"]:
                    openType = ARCHIVE  # no entry points to show, just archive
                    self.showAltViewButton = False
            except Exception as e:
                self.close()
                err = _("Failed to parse metadata; the underlying error was: {0}").format(e)
                messagebox.showerror(_("Malformed taxonomy package"), err)
                mainWin.addToLog(err)
                return
    
        mainWin.showStatus(None)
        
        if openType == DISCLOSURE_SYSTEM:
            y = 3
        else:
            y = 1

        okButton = Button(frame, text=_("OK"), command=self.ok)
        cancelButton = Button(frame, text=_("Cancel"), command=self.close)
        okButton.grid(row=y, column=2, sticky=(S,E,W), pady=3)
        cancelButton.grid(row=y, column=3, sticky=(S,E,W), pady=3, padx=3)
        
        if self.showAltViewButton:
            self.altViewButton = Button(frame, command=self.showAltView)
            self.altViewButton.grid(row=y, column=0, sticky=(S,W), pady=3, padx=3)
        
        self.loadTreeView(openType, colHeader, title)

        self.geometry("+{0}+{1}".format(dialogX+50,dialogY+100))
        frame.grid(row=0, column=0, sticky=(N,S,E,W))
        frame.columnconfigure(0, weight=1)
        frame.rowconfigure(0, weight=1)
        window = self.winfo_toplevel()
        window.columnconfigure(0, weight=1)
        window.rowconfigure(0, weight=1)
        
        self.bind("<Return>", self.ok)
        self.bind("<Escape>", self.close)
        
        self.toolTipText = StringVar()
        if self.hasToolTip:
            self.treeView.bind("<Motion>", self.motion, '+')
            self.treeView.bind("<Leave>", self.leave, '+')
            self.toolTipText = StringVar()
            self.toolTip = ToolTip(self.treeView, 
                                   textvariable=self.toolTipText, 
                                   wraplength=640, 
                                   follow_mouse=True,
                                   state="disabled")
            self.toolTipRowId = None

        self.protocol("WM_DELETE_WINDOW", self.close)
        self.grab_set()
        self.wait_window(self)
        
    def loadTreeView(self, openType, title, colHeader):
        self.title(title)
        self.openType = openType
        selectedNode = None

        # clear previous treeview entries
        for previousNode in self.treeView.get_children(""): 
            self.treeView.delete(previousNode)

        # set up treeView widget and tabbed pane
        if openType in (ARCHIVE, DISCLOSURE_SYSTEM):
            self.treeView.column("#0", width=500, anchor="w")
            self.treeView.heading("#0", text=colHeader)
            try:
                self.isRss = self.filesource.isRss
                if self.isRss:
                    self.treeView.column("#0", width=350, anchor="w")
                    self.treeView["columns"] = ("descr", "date", "instDoc")
                    self.treeView.column("descr", width=50, anchor="center", stretch=False)
                    self.treeView.heading("descr", text="Form")
                    self.treeView.column("date", width=170, anchor="w", stretch=False)
                    self.treeView.heading("date", text="Pub Date")
                    self.treeView.column("instDoc", width=200, anchor="w", stretch=False)
                    self.treeView.heading("instDoc", text="Instance Document")
            except AttributeError:
                self.isRss = False
                self.treeView["columns"] = tuple()
        
            loadedPaths = []
            for i, filename in enumerate(self.filenames):
                if isinstance(filename,tuple):
                    if self.isRss:
                        form, date, instDoc = filename[2:5]
                    filename = filename[0] # ignore tooltip
                    self.hasToolTip = True
                if filename.endswith("/"):
                    filename = filename[:-1]
                path = filename.split("/")
                if not self.isRss and len(path) > 1 and path[:-1] in loadedPaths:
                    parent = "file{0}".format(loadedPaths.index(path[:-1]))
                else:
                    parent = "" 
                node = self.treeView.insert(parent, "end", "file{0}".format(i), text=path[-1])
                if self.isRss:
                    self.treeView.set(node, "descr", form)
                    self.treeView.set(node, "date", date)
                    self.treeView.set(node, "instDoc", os.path.basename(instDoc))
                if self.selection == filename:
                    selectedNode = node
                loadedPaths.append(path)

        elif openType == ENTRY_POINTS:
            self.treeView.column("#0", width=150, anchor="w")
            self.treeView.heading("#0", text="Name")
    
            self.treeView["columns"] = ("url",)
            self.treeView.column("url", width=350, anchor="w")
            self.treeView.heading("url", text="URL")
            
            for name, urls in self.taxonomyPackage["nameToUrls"].items():
                displayUrl = urls[1] # display the canonical URL
                self.treeView.insert("", "end", name, values=[displayUrl], text=name)
                
            self.hasToolTip = True
        else: # unknown openType
            return None
        if selectedNode:
            self.treeView.see(selectedNode)
            self.treeView.selection_set(selectedNode)

        if self.showAltViewButton:
            self.altViewButton.config(text=_("Show Files") if openType == ENTRY_POINTS else _("Show Entries"))

        
    def ok(self, event=None):
        selection = self.treeView.selection()
        if len(selection) > 0:
            if hasattr(self, "taxonomyPackage"):
                # load file source remappings
                self.filesource.mappedPaths = self.taxonomyPackage["remappings"]
            filename = None
            if self.openType in (ARCHIVE, DISCLOSURE_SYSTEM):
                filename = self.filenames[int(selection[0][4:])]
                if isinstance(filename,tuple):
                    if self.isRss:
                        filename = filename[4]
                    else:
                        filename = filename[0]
            elif self.openType == ENTRY_POINTS:
                epName = selection[0]
                #index 0 is the remapped Url, as opposed to the canonical one used for display
                filename = self.taxonomyPackage["nameToUrls"][epName][0]
                if not filename.endswith("/"):
                    # check if it's an absolute URL rather than a path into the archive
                    if not isHttpUrl(filename) and self.metadataFilePrefix != self.taxonomyPkgMetaInf:
                        # assume it's a path inside the archive:
                        filename = self.metadataFilePrefix + filename
            if filename is not None and not filename.endswith("/"):
                if hasattr(self, "taxonomyPackage"):
                    # attempt to unmap the filename to original file
                    # will be mapped again in loading, but this allows schemaLocation to be unmapped
                    for prefix, remapping in self.taxonomyPackage["remappings"].items():
                        if isHttpUrl(remapping):
                            remapStart = remapping
                        else:
                            remapStart = self.metadataFilePrefix + remapping
                        if filename.startswith(remapStart):
                            # set unmmapped file
                            filename = prefix + filename[len(remapStart):]
                            break
                self.filesource.select(filename)
                self.accepted = True
                self.close()
                        
        
    def close(self, event=None):
        self.parent.focus_set()
        self.destroy()
        
    def showAltView(self, event=None):
        if self.openType == ENTRY_POINTS:
            self.loadTreeView(ARCHIVE, _("Select Entry Point"), _("File"))
        else:
            self.loadTreeView(ENTRY_POINTS, _("Select Archive File"), _("File"))
        
    def leave(self, *args):
        self.toolTipRowId = None

    def motion(self, *args):
        tvRowId = self.treeView.identify_row(args[0].y)
        if tvRowId != self.toolTipRowId:
            text = None
            if self.openType in (ARCHIVE, DISCLOSURE_SYSTEM):
                self.toolTipRowId = tvRowId
                if tvRowId and len(tvRowId) > 4:
                    try:
                        text = self.filenames[ int(tvRowId[4:]) ]
                        if isinstance(text, tuple):
                            text = text[1].replace("\\n","\n")
                    except (KeyError, ValueError):
                        pass
            elif self.openType == ENTRY_POINTS:
                try:
                    epUrl = self.taxonomyPackage["nameToUrls"][tvRowId][1]
                    text = "{0}\n{1}".format(tvRowId, epUrl)
                except KeyError:
                    pass
            self.setToolTip(text)
                
    def setToolTip(self, text):
        self.toolTip._hide()
        if text:
            self.toolTipText.set(text)
            self.toolTip.configure(state="normal")
            self.toolTip._schedule()
        else:
            self.toolTipText.set("")
            self.toolTip.configure(state="disabled")
Exemple #9
0
def digiclock(w):
	pane = tkinter.tix.PanedWindow(w, orientation='vertical')
	pane.pack(side=tkinter.tix.TOP, expand=1, fill=BOTH)
	f1 = pane.add('time',size=190)
	f2 = pane.add('options')
	
	f2pane = tkinter.tix.PanedWindow(f2, orientation='horizontal')
	f2pane.pack(side=tkinter.tix.TOP, expand=1, fill=BOTH)
	f2f1 = f2pane.add('alarm',size=150)
	f2f2 = f2pane.add('event')
	
	global al_status,al_time,m
	m='am'
	ts_status=ON
	al_status=OFF
	al_time=str()
	colour=['orange','red','violet','pink','blue','grey']
	def ConfigEvents():
		now=ctime().split()
		year=int(now[4])
		mon=now[1].lower()
		date=int(now[2])
		notes=CalLookUp( mon )
		for each_item in Entries.get_children():
			Entries.delete(each_item)
		ordered=[]
		for memo in notes: 
			if(int(memo) >= date):
				ordered.append(memo)
		ordered.sort()
		for memo in ordered:
			for note in notes[memo]:
				Entries.insert('', 'end', values=( memo, note[0], note[1]) )
	def displayTime(st,ts):
		global al_time,m
		sleep(3)
		day={'Mon'	:	'Monday'	,
			'Tue'  	:	'Tuesday'	,
			'Wed'	:	'Wednesday',
			'Thu'	:	'Thursday',
			'Fri'	:	'Friday'	,
			'Sat'	:	'Saturday',
			'Sun'	:	'Sunday'	}
		while(st):
			ct=ctime().split(' ')
			m='AM'
			if int(ct[3].split(':')[0])>11 : 
				m='PM'
				if int(ct[3].split(':')[0])>12 :	
					ct[3]=str( int( ct[3][:2] )-12 ) + ct[3][2:]
			if (ct[3].split(':')[0] == '00' ):	
				ct[3]='12' + ct[3][2:]
				ConfigEvents()
			#~ if (not int(ct[3].split(':')[2])%10):	ts.config( bg=colour[ int( int( ct[3].split(':')[2] )/10) ] )
			mhs=ct[3].split(':')
			mode=	{
					'time&date'	:'%s-%s-%s\n%s\n%0.2d:%0.2d:%0.2d %s'%(ct[1],ct[2],ct[4],day[ct[0]],int(mhs[0]),int(mhs[1]),int(mhs[2]),m),
					'time'		:'%0.2d:%0.2d:%0.2d %s'%(int(mhs[0]),int(mhs[1]),int(mhs[2]),m)
					}
			text	=mode['time&date']
			#~ print(ct)
			ts.config(text=text)
			#~ print(al_time,mode['time'],al_time==mode['time'])
			if(al_time==mode['time']):
				set.config( text='Stop' )
				cal.config( text='Expired @ ' + al_time[:-2] )
				thread.start_new_thread(lambda snd='ringout', repeat=ON :play( snd, repeat ) ,() )
			sleep(1)
	def sett():
		global al_status,sound_continueous,al_time
		if(al_status):
			al_status = OFF
			sound_continueous = OFF
			al_time = ''
			cal.config( text='No Alarm' )
			set.config( text='Set' )
		else:
			al_status = ON
			al_time = at.entry.get()+' '+ampm.entry.get()
			cal.config( text='Set @ ' + al_time )
			set.config( text='Remove' )
	bg='orange'
	#~ time frame
	tf=Frame( f1, bg='black' )
	ts=Label(		tf
				,text="rajiv.m1991\n@\ngmail.com"
				,font='times 40'
				,bg='violet'
				,width=11
				,fg='white')
	tf.pack(fill=BOTH)
	ts.pack(fill=X)
	#~ alarm frame
	af=Frame(f2f1,bg=bg)
	al=Label(	af
			,text="$ Alarm $"
			,font='times'
			,fg='white'
			,bg='black')
	at=LabelEntry( af, label='HH:MM:SS', bg=bg )
	at.label.config( fg='white', bg=bg )
	at.entry.config( width=13, borderwidth=0 )
	at.entry.insert( 0, '00:00:00' )
	ampm=LabelEntry( af, label='AM / PM ', bg=bg )
	ampm.entry.config( borderwidth=0 )
	ampm.label.config( fg='white', bg=bg)
	if( int( ctime().split(' ')[3].split(':')[0]) > 11 ):		ampm.entry.insert( 0,'PM' )
	else:	ampm.entry.insert( 0, 'AM' )
	set=Button(af
			,text='Set'
			,command=sett
			,fg='brown')
	ast=Label(	af
			,text='Alarm status:'
			,fg='white'
			,bg=bg
			,anchor='sw')
	cal=Label(	af
			,text='No Alarm'
			,fg='white'
			,bg='black'
			,anchor='sw')
	af.pack(fill=BOTH)
	al.pack(fill=X)
	at.pack(fill=X,padx=5,pady=5)
	ampm.pack(fill=X,padx=5,pady=5)
	set.pack()
	ast.pack(fill=X)
	cal.pack(fill=X)
	#~ options
	L=Label(f2f2,text="Upcoming Events")
	L.pack(fill=X)
	tree_columns = ("Dt", "Note", "Category")
	Entries=Treeview(	f2f2,
					columns=tree_columns,
					show="headings",
					height=5)
	vsb = Scrollbar(f2f2,orient="vertical", command=Entries.yview)
	Entries.configure(yscrollcommand=vsb.set)
	for col in tree_columns:
		Entries.heading(col, text=col.title())
	Entries.column(tree_columns[0],width=20)
	Entries.column(tree_columns[1],width=75)
	Entries.column(tree_columns[2],width=75)
	vsb.pack(side=RIGHT,fill=Y)
	Entries.pack(fill=BOTH)
	#~ start clock
	ConfigEvents()
	thread.start_new_thread(lambda st=ts_status ,ts=ts : displayTime(st,ts),())
	print('Digital Clock Successfully built')
class DialogPackageManager(Toplevel):
    def __init__(self, mainWin, packageNamesWithNewerFileDates):
        super(DialogPackageManager, self).__init__(mainWin.parent)
        
        self.ENABLE = _("Enable")
        self.DISABLE = _("Disable")
        self.parent = mainWin.parent
        self.cntlr = mainWin
        
        # copy plugins for temporary display
        self.packagesConfig = PackageManager.packagesConfig
        self.packagesConfigChanged = False
        self.packageNamesWithNewerFileDates = packageNamesWithNewerFileDates
        
        parentGeometry = re.match("(\d+)x(\d+)[+]?([-]?\d+)[+]?([-]?\d+)", self.parent.geometry())
        dialogX = int(parentGeometry.group(3))
        dialogY = int(parentGeometry.group(4))

        self.title(_("Taxonomy Packages Manager"))
        frame = Frame(self)
        
        # left button frame
        buttonFrame = Frame(frame, width=40)
        buttonFrame.columnconfigure(0, weight=1)
        addLabel = Label(buttonFrame, text=_("Find taxonomy packages:"), wraplength=64, justify="center")
        addLocalButton = Button(buttonFrame, text=_("Locally"), command=self.findLocally)
        ToolTip(addLocalButton, text=_("File chooser allows selecting taxonomy packages to add (or reload), from the local file system.  "
                                       "Select either a taxonomy package zip file, or a taxonomy manifest (.taxonomyPackage.xml) within an unzipped taxonomy package.  "), wraplength=240)
        addWebButton = Button(buttonFrame, text=_("On Web"), command=self.findOnWeb)
        ToolTip(addWebButton, text=_("Dialog to enter URL full path to load (or reload) package, from the web or local file system.  "
                                     "URL may be either a taxonomy package zip file, or a taxonomy manifest (.taxonomyPackage.xml) within an unzipped taxonomy package.  "), wraplength=240)
        manifestNameButton = Button(buttonFrame, text=_("Manifest"), command=self.manifestName)
        ToolTip(manifestNameButton, text=_("Provide non-standard archive manifest file name pattern (e.g., *taxonomyPackage.xml).  "
                                           "Uses unix file name pattern matching.  "
                                           "Multiple manifest files are supported in archive (such as oasis catalogs).  "
                                           "(Replaces search for either .taxonomyPackage.xml or catalog.xml).  "), wraplength=240)
        self.manifestNamePattern = ""
        addLabel.grid(row=0, column=0, pady=4)
        addLocalButton.grid(row=1, column=0, pady=4)
        addWebButton.grid(row=2, column=0, pady=4)
        manifestNameButton.grid(row=3, column=0, pady=4)
        buttonFrame.grid(row=0, column=0, rowspan=3, sticky=(N, S, W), padx=3, pady=3)
        
        # right tree frame (packages already known to arelle)
        packagesFrame = Frame(frame, width=700)
        vScrollbar = Scrollbar(packagesFrame, orient=VERTICAL)
        hScrollbar = Scrollbar(packagesFrame, orient=HORIZONTAL)
        self.packagesView = Treeview(packagesFrame, xscrollcommand=hScrollbar.set, yscrollcommand=vScrollbar.set, height=7)
        self.packagesView.grid(row=0, column=0, sticky=(N, S, E, W))
        self.packagesView.bind('<<TreeviewSelect>>', self.packageSelect)
        hScrollbar["command"] = self.packagesView.xview
        hScrollbar.grid(row=1, column=0, sticky=(E,W))
        vScrollbar["command"] = self.packagesView.yview
        vScrollbar.grid(row=0, column=1, sticky=(N,S))
        packagesFrame.columnconfigure(0, weight=1)
        packagesFrame.rowconfigure(0, weight=1)
        packagesFrame.grid(row=0, column=1, columnspan=4, sticky=(N, S, E, W), padx=3, pady=3)
        self.packagesView.focus_set()

        self.packagesView.column("#0", width=120, anchor="w")
        self.packagesView.heading("#0", text=_("Name"))
        self.packagesView["columns"] = ("ver", "status", "date", "update", "descr")
        self.packagesView.column("ver", width=150, anchor="w", stretch=False)
        self.packagesView.heading("ver", text=_("Version"))
        self.packagesView.column("status", width=50, anchor="w", stretch=False)
        self.packagesView.heading("status", text=_("Status"))
        self.packagesView.column("date", width=170, anchor="w", stretch=False)
        self.packagesView.heading("date", text=_("File Date"))
        self.packagesView.column("update", width=50, anchor="w", stretch=False)
        self.packagesView.heading("update", text=_("Update"))
        self.packagesView.column("descr", width=200, anchor="w", stretch=False)
        self.packagesView.heading("descr", text=_("Description"))

        remappingsFrame = Frame(frame)
        vScrollbar = Scrollbar(remappingsFrame, orient=VERTICAL)
        hScrollbar = Scrollbar(remappingsFrame, orient=HORIZONTAL)
        self.remappingsView = Treeview(remappingsFrame, xscrollcommand=hScrollbar.set, yscrollcommand=vScrollbar.set, height=5)
        self.remappingsView.grid(row=0, column=0, sticky=(N, S, E, W))
        hScrollbar["command"] = self.remappingsView.xview
        hScrollbar.grid(row=1, column=0, sticky=(E,W))
        vScrollbar["command"] = self.remappingsView.yview
        vScrollbar.grid(row=0, column=1, sticky=(N,S))
        remappingsFrame.columnconfigure(0, weight=1)
        remappingsFrame.rowconfigure(0, weight=1)
        remappingsFrame.grid(row=1, column=1, columnspan=4, sticky=(N, S, E, W), padx=3, pady=3)
        self.remappingsView.focus_set()
        
        self.remappingsView.column("#0", width=200, anchor="w")
        self.remappingsView.heading("#0", text=_("Prefix"))
        self.remappingsView["columns"] = ("remapping")
        self.remappingsView.column("remapping", width=500, anchor="w", stretch=False)
        self.remappingsView.heading("remapping", text=_("Remapping"))
        
        # bottom frame package info details
        packageInfoFrame = Frame(frame, width=700)
        packageInfoFrame.columnconfigure(1, weight=1)
        
        self.packageNameLabel = Label(packageInfoFrame, wraplength=600, justify="left", 
                                      font=font.Font(family='Helvetica', size=12, weight='bold'))
        self.packageNameLabel.grid(row=0, column=0, columnspan=6, sticky=W)
        self.packageVersionHdr = Label(packageInfoFrame, text=_("version:"), state=DISABLED)
        self.packageVersionHdr.grid(row=1, column=0, sticky=W)
        self.packageVersionLabel = Label(packageInfoFrame, wraplength=600, justify="left")
        self.packageVersionLabel.grid(row=1, column=1, columnspan=5, sticky=W)
        self.packageDescrHdr = Label(packageInfoFrame, text=_("description:"), state=DISABLED)
        self.packageDescrHdr.grid(row=2, column=0, sticky=W)
        self.packageDescrLabel = Label(packageInfoFrame, wraplength=600, justify="left")
        self.packageDescrLabel.grid(row=2, column=1, columnspan=5, sticky=W)
        self.packagePrefixesHdr = Label(packageInfoFrame, text=_("prefixes:"), state=DISABLED)
        self.packagePrefixesHdr.grid(row=3, column=0, sticky=W)
        self.packagePrefixesLabel = Label(packageInfoFrame, wraplength=600, justify="left")
        self.packagePrefixesLabel.grid(row=3, column=1, columnspan=5, sticky=W)
        ToolTip(self.packagePrefixesLabel, text=_("List of prefixes that this package remaps."), wraplength=240)
        self.packageUrlHdr = Label(packageInfoFrame, text=_("URL:"), state=DISABLED)
        self.packageUrlHdr.grid(row=4, column=0, sticky=W)
        self.packageUrlLabel = Label(packageInfoFrame, wraplength=600, justify="left")
        self.packageUrlLabel.grid(row=4, column=1, columnspan=5, sticky=W)
        ToolTip(self.packageUrlLabel, text=_("URL of taxonomy package (local file path or web loaded file)."), wraplength=240)
        self.packageDateHdr = Label(packageInfoFrame, text=_("date:"), state=DISABLED)
        self.packageDateHdr.grid(row=5, column=0, sticky=W)
        self.packageDateLabel = Label(packageInfoFrame, wraplength=600, justify="left")
        self.packageDateLabel.grid(row=5, column=1, columnspan=5, sticky=W)
        ToolTip(self.packageDateLabel, text=_("Date of currently loaded package file (with parenthetical node when an update is available)."), wraplength=240)
        self.packageEnableButton = Button(packageInfoFrame, text=self.ENABLE, state=DISABLED, command=self.packageEnable)
        ToolTip(self.packageEnableButton, text=_("Enable/disable package."), wraplength=240)
        self.packageEnableButton.grid(row=6, column=1, sticky=E)
        self.packageMoveUpButton = Button(packageInfoFrame, text=_("Move Up"), state=DISABLED, command=self.packageMoveUp)
        ToolTip(self.packageMoveUpButton, text=_("Move package up (above other remappings)."), wraplength=240)
        self.packageMoveUpButton.grid(row=6, column=2, sticky=E)
        self.packageMoveDownButton = Button(packageInfoFrame, text=_("Move Down"), state=DISABLED, command=self.packageMoveDown)
        ToolTip(self.packageMoveDownButton, text=_("Move package down (below other remappings)."), wraplength=240)
        self.packageMoveDownButton.grid(row=6, column=3, sticky=E)
        self.packageReloadButton = Button(packageInfoFrame, text=_("Reload"), state=DISABLED, command=self.packageReload)
        ToolTip(self.packageReloadButton, text=_("Reload/update package."), wraplength=240)
        self.packageReloadButton.grid(row=6, column=4, sticky=E)
        self.packageRemoveButton = Button(packageInfoFrame, text=_("Remove"), state=DISABLED, command=self.packageRemove)
        ToolTip(self.packageRemoveButton, text=_("Remove package from packages table (does not erase the package file)."), wraplength=240)
        self.packageRemoveButton.grid(row=6, column=5, sticky=E)
        packageInfoFrame.grid(row=2, column=0, columnspan=5, sticky=(N, S, E, W), padx=3, pady=3)
        packageInfoFrame.config(borderwidth=4, relief="groove")
        
        okButton = Button(frame, text=_("Close"), command=self.ok)
        ToolTip(okButton, text=_("Accept and changes (if any) and close dialog."), wraplength=240)
        cancelButton = Button(frame, text=_("Cancel"), command=self.close)
        ToolTip(cancelButton, text=_("Cancel changes (if any) and close dialog."), wraplength=240)
        okButton.grid(row=3, column=3, sticky=(S,E), pady=3)
        cancelButton.grid(row=3, column=4, sticky=(S,E), pady=3, padx=3)
        
        self.loadTreeViews()

        self.geometry("+{0}+{1}".format(dialogX+50,dialogY+100))
        frame.grid(row=0, column=0, sticky=(N,S,E,W))
        frame.columnconfigure(0, weight=0)
        frame.columnconfigure(1, weight=1)
        frame.rowconfigure(0, weight=1)
        window = self.winfo_toplevel()
        window.columnconfigure(0, weight=1)
        window.rowconfigure(0, weight=1)
        
        self.bind("<Return>", self.ok)
        self.bind("<Escape>", self.close)
        
        self.protocol("WM_DELETE_WINDOW", self.close)
        self.grab_set()
        self.wait_window(self)
        
    def loadTreeViews(self):
        self.selectedModule = None

        # clear previous treeview entries
        for previousNode in self.packagesView.get_children(""): 
            self.packagesView.delete(previousNode)

        for i, packageInfo in enumerate(self.packagesConfig.get("packages", [])):
            name = packageInfo.get("name", "package{}".format(i))
            node = self.packagesView.insert("", "end", "_{}".format(i), text=name)
            self.packagesView.set(node, "ver", packageInfo.get("version"))
            self.packagesView.set(node, "status", packageInfo.get("status"))
            self.packagesView.set(node, "date", packageInfo.get("fileDate"))
            if name in self.packageNamesWithNewerFileDates:
                self.packagesView.set(node, "update", _("available"))
            self.packagesView.set(node, "descr", packageInfo.get("description"))
        
        # clear previous treeview entries
        for previousNode in self.remappingsView.get_children(""): 
            self.remappingsView.delete(previousNode)

        for i, remappingItem in enumerate(sorted(self.packagesConfig.get("remappings", {}).items())):
            prefix, remapping = remappingItem
            node = self.remappingsView.insert("", "end", prefix, text=prefix)
            self.remappingsView.set(node, "remapping", remapping)
            
        self.packageSelect()  # clear out prior selection

    def ok(self, event=None):
        if self.packagesConfigChanged:
            PackageManager.packagesConfig = self.packagesConfig
            PackageManager.packagesConfigChanged = True
            self.cntlr.onPackageEnablementChanged()
        self.close()
        
    def close(self, event=None):
        self.parent.focus_set()
        self.destroy()
                
    def packageSelect(self, *args):
        node = (self.packagesView.selection() or (None,))[0]
        try:
            nodeIndex = int(node[1:])
        except (ValueError, TypeError):
            nodeIndex = -1
        if 0 <= nodeIndex < len(self.packagesConfig["packages"]):
            packageInfo = self.packagesConfig["packages"][nodeIndex]
            self.selectedPackageIndex = nodeIndex
            name = packageInfo["name"]
            self.packageNameLabel.config(text=name)
            self.packageVersionHdr.config(state=ACTIVE)
            self.packageVersionLabel.config(text=packageInfo["version"])
            self.packageDescrHdr.config(state=ACTIVE)
            self.packageDescrLabel.config(text=packageInfo["description"])
            self.packagePrefixesHdr.config(state=ACTIVE)
            self.packagePrefixesLabel.config(text=', '.join(packageInfo["remappings"].keys()))
            self.packageUrlHdr.config(state=ACTIVE)
            self.packageUrlLabel.config(text=packageInfo["URL"])
            self.packageDateHdr.config(state=ACTIVE)
            self.packageDateLabel.config(text=packageInfo["fileDate"] + " " +
                    (_("(an update is available)") if name in self.packageNamesWithNewerFileDates else ""))
            self.packageEnableButton.config(state=ACTIVE,
                                           text={"enabled":self.DISABLE,
                                                 "disabled":self.ENABLE}[packageInfo["status"]])
            self.packageMoveUpButton.config(state=ACTIVE if 0 < nodeIndex else DISABLED)
            self.packageMoveDownButton.config(state=ACTIVE if nodeIndex < (len(self.packagesConfig["packages"]) - 1) else DISABLED)
            self.packageReloadButton.config(state=ACTIVE)
            self.packageRemoveButton.config(state=ACTIVE)
        else:
            self.selectedPackageIndex = -1
            self.packageNameLabel.config(text="")
            self.packageVersionHdr.config(state=DISABLED)
            self.packageVersionLabel.config(text="")
            self.packageDescrHdr.config(state=DISABLED)
            self.packageDescrLabel.config(text="")
            self.packagePrefixesHdr.config(state=DISABLED)
            self.packagePrefixesLabel.config(text="")
            self.packageUrlHdr.config(state=DISABLED)
            self.packageUrlLabel.config(text="")
            self.packageDateHdr.config(state=DISABLED)
            self.packageDateLabel.config(text="")

            self.packageEnableButton.config(state=DISABLED, text=self.ENABLE)
            self.packageMoveUpButton.config(state=DISABLED)
            self.packageMoveDownButton.config(state=DISABLED)
            self.packageReloadButton.config(state=DISABLED)
            self.packageRemoveButton.config(state=DISABLED)
        
    def findLocally(self):
        initialdir = self.cntlr.pluginDir # default plugin directory
        if not self.cntlr.isMac: # can't navigate within app easily, always start in default directory
            initialdir = self.cntlr.config.setdefault("packageOpenDir", initialdir)
        filename = self.cntlr.uiFileDialog("open",
                                           parent=self,
                                           title=_("Choose taxonomy package file"),
                                           initialdir=initialdir,
                                           filetypes=[(_("Taxonomy package files (*.zip)"), "*.zip"),
                                                      (_("Manifest (*.taxonomyPackage.xml)"), "*.taxonomyPackage.xml"),
                                                      (_("Oasis Catalog (*catalog.xml)"), "*catalog.xml")],
                                           defaultextension=".zip")
        if filename:
            # check if a package is selected (any file in a directory containing an __init__.py
            self.cntlr.config["packageOpenDir"] = os.path.dirname(filename)
            packageInfo = PackageManager.packageInfo(filename, packageManifestName=self.manifestNamePattern)
            self.loadFoundPackageInfo(packageInfo, filename)
                

    def findOnWeb(self):
        url = DialogURL.askURL(self)
        if url:  # url is the in-cache or local file
            packageInfo = PackageManager.packageInfo(url, packageManifestName=self.manifestNamePattern)
            self.cntlr.showStatus("") # clear web loading status
            self.loadFoundPackageInfo(packageInfo, url)
                
    def manifestName(self):
        self.manifestNamePattern = simpledialog.askstring(_("Archive manifest file name pattern"),
                                                          _("Provide non-standard archive manifest file name pattern (e.g., *taxonomyPackage.xml).  \n"
                                                            "Uses unix file name pattern matching.  \n"
                                                            "Multiple manifest files are supported in archive (such as oasis catalogs).  \n"
                                                            "(If blank, search for either .taxonomyPackage.xml or catalog.xml).  "),
                                                          initialvalue=self.manifestNamePattern,
                                                          parent=self)
                
    def loadFoundPackageInfo(self, packageInfo, url):
        if packageInfo and packageInfo.get("name"):
            self.addPackageInfo(packageInfo)
            self.loadTreeViews()
        else:
            messagebox.showwarning(_("Package is not itself a taxonomy package.  "),
                                   _("File does not itself contain a manifest file: \n\n{0}\n\n  "
                                     "If opening an archive file, the manifest file search pattern currently is \"\", please press \"Manifest\" to change manifest file name pattern, e.g.,, \"*.taxonomyPackage.xml\", if needed.  ")
                                   .format(url),
                                   parent=self)
            
    def removePackageInfo(self, name, version):
        # find package entry
        packagesList = self.packagesConfig["packages"]
        j = -1
        for i, packageInfo in enumerate(packagesList):
            if packageInfo['name'] == name and packageInfo['version'] == version:
                j = i
                break
        if 0 <= j < len(packagesList):
            del self.packagesConfig["packages"][i]
            self.packagesConfigChanged = True

    def addPackageInfo(self, packageInfo):
        name = packageInfo["name"]
        version = packageInfo["version"]
        self.removePackageInfo(name, version)  # remove any prior entry for this package
        self.packageNamesWithNewerFileDates.discard(name) # no longer has an update available
        self.packagesConfig["packages"].append(packageInfo)
        PackageManager.rebuildRemappings()
        self.packagesConfigChanged = True

    def packageEnable(self):
        if 0 <= self.selectedPackageIndex < len(self.packagesConfig["packages"]):
            packageInfo = self.packagesConfig["packages"][self.selectedPackageIndex]
            if self.packageEnableButton['text'] == self.ENABLE:
                packageInfo["status"] = "enabled"
                self.packageEnableButton['text'] = self.DISABLE
            elif self.packageEnableButton['text'] == self.DISABLE:
                packageInfo["status"] = "disabled"
                self.packageEnableButton['text'] = self.ENABLE
            self.packagesConfigChanged = True
            PackageManager.rebuildRemappings()
            self.loadTreeViews()
            
    def packageMoveUp(self):
        if 1 <= self.selectedPackageIndex < len(self.packagesConfig["packages"]):
            packages = self.packagesConfig["packages"]
            packageInfo = packages[self.selectedPackageIndex]
            del packages[self.selectedPackageIndex]
            packages.insert(self.selectedPackageIndex -1, packageInfo)
            self.packagesConfigChanged = True
            PackageManager.rebuildRemappings()
            self.loadTreeViews()
            
    def packageMoveDown(self):
        if 0 <= self.selectedPackageIndex < len(self.packagesConfig["packages"]) - 1:
            packages = self.packagesConfig["packages"]
            packageInfo = packages[self.selectedPackageIndex]
            del packages[self.selectedPackageIndex]
            packages.insert(self.selectedPackageIndex + 1, packageInfo)
            self.packagesConfigChanged = True
            PackageManager.rebuildRemappings()
            self.loadTreeViews()
            
    def packageReload(self):
        if 0 <= self.selectedPackageIndex < len(self.packagesConfig["packages"]):
            packageInfo = self.packagesConfig["packages"][self.selectedPackageIndex]
            url = packageInfo.get("URL")
            if url:
                packageInfo = PackageManager.packageInfo(url, reload=True, packageManifestName=packageInfo.get("manifestName"))
                if packageInfo:
                    self.addPackageInfo(packageInfo)
                    PackageManager.rebuildRemappings()
                    self.loadTreeViews()
                    self.cntlr.showStatus(_("{0} reloaded").format(packageInfo.get("name")), clearAfter=5000)
                else:
                    messagebox.showwarning(_("Package error"),
                                           _("File or package cannot be reloaded: \n\n{0}")
                                           .format(url),
                                           parent=self)

    def packageRemove(self):
        if 0 <= self.selectedPackageIndex < len(self.packagesConfig["packages"]):
            packageInfo = self.packagesConfig["packages"][self.selectedPackageIndex]
            self.removePackageInfo(packageInfo["name"], packageInfo["version"])
            self.packagesConfigChanged = True
            PackageManager.rebuildRemappings()
            self.loadTreeViews()
class ComponentsDumpWindow(Toplevel):
	def __init__(self, application, barNumber = None, **kwargs):
		Toplevel.__init__(self)
		
		self.application = application
		self.barNumber = barNumber
		
		
		self.fromLabel = Label(self)
		self.fromLabel.grid(column = 0, row = 0)
		
		self.fromVar = StringVar()
		self.fromEntry = Entry(self, textvariable = self.fromVar, justify = RIGHT)
		self.fromEntry.grid(column = 1, row = 0, sticky = W + E)
		self.columnconfigure(1, weight = 1)
		
		
		self.toLabel = Label(self)
		self.toLabel.grid(column = 2, row = 0)
		
		self.toVar = StringVar()
		self.toEntry = Entry(self, textvariable = self.toVar, justify = RIGHT)
		self.toEntry.grid(column = 3, row = 0, sticky = W + E)
		self.columnconfigure(3, weight = 1)
		
		
		self.stepLabel = Label(self, text = "dx:")
		self.stepLabel.grid(column = 4, row = 0)
		
		self.stepVar = StringVar()
		self.stepEntry = Entry(self, textvariable = self.stepVar, justify = RIGHT)
		self.stepEntry.grid(column = 5, row = 0, sticky = W + E)
		self.columnconfigure(5, weight = 1)
		
		
		self.calculateButton = Button(self, text = "Рассчитать",
									  command = self.onCalculateButtonClicked)
		self.calculateButton.grid(column = 6, row = 0, columnspan = 2)
		
		
		# Таблица рассчитанных значений
		columns = ("№ стержня", "x", "Nx", "U", "σ")
		
		self.tree = Treeview(self, columns = columns, displaycolumns = columns)
		self.tree.grid(column = 0, row = 1, columnspan = 7, sticky = W + N + E + S)
		self.tree.column("#0", width = 0, stretch = 0)
		
		# Настройки отображения таблицы
		self.tree.column(columns[0], anchor = CENTER)
		self.tree.heading(columns[0], text = columns[0], anchor = CENTER)
		
		for x in columns[1:]:
			self.tree.column(x, anchor = E)
			self.tree.heading(x, text = x, anchor = E)
		
		self.rowconfigure(1, weight = 1)
		
		
		self.bind("<Destroy>", self.onWindowDestroy)
		
		
		self.updateTitles()
		self.onConstructionChanged(False)
	
	
	def updateTitles(self):
		if self.barNumber is None:
			titleDescStr = ""
			xDescStr     = "global"
		else:
			titleDescStr = "%sСтержень (%d)" % (self.application.nameDelim, self.barNumber)
			xDescStr     = "local"
		
		self.title("%s%sКомпоненты%s" \
				   % (self.application.name, self.application.nameDelim, titleDescStr))
		
		self.fromLabel["text"] = "От x(" + xDescStr + "):"
		self.toLabel["text"] = "До x(" + xDescStr + "):"
	
	
	def onWindowDestroy(self, event):
		self.application.onWindowDestroy(self)
	
	
	def onCalculateButtonClicked(self):
		try:
			self.calculate()
		except Exception as e:
			self.showError(e)
	
	
	def onConstructionChanged(self, constructed = True):
		if not constructed:
			for var in self.fromVar, self.toVar, self.stepVar:
				var.set("0")
			return
		
		try:
			self.calculate()
		except Exception:
			self.clear()
	
	
	def onPointCalculated(self, barNumber, x, N, U, Sigma):
		if self.barNumber is not None and barNumber != self.barNumber:
			return
		
		self.tree.insert(parent = "", index = "end",
						 values = ("—" if barNumber is None else str(barNumber),
								   "%.14f" % x, "%.14f" % N,
								   "%.14f" % U, "%.14f" % Sigma))
	
	
	def clear(self):
		self.tree.delete(*self.tree.get_children())
	
	
	def calculate(self):
		self.clear()
		
		if self.barNumber not in range(0, self.application.logic.barsCount()):
			self.barNumber = None
			self.updateTitles()
		
		for var in self.fromVar, self.toVar, self.stepVar:
			try:
				float(var.get())
			except ValueError:
				var.set("0")
		
		xFrom = float(self.fromVar.get())
		xTo = float(self.toVar.get())
		xStep = float(self.stepVar.get())
		
		self.application.logic.calculateComponents(xFrom, xTo, xStep, barNumber = self.barNumber,
												   onPointCalculated = self.onPointCalculated)
	
	
	def showError(self, message):
		tkinter.messagebox.showerror("Ошибка", message)
class showIncome:
    def __init__(self):
        self.win=Tk()
        self.canvas = Canvas(self.win, width=800, height=450, bg="white")
        self.canvas.pack(expand=YES, fill=BOTH)

        # bringing the screen in the centre
        width = self.win.winfo_screenwidth()
        height = self.win.winfo_screenheight()
        x = int(width / 2 - 800 / 2)
        y = int(height / 2 - 450 / 2)
        strl = "800x450+" + str(x) + "+" + str(y)
        self.win.geometry(strl)

        # disable resize of the window

        self.win.resizable(width=False, height=False)

        # change the title of the window
        self.win.title("WELCOME | Show income | ADMINISTRATOR")

    def add_frame(self):
        self.frame=Frame(self.win, width=600, height=350)
        self.frame.place(x=100, y=20)
        x, y= 70,20
        # using treeview to show the table
        # mention number of columns
        self.tr=Treeview(self.frame, columns=('A','B','C','D'), selectmode="extended")
        # heading key+text
        self.tr.heading('#0', text='Sr no')
        self.tr.column('#0', minwidth=0, width=100, stretch=NO)
        self.tr.heading('#1', text='Source')
        self.tr.column('#1', minwidth=0, width=100, stretch=NO)
        self.tr.heading('#2', text='Income')
        self.tr.column('#2', minwidth=0, width=100, stretch=NO)
        self.tr.heading('#3', text='Update')
        self.tr.column('#3', minwidth=0, width=100, stretch=NO)
        self.tr.heading('#4', text='Delete')
        self.tr.column('#4', minwidth=0, width=100, stretch=NO)

        j=0
        for i in db.db.show_income():
            self.tr.insert('', index=j, text=i[0], values=(i[1], i[2], 'Update', 'Delete'))
            j+=1

        # create an action on selected row
        self.tr.bind('<Double-Button-1>', self.actions)
        self.tr.place(x=50, y=y+50)
        self.win.mainloop()
    def actions(self,e):
       # get the value of selected row
       tt=self.tr.focus()

       # get the column id
       col=self.tr.identify_column(e.x)
       print(col)

       print(self.tr.item(tt))
       tup=(
           self.tr.item(tt).get('text'),
       )
       if col=='#4':
           res=messagebox.askyesno("Message","Do you want to delete?")
           if res:
               rs=db.db.delete_income(tup)
               if rs:
                   messagebox.showinfo("Message","Message deleted")
                   self.win.destroy()
                   z=showIncome()
                   z.add_frame()
               else:
                   self.win.destroy()
                   z=showIncome()
                   z.add_frame()
       elif col=='#3':
           res=income.addIncome.IncomeWindow(self.tr.item(tt))
           self.win.destroy()
           res.add_frame()
Exemple #13
0
class tabel():
    def __init__(self,data,y,m):
        w=Toplevel()
        w.geometry('{0}x{1}+0+0'.format(120+25*21,w.winfo_screenheight()-80))
        
        w.columnconfigure(0,weight=1)
        w.rowconfigure(0,weight=1)
        
        d=data[y][m]
        v='план'
        if 'табель' in d['degur']:
            v='табель'
        w.wm_title('{0} {1} {2}'.format(v,y,m))
        #deg=data['2013']['11']['degurs']  # ЗАГЛУШКА : список дежурных
        deg=d['degurs']  # ЗАГЛУШКА : список дежурных
        cc=list(range(1,17))
        cols=[str(c) for c in cc]+['s','сум','ноч','пра','доп']
        
        self.t=Treeview(w,columns=cols)
        self.t.column('#0',width=100)
        for c in cols:
            self.t.heading(c,text=c)
            self.t.column(c,width=25,anchor='center')
        self.t.tag_configure('title',background='gray')
        self.scrX=Scrollbar(w,orient='horizontal',command=self.t.xview)
        self.scrY=Scrollbar(w,orient='vertical',command=self.t.yview)
        self.t['xscrollcommand']=self.scrX.set
        self.t['yscrollcommand']=self.scrY.set
        self.t.grid(row=0,column=0,sticky=N+S+E+W)
        self.scrX.grid(row=1,column=0,sticky=E+W)
        self.scrY.grid(row=0,column=1,sticky=N+S)

        rez=dict()
        for j,s in d['degur'][v].items():
                rez[j]=analyse2(s,d)
        for j in deg:
            ww1=[]
            ww2=[]
            a=0
            nn1=[]
            for x in d['degur'][v].get(j,''):
                if a:
                    if x=='Д':
                        ww1.append('!!')
                        nn1+=[0,0]
                        y=a+12
                        a=0
                    elif x in [str(xx) for xx in range(1,10)]:
                        ww1.append('Я')
                        nn1+=[0,0]
                        y=a+int(x)
                        a=0
                    elif x=='Н':
                        ww1.append('!')
                        nn1+=[2,6]
                        y=a+4
                        a=8
                    elif x=='-':
                        ww1.append('Н')
                        nn1+=[0,0]
                        y=a+0
                        a=0
                    else:
                        ww1.append('!')
                        nn1+=[0,0]
                        y=a+0
                        a=0
                else:
                    if x=='Д':
                        ww1.append('Я')
                        nn1+=[0,0]
                        y=12
                        a=0
                    elif x in [str(xx) for xx in range(1,10)]:
                        ww1.append('Я')
                        nn1+=[0,0]
                        y=int(x)
                        a=0
                    elif x=='Н':
                        ww1.append(x)
                        nn1+=[2,6]
                        y=4
                        a=8
                    elif x=='-':
                        ww1.append('В')
                        nn1+=[0,0]
                        y=0
                        a=0
                    else:
                        ww1.append(x)
                        nn1+=[0,0]
                        y=0
                        a=0
                ww2.append(y)
            ww=rez.get(j,(0,0,0,0))[0]
            ee=rez.get(j,(0,0,0,0))[0] -rez.get(j,(0,0,0,0))[3]
            #ee=rez.get(j,(0,0,0,0))[3]
            nn=rez.get(j,(0,0,0,0))[1]
            hh=rez.get(j,(0,0,0,0))[2]
            s1=sum([x and 1 for x in ww2[1:16]])
            s2=sum([x and 1 for x in ww2[16:-1]])
            n0=sum([x=='Н' and 1 or 0 for x in ww1[1:-1]])

            z=self.t.insert('','end',text=j)
            self.t.insert(z,'end',text='',values=list(range(1,16)),tag='title')
            self.t.insert(z,'end',text='',values=ww1[1:16]+['',s1])
            self.t.insert(z,'end',text='',values=[x or '-' for x in ww2[1:16]]+ \
                    ['']+[sum(ww2[1:16])])
            self.t.insert(z,'end',text='',values=list(range(16,32)),tag='title')
            self.t.insert(z,'end',text='',values=ww1[16:-1]+['']*(33-len(ww1))+ \
                    [s2,s1+s2,n0])
            self.t.insert(z,'end',text='',values=[x or '-' for x in ww2[16:-1]]+ \
                    ['']*(16-len(ww2[16:-1]))+[sum(ww2[16:-1]),sum(ww2[1:-1]),sum(nn1[1:-3]),hh,ee])
Exemple #14
0
class statistic_xx():
    def __init__(self,data,y,v='план'):
        
        w=Toplevel()
        w.wm_title('Итоги по месяцам за {0} год ({1}) '.format(y,v))
        w.columnconfigure(0,weight=1)
        w.rowconfigure(0,weight=1)
        
        cols=data[y]['degurs']  # ЗАГЛУШКА : список дежурных
        
        self.t=Treeview(w,columns=cols)
        self.t.column('#0',width=120)
        for c in cols:
            self.t.heading(c,text=c)
            self.t.column(c,width=65,anchor='center')
        self.t.tag_configure('табель',background='green')
        self.t.tag_configure('ош',background='red')
        self.scrX=Scrollbar(w,orient='horizontal',command=self.t.xview)
        self.scrY=Scrollbar(w,orient='vertical',command=self.t.yview)
        self.t['xscrollcommand']=self.scrX.set
        self.t['yscrollcommand']=self.scrY.set
        self.t.grid(row=0,column=0,sticky=N+S+E+W)
        self.scrX.grid(row=1,column=0,sticky=E+W)
        self.scrY.grid(row=0,column=1,sticky=N+S)
        roots=dict()
        for m in ['01','02','03','04','05','06','07','08','09','10','11','12']:
            d0=data[y]
            if m not in d0: continue
            roots[m]=self.t.insert('','end',text=m+' ('+data[y][m]['month']+')')
        #r=self.t.insert('','end',text='рабочих')
        #x=self.t.insert('','end',text='xxx')
        #w=self.t.insert('','end',text='отработано')
        #e=self.t.insert('','end',text='дополнительные')
        #n=self.t.insert('','end',text='ночные')
        #h=self.t.insert('','end',text='праздничные')
        #rz_root=self.t.insert('','end',text='резерв')
        
        for m in ['01','02','03','04','05','06','07','08','09','10','11','12']:
            d0=data[y]
            if m not in d0: continue
            d=d0[m]

            rez=dict()
            tag=''
            if v=='авто':
                if 'табель' in d['degur']:
                    vv='табель'
                    tag=vv
                else:
                    vv='план'
            elif v=='табель':
                if 'табель' not in d['degur']:
                    vv='план'
                    tag='ош'
                else:
                    vv=v
                    tag=vv
            else:
                vv=v

            for j,s in d['degur'][vv].items():
                rez[j]=analyse2(s,d)
            NUL=(0,0,0,0,0,0,0)
            ww=[rez.get(j,NUL)[0] for j in cols]
            ee=[rez.get(j,NUL)[0]-rez.get(j,NUL)[3]+rez.get(j,NUL)[4] for j in cols]
            xx=[rez.get(j,NUL)[0]-rez.get(j,NUL)[3] for j in cols]
            nn=[rez.get(j,NUL)[1] for j in cols]
            hh=[rez.get(j,NUL)[2] for j in cols]
            rr=[rez.get(j,NUL)[3]-rez.get(j,NUL)[4] for j in cols]
            rz=[rez.get(j,NUL)[5] for j in cols]
            self.t.insert(roots[m],'end',text='отработано',values=ww,tag=tag)
            self.t.insert(roots[m],'end',text='рабочие',values=rr,tag=tag)
            self.t.insert(roots[m],'end',text='дополнительные',values=ee,tag=tag)
            self.t.insert(roots[m],'end',text='ночные',values=nn,tag=tag)
            self.t.insert(roots[m],'end',text='праздничные',values=hh,tag=tag)
Exemple #15
0
class statistic_q():
    def __init__(self,data,y,v='план'):
        
        w=Toplevel()
        w.wm_title('Поквартальная статистика за {0} год ({1})'.format(y,v))
        w.columnconfigure(0,weight=1)
        w.rowconfigure(0,weight=1)
        
        cols=data[y]['degurs']  # ЗАГЛУШКА : список дежурных
        
        self.t=Treeview(w,columns=cols)
        self.t.column('#0',width=120)
        for c in cols:
            self.t.heading(c,text=c)
            self.t.column(c,width=65,anchor='center')
        self.t.tag_configure('табель',background='green')
        self.t.tag_configure('ош',background='red')
        self.scrX=Scrollbar(w,orient='horizontal',command=self.t.xview)
        self.scrY=Scrollbar(w,orient='vertical',command=self.t.yview)
        self.t['xscrollcommand']=self.scrX.set
        self.t['yscrollcommand']=self.scrY.set
        self.t.grid(row=0,column=0,sticky=N+S+E+W)
        self.scrX.grid(row=1,column=0,sticky=E+W)
        self.scrY.grid(row=0,column=1,sticky=N+S)
        r=self.t.insert('','end',text='рабочих')
        w=self.t.insert('','end',text='отработано')
        e=self.t.insert('','end',text='дополнительные')
        n=self.t.insert('','end',text='ночные')
        h=self.t.insert('','end',text='праздничные')
        x=self.t.insert('','end',text='xxx')
        rz_root=self.t.insert('','end',text='резерв')
        
        rez=dict()
        wwY=[]
        rrY=[]
        eeY=[]
        xxY=[]
        nnY=[]
        hhY=[]
        rzY=[]
        for mm in [1,2,3,4]:
            mmm=[str((mm-1)*3+x).zfill(2) for x in [1,2,3]]
            mmm=[x for x in mmm if x in data[y]]
            tag=''
            
            k=['табель' in data[y][m]['degur'] for m in mmm]
            #print(k)
            if v=='авто':
                if k==[True, True, True]:
                    vv='табель'
                    tag=vv
                else:
                    vv='план'
            elif v=='табель':
                if k!=[True, True, True]:
                    vv='план'
                    tag='ош'
                else:
                    vv=v
                    tag=vv
            else:
                vv=v
            
            ww=[]
            rr=[]
            ee=[]
            xx=[]
            nn=[]
            hh=[]
            rz=[]
            for m in mmm:
                d=data[y][m]
                for j in cols:
                    s=d['degur'][vv].get(j,'*ООООООООООООООООООООООООООООООО*')
                    rez[j]=analyse2(s,d)
                NUL=(0,0,0,0,0,0,0)
                ww.append([rez.get(j,NUL)[0] for j in cols])
                ee.append([rez.get(j,NUL)[0]-rez.get(j,NUL)[3] + \
                        rez.get(j,NUL)[4] for j in cols])
                xx.append([rez.get(j,NUL)[0]-rez.get(j,NUL)[3] for j in cols])
                rr.append([rez.get(j,NUL)[3]-rez.get(j,NUL)[4] for j in cols])
                nn.append([rez.get(j,NUL)[1] for j in cols])
                hh.append([rez.get(j,NUL)[2] for j in cols])
                rz.append([rez.get(j,NUL)[5] for j in cols])
            ww=[sum(x) for x in zip(*ww)]
            rr=[sum(x) for x in zip(*rr)]
            ee=[sum(x) for x in zip(*ee)]
            xx=[sum(x) for x in zip(*xx)]
            nn=[sum(x) for x in zip(*nn)]
            hh=[sum(x) for x in zip(*hh)]
            rz=[sum(x) for x in zip(*rz)]
            wwY.append(ww)
            rrY.append(rr)
            eeY.append(ee)
            xxY.append(xx)
            nnY.append(nn)
            hhY.append(hh)
            rzY.append(rz)
            self.t.insert(w,'end',text=mm,values=ww,tag=tag)
            self.t.insert(r,'end',text=mm,values=rr,tag=tag)
            self.t.insert(n,'end',text=mm,values=nn,tag=tag)
            self.t.insert(h,'end',text=mm,values=hh,tag=tag)
            self.t.insert(e,'end',text=mm,values=ee,tag=tag)
            self.t.insert(x,'end',text=mm,values=xx,tag=tag)
            self.t.insert(rz_root,'end',text=mm,values=rz,tag=tag)
        wwY=[sum(x) for x in zip(*wwY)]
        rrY=[sum(x) for x in zip(*rrY)]
        eeY=[sum(x) for x in zip(*eeY)]
        xxY=[sum(x) for x in zip(*xxY)]
        nnY=[sum(x) for x in zip(*nnY)]
        hhY=[sum(x) for x in zip(*hhY)]
        rzY=[sum(x) for x in zip(*rzY)]
        self.t.insert(w,'end',text='итого',values=wwY,tag='Y')
        self.t.insert(r,'end',text='итого',values=rrY,tag='Y')
        self.t.insert(n,'end',text='итого',values=nnY,tag='Y')
        self.t.insert(h,'end',text='итого',values=hhY,tag='Y')
        self.t.insert(e,'end',text='итого',values=eeY,tag='Y')
        self.t.insert(x,'end',text='итого',values=xxY,tag='Y')
        self.t.insert(rz_root,'end',text='итого',values=rzY,tag='Y')
Exemple #16
0
class Gr():
    def __init__(self,root,data,SCRY=None):
        self.data=data
        self.columns=[x for x in range(1,8)]+['day']
        root.rowconfigure(1,weight=1)
        root.columnconfigure(0,weight=1)
        root.columnconfigure(1,weight=1)
        root.columnconfigure(2,weight=1)
        f=Frame(root)
        f.columnconfigure(0,weight=1)
        f.rowconfigure(1,weight=1)
        self.v=Combobox(root)
        self.v.grid(row=0,column=0)
        self.v.bind('<<ComboboxSelected>>',self.select_ver)
        f.grid(row=1,column=0,columnspan=3,sticky=N+S)
        self.tree=Treeview(f,
                columns=self.columns,
                displaycolumns=['day']+self.columns[:-1],
                show='headings')
        #self.tree.tag_configure('odd',background='white')
        #self.tree.tag_configure('even',background='gray')
        self.tree.tag_configure('dif',foreground='brown')
        self.tree.tag_configure('work',background='white')
        self.tree.tag_configure('short',background='#F5EFE0')
        self.tree.tag_configure('rest',background='#E0B0B0')
        self.tree.tag_configure('holyday',background='#E7B7A4')
        for c in self.columns:
            self.tree.heading(c,text=c)
            self.tree.column(c,width=65,anchor='center')
        self.tree.column('day',width=30)
        scrX=Scrollbar(f,orient='horizontal',command=self.tree.xview)
        self.tree['xscrollcommand']=scrX.set
        if not SCRY:
            self.scrY=Scrollbar(f,orient='vertical',command=self.yview)
            self.tree['yscrollcommand']=self.scrY.set
        else:
            self.tree['yscrollcommand']=SCRY.set
        self.tree.grid(row=1,column=0,sticky=N+S)
        if not SCRY:
            self.scrY.grid(row=1,column=1,sticky=N+S)
        scrX.grid(row=2,column=0,sticky=E+W)
    def set(self,y,m):
        self.y=y
        self.m=m
        self.show()
    def yview(self,*args):
        self.tree.yview(*args)
        self.yview2(*args)
    def yview2(self,*args):
        pass
    def show(self):
        d=self.data[self.y][self.m]
        V=list(d['degur'].keys())
        self.v['values']=V
        self.v.set(V[0])
        self.select_ver()
    def select_ver(self,*e):
        self.tree.delete(*self.tree.get_children())
        d=self.data[self.y][self.m]
        offset=d['offset']
        v=self.v.get()
        col=[]
        for i,deg in enumerate(d['degurs']):
            self.tree.heading(i+1,text=deg)
            col.append(i+1)
        self.tree.configure(displaycolumns=['day']+col)
        items=dict()

        if 'табель' in d['degur']:
            a=[''.join(x) for x in zip(*[[x for x in d['degur']['план'][j]] \
                    for j in d['degurs']])]
            b=[''.join(x) for x in zip(*[[x for x in d['degur']['табель'][j]] \
                    for j in d['degurs']])]
            c=[x!=y for x,y  in zip(a,b)]
        else:
            c=[False]*32

        for i in range(1,d['days']+1):
            tag = (i+offset) % 7 in [0,6] and 'rest' or 'work'
            if i in d['holydays'] : tag='holyday'
            elif i in d['restdays'] : tag='rest'
            elif i in d['shortdays'] : tag='short'
            elif i in d['workdays'] : tag='work'
            if c[i]: tag=[tag,'dif']
            ii=self.tree.insert('','end',values=['-','-','-','-','-'],tag=tag)
            self.tree.set(ii,column='day',value=i)
            items[i]=ii

        
        for j,s in d['degur'][v].items(): # j-degur
            if not s: continue
            for i,val in enumerate(s[1:-1]):
                if val=='J':
                    val='до'
                elif val=='j':
                    val='од'
                elif val=='a':
                    val='10'
                self.tree.set(items[i+1],column=d['degurs'].index(j)+1,value=val)
            if s[0]=='Н':
                if s[1]=='-':
                    self.tree.set(items[1],column=d['degurs'].index(j)+1,value='Н(8)')
                else:
                    self.tree.set(items[1],column=d['degurs'].index(j)+1,value='!')
            if s[-2]=='Н':
                if s[-1]=='-':
                    self.tree.set(items[len(s)-2],column=d['degurs'].index(j)+1,value='Н(4)')
                else:
                    self.tree.set(items[len(s)-2],column=d['degurs'].index(j)+1,value='!')
        self.calc(self.y,self.m)
    def calc(self,y,m):
        d=self.data[y][m]
        offset=d['offset']
        WH=0
        for i in range(1,d['days']+1):
            if i in d['holydays']: wh=0
            elif i in d['restdays'] : wh=0
            elif i in d['shortdays'] : wh=7
            elif i in d['workdays'] : wh=8
            elif (i+offset) % 7 in [0,6]: wh=0
            else: wh=8
            WH+=wh
class ElementListWidget(Frame):
	def __init__(self, parent, label, columns, showError):
		Frame.__init__(self, parent)
		
		self.showError = showError
		
		self.columnconfigure(0, weight = 1)
		self.rowconfigure(1, weight = 1)
		
		
		# Название таблицы
		self.titleLabel = Label(self, text = label)
		self.titleLabel.grid(column = 0, row = 0, sticky = W + E)
		
		
		# Таблица значений
		columns = ("Метка", "№") + columns
		self.tree = Treeview(self, columns = columns, displaycolumns = columns,
							 selectmode = "browse")
		self.tree.grid(column = 0, row = 1, sticky = W + N + E + S)
		
		# Настраиваем внешний вид таблицы (первые колонки)
		self.tree.column("#0", width = 0, stretch = 0)	# Прячем колонку с иконкой
		
		self.tree.column( columns[0], anchor = W, width = 150)
		self.tree.heading(columns[0], anchor = W, text = columns[0])
		
		self.tree.column( columns[1], anchor = E, width = 80)
		self.tree.heading(columns[1], anchor = E, text = columns[1])
		
		self.tree.bind("<<TreeviewSelect>>", self.onSelectionChanged)
		
		
		# Панель с кнопками
		self.buttonPanel = Frame(self)
		self.buttonPanel.grid(column = 0, row = 2, sticky = W + E)
		
		self.buttonPanel.columnconfigure(0, weight = 1)
		self.buttonPanel.columnconfigure(3, minsize = emptySpaceSize, weight = 0)
		self.buttonPanel.columnconfigure(6, minsize = emptySpaceSize, weight = 0)
		self.buttonPanel.columnconfigure(9, weight = 1)
		
		# Кнопки добавления/удаления элемента
		self.buttonAdd = Button(self.buttonPanel, text = "+", width = 3,
								command = self.onButtonAddClicked)
		self.buttonAdd.grid(column = 1, row = 0)
		
		self.buttonRemove = Button(self.buttonPanel, text = "-", width = 3, state = DISABLED,
								   command = self.onButtonRemoveClicked)
		self.buttonRemove.grid(column = 2, row = 0)
		
		# Кнопки перемещения элемента
		self.buttonUp = Button(self.buttonPanel, text = "↑", width = 3, state = DISABLED,
							   command = self.onButtonUpClicked)
		self.buttonUp.grid(column = 4, row = 0)
		
		self.buttonDown = Button(self.buttonPanel, text = "↓", width = 3, state = DISABLED,
								 command = self.onButtonDownClicked)
		self.buttonDown.grid(column = 5, row = 0)
		
		# Кнопки применить/отменить (для выбранного элемента)
		self.buttonCancel = Button(self.buttonPanel, text = "✗", width = 3,
								   command = self.updateSelectedFrame)
		self.buttonCancel.grid(column = 7, row = 0)
		
		self.buttonApply = Button(self.buttonPanel, text = "✓", width = 3,
								  command = self.onButtonApplyClicked)
		self.buttonApply.grid(column = 8, row = 0)
		
		
		# Редактирование выделенного элемента
		self.i     = StringVar()
		self.label = (StringVar(), StringVar())
		
		self.selectedFrame = Frame(self)
		self.selectedFrame.grid(column = 0, row = 3, sticky = W + E)
		
		# Номер
		Label(self.selectedFrame, text = "№:") \
			.grid(column = 0, row = 0)
		Label(self.selectedFrame, textvariable = self.i, width = 3, justify = RIGHT) \
			.grid(column = 1, row = 0)
		
		# Пустое пространство
		self.selectedFrame.columnconfigure(2, minsize = emptySpaceSize, weight = 0)
		
		# Метка
		Entry(self.selectedFrame, textvariable = self.label[0]) \
			.grid(column = 3, row = 0, sticky = W + E)
		
		Entry(self.selectedFrame, textvariable = self.label[1], bg = defaultValueBG) \
			.grid(column = 4, row = 0, sticky = W + E)
		
		# Виджет для элементов классов-потомков
		self.detailFrame = Frame(self.selectedFrame)
		self.detailFrame.grid(column = 3, row = 1, columnspan = 2, sticky = W + N + E + S)
		
		self.selectedFrame.columnconfigure(3, weight = 1)
		self.selectedFrame.columnconfigure(4, weight = 1)
		self.selectedFrame.rowconfigure(1, weight = 1)
	
	
	def onButtonUpClicked(self):
		item = self.selectedItem()
		if item is None: return
		
		prev = self.tree.prev(item)
		if prev != "":
			parent, index = self.tree.parent(item), self.tree.index(item)
			self.tree.move(item, parent, index - 1)
			
			# Корректируем номера элементов
			self.tree.set(item, "№", index - 1)
			self.tree.set(prev, "№", index)
			
			self.updateSelectedFrame(item)
	
	
	def onButtonDownClicked(self):
		item = self.selectedItem()
		if item is None: return
		
		next = self.tree.next(item)
		if next != "":
			parent, index = self.tree.parent(item), self.tree.index(item)
			self.tree.move(item, parent, index + 1)
			
			# Корректируем номера элементов
			self.tree.set(item, "№", index + 1)
			self.tree.set(next, "№", index)
			
			self.updateSelectedFrame(item)
	
	
	def onButtonAddClicked(self):
		pass
	
	
	def onButtonRemoveClicked(self):
		item = self.selectedItem()
		if item is None: return
		
		next = self.tree.next(item)
		self.tree.delete(item)
		
		while next != "":
			i = int(self.tree.set(next, "№"))
			self.tree.set(next, "№", i - 1)
			next = self.tree.next(next)
		
		self.onSelectionChanged()
	
	
	def onButtonApplyClicked(self, item = None):
		if item is None: item = self.selectedItem()
		if item is None: return None
		
		label = self.label[0].get()
		self.tree.set(item, "Метка", label)
		
		return item
	
	
	def onSelectionChanged(self, event = None):
		item = self.selectedItem()
		
		# Обновляем состояние кнопок
		state = DISABLED if item is None else NORMAL
		for x in (self.buttonRemove, self.buttonUp, self.buttonDown):
			x["state"] = state
		
		self.updateSelectedFrame(item)
	
	
	def selectedItem(self):
		selection = self.tree.selection()
		return None if type(selection) == type("") else selection[0]
	
	
	def clear(self):
		for item in self.tree.get_children():
			self.tree.delete(item)
	
	
	def updateSelectedFrame(self, item = None, values = None):
		if item is None: item = self.selectedItem()
		values = None
		
		if item is None:
			i     = ""
			label = ""
		else:
			if values is None: values = self.tree.set(item)
			
			i     = values["№"]
			label = values["Метка"]
		
		self.i.set(i)
		self.label[0].set(label)
		
		return (item, values)
	
	
	def addElement(self, values):
		self.tree.insert(parent = "", index = END, values = values)
	
	
	def setDefaultElement(self, label):
		self.label[1].set(label)
	
	
	def elementsCount(self):
		return len(self.tree.get_children())
	
	
	def elements(self, transform):
		return [ transform(item) for item in self.tree.get_children() ]
Exemple #18
0
class DialogOpenArchive(Toplevel):
    def __init__(self, parent, openType, filesource, filenames, title, colHeader, showAltViewButton=False):
        if isinstance(parent, Cntlr):
            cntlr = parent
            parent = parent.parent # parent is cntlrWinMain
        else: # parent is a Toplevel dialog
            cntlr = parent.cntlr
        super(DialogOpenArchive, self).__init__(parent)
        self.parent = parent
        self.showAltViewButton = showAltViewButton
        parentGeometry = re.match("(\d+)x(\d+)[+]?([-]?\d+)[+]?([-]?\d+)", parent.geometry())
        dialogX = int(parentGeometry.group(3))
        dialogY = int(parentGeometry.group(4))
        self.accepted = False

        self.transient(self.parent)
        
        frame = Frame(self)

        treeFrame = Frame(frame, width=500)
        vScrollbar = Scrollbar(treeFrame, orient=VERTICAL)
        hScrollbar = Scrollbar(treeFrame, orient=HORIZONTAL)
        self.treeView = Treeview(treeFrame, xscrollcommand=hScrollbar.set, yscrollcommand=vScrollbar.set)
        self.treeView.grid(row=0, column=0, sticky=(N, S, E, W))
        hScrollbar["command"] = self.treeView.xview
        hScrollbar.grid(row=1, column=0, sticky=(E,W))
        vScrollbar["command"] = self.treeView.yview
        vScrollbar.grid(row=0, column=1, sticky=(N,S))
        treeFrame.columnconfigure(0, weight=1)
        treeFrame.rowconfigure(0, weight=1)
        treeFrame.grid(row=0, column=0, columnspan=4, sticky=(N, S, E, W), padx=3, pady=3)
        self.treeView.focus_set()
        
        if openType not in (PLUGIN, PACKAGE):
            cntlr.showStatus(_("loading archive {0}").format(filesource.url))
        self.filesource = filesource
        self.filenames = filenames
        self.selection = filesource.selection
        self.hasToolTip = False
        selectedNode = None

        if openType == ENTRY_POINTS:
            try:
                metadataFiles = filesource.taxonomyPackageMetadataFiles
                ''' take first for now
                if len(metadataFiles) != 1:
                    raise IOError(_("Taxonomy package contained more than one metadata file: {0}.")
                                  .format(', '.join(metadataFiles)))
                '''
                metadataFile = metadataFiles[0]
                metadata = filesource.url + os.sep + metadataFile
                self.metadataFilePrefix = os.sep.join(os.path.split(metadataFile)[:-1])
                if self.metadataFilePrefix:
                    self.metadataFilePrefix += "/"  # zip contents have /, never \ file seps
                self.taxonomyPkgMetaInf = '{}/META-INF/'.format(
                            os.path.splitext(os.path.basename(filesource.url))[0])

        
                self.taxonomyPackage = parsePackage(cntlr, filesource, metadata,
                                                    os.sep.join(os.path.split(metadata)[:-1]) + os.sep)
                
                
                if self.taxonomyPackage["entryPoints"]:
                    # may have instance documents too
                    self.packageContainedInstances = []
                    packageContentTypeCounts = {}
                    for suffix in (".xhtml", ".htm", ".html"):
                        for potentialInstance in filesource.dir:
                            if potentialInstance.endswith(".xhtml"):
                                _type = "Inline Instance"
                                self.packageContainedInstances.append([potentialInstance, _type])
                                packageContentTypeCounts[potentialInstance] = packageContentTypeCounts.get(potentialInstance, 0) + 1
                        if self.packageContainedInstances:
                            break 
                    if self.packageContainedInstances: # add sequences to any duplicated entry types
                        for _type, count in packageContentTypeCounts.items():
                            if count > 1:
                                _dupNo = 0
                                for i in range(len(self.packageContainedInstances)):
                                    if self.packageContainedInstances[i][0] == _type:
                                        _dupNo += 1
                                        self.packageContainedInstances[i][0] = "{} {}".format(_type, _dupNo)
                                    
                else:
                    # may be a catalog file with no entry oint names
                    openType = ARCHIVE  # no entry points to show, just archive
                    self.showAltViewButton = False
            except Exception as e:
                self.close()
                err = _("Failed to parse metadata; the underlying error was: {0}").format(e)
                messagebox.showerror(_("Malformed taxonomy package"), err)
                cntlr.addToLog(err)
                return
    
        if openType not in (PLUGIN, PACKAGE):
            cntlr.showStatus(None)
        
        if openType in (DISCLOSURE_SYSTEM, PLUGIN, PACKAGE):
            y = 3
        else:
            y = 1

        okButton = Button(frame, text=_("OK"), command=self.ok)
        cancelButton = Button(frame, text=_("Cancel"), command=self.close)
        okButton.grid(row=y, column=2, sticky=(S,E,W), pady=3)
        cancelButton.grid(row=y, column=3, sticky=(S,E,W), pady=3, padx=3)
        
        if self.showAltViewButton:
            self.altViewButton = Button(frame, command=self.showAltView)
            self.altViewButton.grid(row=y, column=0, sticky=(S,W), pady=3, padx=3)
        
        self.loadTreeView(openType, colHeader, title)

        self.geometry("+{0}+{1}".format(dialogX+50,dialogY+100))
        frame.grid(row=0, column=0, sticky=(N,S,E,W))
        frame.columnconfigure(0, weight=1)
        frame.rowconfigure(0, weight=1)
        window = self.winfo_toplevel()
        window.columnconfigure(0, weight=1)
        window.rowconfigure(0, weight=1)
        
        self.bind("<Return>", self.ok)
        self.bind("<Escape>", self.close)
        
        self.toolTipText = StringVar()
        if self.hasToolTip:
            self.treeView.bind("<Motion>", self.motion, '+')
            self.treeView.bind("<Leave>", self.leave, '+')
            self.toolTipText = StringVar()
            self.toolTip = ToolTip(self.treeView, 
                                   textvariable=self.toolTipText, 
                                   wraplength=640, 
                                   follow_mouse=True,
                                   state="disabled")
            self.toolTipRowId = None

        self.protocol("WM_DELETE_WINDOW", self.close)
        self.grab_set()
        
        self.wait_window(self)

    
        
        
    def loadTreeView(self, openType, title, colHeader):
        self.title(title)
        self.openType = openType
        selectedNode = None

        # clear previous treeview entries
        for previousNode in self.treeView.get_children(""): 
            self.treeView.delete(previousNode)

        # set up treeView widget and tabbed pane
        if openType in (ARCHIVE, DISCLOSURE_SYSTEM, PLUGIN, PACKAGE):
            if openType in (PLUGIN, PACKAGE): width = 770
            else: width = 500
            self.treeView.column("#0", width=width, anchor="w")
            self.treeView.heading("#0", text=colHeader)
            self.isRss = getattr(self.filesource, "isRss", False)
            if self.isRss:
                self.treeView.column("#0", width=350, anchor="w")
                self.treeView["columns"] = ("descr", "date", "instDoc")
                self.treeView.column("descr", width=50, anchor="center", stretch=False)
                self.treeView.heading("descr", text="Form")
                self.treeView.column("date", width=170, anchor="w", stretch=False)
                self.treeView.heading("date", text="Pub Date")
                self.treeView.column("instDoc", width=200, anchor="w", stretch=False)
                self.treeView.heading("instDoc", text="Instance Document")
            elif openType == PLUGIN:
                self.treeView.column("#0", width=150, anchor="w")
                self.treeView["columns"] = ("name", "vers", "descr", "license")
                self.treeView.column("name", width=150, anchor="w", stretch=False)
                self.treeView.heading("name", text="Name")
                self.treeView.column("vers", width=60, anchor="w", stretch=False)
                self.treeView.heading("vers", text="Version")
                self.treeView.column("descr", width=300, anchor="w", stretch=False)
                self.treeView.heading("descr", text="Description")
                self.treeView.column("license", width=60, anchor="w", stretch=False)
                self.treeView.heading("license", text="License")
            elif openType == PACKAGE:
                self.treeView.column("#0", width=200, anchor="w")
                self.treeView["columns"] = ("vers", "descr", "license")
                self.treeView.column("vers", width=100, anchor="w", stretch=False)
                self.treeView.heading("vers", text="Version")
                self.treeView.column("descr", width=400, anchor="w", stretch=False)
                self.treeView.heading("descr", text="Description")
                self.treeView.column("license", width=70, anchor="w", stretch=False)
                self.treeView.heading("license", text="License")
            else:
                self.treeView["columns"] = tuple()
        
            loadedPaths = []
            for i, filename in enumerate(self.filenames):
                if isinstance(filename,tuple):
                    if self.isRss:
                        form, date, instDoc = filename[2:5]
                    elif openType == PLUGIN:
                        name, vers, descr, license = filename[3:7]
                    elif openType == PACKAGE:
                        vers, descr, license = filename[3:6]
                    filename = filename[0] # ignore tooltip
                    self.hasToolTip = True
                if filename.endswith("/"):
                    filename = filename[:-1]
                path = filename.split("/")
                if not self.isRss and len(path) > 1 and path[:-1] in loadedPaths:
                    parent = "file{0}".format(loadedPaths.index(path[:-1]))
                else:
                    parent = "" 
                node = self.treeView.insert(parent, "end", "file{0}".format(i), text=path[-1])
                if self.isRss:
                    self.treeView.set(node, "descr", form)
                    self.treeView.set(node, "date", date)
                    self.treeView.set(node, "instDoc", os.path.basename(instDoc))
                elif openType == PLUGIN:
                    self.treeView.set(node, "name", name)
                    self.treeView.set(node, "vers", vers)
                    self.treeView.set(node, "descr", descr)
                    self.treeView.set(node, "license", license)
                elif openType == PACKAGE:
                    self.treeView.set(node, "vers", vers)
                    self.treeView.set(node, "descr", descr)
                    self.treeView.set(node, "license", license)
                if self.selection == filename:
                    selectedNode = node
                loadedPaths.append(path)

        elif openType == ENTRY_POINTS:
            self.treeView.column("#0", width=200, anchor="w")
            self.treeView.heading("#0", text="Name")
    
            self.treeView["columns"] = ("url",)
            self.treeView.column("url", width=300, anchor="w")
            self.treeView.heading("url", text="URL")
            
            for fileType, fileUrl in getattr(self, "packageContainedInstances", ()):
                self.treeView.insert("", "end", fileUrl, 
                                     values=fileType, 
                                     text=fileUrl or urls[0][2])
            for name, urls in sorted(self.taxonomyPackage["entryPoints"].items(), key=lambda i:i[0][2]):
                self.treeView.insert("", "end", name, 
                                     values="\n".join(url[1] for url in urls), 
                                     text=name or urls[0][2])
                
            self.hasToolTip = True
        else: # unknown openType
            return None
        if selectedNode:
            self.treeView.see(selectedNode)
            self.treeView.selection_set(selectedNode)

        if self.showAltViewButton:
            self.altViewButton.config(text=_("Show Files") if openType == ENTRY_POINTS else _("Show Entries"))

        
    def ok(self, event=None):
        selection = self.treeView.selection()
        if len(selection) > 0:
            if hasattr(self, "taxonomyPackage"):
                # load file source remappings
                self.filesource.mappedPaths = self.taxonomyPackage["remappings"]
            filename = None
            if self.openType in (ARCHIVE, DISCLOSURE_SYSTEM):
                filename = self.filenames[int(selection[0][4:])]
                if isinstance(filename,tuple):
                    if self.isRss:
                        filename = filename[4]
                    else:
                        filename = filename[0]
            elif self.openType == ENTRY_POINTS:
                epName = selection[0]
                #index 0 is the remapped Url, as opposed to the canonical one used for display
                # Greg Acsone reports [0] does not work for Corep 1.6 pkgs, need [1], old style packages
                filenames = []
                for _url, _type in self.packageContainedInstances: # check if selection was an inline instance
                    if _type == epName:
                        filenames.append(_url)
                if not filenames: # else if it's a named taxonomy entry point
                    for url in self.taxonomyPackage["entryPoints"][epName]:
                        filename = url[0]
                        if not filename.endswith("/"):
                            # check if it's an absolute URL rather than a path into the archive
                            if not isHttpUrl(filename) and self.metadataFilePrefix != self.taxonomyPkgMetaInf:
                                # assume it's a path inside the archive:
                                filename = self.metadataFilePrefix + filename
                        filenames.append(filename)
                if filenames:
                    self.filesource.select(filenames)
                    self.accepted = True
                    self.close()
                return
            elif self.openType in (PLUGIN, PACKAGE):
                filename = self.filenames[int(selection[0][4:])][2]
            if filename is not None and not filename.endswith("/"):
                if hasattr(self, "taxonomyPackage"):
                    # attempt to unmap the filename to original file
                    # will be mapped again in loading, but this allows schemaLocation to be unmapped
                    for prefix, remapping in self.taxonomyPackage["remappings"].items():
                        if isHttpUrl(remapping):
                            remapStart = remapping
                        else:
                            remapStart = self.metadataFilePrefix + remapping
                        if filename.startswith(remapStart):
                            # set unmmapped file
                            filename = prefix + filename[len(remapStart):]
                            break
                if self.openType in (PLUGIN, PACKAGE):
                    self.filesource.selection = filename
                else:
                    self.filesource.select(filename)
                self.accepted = True
                self.close()
                        
        
    def close(self, event=None):
        self.parent.focus_set()
        self.destroy()
        
    def showAltView(self, event=None):
        if self.openType == ENTRY_POINTS:
            self.loadTreeView(ARCHIVE, _("Select Entry Point"), _("File"))
        else:
            self.loadTreeView(ENTRY_POINTS, _("Select Archive File"), _("File"))
        
    def leave(self, *args):
        self.toolTipRowId = None

    def motion(self, *args):
        tvRowId = self.treeView.identify_row(args[0].y)
        if tvRowId != self.toolTipRowId:
            text = None
            if self.openType in (ARCHIVE, DISCLOSURE_SYSTEM, PLUGIN, PACKAGE):
                self.toolTipRowId = tvRowId
                if tvRowId and len(tvRowId) > 4:
                    try:
                        text = self.filenames[ int(tvRowId[4:]) ]
                        if isinstance(text, tuple):
                            text = (text[1] or "").replace("\\n","\n")
                    except (KeyError, ValueError):
                        pass
            elif self.openType == ENTRY_POINTS:
                try:
                    text = "{0}\n{1}".format(tvRowId, 
                             "\n".join(url[1] for url in self.taxonomyPackage["entryPoints"][tvRowId]))
                except KeyError:
                    pass
            self.setToolTip(text)
                
    def setToolTip(self, text):
        self.toolTip._hide()
        if text:
            self.toolTipText.set(text)
            self.toolTip.configure(state="normal")
            self.toolTip._schedule()
        else:
            self.toolTipText.set("")
            self.toolTip.configure(state="disabled")
Exemple #19
0
def main():
    """
    основной метод - создание графического интерфейса TKinter
    :return:
    """
    global params
    window = Tk()
    window.title("Отражение в параболическом зеркале")
    window.geometry('500x400')
    canv = Frame(window)
    setup = LabelFrame(window, text='Настройки', width=450, height=150)
    c = Canvas(canv, width=450, height=230, bg='black')
    c.pack(side=TOP, padx=10)

    setup1 = Frame(setup)
    butFrame = Frame(setup1)

    scal = Scale(setup1,
                 orient=HORIZONTAL,
                 length=200,
                 from_=0.002,
                 to=0.01,
                 tickinterval=0.002,
                 resolution=0.002)
    scal.set(0.002)
    scal.pack(side=TOP, pady=(0, 10), padx=(10, 10))
    scal.bind("<ButtonRelease-1>",
              lambda event, draw_canv=c: redraw(event, draw_canv))

    Button(butFrame, text='Очистить', width=12,
           command=lambda event=None, draw_canv=c, flag=True: redraw(event, draw_canv,
                                                                     setarrow=flag)) \
        .pack(side=LEFT, padx=(10, 5), pady=(5, 10))
    Button(butFrame,
           text='Закрыть',
           width=12,
           command=lambda flag=0: sys.exit(flag)).pack(side=LEFT,
                                                       padx=(5, 10),
                                                       pady=(5, 10))

    butFrame.pack(side=TOP)

    setup1.pack(side=LEFT)

    columns = ('#1', '#2')
    params = Treeview(setup, show='headings', columns=columns)
    params.heading('#1', text='Параметр')
    params.heading('#2', text='Значение')
    params.column('#1', width=100, minwidth=50, stretch=NO, anchor=N)
    params.column('#2', width=100, minwidth=50, stretch=NO, anchor=N)
    params.pack(side=LEFT, padx=(5, 10), pady=(0, 10))

    canv.pack(side=TOP, pady=(10, 10))
    setup.pack(side=TOP, pady=(0, 10), padx=(25, 25))

    draw_parabola(c)

    window.bind('<Button-1>', press)
    window.bind('<ButtonRelease-1>',
                lambda event, draw_canv=c: release(event, draw_canv))
    window.mainloop()
class IncomeGUI(Frame):   
    inDB = incomeDB()

    def createIncome(self):
        addIncome = Button(self, text="Add income", command=lambda: self.sequence(self.addMonth))
        addIncome.pack(fill=X, padx=10, pady=20)

        incomeButton = Button(self, text="View income", command =lambda: self.sequence(self.viewIncome))
        incomeButton.pack(fill=X, padx=10, pady=5)

        backButton = Button(self, text="Back")
        backButton.pack(side=BOTTOM)

    def addMonth(self):
        monthlabel = Label(self, text = "Select Month: ")
        monthlabel.pack()
        self.monthChoice = IntVar(self)
        months = self.numberings(1, 12)
        self.monthChoice.set(1) 
        self.monthInput = OptionMenu(self, self.monthChoice, *months)
        self.monthInput.pack()
        yearlabel = Label(self, text = "Select Year: ")
        yearlabel.pack()
        self.yearChoice = IntVar(self)
        years = self.numberings(2000, 2020)
        self.yearChoice.set(2000) 
        self.yearInput = OptionMenu(self, self.yearChoice, *years)
        self.yearInput.pack()
        

        nextButton = Button(self, text="Next", command=lambda: self.sequence(self.addIncome))
        nextButton.pack()
        backButton = Button(self, text="Back", command=lambda: self.sequence(
            self.createIncome))
        backButton.pack()

    def addIncome(self):
        month = self.monthChoice.get()
        self.income = income(month)
        self.income.year = self.yearChoice.get()

        amountlabel = Label(self, text="Amount of items sold this month: ")
        amountlabel.pack()
        self.amountinput = Entry(self)
        self.amountinput.pack()

        incomelabel = Label(self, text="Income earned: ")
        incomelabel.pack()
        self.incomeinput = Entry(self)
        self.incomeinput.pack()

        nextButton = Button(self, text="Next",
                            command= self.saveDetails)
        nextButton.pack()
        backButton = Button(self, text="Back", command=lambda: self.sequence(
            self.createIncome))
        backButton.pack()

    def saveDetails(self):
        self.income.amount = self.amountinput.get()
        self.income.income = self.incomeinput.get()
        self.sequence(self.confirmation)

    def confirmation(self):

        year = Label(self, text="Year: ")
        year.pack()
        yearin = Label(self, text=self.income.year)
        yearin.pack()

        month = Label(self, text="Month: ")
        month.pack()
        monthin = Label(self, text=self.income.month)
        monthin.pack()

        quantity = Label(self, text="Amount of items sold this month: ")
        quantity.pack()
        itemQuantity = Label(self, text=self.income.amount)
        itemQuantity.pack()

        price = Label(self, text="Income earned: ")
        price.pack()
        itemPrice = Label(self, text=self.income.income)
        itemPrice.pack()        

        nextButton = Button(self, text="Next",
                            command=lambda: self.sequence(self.addToIncomeDatabase))
        nextButton.pack()
        backButton = Button(self, text="Back", command=lambda: self.sequence(
            self.createIncome))
        backButton.pack()

    def addToIncomeDatabase(self):
        self.incomeDB.insertIntoDB(self.income)

        addedMessage = Message(self, text = "Added to database!")
        addedMessage.pack()

        endSessionButton = Button(self, text = "End Session", command=lambda: self.sequence(self.createIncome))
        endSessionButton.pack()

    def viewIncome(self):
        self.tree = Treeview(height="20", columns=("Year", "Month", "Income"))
        self.tree.pack()
        self.tree.heading('#1', text = "Year", anchor = CENTER)
        self.tree.heading('#2', text = "Month", anchor = CENTER)
        self.tree.heading('#3', text = "Income", anchor = CENTER)
        self.tree.column('#1', minwidth=0, width = 100)
        self.tree.column('#2', minwidth=0, width = 100)
        self.tree.column('#3', minwidth=0, width = 100)
        self.tree.column('#0', minwidth=0, width = 0)

        for row in (self.incomeDB.getInfo()):
            year = row[1]
            month = row[0]
            income = row[3]

            self.tree.insert("", "end", values = (year,month,income))

        backButton = Button(self, text="Back", command=lambda: self.sequence(
            self.createIncome))
        backButton.pack()
        

    def sequence(self, funct):
        for child in self.winfo_children():
            child.destroy()
        funct()

    def numberings(self, first, last):
        num = range(first, last + 1)
        return num

    def __init__(self, master=None):
        Frame.__init__(self, master)
        self.pack()
        self.createIncome()
        self.incomeDB = incomeDB()
        #self.incomeDB.createDB()
        self.master.title("Income")
class DialogPluginManager(Toplevel):
    def __init__(self, mainWin, modulesWithNewerFileDates):
        super(DialogPluginManager, self).__init__(mainWin.parent)

        self.ENABLE = _("Enable")
        self.DISABLE = _("Disable")
        self.parent = mainWin.parent
        self.cntlr = mainWin

        # copy plugins for temporary display
        self.pluginConfig = PluginManager.pluginConfig
        self.pluginConfigChanged = False
        self.uiClassMethodsChanged = False
        self.modelClassesChanged = False
        self.disclosureSystemTypesChanged = False
        self.modulesWithNewerFileDates = modulesWithNewerFileDates

        parentGeometry = re.match("(\d+)x(\d+)[+]?([-]?\d+)[+]?([-]?\d+)",
                                  self.parent.geometry())
        dialogX = int(parentGeometry.group(3))
        dialogY = int(parentGeometry.group(4))

        self.title(_("Plug-in Manager"))
        frame = Frame(self)

        # left button frame
        buttonFrame = Frame(frame, width=40)
        buttonFrame.columnconfigure(0, weight=1)
        addLabel = Label(buttonFrame,
                         text=_("Find plug-in modules:"),
                         wraplength=60,
                         justify="center")
        addLocalButton = Button(buttonFrame,
                                text=_("Locally"),
                                command=self.findLocally)
        ToolTip(
            addLocalButton,
            text=
            _("File chooser allows selecting python module files to add (or reload) plug-ins, from the local file system."
              ),
            wraplength=240)
        addWebButton = Button(buttonFrame,
                              text=_("On Web"),
                              command=self.findOnWeb)
        ToolTip(
            addWebButton,
            text=
            _("Dialog to enter URL full path to load (or reload) plug-ins, from the web or local file system."
              ),
            wraplength=240)
        addLabel.grid(row=0, column=0, pady=4)
        addLocalButton.grid(row=1, column=0, pady=4)
        addWebButton.grid(row=2, column=0, pady=4)
        buttonFrame.grid(row=0,
                         column=0,
                         rowspan=2,
                         sticky=(N, S, W),
                         padx=3,
                         pady=3)

        # right tree frame (plugins already known to arelle)
        modulesFrame = Frame(frame, width=700)
        vScrollbar = Scrollbar(modulesFrame, orient=VERTICAL)
        hScrollbar = Scrollbar(modulesFrame, orient=HORIZONTAL)
        self.modulesView = Treeview(modulesFrame,
                                    xscrollcommand=hScrollbar.set,
                                    yscrollcommand=vScrollbar.set,
                                    height=7)
        self.modulesView.grid(row=0, column=0, sticky=(N, S, E, W))
        self.modulesView.bind('<<TreeviewSelect>>', self.moduleSelect)
        hScrollbar["command"] = self.modulesView.xview
        hScrollbar.grid(row=1, column=0, sticky=(E, W))
        vScrollbar["command"] = self.modulesView.yview
        vScrollbar.grid(row=0, column=1, sticky=(N, S))
        modulesFrame.columnconfigure(0, weight=1)
        modulesFrame.rowconfigure(0, weight=1)
        modulesFrame.grid(row=0,
                          column=1,
                          columnspan=4,
                          sticky=(N, S, E, W),
                          padx=3,
                          pady=3)
        self.modulesView.focus_set()

        self.modulesView.column("#0", width=120, anchor="w")
        self.modulesView.heading("#0", text=_("Name"))
        self.modulesView["columns"] = ("author", "ver", "status", "date",
                                       "update", "descr", "license")
        self.modulesView.column("author", width=100, anchor="w", stretch=False)
        self.modulesView.heading("author", text=_("Author"))
        self.modulesView.column("ver", width=50, anchor="w", stretch=False)
        self.modulesView.heading("ver", text=_("Version"))
        self.modulesView.column("status", width=50, anchor="w", stretch=False)
        self.modulesView.heading("status", text=_("Status"))
        self.modulesView.column("date", width=70, anchor="w", stretch=False)
        self.modulesView.heading("date", text=_("File Date"))
        self.modulesView.column("update", width=50, anchor="w", stretch=False)
        self.modulesView.heading("update", text=_("Update"))
        self.modulesView.column("descr", width=200, anchor="w", stretch=False)
        self.modulesView.heading("descr", text=_("Description"))
        self.modulesView.column("license", width=70, anchor="w", stretch=False)
        self.modulesView.heading("license", text=_("License"))

        classesFrame = Frame(frame)
        vScrollbar = Scrollbar(classesFrame, orient=VERTICAL)
        hScrollbar = Scrollbar(classesFrame, orient=HORIZONTAL)
        self.classesView = Treeview(classesFrame,
                                    xscrollcommand=hScrollbar.set,
                                    yscrollcommand=vScrollbar.set,
                                    height=5)
        self.classesView.grid(row=0, column=0, sticky=(N, S, E, W))
        hScrollbar["command"] = self.classesView.xview
        hScrollbar.grid(row=1, column=0, sticky=(E, W))
        vScrollbar["command"] = self.classesView.yview
        vScrollbar.grid(row=0, column=1, sticky=(N, S))
        classesFrame.columnconfigure(0, weight=1)
        classesFrame.rowconfigure(0, weight=1)
        classesFrame.grid(row=1,
                          column=1,
                          columnspan=4,
                          sticky=(N, S, E, W),
                          padx=3,
                          pady=3)
        self.classesView.focus_set()

        self.classesView.column("#0", width=200, anchor="w")
        self.classesView.heading("#0", text=_("Class"))
        self.classesView["columns"] = ("modules", )
        self.classesView.column("modules",
                                width=500,
                                anchor="w",
                                stretch=False)
        self.classesView.heading("modules", text=_("Modules"))

        # bottom frame module info details
        moduleInfoFrame = Frame(frame, width=700)
        moduleInfoFrame.columnconfigure(1, weight=1)

        self.moduleNameLabel = Label(moduleInfoFrame,
                                     wraplength=600,
                                     justify="left",
                                     font=font.Font(family='Helvetica',
                                                    size=12,
                                                    weight='bold'))
        self.moduleNameLabel.grid(row=0, column=0, columnspan=4, sticky=W)
        self.moduleAuthorHdr = Label(moduleInfoFrame,
                                     text=_("author:"),
                                     state=DISABLED)
        self.moduleAuthorHdr.grid(row=1, column=0, sticky=W)
        self.moduleAuthorLabel = Label(moduleInfoFrame,
                                       wraplength=600,
                                       justify="left")
        self.moduleAuthorLabel.grid(row=1, column=1, columnspan=3, sticky=W)
        self.moduleDescrHdr = Label(moduleInfoFrame,
                                    text=_("description:"),
                                    state=DISABLED)
        self.moduleDescrHdr.grid(row=2, column=0, sticky=W)
        self.moduleDescrLabel = Label(moduleInfoFrame,
                                      wraplength=600,
                                      justify="left")
        self.moduleDescrLabel.grid(row=2, column=1, columnspan=3, sticky=W)
        self.moduleClassesHdr = Label(moduleInfoFrame,
                                      text=_("classes:"),
                                      state=DISABLED)
        self.moduleClassesHdr.grid(row=3, column=0, sticky=W)
        self.moduleClassesLabel = Label(moduleInfoFrame,
                                        wraplength=600,
                                        justify="left")
        self.moduleClassesLabel.grid(row=3, column=1, columnspan=3, sticky=W)
        ToolTip(self.moduleClassesLabel,
                text=_("List of classes that this plug-in handles."),
                wraplength=240)
        self.moduleUrlHdr = Label(moduleInfoFrame,
                                  text=_("URL:"),
                                  state=DISABLED)
        self.moduleUrlHdr.grid(row=4, column=0, sticky=W)
        self.moduleUrlLabel = Label(moduleInfoFrame,
                                    wraplength=600,
                                    justify="left")
        self.moduleUrlLabel.grid(row=4, column=1, columnspan=3, sticky=W)
        ToolTip(
            self.moduleUrlLabel,
            text=_(
                "URL of plug-in module (local file path or web loaded file)."),
            wraplength=240)
        self.moduleDateHdr = Label(moduleInfoFrame,
                                   text=_("date:"),
                                   state=DISABLED)
        self.moduleDateHdr.grid(row=5, column=0, sticky=W)
        self.moduleDateLabel = Label(moduleInfoFrame,
                                     wraplength=600,
                                     justify="left")
        self.moduleDateLabel.grid(row=5, column=1, columnspan=3, sticky=W)
        ToolTip(
            self.moduleDateLabel,
            text=
            _("Date of currently loaded module file (with parenthetical node when an update is available)."
              ),
            wraplength=240)
        self.moduleLicenseHdr = Label(moduleInfoFrame,
                                      text=_("license:"),
                                      state=DISABLED)
        self.moduleLicenseHdr.grid(row=6, column=0, sticky=W)
        self.moduleLicenseLabel = Label(moduleInfoFrame,
                                        wraplength=600,
                                        justify="left")
        self.moduleLicenseLabel.grid(row=6, column=1, columnspan=3, sticky=W)
        self.moduleImportsHdr = Label(moduleInfoFrame,
                                      text=_("imports:"),
                                      state=DISABLED)
        self.moduleImportsHdr.grid(row=7, column=0, sticky=W)
        self.moduleImportsLabel = Label(moduleInfoFrame,
                                        wraplength=600,
                                        justify="left")
        self.moduleImportsLabel.grid(row=7, column=1, columnspan=3, sticky=W)
        self.moduleEnableButton = Button(moduleInfoFrame,
                                         text=self.ENABLE,
                                         state=DISABLED,
                                         command=self.moduleEnable)
        ToolTip(self.moduleEnableButton,
                text=_("Enable/disable plug in."),
                wraplength=240)
        self.moduleEnableButton.grid(row=8, column=1, sticky=E)
        self.moduleReloadButton = Button(moduleInfoFrame,
                                         text=_("Reload"),
                                         state=DISABLED,
                                         command=self.moduleReload)
        ToolTip(self.moduleReloadButton,
                text=_("Reload/update plug in."),
                wraplength=240)
        self.moduleReloadButton.grid(row=8, column=2, sticky=E)
        self.moduleRemoveButton = Button(moduleInfoFrame,
                                         text=_("Remove"),
                                         state=DISABLED,
                                         command=self.moduleRemove)
        ToolTip(
            self.moduleRemoveButton,
            text=
            _("Remove plug in from plug in table (does not erase the plug in's file)."
              ),
            wraplength=240)
        self.moduleRemoveButton.grid(row=8, column=3, sticky=E)
        moduleInfoFrame.grid(row=2,
                             column=0,
                             columnspan=5,
                             sticky=(N, S, E, W),
                             padx=3,
                             pady=3)
        moduleInfoFrame.config(borderwidth=4, relief="groove")

        okButton = Button(frame, text=_("Close"), command=self.ok)
        ToolTip(okButton,
                text=_("Accept and changes (if any) and close dialog."),
                wraplength=240)
        cancelButton = Button(frame, text=_("Cancel"), command=self.close)
        ToolTip(cancelButton,
                text=_("Cancel changes (if any) and close dialog."),
                wraplength=240)
        okButton.grid(row=3, column=3, sticky=(S, E), pady=3)
        cancelButton.grid(row=3, column=4, sticky=(S, E), pady=3, padx=3)

        enableDisableFrame = Frame(frame)
        enableDisableFrame.grid(row=3, column=1, sticky=(S, W), pady=3)
        enableAllButton = Button(enableDisableFrame,
                                 text=_("Enable All"),
                                 command=self.enableAll)
        ToolTip(enableAllButton,
                text=_("Enable all plug ins."),
                wraplength=240)
        disableAllButton = Button(enableDisableFrame,
                                  text=_("Disable All"),
                                  command=self.disableAll)
        ToolTip(disableAllButton,
                text=_("Disable all plug ins."),
                wraplength=240)
        enableAllButton.grid(row=1, column=1)
        disableAllButton.grid(row=1, column=2)

        self.loadTreeViews()

        self.geometry("+{0}+{1}".format(dialogX + 50, dialogY + 100))
        frame.grid(row=0, column=0, sticky=(N, S, E, W))
        frame.columnconfigure(0, weight=0)
        frame.columnconfigure(1, weight=1)
        frame.rowconfigure(0, weight=1)
        window = self.winfo_toplevel()
        window.columnconfigure(0, weight=1)
        window.rowconfigure(0, weight=1)

        self.bind("<Return>", self.ok)
        self.bind("<Escape>", self.close)

        self.protocol("WM_DELETE_WINDOW", self.close)
        self.grab_set()
        self.wait_window(self)

    def loadTreeViews(self):
        self.selectedModule = None

        # clear previous treeview entries
        for previousNode in self.modulesView.get_children(""):
            self.modulesView.delete(previousNode)

        def loadSubtree(parentNode, moduleItems):
            for moduleItem in sorted(moduleItems, key=lambda item: item[0]):
                moduleInfo = moduleItem[1]
                if parentNode or not moduleInfo.get("isImported"):
                    name = moduleInfo.get("name", moduleItem[0])
                    node = self.modulesView.insert(parentNode,
                                                   "end",
                                                   name,
                                                   text=name)
                    self.modulesView.set(node, "author",
                                         moduleInfo.get("author"))
                    self.modulesView.set(node, "ver",
                                         moduleInfo.get("version"))
                    self.modulesView.set(node, "status",
                                         moduleInfo.get("status"))
                    self.modulesView.set(node, "date",
                                         moduleInfo.get("fileDate"))
                    if name in self.modulesWithNewerFileDates:
                        self.modulesView.set(node, "update", _("available"))
                    self.modulesView.set(node, "descr",
                                         moduleInfo.get("description"))
                    self.modulesView.set(node, "license",
                                         moduleInfo.get("license"))
                    if moduleInfo.get("imports"):
                        loadSubtree(
                            node,
                            [(importModuleInfo["name"], importModuleInfo)
                             for importModuleInfo in moduleInfo["imports"]])

        loadSubtree("", self.pluginConfig.get("modules", {}).items())

        # clear previous treeview entries
        for previousNode in self.classesView.get_children(""):
            self.classesView.delete(previousNode)

        for i, classItem in enumerate(
                sorted(self.pluginConfig.get("classes", {}).items())):
            className, moduleList = classItem
            node = self.classesView.insert("",
                                           "end",
                                           className,
                                           text=className)
            self.classesView.set(node, "modules", ', '.join(moduleList))

        self.moduleSelect()  # clear out prior selection

    def ok(self, event=None):
        if self.pluginConfigChanged:
            PluginManager.pluginConfig = self.pluginConfig
            PluginManager.pluginConfigChanged = True
            PluginManager.reset()  # force reloading of modules
        if self.uiClassMethodsChanged or self.modelClassesChanged or self.disclosureSystemTypesChanged:  # may require reloading UI
            affectedItems = ""
            if self.uiClassMethodsChanged:
                affectedItems += _("menus of the user interface")
            if self.modelClassesChanged:
                if self.uiClassMethodsChanged:
                    affectedItems += _(" and ")
                affectedItems += _("model objects of the processor")
            if (self.uiClassMethodsChanged or self.modelClassesChanged):
                affectedItems += _(" and ")
            if self.disclosureSystemTypesChanged:
                if (self.uiClassMethodsChanged or self.modelClassesChanged):
                    affectedItems += _(" and ")
                affectedItems += _("disclosure system types")
            if messagebox.askyesno(
                    _("User interface plug-in change"),
                    _("A change in plug-in class methods may have affected {0}.  "
                      "Please restart Arelle to due to these changes.  \n\n"
                      "Should Arelle restart itself now "
                      "(if there are any unsaved changes they would be lost!)?"
                      ).format(affectedItems),
                    parent=self):
                self.cntlr.uiThreadQueue.put((self.cntlr.quit, [None, True]))
        self.close()

    def close(self, event=None):
        self.parent.focus_set()
        self.destroy()

    def moduleSelect(self, *args):
        node = (self.modulesView.selection() or (None, ))[0]
        moduleInfo = self.pluginConfig.get("modules", {}).get(node)
        if moduleInfo:
            self.selectedModule = node
            name = moduleInfo["name"]
            self.moduleNameLabel.config(text=name)
            self.moduleAuthorHdr.config(state=ACTIVE)
            self.moduleAuthorLabel.config(text=moduleInfo["author"])
            self.moduleDescrHdr.config(state=ACTIVE)
            self.moduleDescrLabel.config(text=moduleInfo["description"])
            self.moduleClassesHdr.config(state=ACTIVE)
            self.moduleClassesLabel.config(
                text=', '.join(moduleInfo["classMethods"]))
            self.moduleUrlHdr.config(state=ACTIVE)
            self.moduleUrlLabel.config(text=moduleInfo["moduleURL"])
            self.moduleDateHdr.config(state=ACTIVE)
            self.moduleDateLabel.config(
                text=moduleInfo["fileDate"] + " " +
                (_("(an update is available)") if name in
                 self.modulesWithNewerFileDates else ""))
            self.moduleLicenseHdr.config(state=ACTIVE)
            self.moduleLicenseLabel.config(text=moduleInfo["license"])
            if moduleInfo.get("imports"):
                self.moduleImportsHdr.config(state=ACTIVE)
                _text = ", ".join(mi["name"]
                                  for mi in moduleInfo["imports"][:3])
                if len(moduleInfo["imports"]) >= 3:
                    _text += ", ..."
                self.moduleImportsLabel.config(text=_text)
            _buttonState = DISABLED if moduleInfo.get("isImported") else ACTIVE
            self.moduleEnableButton.config(state=_buttonState,
                                           text={
                                               "enabled": self.DISABLE,
                                               "disabled": self.ENABLE
                                           }[moduleInfo["status"]])
            self.moduleReloadButton.config(state=_buttonState)
            self.moduleRemoveButton.config(state=_buttonState)
        else:
            self.selectedModule = None
            self.moduleNameLabel.config(text="")
            self.moduleAuthorHdr.config(state=DISABLED)
            self.moduleAuthorLabel.config(text="")
            self.moduleDescrHdr.config(state=DISABLED)
            self.moduleDescrLabel.config(text="")
            self.moduleClassesHdr.config(state=DISABLED)
            self.moduleClassesLabel.config(text="")
            self.moduleUrlHdr.config(state=DISABLED)
            self.moduleUrlLabel.config(text="")
            self.moduleDateHdr.config(state=DISABLED)
            self.moduleDateLabel.config(text="")
            self.moduleLicenseHdr.config(state=DISABLED)
            self.moduleLicenseLabel.config(text="")
            self.moduleImportsHdr.config(state=DISABLED)
            self.moduleImportsLabel.config(text="")
            self.moduleEnableButton.config(state=DISABLED, text=self.ENABLE)
            self.moduleReloadButton.config(state=DISABLED)
            self.moduleRemoveButton.config(state=DISABLED)

    def findLocally(self):
        initialdir = self.cntlr.pluginDir  # default plugin directory
        if not self.cntlr.isMac:  # can't navigate within app easily, always start in default directory
            initialdir = self.cntlr.config.setdefault("pluginOpenDir",
                                                      initialdir)
        filename = self.cntlr.uiFileDialog(
            "open",
            parent=self,
            title=_("Choose plug-in module file"),
            initialdir=initialdir,
            filetypes=[(_("Python files"), "*.py")],
            defaultextension=".py")
        if filename:
            # check if a package is selected (any file in a directory containing an __init__.py
            #if (os.path.basename(filename) == "__init__.py" and os.path.isdir(os.path.dirname(filename)) and
            #    os.path.isfile(filename)):
            #    filename = os.path.dirname(filename) # refer to the package instead
            self.cntlr.config["pluginOpenDir"] = os.path.dirname(filename)
            moduleInfo = PluginManager.moduleModuleInfo(filename)
            self.loadFoundModuleInfo(moduleInfo, filename)

    def findOnWeb(self):
        url = DialogURL.askURL(self)
        if url:  # url is the in-cache or local file
            moduleInfo = PluginManager.moduleModuleInfo(url)
            self.cntlr.showStatus("")  # clear web loading status
            self.loadFoundModuleInfo(moduleInfo, url)

    def loadFoundModuleInfo(self, moduleInfo, url):
        if moduleInfo and moduleInfo.get("name"):
            self.addPluginConfigModuleInfo(moduleInfo)
            self.loadTreeViews()
        else:
            messagebox.showwarning(
                _("Module is not itself a plug-in or in a directory with package __init__.py plug-in.  "
                  ),
                _("File does not itself contain a python program with an appropriate __pluginInfo__ declaration: \n\n{0}"
                  ).format(url),
                parent=self)

    def checkIfImported(self, moduleInfo):
        if moduleInfo.get("isImported"):
            messagebox.showwarning(
                _("Plug-in is imported by a parent plug-in.  "),
                _("Plug-in has a parent, please request operation on the parent: \n\n{0}"
                  ).format(moduleInfo.get("name")),
                parent=self)
            return True
        return False

    def removePluginConfigModuleInfo(self, name):
        moduleInfo = self.pluginConfig["modules"].get(name)
        if moduleInfo:
            if self.checkIfImported(moduleInfo):
                return

            def _removePluginConfigModuleInfo(moduleInfo):
                _name = moduleInfo.get("name")
                if _name:
                    for classMethod in moduleInfo["classMethods"]:
                        classMethods = self.pluginConfig["classes"].get(
                            classMethod)
                        if classMethods and _name in classMethods:
                            classMethods.remove(_name)
                            if not classMethods:  # list has become unused
                                del self.pluginConfig["classes"][
                                    classMethod]  # remove class
                            if classMethod.startswith("CntlrWinMain.Menu"):
                                self.uiClassMethodsChanged = True  # may require reloading UI
                            elif classMethod == "ModelObjectFactory.ElementSubstitutionClasses":
                                self.modelClassesChanged = True  # model object factor classes changed
                            elif classMethod == "DisclosureSystem.Types":
                                self.disclosureSystemTypesChanged = True  # disclosure system types changed
                    for importModuleInfo in moduleInfo.get(
                            "imports", EMPTYLIST):
                        _removePluginConfigModuleInfo(importModuleInfo)
                    del self.pluginConfig["modules"][_name]

            _removePluginConfigModuleInfo(moduleInfo)
            self.pluginConfigChanged = True

    def addPluginConfigModuleInfo(self, moduleInfo):
        if self.checkIfImported(moduleInfo):
            return
        name = moduleInfo.get("name")
        self.removePluginConfigModuleInfo(
            name)  # remove any prior entry for this module

        def _addPlugin(moduleInfo):
            _name = moduleInfo.get("name")
            if _name:
                self.modulesWithNewerFileDates.discard(
                    _name)  # no longer has an update available
                self.pluginConfig["modules"][_name] = moduleInfo
                # add classes
                for classMethod in moduleInfo["classMethods"]:
                    classMethods = self.pluginConfig["classes"].setdefault(
                        classMethod, [])
                    if name not in classMethods:
                        classMethods.append(_name)
                    if classMethod.startswith("CntlrWinMain.Menu"):
                        self.uiClassMethodsChanged = True  # may require reloading UI
                    elif classMethod == "ModelObjectFactory.ElementSubstitutionClasses":
                        self.modelClassesChanged = True  # model object factor classes changed
                    elif classMethod == "DisclosureSystem.Types":
                        self.disclosureSystemTypesChanged = True  # disclosure system types changed
            for importModuleInfo in moduleInfo.get("imports", EMPTYLIST):
                _addPlugin(importModuleInfo)

        _addPlugin(moduleInfo)
        self.pluginConfigChanged = True

    def moduleEnable(self):
        if self.selectedModule in self.pluginConfig["modules"]:
            moduleInfo = self.pluginConfig["modules"][self.selectedModule]
            if self.checkIfImported(moduleInfo):
                return

            def _moduleEnable(moduleInfo):
                if self.moduleEnableButton['text'] == self.ENABLE:
                    moduleInfo["status"] = "enabled"
                elif self.moduleEnableButton['text'] == self.DISABLE:
                    moduleInfo["status"] = "disabled"
                for importModuleInfo in moduleInfo.get("imports", EMPTYLIST):
                    _moduleEnable(importModuleInfo)

            _moduleEnable(moduleInfo)
            if self.moduleEnableButton['text'] == self.ENABLE:
                self.moduleEnableButton['text'] = self.DISABLE
            elif self.moduleEnableButton['text'] == self.DISABLE:
                self.moduleEnableButton['text'] = self.ENABLE
            self.pluginConfigChanged = True
            self.loadTreeViews()

    def moduleReload(self):
        if self.selectedModule in self.pluginConfig["modules"]:
            url = self.pluginConfig["modules"][self.selectedModule].get(
                "moduleURL")
            if url:
                moduleInfo = PluginManager.moduleModuleInfo(url, reload=True)
                if moduleInfo:
                    if self.checkIfImported(moduleInfo):
                        return
                    self.addPluginConfigModuleInfo(moduleInfo)
                    self.loadTreeViews()
                    self.cntlr.showStatus(_("{0} reloaded").format(
                        moduleInfo["name"]),
                                          clearAfter=5000)
                else:
                    messagebox.showwarning(
                        _("Module error"),
                        _("File or module cannot be reloaded: \n\n{0}").format(
                            url),
                        parent=self)

    def moduleRemove(self):
        if self.selectedModule in self.pluginConfig["modules"]:
            self.removePluginConfigModuleInfo(self.selectedModule)
            self.pluginConfigChanged = True
            self.loadTreeViews()

    def enableAll(self):
        self.enableDisableAll(True)

    def disableAll(self):
        self.enableDisableAll(False)

    def enableDisableAll(self, doEnable):
        for module in self.pluginConfig["modules"]:
            if not module.get("isImported"):
                moduleInfo = self.pluginConfig["modules"][module]

                def _enableDisableAll(moduleInfo):
                    if doEnable:
                        moduleInfo["status"] = "enabled"
                    else:
                        moduleInfo["status"] = "disabled"
                    for importModuleInfo in moduleInfo.get(
                            "imports", EMPTYLIST):
                        _enableDisableAll(importModuleInfo)

                _enableDisableAll(moduleInfo)
                if doEnable:
                    self.moduleEnableButton['text'] = self.DISABLE
                else:
                    self.moduleEnableButton['text'] = self.ENABLE
        self.pluginConfigChanged = True
        self.loadTreeViews()
def customer_homePage(phno2):
    def customer_analysis():
        print(phno2.get())

        def get_selected_date(selection):
            selected_date = selection
            print(selected_date)

        rootan = Tk()
        rootan.geometry("940x610+100+50")
        rootan.title("Customer Analysis")
        rootan.config(bg="#4fc3f7")
        selected_date = StringVar(rootan)

        x = []
        y = []
        a = []
        b = []

        analysislabel = Label(rootan,
                              text="Customer Analysis",
                              font=("Lobster Two", 20, "bold"),
                              fg="#ffffff",
                              bg="#4fc3f7")
        analysislabel.pack()

        g1 = con.cursor()
        g1.execute(
            "select pcategory as purchased from inventory,sales where inventory.pid = sales.pid and cmobnum = ? GROUP by pcategory;",
            (phno2.get(), ))
        fetch = g1.fetchall()

        for data in fetch:
            x.extend(data)

        g2 = con.cursor()
        g2.execute(
            "select count(sales.pid) as purchased from inventory,sales where inventory.pid = sales.pid and cmobnum = ? GROUP by pcategory;",
            (phno2.get(), ))
        fet = g2.fetchall()

        for dat in fet:
            y.extend(dat)

        fig = Figure(figsize=(5, 3), dpi=80)
        fig.suptitle('Category - wise', fontsize=16)
        axes = fig.add_subplot(111)
        axes.plot(x, y)

        canvas = FigureCanvasTkAgg(fig, rootan)
        canvas.get_tk_widget().place(x=20, y=350)
        fig.set_facecolor("#81d4fa")

        c = con.cursor()
        top = c.execute(
            "select pname,pcategory,count(pname) from inventory,sales where inventory.pid = sales.pid and cmobnum = ? group by pname order by count(pname) DESC LIMIT 5;",
            (phno2.get(), ))
        fetc = c.fetchall()

        top5 = Label(rootan,
                     text="Most recently bought :",
                     font=("Oxygen", 16, "bold"),
                     fg="#212121",
                     bg="#4fc3f7")
        top5.place(x=650, y=100)

        tree = Treeview(rootan, columns=('pname', 'pcategory', 'count(pname)'))
        tree.heading('pname', text='Product Name')
        tree.heading('pcategory', text='Category')
        tree.heading('count(pname)', text='Purchased count')
        tree.column("pname", width=90)
        tree.column("pcategory", width=90)
        tree.column("count(pname)", width=90)
        tree.place(x=650, y=150)
        tree['show'] = 'headings'

        for data in fetc:
            tree.insert('', 'end', values=(data))

        options = []

        d = con.cursor()
        d.execute("select distinct(date) from sales;")
        val = d.fetchall()

        for data in val:
            options.extend(data)

        selected_date.set(options[1])

        p = con.cursor()
        p.execute(
            """select sum(pprice) from inventory,sales where sales.pid = inventory.pid and cmobnum = ? group by strftime("%m",date) order by strftime("%m",date)""",
            (phno2.get(), ))
        fetc = p.fetchall()

        i = con.cursor()
        i.execute(
            """select distinct  strftime("%m",date) as month from sales order by month;"""
        )
        fet = i.fetchall()

        for dat in fetc:
            a.extend(dat)

        for data in fet:
            b.extend(data)

        fig2 = Figure(figsize=(5, 3), dpi=80)
        fig2.suptitle('Monthly Spendings', fontsize=16)
        axes2 = fig2.add_subplot(111)
        axes2.plot(b, a)

        canvas2 = FigureCanvasTkAgg(fig2, rootan)
        canvas2.get_tk_widget().place(x=20, y=80)
        fig2.set_facecolor("#81d4fa")

        outbtn = Button(rootan,
                        text="Back",
                        font=("Noto sans", 12, "bold"),
                        fg="#ffffff",
                        bg="#c62828",
                        relief="flat",
                        command=rootan.destroy)
        outbtn.place(x=830, y=5)

        rootan.mainloop()

    def add_sales(roots):
        roots.destroy()
        a = con.cursor()
        b = con.cursor()
        c = con.cursor()
        d = con.cursor()
        flag = 0
        for data in tree2.get_children():
            val = (tree2.item(data)["values"][0])
            a.execute("SELECT pid FROM inventory WHERE pname = ?", (val, ))
            fetch = a.fetchone()
            for x in fetch:
                d.execute("SELECT total_quantity FROM stock WHERE pid = ?",
                          (x, ))
                val = d.fetchone()
                for y in val:
                    print(y)
                    if (y >= 1):
                        b.execute(
                            "INSERT INTO sales(cmobnum,pid,date) VALUES (?,?,?)",
                            (
                                phno2.get(),
                                x,
                                datetime.date(datetime.now()),
                            ))
                        c.execute(
                            "UPDATE stock SET total_quantity = total_quantity -1 WHERE pid = ?",
                            (x, ))
                        flag = flag + 1
                    else:
                        messagebox.showerror("Error", "Stock Empty!")

        if flag > 0:
            messagebox.showinfo("Success", "Item Purchased")
        # charge()
        con.commit()

    def submit(tree2):
        roots = Tk()
        roots.geometry("920x570+100+50")
        roots.title("Billing")
        roots.config(bg="#ffe0b2")

        c = con.cursor()

        s = 0
        for child in tree2.get_children():
            s = s + tree2.item(child)["values"][1]
        totalSum.set(s)

        navbar2 = Frame(roots, bg="#212121", height=50, width=920)
        navbar2.place(x=0, y=0)

        outbtn = Button(navbar2,
                        text="Back",
                        font=("Noto sans", 12, "bold"),
                        fg="#ffffff",
                        bg="#c62828",
                        relief="flat",
                        command=roots.destroy)
        outbtn.place(x=830, y=5)

        tree3 = Treeview(roots, columns=('pname', 'pprice'))
        tree3.heading('pname', text='Product Name')
        tree3.heading('pprice', text='Price')
        tree3.column("pname", width=90)
        tree3.column("pprice", width=90)
        tree3.pack(side=LEFT, anchor=N, fill='x', expand=TRUE, pady=(90, 0))
        tree3['show'] = 'headings'

        for data in tree2.get_children():
            tree3.insert('', '0', values=(tree2.item(data)["values"]))

        buyButton = Button(roots,
                           text="Buy",
                           font=("Noto sans", 12, "bold"),
                           fg="#ffffff",
                           bg="#c62828",
                           relief="flat",
                           command=lambda: add_sales(roots))
        buyButton.place(x=830, y=450)

        total_label = Label(roots,
                            text="Total : ",
                            font=("Noto sans", 12, "bold"),
                            fg="#212121",
                            bg="#ffe0b2")
        total_label.place(x=200, y=400)

        total_labelVal = Label(roots,
                               text=totalSum.get(),
                               font=("Noto sans", 12, "bold"),
                               fg="#212121",
                               bg="#ffe0b2")
        total_labelVal.place(x=260, y=400)

        roots.mainloop()

    rootc = Tk()
    rootc.geometry("920x570+100+50")
    rootc.title("Home")
    rootc.config(bg="#ffe0b2")

    searchVar = StringVar(rootc)
    totalSum = IntVar(rootc)
    treeVals = []
    loginName = StringVar()
    c = con.cursor()

    navbar = Frame(rootc, bg="#212121", height=50, width=920)
    navbar.place(x=0, y=0)

    u = con.cursor()
    u.execute("SELECT cname from customer where cmobnum = ?", (phno2.get(), ))
    fe = u.fetchone()

    for x in fe:
        loginName.set(x)

    welcomeUser = Label(navbar,
                        text="Hello : ",
                        font=("Noto sans", 12, "bold"),
                        fg="#ffffff",
                        bg="#212121")
    welcomeUser.place(x=10, y=8)

    welcomeUserVal = Label(navbar,
                           text=loginName.get(),
                           font=("Oxygen", 12, "bold"),
                           fg="#ffffff",
                           bg="#212121")
    welcomeUserVal.place(x=70, y=8)

    analysisbtn = Button(navbar,
                         text="Analysis",
                         font=("Noto sans", 12, "bold"),
                         fg="#ffffff",
                         bg="#2979ff",
                         relief="flat",
                         command=lambda: customer_analysis())
    analysisbtn.place(x=260, y=5)

    outbtn = Button(navbar,
                    text="Back",
                    font=("Noto sans", 12, "bold"),
                    fg="#ffffff",
                    bg="#c62828",
                    relief="flat",
                    command=rootc.destroy)
    outbtn.place(x=830, y=5)

    def check():
        s = 0
        for child in tree2.get_children():
            s = s + tree2.item(child)["values"][1]
        totalSum.set(s)
        total_label = Label(rootc,
                            text=totalSum.get(),
                            font=("Noto sans", 12, "bold"),
                            fg="#212121",
                            bg="#ffe0b2")
        total_label.place(x=245, y=544)

    def add_name():

        x = tree.focus()
        y = tree.item(x, "values")
        tree2.insert('', '0', values=(y))

    def remove_name():
        x = tree2.selection()
        tree2.delete(x)

    def command(self, *args):
        selections = []

        for i in range(len(treeVals)):
            if searchVar.get() != "" and searchVar.get(
            ) == treeVals[i][:len(searchVar.get())]:
                selections.append(ids[i])
                print(
                    selections
                )  #if it matches it appends the id to the selections list
        tree.selection_set(selections)

    c.execute("SELECT pname,pprice FROM `inventory` ORDER BY pid ASC")
    fetch = c.fetchall()

    selection_label = Label(rootc,
                            text="Select Product To Add  ",
                            font=("Noto sans", 10, "bold"),
                            fg="#212121",
                            bg="#ffe0b2")
    selection_label.place(x=740, y=52)

    tree = Treeview(rootc, columns=('pname', 'pprice'))
    tree.heading('pname', text='Product Name')
    tree.heading('pprice', text='Price')
    tree.column("pname", width=90)
    tree.column("pprice", width=90)
    tree.pack(side=RIGHT, anchor=NE, fill='y', pady=(72, 0))
    tree['show'] = 'headings'

    searchVar.trace("w", command)
    search = Entry(rootc,
                   width=34,
                   relief="flat",
                   bg="#ffffff",
                   textvariable=searchVar,
                   font=("Oxygen", 10))
    search.insert(0, 'Quick Search')
    search.place(x=500, y=15)

    ids = []
    for data in fetch:
        ids.append(tree.insert('', 'end', values=(data)))

    for child in tree.get_children():
        treeVals.append(tree.item(child)['values'][0])

    print(ids)
    print(treeVals)

    cart_label = Label(rootc,
                       text="Your Cart : Select to remove an item ",
                       font=("Noto sans", 10, "bold"),
                       fg="#212121",
                       bg="#ffe0b2")
    cart_label.place(x=2, y=52)

    tree2 = Treeview(rootc, columns=('pname', 'pprice'))
    tree2.heading('pname', text='Product Name')
    tree2.heading('pprice', text='Price')
    tree2.column("pname", width=90)
    tree2.column("pprice", width=90)
    tree2.pack(side=LEFT, anchor=W, fill='y', pady=(72, 0))
    tree2['show'] = 'headings'

    add_button = Button(rootc,
                        text='Add',
                        font=("Oxygen", 10, "bold"),
                        fg="#ffffff",
                        bg="#0091ea",
                        relief="flat",
                        command=add_name)
    add_button.place(x=380, y=235)

    remove_button = Button(rootc,
                           text='Remove',
                           font=("Oxygen", 10, "bold"),
                           fg="#ffffff",
                           bg="#0091ea",
                           relief="flat",
                           command=remove_name)
    remove_button.place(x=428, y=235)

    check_button = Button(rootc,
                          text='Check',
                          font=("Oxygen", 10, "bold"),
                          fg="#ffffff",
                          bg="#0091ea",
                          relief="flat",
                          command=check)
    check_button.place(x=500, y=235)

    submit_button = Button(rootc,
                           text='Submit',
                           font=("Oxygen", 10, "bold"),
                           fg="#ffffff",
                           bg="#1de9b6",
                           relief="flat",
                           command=lambda: submit(tree2))
    submit_button.place(relx=0.5, rely=0.5, anchor=CENTER)

    total_label = Label(rootc,
                        text="Total : ",
                        font=("Noto sans", 12, "bold"),
                        fg="#212121",
                        bg="#ffe0b2")
    total_label.pack(side=BOTTOM, anchor=SW)

    con.commit()
    rootc.mainloop()
Exemple #23
0
scroll_x.config(command=student_table.xview)
scroll_y.config(command=student_table.yview)

student_table.heading('Id', text='Id')
student_table.heading('Name', text='Name')
student_table.heading('Mobile No.', text='Mobile No.')
student_table.heading('Email', text='Email')
student_table.heading('Address', text='Address')
student_table.heading('Gender', text='Gender')
student_table.heading('D.O.B', text='DOB')
student_table.heading('Added Date', text='Added Date')
student_table.heading('Added Time', text='Add time')

student_table['show'] = 'headings'

student_table.column('Id', width=100)
student_table.column('Name', width=200)
student_table.column('Mobile No.', width=200)
student_table.column('Email', width=300)
student_table.column('Address', width=300)
student_table.column('Gender', width=100)
student_table.column('D.O.B', width=150)
student_table.column('Added Date', width=150)
student_table.column('Added Time', width=150)

student_table.pack(fill=BOTH, expand=1)

######################################## Title and Label #################################################
ss = "Student Management System "
text = ''
count = 0
Exemple #24
0
                     bd=2,
                     bg='#C4DCCE',
                     font=('bold', 20)).place(x=14, y=102)
sub_frameEt = LabelFrame(FrameEt,
                         width=632,
                         height=556,
                         bd=2,
                         font=('bold', 20)).place(x=23, y=130)
tv_et = Treeview(sub_frameEt,
                 columns=(1, 2, 3, 4, 5),
                 show='headings',
                 height=12)
tv_et.place(x=56, y=400)

tv_et.heading(1, text='id étudinat')
tv_et.column(1, anchor='center', width=90)

tv_et.heading(2, text='nom')
tv_et.column(2, anchor='center', width=120)

tv_et.heading(3, text='prénom')
tv_et.column(3, anchor='center', width=120)

tv_et.heading(4, text='age')
tv_et.column(4, anchor='center', width=95)

tv_et.heading(5, text='filière')
tv_et.column(5, anchor='center', width=125)

scroll_et = Scrollbar(sub_frameEt, orient=VERTICAL, command=tv_et.yview)
tv_et.configure(yscroll=scroll_et.set)
Exemple #25
0
def calender(w):
    global year, mon
    date_bg = "white"
    date_fg = "black"
    date_fgb = "blue"
    date_bgt = "white"
    date_fgt = "red"
    day_bg = "orange"
    day_fg = "white"
    mon_bg = "violet"
    mon_fg = "white"
    Magic_Sequence = "2345012356013456123460124560"
    month = {
        "jan": 0,
        "feb": 8,
        "mar": 25,
        "apr": 5,
        "may": 1,
        "jun": 9,
        "jul": 5,
        "aug": 13,
        "sep": 21,
        "oct": 17,
        "nov": 25,
        "dec": 21,
    }
    months = ["jan", "feb", "mar", "apr", "may", "jun", "jul", "aug", "sep", "oct", "nov", "dec"]
    day = ["sun", "mon", "tue", "wed", "thu", "fri", "sat"]
    # ~ current year and month
    now = ctime().split()
    year = int(now[4])
    mon = now[1].lower()
    date = int(now[2])

    def Cal_config(modify=False):
        global year, mon
        mon_limit = [31, 28, 31, 30, 31, 30, 31, 31, 30, 31, 30, 31]
        now = ctime().split()
        cyear = int(now[4])
        cmon = now[1].lower()
        cdate = int(now[2])
        if modify == "go":
            year, mon = int(y.entry.get()), m.entry.get()
        elif modify:
            if months.index(mon) + modify > 11:
                year, mon = year + 1, "jan"
            elif months.index(mon) + modify < 0:
                year, mon = year - 1, "dec"
            else:
                mon = months[months.index(mon) + modify]
        monl.config(text="%s - %d" % (mon.title(), year))
        if not year % 4:
            mon_limit[1] = 29  # Leap year Check
        year_id = (year + 3) % 28
        Required_Sequence = Magic_Sequence[month[mon] :] + Magic_Sequence[: month[mon]]
        addition_factor = int(Required_Sequence[year_id])
        notes = CalLookUp(mon)
        d = 1
        for i in range(37):
            if i < addition_factor or d > mon_limit[months.index(mon)]:  # blank positions
                datebuttons[i].config(text="", bg=date_bg, activebackground=date_bg)
            else:  # positions with date
                bc, fc = date_bg, date_fg
                bracket = 0
                if year == cyear and mon == cmon and d == cdate:
                    bc, fc, bracket = date_bgt, date_fgt, 1
                if "%0.2d" % (d) in notes:
                    fc = date_fgb
                datebuttons[i].config(
                    text="%s%0.2d%s" % ("(" * bracket, d, ")" * bracket),
                    bg=bc,
                    fg=fc,
                    activebackground="yellow",
                    activeforeground="black",
                )
                d += 1
        for each_item in Entries.get_children():
            Entries.delete(each_item)
        ordered = []
        for memo in notes:
            ordered.append(memo)
        ordered.sort()
        for memo in ordered:
            for note in notes[memo]:
                Entries.insert("", "end", values=(memo, note[0], note[1]))
        print("Cal configured to", mon, year)
        # ~ main calender frame

    pane = tkinter.tix.PanedWindow(w, orientation="vertical")
    pane.pack(side=tkinter.tix.TOP, fill=BOTH)
    f1 = pane.add("top", size=190, expand="0", allowresize=0)
    f2 = pane.add("info", expand="0", allowresize=0)

    f1pane = tkinter.tix.PanedWindow(f1, orientation="horizontal")
    f1pane.pack(side=tkinter.tix.TOP, fill=BOTH)
    f1f1 = f1pane.add("calender", size=200, allowresize=0)
    f1f2 = f1pane.add("options", allowresize=0)

    # ~ month heading
    calhead = Frame(f1f1, bg=date_bg)
    back = Button(
        calhead,
        text="<<<",
        width=5,
        bg=date_bg,
        activebackground="red",
        activeforeground="white",
        borderwidth=0,
        command=lambda modify=-1: Cal_config(modify),
    )
    monl = Label(calhead, width=15, bg=mon_bg, fg=mon_fg)
    next = Button(
        calhead,
        text=">>>",
        width=5,
        bg=date_bg,
        activebackground="red",
        activeforeground="white",
        borderwidth=0,
        command=lambda modify=1: Cal_config(modify),
    )
    back.pack(side=LEFT)
    monl.pack(side=LEFT, padx=10)
    next.pack(side=LEFT)
    calhead.pack(fill=X)
    # ~ day lables
    DayFrame = Frame(f1f1, bg=day_bg)
    daylabels = []
    for i in range(7):
        daylabels.append(Label(DayFrame, text=day[i], width=3, bg=day_bg, fg=day_fg))
        daylabels[i].pack(side=LEFT, padx=2)
    DayFrame.pack(fill=X)
    # ~ date buttons
    datebuttons = []
    dfl = []
    for i in range(6):
        dfl.append(Frame(f1f1, bg=date_bg))
        dfl[i].pack(fill=X)
    j = 0
    for i in range(37):
        datebuttons.append(Button(dfl[j], width=3, borderwidth=0))
        datebuttons[i].pack(side=LEFT, padx=2)
        if not (i + 1) % 7:
            j += 1
        # ~ information frame
    mem = Label(f2, text="Memos :")
    disp_frame = tkinter.Frame(f2)
    tree_columns = ("Date", "Note", "Category")
    Entries = Treeview(disp_frame, columns=tree_columns, show="headings", height=5)
    vsb = Scrollbar(disp_frame, orient="vertical", command=Entries.yview)
    Entries.configure(yscrollcommand=vsb.set)
    for col in tree_columns:
        Entries.heading(col, text=col.title())
    Entries.column("Date", width=50)
    Entries.column("Note", width=150)
    Entries.column("Category", width=100)
    vsb.pack(side=RIGHT, fill=Y)
    Entries.pack(fill=BOTH)
    mem.pack(fill=X)
    disp_frame.pack(fill=BOTH)
    # ~ option frame
    L = Label(f1f2, text="More Options:")
    view = Frame(f1f2)
    y = ComboBox(view, editable=1)
    y.entry.config(width=5)
    y.entry.insert(0, year)
    m = ComboBox(view, editable=1)
    m.entry.config(width=4)
    m.entry.insert(0, mon)
    go = Button(f1f2, text="<<< Go", command=lambda modify="go": Cal_config(modify))
    for i in range(200):
        y.insert(END, "%d" % (i + 1901))
    for i in months:
        m.insert(END, i)
    y.pack(side=LEFT)
    m.pack()
    L.pack(fill=X)
    view.pack(fill=X)
    go.pack(fill=X)
    # ~ first config
    Cal_config()
Exemple #26
0
    DatabaseTable.heading('Username',text='Username')
    DatabaseTable.heading('Password',text='Password')
    DatabaseTable.heading('Account No',text='Account No')
    DatabaseTable.heading('Account Holder',text='Account Holder')
    DatabaseTable.heading('Father Name',text='Father Name')
    DatabaseTable.heading('D-O-B',text='D-O-B')
    DatabaseTable.heading('Gender',text='Gender')
    DatabaseTable.heading('Mobile No',text='Mobile No')
    DatabaseTable.heading('Mail Id',text='Mail Id')
    DatabaseTable.heading('Nationality',text='Nationality')
    DatabaseTable.heading('Address',text='Address')
    DatabaseTable.heading('Added Date',text='Added Date')
    DatabaseTable.heading('Added Time',text='Added Time')
    DatabaseTable['show']='headings'

    DatabaseTable.column('Id',width=100)
    DatabaseTable.column('Address',width=300)
    DatabaseTable.column('Mail Id',width=300)

    DatabaseTable.pack(fill=BOTH,expand=1)

    ############################################################## ---------------TimeDate--------------
    try:
        def TimeDate():
            Time_Zone=time.strftime("%H:%M:%S")
            Date_Zone=time.strftime("%d/%m/%y")
            Clock.config(text='Date:'+Date_Zone+'\n'+'Time:'+Time_Zone)
            Clock.after(200,TimeDate)
        Clock=Label(root,font=('times',14,'bold'))
        Clock.place(x=0,y=0)
        TimeDate()
Exemple #27
0
class hyGUI(Frame):


    def __init__(self):


        Frame.__init__(self)
        self.master.title("Hockey team Data")

        self.master.maxsize(1400, 1000)      ##  Maximum Frame size
        self.pack()
        self._treeview = Treeview(self)      ## initialize the treeview


##  Writing label on gui and creating a data insert box to get user input when clicking a button

        self.gameLocationLabel = Label(self, text = "Enter game location")
        self.gameLocationLabel.pack()

        self.gameLocationVar = StringVar()
        self.gameLocationEntry = Entry(self, textvariable = self.gameLocationVar, width=30)
        self.gameLocationEntry.pack()



        self.gameDateLabel = Label(self, text = "Enter game date")
        self.gameDateLabel.pack()

        self.gameDateVar = StringVar()
        self.gameDateEntry = Entry(self, textvariable = self.gameDateVar, width = 30)
        self.gameDateEntry.pack()



        self.hatSoldLabel = Label(self, text = "Enter how many hats were sold")
        self.hatSoldLabel.pack()

        self.hatSoldVar = StringVar()
        self.hatSoldEntry = Entry(self, textvariable = self.hatSoldVar, width = 30)
        self.hatSoldEntry.pack()



        self.posterSoldLabel = Label(self, text = "Enter how many poster were sold")
        self.posterSoldLabel.pack()

        self.posterSoldVar = StringVar()
        self.posterSoldEntry = Entry(self, textvariable = self.posterSoldVar, width = 30)
        self.posterSoldEntry.pack()


        self.jerseySoldLabel = Label(self, text = "Enter how many jersey were sold")
        self.jerseySoldLabel.pack()

        self.jerseySoldVar = StringVar()
        self.jerseySoldEntry = Entry(self, textvariable = self.jerseySoldVar, width = 30)
        self.jerseySoldEntry.pack()


        self.hockeyStickSoldLabel = Label(self, text = "Enter how many hockey stick were sold")
        self.hockeyStickSoldLabel.pack()

        self.hockeyStickSoldVar = StringVar()
        self.hockeyStickSoldEntry = Entry(self, textvariable = self.hockeyStickSoldVar, width = 30)
        self.hockeyStickSoldEntry.pack()



##  Creating space between the button on the GUI interface
        self._resultVar = StringVar()
        self._resultLabel = Label(self, text=" \n ", textvariable=self._resultVar)
        self._resultLabel.pack()


##  Add button
        self._addButton = Button(self, text="Add", command=self._add)
        self._addButton.pack()


        self._resultVar = StringVar()
        self._resultLabel = Label(self, text=" \n ", textvariable=self._resultVar)
        self._resultLabel.pack()


## Delete button
        self._addButton = Button(self, text="Delete", command=self._delete)
        self._addButton.pack()

        self._resultVar = StringVar()
        self._resultLabel = Label(self, text=" \n ", textvariable=self._resultVar)
        self._resultLabel.pack()


## Exit button
        self._exitButton = Button(self, text="Exit", command=self._exit)
        self._exitButton.pack()

        self._resultVar = StringVar()
        self._resultLabel = Label(self, text=" \n ", textvariable=self._resultVar)
        self._resultLabel.pack()


## Best item sold button
        self._bestItemButton = Button(self, text="Best Item Sold", command=self._bestItem)
        self._bestItemButton.pack()

        self._resultVar = StringVar()
        self._resultLabel = Label(self, text=" \n ", textvariable=self._resultVar)
        self._resultLabel.pack()


##  Worst item sold button
        self._worstItemButton = Button(self, text="Worst Item Sold", command=self._worstItem)
        self._worstItemButton.pack()

        self._resultVar = StringVar()
        self._resultLabel = Label(self, text=" \n ", textvariable=self._resultVar)
        self._resultLabel.pack()


##  Best sales per game button
        self._itemButton = Button(self, text="Game for best Sales", command=self._item)
        self._itemButton.pack()


## this button is not packed but, it is needed to populate the table
        self._tableButton = Button(self, text = "Show the Complete table", command =self._maketable())



        self._resultVar = StringVar()
        self._resultLabel = Label(self, text=" \n ", textvariable=self._resultVar)
        self._resultLabel.pack()


##  Using empty sting label to display the different text on GUI Frame when clicking button
        self.resultBestLabel = Label(self, text = "")
        self.resultBestLabel.pack()


        self._treeview['columns']=('location', 'date', 'no_hats', 'val_hats', 'no_jerseys', 'val_jerseys',
                                   'no_hockstick', 'val_hockstick', 'no_posters', 'val_posters','total_sales')


##  Creating a columns name heading for the table
        self._treeview.heading('location', text = "Location")
        self._treeview.column('#0', width = 0)
        self._treeview.heading('date', text = "Date")
        self._treeview.heading('no_hats', text = "# hats")
        self._treeview.heading('val_hats', text = "$ hats")
        self._treeview.heading('no_jerseys', text = "# jerseys")
        self._treeview.heading('val_jerseys', text = "$ jerseys")
        self._treeview.heading('no_hockstick', text = "# hockey stick")
        self._treeview.heading('val_hockstick', text = "$ hockey stick")
        self._treeview.heading('no_posters', text = "# posters")
        self._treeview.heading('val_posters', text = "$ posters")
        self._treeview.heading('total_sales', text = "Total Sales")

##  The column size is 100
        for item in self._treeview['columns']:
            self._treeview.column(item, width = 100)


        self._treeview.pack()



##  Calling for database table to be displayed on GUI frame
    def _maketable(self):
        makeTableDatabase(self)







## when clicking add button with the user input, it will get the user input and add the data to the database

    def _add(self):
        location = self.gameLocationVar.get()
        date = self.gameDateVar.get()
        hat = self.hatSoldVar.get()
        jersey = self.jerseySoldVar.get()
        stick = self.hockeyStickSoldVar.get()
        poster = self.posterSoldVar.get()

        hatTotal = int(hat) * 20         ## Calculate hat quantity sold with hat retail price of $20
        jerseyTotal = int(jersey) * 40   ## Calculate jersey quantity sold with jersey retail price of $20
        stickTotal = int(stick) * 30     ## Calculate hockey stick quantity sold with hockey stick retail price of $20
        posterTotal = int(poster) * 10   ## Calculate poster quantity sold with poster retail price of $20

        TotalSales = posterTotal + stickTotal + jerseyTotal + hatTotal   # calculation of total sales of the game


##  Calling add_data method with the user input and calculated value to a add a data to a database
        add_data(location, date, hat, hatTotal, jersey, jerseyTotal, stick, stickTotal, poster, posterTotal, TotalSales)

##  update the data on the table
        update_table(self)



##  when delete button is pressed, it will call deleteData method
    def _delete(self):
        deleteData(self)


#  when exit button is clicked, the GUI frame close
    def _exit(self):
        sys.exit()


# when best item button is clicked, it will calculate the best item sold amount per game
    def _bestItem(self):
        bestItem(self)




# when worst item button is clicked, it will calculate the worst item sold amount per game

    def _worstItem(self):
        worstItem(self)


#  when game for best sales button were clicked, it will display the game location
#  for the best total sales per game
    def _item(self):
        bestSalesGame(self)
Exemple #28
0
class NameView(object):
    """Shows a treeview of unique names."""

    def __init__(self, master, names):
        self.widget = Frame(master)
        self._tree = Treeview(self.widget, columns='name')
        self._tree.grid(row=0,column=0, sticky=(N,S,W,E))
        self._tree.view = self
        self.widget.columnconfigure(0, weight=1)
        self.widget.rowconfigure(0,weight=1)
        self._tree.column('name', width=50)
        self._tree['show'] = 'tree'
        actions = {'edit': lambda e: self.edit(),
                'search': lambda e: self.search(),
                'focus_next': lambda e: self.focus_next(),
                'focus_prev': lambda e: self.focus_prev(),
                'select': lambda e: self._tree.selection_toggle(self._tree.focus()),
                'clear_selection': lambda e: self._tree.selection_set([])
                }
        kb.make_bindings(kb.tagview, actions, self._tree.bind)
        self._iids = dict()
        self._names = dict()
        logger.debug('Names: %s', names)
        self.widget.focus_set = self._tree.focus_set
        for name in sorted(names):
            iid = self._tree.insert('', 'end', text=name)
            self._names[iid] = name
            self._iids[name] = iid
        self._scroll = Scrollbar(self.widget, command=self._tree.yview)
        self._tree['yscrollcommand'] = self._scroll.set
        self._scroll.grid(row=0, column=1, sticky=(N, S))
        self.widget.columnconfigure(1, weight=0)


    def selection(self):
        logger.debug('Selection: %s', self._tree.selection())
        return [self._names[iid] for iid in self._tree.selection()]

    def edit(self):
        self._tree.event_generate('<<NameViewEdit>>')

    def search(self):
        if len(self._tree.selection()) == 0:
            self._tree.selection_add(self._tree.focus())
        self._tree.event_generate('<<NameViewSearch>>')

    def append(self, names):
        logger.debug('Append names: %s', names)
        for name in names:
            if name not in self._names.values():
                iid = self._tree.insert('', 'end', text=name)
                self._names[iid] = name
                self._iids[name] = iid

    def delete(self, name):
        self._tree.delete(self._iids[name])
        del self._names[self._iids[name]]
        del self._iids[name]

    def _focus(self, iid):
        self._tree.focus(iid)
        self._tree.see(iid)

    def focus_next(self):
        cur_iid = self._tree.focus()
        next_iid = self._tree.next(cur_iid)
        if next_iid == '':
            iids = self._tree.get_children()
            next_iid = iids[0]
        self._focus(next_iid)

    def focus_prev(self):
        cur_iid = self._tree.focus()
        prev_iid = self._tree.prev(cur_iid)
        if prev_iid == '':
            iids = self._tree.get_children()
            prev_iid = iids[-1]
        self._focus(prev_iid)

    def jump_to(self, name):
        try:
            iid = self._iids[name]
            self._focus(iid)
        except KeyError:
            pass

    def get_names(self):
        return tuple(self._names.values())

    def set(self, names):
        self._tree.delete(*self._iids.values())
        self._iids.clear()
        self._names.clear()
        for name in sorted(names):
            iid = self._tree.insert('', 'end', text=name)
            self._names[iid] = name
            self._iids[name] = iid
    def customer_analysis():
        print(phno2.get())

        def get_selected_date(selection):
            selected_date = selection
            print(selected_date)

        rootan = Tk()
        rootan.geometry("940x610+100+50")
        rootan.title("Customer Analysis")
        rootan.config(bg="#4fc3f7")
        selected_date = StringVar(rootan)

        x = []
        y = []
        a = []
        b = []

        analysislabel = Label(rootan,
                              text="Customer Analysis",
                              font=("Lobster Two", 20, "bold"),
                              fg="#ffffff",
                              bg="#4fc3f7")
        analysislabel.pack()

        g1 = con.cursor()
        g1.execute(
            "select pcategory as purchased from inventory,sales where inventory.pid = sales.pid and cmobnum = ? GROUP by pcategory;",
            (phno2.get(), ))
        fetch = g1.fetchall()

        for data in fetch:
            x.extend(data)

        g2 = con.cursor()
        g2.execute(
            "select count(sales.pid) as purchased from inventory,sales where inventory.pid = sales.pid and cmobnum = ? GROUP by pcategory;",
            (phno2.get(), ))
        fet = g2.fetchall()

        for dat in fet:
            y.extend(dat)

        fig = Figure(figsize=(5, 3), dpi=80)
        fig.suptitle('Category - wise', fontsize=16)
        axes = fig.add_subplot(111)
        axes.plot(x, y)

        canvas = FigureCanvasTkAgg(fig, rootan)
        canvas.get_tk_widget().place(x=20, y=350)
        fig.set_facecolor("#81d4fa")

        c = con.cursor()
        top = c.execute(
            "select pname,pcategory,count(pname) from inventory,sales where inventory.pid = sales.pid and cmobnum = ? group by pname order by count(pname) DESC LIMIT 5;",
            (phno2.get(), ))
        fetc = c.fetchall()

        top5 = Label(rootan,
                     text="Most recently bought :",
                     font=("Oxygen", 16, "bold"),
                     fg="#212121",
                     bg="#4fc3f7")
        top5.place(x=650, y=100)

        tree = Treeview(rootan, columns=('pname', 'pcategory', 'count(pname)'))
        tree.heading('pname', text='Product Name')
        tree.heading('pcategory', text='Category')
        tree.heading('count(pname)', text='Purchased count')
        tree.column("pname", width=90)
        tree.column("pcategory", width=90)
        tree.column("count(pname)", width=90)
        tree.place(x=650, y=150)
        tree['show'] = 'headings'

        for data in fetc:
            tree.insert('', 'end', values=(data))

        options = []

        d = con.cursor()
        d.execute("select distinct(date) from sales;")
        val = d.fetchall()

        for data in val:
            options.extend(data)

        selected_date.set(options[1])

        p = con.cursor()
        p.execute(
            """select sum(pprice) from inventory,sales where sales.pid = inventory.pid and cmobnum = ? group by strftime("%m",date) order by strftime("%m",date)""",
            (phno2.get(), ))
        fetc = p.fetchall()

        i = con.cursor()
        i.execute(
            """select distinct  strftime("%m",date) as month from sales order by month;"""
        )
        fet = i.fetchall()

        for dat in fetc:
            a.extend(dat)

        for data in fet:
            b.extend(data)

        fig2 = Figure(figsize=(5, 3), dpi=80)
        fig2.suptitle('Monthly Spendings', fontsize=16)
        axes2 = fig2.add_subplot(111)
        axes2.plot(b, a)

        canvas2 = FigureCanvasTkAgg(fig2, rootan)
        canvas2.get_tk_widget().place(x=20, y=80)
        fig2.set_facecolor("#81d4fa")

        outbtn = Button(rootan,
                        text="Back",
                        font=("Noto sans", 12, "bold"),
                        fg="#ffffff",
                        bg="#c62828",
                        relief="flat",
                        command=rootan.destroy)
        outbtn.place(x=830, y=5)

        rootan.mainloop()
class Expenses(Frame):

    # Creates the first option menus in the expense window
    def createOptionButtons(self):
        self.master.title("Expenses")

        # Creates the add item to inventory button
        addItem = Button(root, text="Add item to inventory", command=lambda: self.sequence(self.addItem))#addItem(master)))  # This button will send to the user to the add item page
        addItem.place(x = 130, y = 100)

        # Creates the view items in inventory button
        inventoryButton = Button(root, text="View items in inventory", command=lambda: self.sequence(self.viewInveroty))  # This button will send the user to the view inventory page
        inventoryButton.place(x = 130, y = 150)

        # Create the total cost button
        totalCost = Button(root, text="Total Cost", command=lambda: self.sequence(self.viewTotalCost))
        totalCost.place(x = 130, y = 200)

        # Creates the back button
        backButton = Button(root, text="Back", command=returnHome)  # This button will return the user to the main page. Still working on it.
        backButton.place(x = 50, y = 350)

    # Creates the add item to inventory button and entries
    def addItem(self):
        self.master.title("Add new item")  # Changes the title of the page to Add New Item

        # Creates a label called nameOfItems and an entry called itemName
        nameOfItem = Label(root, text="Item Name: ")
        nameOfItem.place(x = 110, y = 100)
        self.itemName = Entry(root)       # This will allow the user to enter the name of the item that they will be adding
        self.itemName.place(x = 190, y = 100)

        # Creates the label called itemTypeLabel and a drop down menu called itemTypeChoice
        itemTypeLabel = Label(root, text = "Item's type: ")
        itemTypeLabel.place(x = 110, y = 160)
        self.itemTypeChoice = StringVar(root)       # This makes itemTypeChoice a permanent String
        self.itemTypeChoice.set("Tree")             # Tree is set to the default string of itemTypeChoice
        typeChoices = OptionMenu(root, self.itemTypeChoice, "Tree", "Animal", "Machine")    # Drop down menu is created and options Tree, Animal, and Machine are added to the menu
        typeChoices.place(x = 190, y = 160)


        backButton = Button(root, text = "Back", command=lambda: self.sequence(self.createOptionButtons))
        backButton.place(x = 50, y = 350)
        # Next button
        nextButton = Button(root, text = "Next", command=self.saveNameAndType) #This button will send the user to the add inventory page
        nextButton.place(x = 350, y = 350)

    # Function that creates a new item object and assigns it a name and the type
    def saveNameAndType(self):
        name = self.itemName.get()
        self.item = Inventory(name)
        itemType = self.itemTypeChoice.get()
        self.item.itemType = itemType
        self.sequence(self.addToInventory)

    # Creates the add to inventory options
    def addToInventory(self):
        self.master.title("Add %s to %s inventory" % (self.item.name, self.item.itemType))

        # This assigns the variables month, day, and year to be value holder for integer values
        # They are also set to be values of the class expenses (by using self) so that they can
        # be used in the function updateDay and SaveDate
        self.month = IntVar(self)
        self.day = IntVar(self)
        self.year = IntVar(self)

        # This trace function is used to keep track of when the selected months and years change. This is
        # done to adjust the days of the month according to the month or the year
        self.month.trace('w', self.updateDay)
        self.year.trace('w', self.updateDay)

        numMonths = self.nums(1, 12)  # Runs the nums function that creates a list from 1 to 12
        numYears = self.nums(2015, 2030)  # Runs the nums function that creates a list from 2015 to 2030

        # This creates the drop down menu and assigns the options is the menu. The day menu is left empty and
        # is assigned in the updateDay function
        self.optionmenu_month = OptionMenu(root, self.month, *numMonths)
        self.optionmenu_day = OptionMenu(root, self.day, '')
        self.optionmenu_year = OptionMenu(root, self.year, *numYears)

        # Sets the default value of the month and year options to 1 and 2015 respectively
        self.month.set(numMonths[0])
        self.year.set(numYears[0])

        self.optionmenu_month.place(x = 100, y = 120)
        self.optionmenu_day.place(x = 150, y = 120)
        self.optionmenu_year.place(x = 200, y = 120)


        datePurchased = Label(root, text = "Date Purchased")
        datePurchased.place(x = 150, y = 95)

        quantityPurchasedLabel = Label(root, text="Amount purchased:")
        quantityPurchasedLabel.place(x = 50, y = 180)
        self.quantityPurchasedEntry = Entry(root, bd=5) # Creates input box for user to insert the amount of items purchased
        self.quantityPurchasedEntry.place(x = 180, y = 180)

        pricePaidLabe = Label(root, text="Price paid for all: ")
        pricePaidLabe.place(x = 50, y = 210)
        self.pricePaidEntry = Entry(root, bd=5) # Creates input box for user to insert the price paid for the item
        self.pricePaidEntry.place(x = 180, y = 210)


        backButton = Button(root, text = "Back", command=lambda: self.sequence(self.addItem))
        backButton.place(x = 50, y = 350)

        nextButton = Button(root, text = "Next", command=self.saveQuanAndPrice)
        nextButton.place(x = 350, y = 350)

    # This function will update the days of the month according to the selected month and year
    def updateDay(self, *args):
        # The .get() will obtain the selected month and year values from the drop down menu above
        month = self.month.get()
        year = self.year.get()

        # Creates a loop which chooses the last day of the month according to the month or the year
        if month == 1 or month  == 3 or month  == 5 or month  == 7 or month  == 8 or month  == 10 or month  == 12:
            lastDay = 31
        elif month  == 4 or month  == 6 or month  == 9 or month  == 11:
            lastDay = 30
        # This elif loop uses the leap year formula at account for leap years
        elif month  == 2:
            if (year % 4) == 0:
                if (year % 100) == 0:
                    if (year % 400) == 0:
                        lastDay = 29
                    else:
                        lastDay = 28
                else:
                    lastDay = 29
            else:
                lastDay = 28

        numDays = self.nums(1,lastDay)

        # Assigns menu to the day drop down menu and deletes all of the options in the menu
        menu = self.optionmenu_day['menu']
        menu.delete(0, 'end')

        # Loop for generating the new day menu
        for day in numDays:
            menu.add_command(label=day, command=lambda d = day: self.day.set(d))
        self.day.set(1)

    # Function that creates the range of numbers for the drop down menu
    def nums(self, numStart, numEnd):
        num = range(numStart, numEnd + 1)
        return num

    # Function that assigns the price and quantity to an item
    def saveQuanAndPrice(self):
        self.item.price = self.pricePaidEntry.get()
        self.item.quantity = self.quantityPurchasedEntry.get()
        self.saveDate()
        self.sequence(self.confirmation)

    # Function that assigns the purchase date to an item
    def saveDate(self):
        self.item.purchaseMonth = self.month.get()
        self.item.purchaseDay = self.day.get()
        self.item.purchaseYear = self.year.get()
        self.item.purchaseDate = ("%s/%s/%s" % (self.item.purchaseMonth, self.item.purchaseDay, self.item.purchaseYear))

    # Function that displays the user inputted information
    def confirmation(self):
        self.master.title("Confirm %s information" % self.item.name)
        name = Label(root, text="Name of item: ")
        name.place(x = 100, y = 50)
        itemName = Label(root, text=self.item.name)
        itemName.place(x = 100, y = 65)

        type = Label(root, text="%s type: " % self.item.name)
        type.place(x = 100, y = 90)
        itemType = Label(root, text=self.item.itemType)
        itemType.place(x = 100, y = 105)

        quantity = Label(root, text="How many %s were bought?" % self.item.name)
        quantity.place(x = 100, y = 130)
        itemQuantity = Label(root, text=self.item.quantity)
        itemQuantity.place(x = 100, y = 145)

        price = Label(root, text="How much did the %s %s cost?" % (self.item.quantity, self.item.name))
        price.place(x = 100, y = 170)
        itemPrice = Label(root, text=self.item.price)
        itemPrice.place(x = 100, y = 185)

        date = Label(root, text="When were %s bought?" % self.item.name)
        date.place(x = 100, y = 210)
        itemDate = Label(root, text=self.item.purchaseDate)
        itemDate.place(x = 100, y = 225)


        backButton = Button(root, text = "Back", command=lambda: self.sequence(self.addToInventory))
        backButton.place(x = 50, y = 350)

        startOverButton = Button(root, text = "Start Over", command=lambda: self.sequence(self.createOptionButtons))
        startOverButton.place(x = 200, y = 350)

        confirmButton = Button(root, text = "Confirm", command=lambda: self.sequence(self.addToDatabase))
        confirmButton.place(x = 320, y = 350)

    # Adds the item to the database
    def addToDatabase(self):
        self.inventoryDB.insertInvetory(self.item)
        return self.successful()

    # Displays a success message when the item is added
    def successful(self):
        self.master.title("%s was added successfully!" % self.item.name)

        succMessage = Message(root, text = "%s was successfully added to the %s list!" % (self.item.name, self.item.itemType))
        succMessage.place(x = 150, y = 150)

        startOverButton = Button(root, text = "Start Over", command=lambda: self.sequence(self.createOptionButtons))#self.saveNameAndType(itemName)))#(self.saveNameAndType(itemName)))  # (itemName)))# lambda: self.sequence(self.test))  #This button will send the user to the add inventory page
        startOverButton.place(x = 150, y = 350)

    # Used to view the inventory
    def viewInveroty(self):
        # Creates the label called chooseTypeLabel and a drop down menu called chooseItemType
        chooseTypeLabel = Label(root, text = "Item's type: ")
        chooseTypeLabel.place(x = 110, y = 160)
        self.chooseItemType = StringVar(root)       # The drop down menu is created and assigned to chooseItemType
        self.chooseItemType.set("Tree")             # Tree is set to the default option in the drop down menu
        typeChoices = OptionMenu(root, self.chooseItemType, "Tree", "Animal", "Machine", "All")    # Options Tree, Animal, Machine, and ALL are added to the drop down menu
        typeChoices.place(x = 190, y = 160)

        backButton = Button(root, text = "Back", command=lambda: self.sequence(self.createOptionButtons))  # This button will return the user to the expenses option page
        backButton.place(x = 50, y = 350)

        nextButton = Button(root, text = "Next", command=lambda: self.sequence(self.displayGeneralInventory))#self.saveNameAndType(itemName)))#(self.saveNameAndType(itemName)))  # (itemName)))# lambda: self.sequence(self.test))  #This button will send the user to the add inventory page
        nextButton.place(x = 350, y = 350)

    # Used to create the inventory table
    def displayGeneralInventory(self):
        # This creates a table using the function Treeview
        self.tree = Treeview(height="20", columns=("Name", "Current Quantity"))
        self.tree.pack()
        self.tree.heading('#1', text = "Name", anchor = CENTER)
        self.tree.heading('#2', text = "Current Quantity", anchor = CENTER)
        self.tree.column('#1', minwidth=0, width = 100)
        self.tree.column('#2', minwidth=0, width = 100)
        self.tree.column('#0', minwidth=0, width = 0)

        itemType = self.chooseItemType.get()

        if(itemType == "All"):
            self.obtainData("Tree")
            self.obtainData("Animal")
            self.obtainData("Machine")

        else:
            self.obtainData(itemType)

    # Adds database data to the inventory table
    def obtainData(self, type):
        for row in (self.inventoryDB.getOverviewInventory(type)):
            name = row[0]
            totalQuantity = row[1]

            # Inserts data into the table. Each entry is tagged with the name and the type
            # This is done in order to make identifying the entries easier for when detailed
            # tables are requested
            self.tree.insert("", "end", values = (name,totalQuantity), tag= [name, type])

        # Creates a bak function that is used in the displayGeneralInventory functions
        self.backFunction = self.displayGeneralInventory

        # Binds a double click function to the Treeview table. If an entry is double clicked,
        # the function displayGeneralInventory is ran
        self.tree.bind("<Double-1>", self.displayDetailedInventory)

        backButton = Button(root, text="Back", command=lambda: self.sequence(self.viewInveroty))  # This button will return the user to the main page. Still working on it.
        backButton.place(x = 50, y = 350)

    # Creates table when an entry is double clicked
    def displayDetailedInventory(self, event):
        # The selected item's tag are extracted and assigned to name and type
        itemSelected = self.tree.selection()
        name = self.tree.item(itemSelected,"tag")[0]
        type = self.tree.item(itemSelected, "tag")[1]

        for child in root.winfo_children():
            child.destroy()

        self.createDisplayTable()

        self.obtainDetailedData(name, type)

    # Adds detailed database data to the inventory table
    def obtainDetailedData(self,name, type):
        for row in (self.inventoryDB.getDetailedInventory(type, name)):
            name = row[0]
            purchaseDate = row[1]
            Quantity = row[3]
            Price = row[4]
            self.tree.insert("", "end", values = (name,purchaseDate,Quantity, Price))

        backButton = Button(root, text="Back", command=lambda: self.sequence(self.backFunction))
        backButton.place(x = 50, y = 350)

    # Creates the view total cost by month and year buttons
    def viewTotalCost(self):
        viewMonth = Button(root, text="View by month", command=lambda: self.sequence(self.viewByMonth))
        viewMonth.place(x = 120, y = 100)

        viewYear = Button(root, text="View by year", command=lambda: self.sequence(self.viewByYear))
        viewYear.place(x = 120, y = 150)

        backButton = Button(root, text="Back", command=lambda: self.sequence(self.createOptionButtons))#displayGeneralInventory))  # This button will return the user to the main page. Still working on it.
        backButton.place(x = 50, y = 350)

    # Creates the options for the user to select a month and year
    def viewByMonth(self):
        monthLabel = Label(root, text="Month")
        yearLabel = Label(root, text="Year")

        self.month = IntVar(self)
        self.year = IntVar(self)

        numMonths = self.nums(1, 12)
        numYears = self.nums(2015, 2030)

        self.optionmenu_month = OptionMenu(root, self.month, *numMonths)
        self.optionmenu_year = OptionMenu(root, self.year, *numYears)

        self.month.set(numMonths[0])
        self.year.set(numYears[0])

        self.optionmenu_month.place(x = 100, y = 100)
        self.optionmenu_year.place(x = 150, y = 100)

        monthLabel.place(x = 100, y = 140)
        yearLabel.place(x = 150, y = 140)

        backButton = Button(root, text = "Back", command=lambda: self.sequence(self.viewTotalCost))  # This button will return the user to the expenses option page
        backButton.place(x = 50, y = 350)

        nextButton = Button(root, text = "Next", command= self.viewTotalCostMonth)#self.viewTotalCostMonth)#self.saveNameAndType(itemName)))#(self.saveNameAndType(itemName)))  # (itemName)))# lambda: self.sequence(self.test))  #This button will send the user to the add inventory page
        nextButton.place(x = 350, y = 350)

    # Creates database table and inserts the respective values by month and year
    def viewTotalCostMonth(self):
        self.createDisplayTable()

        self.totalPrice = 0
        month = self.month.get()
        year = self.year.get()

        self.lengthMonth = len(str(month))
        self.searchDate = str(month) + "/" + str(year)

        InventoryDB = getDatabaseConnection()
        database = InventoryDB.cursor()

        self.insertData("DetailedTreeInventory", "Tree", database, "Month")
        self.insertData("DetailedAnimalInventory", "Animal", database, "Month")
        self.insertData("DetailedMachineInventory", "Machine", database, "Month")

        InventoryDB.close()

        totalPriceLabel = Label(root, text=("Total price for " + calendar.month_name[month] + " in " + str(year) + " is: " + str(self.totalPrice)))
        totalPriceLabel.place(x = 100, y = 350)

        backButton = Button(root, text = "Back", command=lambda: self.sequence(self.viewByMonth))  # This button will return the user to the expenses option page
        backButton.place(x = 50, y = 350)

    # Creates the option for the user to select the year
    def viewByYear(self):
        yearLabel = Label(root, text="Year")

        self.year = IntVar(self)

        numYears = self.nums(2015, 2030)

        self.optionmenu_year = OptionMenu(root, self.year, *numYears)

        self.year.set(numYears[0])

        self.optionmenu_year.place(x = 100, y = 100)
        yearLabel.place(x = 100, y = 140)


        backButton = Button(root, text = "Back", command=lambda: self.sequence(self.viewTotalCost))  # This button will return the user to the expenses option page
        backButton.place(x = 50, y = 350)

        nextButton = Button(root, text = "Next", command= self.viewTotalCostYear)#self.viewTotalCostMonth)#self.saveNameAndType(itemName)))#(self.saveNameAndType(itemName)))  # (itemName)))# lambda: self.sequence(self.test))  #This button will send the user to the add inventory page
        nextButton.place(x = 350, y = 350)

    # Creates database table and inserts the respective values by year
    def viewTotalCostYear(self):
        self.createDisplayTable()

        self.totalPrice = 0
        year = self.year.get()

        InventoryDB = getDatabaseConnection()
        database = InventoryDB.cursor()

        self.insertData("DetailedTreeInventory", "Tree", database, "Year")
        self.insertData("DetailedAnimalInventory", "Animal", database, "Year")
        self.insertData("DetailedMachineInventory", "Machine", database, "Year")

        totalPriceLabel = Label(root, text="Total price for " + str(year) + " is: " + str(self.totalPrice))
        totalPriceLabel.place(x = 100, y = 350)

        backButton = Button(root, text = "Back", command=lambda: self.sequence(self.viewByYear))  # This button will return the user to the expenses option page
        backButton.place(x = 50, y = 350)

    # Inserts the detailed values into the detailed table
    def insertData(self, table, type, database, yearOrMonth):
        if yearOrMonth == "Year":
            for row in database.execute("SELECT * FROM %s" % table ):
                itemdate = row[1]

                if ( str(self.year.get()) == itemdate[-4:]):
                    name = row[0]
                    purchaseDate = row[1]
                    Quantity = row[3]
                    Price = row[4]

                    self.tree.insert("", "end", values = (name,purchaseDate,Quantity, Price),tag = [name, type] )
                    self.totalPrice = self.totalPrice + Price

                self.backFunction = self.viewTotalCostYear

        else:
            for row in database.execute("SELECT * FROM %s" % table ):
                itemdate = row[1]

                if (self.searchDate == (itemdate[0:(self.lengthMonth + 1)] + itemdate[-4:])):
                    name = row[0]
                    purchaseDate = row[1]
                    Quantity = row[3]
                    Price = row[4]

                    self.tree.insert("", "end", values = (name,purchaseDate,Quantity, Price), tag = [name, type])
                    self.totalPrice = self.totalPrice + Price

                self.backFunction = self.viewTotalCostMonth

        # If entry is double clicked, the table will acknoledge the click and display the detailed table
        self.tree.bind("<Double-1>", self.displayDetailedInventory)

    def createDisplayTable(self):
        for child in root.winfo_children():
            child.destroy()

        self.tree = Treeview(height="15", columns=("Name", "Purchase Date", "Quantity", "Price"))#, "Description"))
        self.tree.pack()
        self.tree.heading('#1', text = "Name",          anchor = CENTER)
        self.tree.heading('#2', text = "Purchase Date", anchor = CENTER)
        self.tree.heading('#3', text = "Quantity",      anchor = CENTER)
        self.tree.heading('#4', text = "Price",         anchor = CENTER)
        self.tree.column('#1', minwidth=0, width = 95)
        self.tree.column('#2', minwidth=0, width = 95)
        self.tree.column('#3', minwidth=0, width = 95)
        self.tree.column('#4', minwidth=0, width = 95)
        self.tree.column('#0', minwidth=0, width = 0)

    # This is a helper function that will delete the current widgets of the frame
    def sequence(self, run):
        for child in root.winfo_children():
            child.destroy()
        run()

    def __init__(self, master=None):
        Frame.__init__(self, master)
        self.place();
        self.inventoryDB = InventoryDatabase()
        # self.inventoryDB.createTable()
        self.createOptionButtons()
Exemple #31
0
class App(Tk):
    STEP_MODE: IntVar  # Пошаговое проигрывание анимации.
    SHOW_INFLECTION_POINTS: IntVar

    started = False  # Мы начали искать корни, в это время нельзя менять менять уравнение.
    paused = False  # Пауза для анимации.
    done: bool = False
    st: float
    en: float
    div: int
    eps: float

    lin_x: any  # Множество точек для построения графика.
    lin_space_size: int = 400  # Кол-во точек для построения графика

    solver: HordEquationSolver

    expr: StringVar  # Введенное пользователем выражение

    # График
    ax: plt.Axes
    plots: List[Line2D] = []
    h_lines: List[Line2D] = []  # Горизонтальные линии
    main_plot: any = None
    deriv_plot: any = None
    inflection_points: any = None

    # Список решений
    solutions: List[Solution] = []
    solution_ids: List[str] = []

    tree: Treeview  # Таблица результатов
    b_start: Button  # Кнопка начала/остановки
    lin_space_label: Label  # Надпись о точности графика

    cached_function: any  # Декодированная функция, что бы каждый раз не вызывать eval
    after_job_id: any = None  # id отложенного вызова функции для её отмены

    def f(self, x):
        return self.cached_function(x)

    def __init__(self, st: float, en: float, div: int, eps: float):
        super().__init__()
        self.st = st
        self.en = en
        self.div = div
        self.eps = eps
        self.lin_x = np.linspace(
            st, en,
            self.lin_space_size)  # Множество точек для построения графика.

        fig = plt.Figure(tight_layout=True)
        self.ax = fig.add_subplot()

        self.ax.axhline(0, color='black')

        self.grid_columnconfigure(0, weight=2)
        self.grid_columnconfigure(1, weight=1)
        self.grid_rowconfigure(0, weight=1)
        self.fagg = FigureCanvasTkAgg(fig, self)
        self.fagg.get_tk_widget().grid(row=0, column=0, sticky='WNSE')
        self.frame = Frame(self)
        self.frame.grid(row=0, column=1, sticky='WNSE', rowspan=2)

        self.init_sidebar()

        self.solver = HordEquationSolver(st, en, div, eps, self.f)

        self.prepare()

        self.fagg.draw()
        button_frame = Frame(self)
        button_frame.grid(row=1, column=0, sticky='WE')
        self.b_start = Button(button_frame, text='start')
        self.b_start.pack(side='left', anchor='center')
        self.b_start.bind('<Button>', self.start)
        Button(button_frame, text='reset',
               command=self.reset).pack(side='left', anchor='center')

    def init_sidebar(self):
        self.cached_function = eval('lambda x: ' + DEFAULT_EXPRESSION)
        self.expr = StringVar(self)
        self.expr.set(DEFAULT_EXPRESSION)
        self.expr.trace_variable('w', self.var_debounce(self.expression_input))

        # Динамические переменные для входных полей
        start_v = DoubleVar(self, value=self.st)
        end = DoubleVar(self, value=self.en)
        epsilon = DoubleVar(self, value=self.eps)
        divs = IntVar(self, value=self.div)
        lin_space_var = DoubleVar(self,
                                  value=math.log(self.lin_space_size,
                                                 LOG_BASE))
        variables = ((start_v, 'st'), (end, 'en'), (epsilon, 'eps'), (divs,
                                                                      'div'))

        # Функция обертка для сигнализирования о смене переменной.
        def outer(var, var_name):
            def inner(*_args):
                try:
                    self.params_input(var.get(), var_name)
                except Exception:
                    pass

            return inner

        for (v, name) in variables:
            v.trace('w', self.debounce(outer(v, name), 250))

        lin_debouncer = self.debounce(self.modify_lin_space_size, 150)
        lin_space_var.trace(
            'w', lambda *_args: self.modify_lin_space_size_callback(
                lin_space_var.get(), lin_debouncer))

        self.frame.columnconfigure(1, weight=2)
        Label(self.frame, text='Выражение:').grid(column=0,
                                                  row=0,
                                                  columnspan=2,
                                                  sticky='EW')
        Entry(self.frame, textvariable=self.expr).grid(column=0,
                                                       row=1,
                                                       columnspan=2,
                                                       sticky='EW')

        self.frame.rowconfigure(2, minsize=25)
        Label(self.frame, text='Начало').grid(column=0, row=3, sticky='W')
        Entry(self.frame, textvariable=start_v).grid(column=1,
                                                     row=3,
                                                     sticky='EW')

        Label(self.frame, text='Конец').grid(column=0, row=4, sticky='W')
        Entry(self.frame, textvariable=end).grid(column=1, row=4, sticky='EW')

        Label(self.frame, text='Точность').grid(column=0, row=5, sticky='W')
        Entry(self.frame, textvariable=epsilon).grid(column=1,
                                                     row=5,
                                                     sticky='EW')

        Label(self.frame, text='Разделение').grid(column=0, row=6, sticky='W')
        Entry(self.frame, textvariable=divs).grid(column=1, row=6, sticky='EW')

        self.frame.rowconfigure(7, minsize=25)
        self.lin_space_label = Label(
            self.frame,
            text=f'Количество точек графика: {self.lin_space_size}')
        self.lin_space_label.grid(column=0, row=8, columnspan=2, sticky='W')
        w = Scale(self.frame,
                  from_=math.log(5, LOG_BASE),
                  to=math.log(MAX_LINE_SPACE_SIZE, LOG_BASE),
                  resolution=0.1 / LOG_BASE,
                  orient=HORIZONTAL,
                  variable=lin_space_var)
        w.grid(column=0, row=9, columnspan=2, sticky='EW')

        self.tree = Treeview(self.frame)
        self.tree['columns'] = (1, 2, 3, 4, 5)
        self.tree.column('#0', width=35)
        self.tree.column(1, width=130, anchor='center')
        self.tree.column(2, width=80, anchor='center')
        self.tree.column(3, width=80, anchor='center')
        self.tree.column(4, width=80, anchor='center')
        self.tree.column(5, width=80, anchor='center')
        self.tree.heading('#0', text='№')
        self.tree.heading(1, text='Интервал')
        self.tree.heading(2, text='Корень')
        self.tree.heading(3, text='Значение')
        self.tree.heading(4, text='Итераций')
        self.tree.heading(5, text='Ошибка')

        self.tree.grid(column=0, row=10, columnspan=2, sticky='EWSN')

        self.STEP_MODE = IntVar(self, value=0)
        self.SHOW_INFLECTION_POINTS = IntVar(self, value=1)
        self.SHOW_INFLECTION_POINTS.trace(
            'w', lambda *_args: self.redraw_main_plot(True))
        Checkbutton(self.frame,
                    text='Пошаговый режим',
                    variable=self.STEP_MODE).grid(column=0,
                                                  row=11,
                                                  sticky='WS')
        Checkbutton(self.frame, text='Показывать точка перегиба', variable=self.SHOW_INFLECTION_POINTS)\
            .grid(column=0, row=12, sticky='WS')

    def modify_lin_space_size_callback(self, value, callback):
        self.lin_space_label.configure(
            text=f'Количество точек графика: {round(LOG_BASE**value)}')
        callback(value)

    def modify_lin_space_size(self, size):
        self.lin_space_size = round(LOG_BASE**size)
        self.redraw_main_plot(True)

    def redraw_main_plot(self, draw=False):
        if self.st != self.lin_x.min() or self.en != self.lin_x.max(
        ) or self.lin_space_size != len(self.lin_x):
            self.lin_x = np.linspace(self.st, self.en, self.lin_space_size)

        if self.main_plot:
            self.main_plot.remove()
        if self.deriv_plot:
            self.deriv_plot.remove()
            self.deriv_plot = None
        if self.inflection_points:
            self.inflection_points.remove()
            self.inflection_points = None

        v = self.f(self.lin_x)
        self.main_plot = self.ax.plot(self.lin_x,
                                      v,
                                      label='f(x)',
                                      color='tab:blue')[0]

        if self.SHOW_INFLECTION_POINTS.get():
            v2 = np.diff(v)
            v2 = np.insert(v2, 0, v2[0] - (v2[1] - v2[0]))
            v2 /= ((self.en - self.st) / self.lin_space_size)

            v2 = np.diff(v2)
            second_derivative_is_zero = all([x < self.eps for x in v2])
            if not second_derivative_is_zero:
                v2 = np.append(v2, v2[-1])
                v2 /= ((self.en - self.st) / self.lin_space_size)
                inflection_points_x = []
                inflection_points_y = []
                for i in range(1, len(v2)):
                    if v2[i - 1] * v2[i] <= 0:
                        if v[i - 1] == 0:
                            continue
                        n = i - 1 if v2[i - 1] < v2[i] else i
                        x = self.st + (self.en -
                                       self.st) / self.lin_space_size * n
                        y = self.f(x)

                        inflection_points_x.append(x)
                        inflection_points_y.append(y)

                self.inflection_points = self.ax.scatter(inflection_points_x,
                                                         inflection_points_y,
                                                         80,
                                                         marker='x',
                                                         color='violet')

                self.deriv_plot = self.ax.plot(self.lin_x,
                                               v2,
                                               label="f''(x)",
                                               color='tab:green')[0]

        mx_y = max(v)
        mn_y = min(v)
        m = (mx_y - mn_y) / 50
        dx = abs(self.en - self.st) * 0.05
        self.ax.set_ylim(mn_y - m, mx_y + m)
        self.ax.set_xlim(self.st - dx, self.en + dx)

        if draw:
            self.fagg.draw()

    # Первичное отображение, подготавливает все данные для него.
    def prepare(self):
        step = (self.en - self.st) / self.div

        self.redraw_main_plot()

        for plt in self.plots:
            plt.remove()
        self.plots.clear()
        for line in self.h_lines:
            line.remove()
        self.h_lines.clear()

        for i in range(self.div + 1):
            x = (self.st + step * i)
            self.h_lines.append(self.ax.axvline(x, color='black'))

        self.plots = [
            self.ax.plot(self.lin_x,
                         self.solver.hord.k * self.lin_x + self.solver.hord.b,
                         label='lin',
                         color='tab:orange')[0],
            self.ax.scatter([self.solver.p1.x], [self.solver.p1.y],
                            marker='o',
                            color='red'),
            self.ax.scatter([self.solver.p_fixed.x], [self.solver.p_fixed.y],
                            marker='o',
                            color='blue')
        ]
        self.fagg.draw()

    def var_debounce(self,
                     func: Callable[[str], None],
                     t: int = 500) -> Callable:
        def inner(*args):
            func(self.tk.globalgetvar(args[0]))

        return self.debounce(inner, t)

    def debounce(self, func: Callable[..., None], t: int = 500) -> Callable:
        return Debouncer(self, func, t)

    def expression_input(self, value):
        try:
            self.cached_function = eval('lambda x: ' + value)
            self.reset()
        except Exception as e:
            # traceback.print_exc()
            # print(e)
            pass

    def params_input(self, value, var_name):
        self.__setattr__(var_name, value)
        self.reset()

    def reset(self):
        if self.after_job_id:
            self.after_cancel(self.after_job_id)
        self.started = False
        self.done = False
        self.tree.delete(*self.solution_ids)
        self.solutions.clear()
        self.solution_ids.clear()
        self.solver = HordEquationSolver(self.st, self.en, self.div, self.eps,
                                         self.f)
        self.b_start.configure(text='start')
        self.b_start.bind('<Button>', self.start)
        self.prepare()

    def start(self, event):
        if self.STEP_MODE.get():
            self.step_solve()
        else:
            if not self.started or self.paused:
                self.started = True
                self.paused = False
                self.step_solve()
                event.widget.configure(text='stop')
                event.widget.bind('<Button>', self.stop)

    def stop(self, event):
        self.paused = True
        if self.after_job_id:
            self.after_cancel(self.after_job_id)
        event.widget.configure(text='start')
        event.widget.bind('<Button>', self.start)

    # Перерисовка хорды и точек пересечения.
    def redraw_solution(self):
        for pt in self.plots:
            pt.remove()
        self.plots = [
            self.ax.plot(self.lin_x,
                         self.solver.hord.k * self.lin_x + self.solver.hord.b,
                         label='lin',
                         color='tab:orange')[0],
            self.ax.scatter([self.solver.p1.x], [self.solver.p1.y],
                            marker='o',
                            color='red'),
            self.ax.scatter([self.solver.p_fixed.x], [self.solver.p_fixed.y],
                            marker='o',
                            color='blue')
        ]
        self.fagg.draw()
        self.ax.relim()

    def step_solve(self):
        if self.started and not self.solver.done or self.STEP_MODE.get():
            status = self.solver.next_step()
            self.redraw_solution()
            if not status:
                if self.started and not self.paused and not self.STEP_MODE.get(
                ):
                    self.after_job_id = self.after(100, self.step_solve)
            else:
                self.add_solution(self.solver.get_solution())
                if self.solver.next_segment():
                    print('DONE!!!!')
                    self.b_start.configure(text='DONE!!!!')
                    self.b_start.unbind('<Button>')
                else:
                    self.redraw_solution()
                    if not self.STEP_MODE.get():
                        self.after_job_id = self.after(200, self.step_solve)

    def add_solution(self, sol):
        if sol.err == 0:
            interval = f'({sol.interval[0]:.5} : {sol.interval[1]:.5})'
            iid = self.tree.insert('',
                                   'end',
                                   text=str(len(self.solutions) + 1),
                                   values=(interval, f'{sol.x:.7}',
                                           f'{sol.y:.5}', sol.iter, sol.err))
        else:
            iid = self.tree.insert('',
                                   'end',
                                   text=str(len(self.solutions) + 1),
                                   values=('', '', '', '', sol.err))
        self.solutions.append(sol)
        self.solution_ids.append(iid)
Exemple #32
0
class NameView(object):
    """Shows a treeview of unique names."""
    def __init__(self, master, names):
        self.widget = Frame(master)
        self._tree = Treeview(self.widget, columns='name')
        self._tree.grid(row=0, column=0, sticky=(N, S, W, E))
        self._tree.view = self
        self.widget.columnconfigure(0, weight=1)
        self.widget.rowconfigure(0, weight=1)
        self._tree.column('name', width=50)
        self._tree['show'] = 'tree'
        actions = {
            'edit': lambda e: self.edit(),
            'search': lambda e: self.search(),
            'focus_next': lambda e: self.focus_next(),
            'focus_prev': lambda e: self.focus_prev(),
            'select':
            lambda e: self._tree.selection_toggle(self._tree.focus()),
            'clear_selection': lambda e: self._tree.selection_set([])
        }
        kb.make_bindings(kb.tagview, actions, self._tree.bind)
        self._iids = dict()
        self._names = dict()
        logger.debug('Names: %s', names)
        self.widget.focus_set = self._tree.focus_set
        for name in sorted(names):
            iid = self._tree.insert('', 'end', text=name)
            self._names[iid] = name
            self._iids[name] = iid
        self._scroll = Scrollbar(self.widget, command=self._tree.yview)
        self._tree['yscrollcommand'] = self._scroll.set
        self._scroll.grid(row=0, column=1, sticky=(N, S))
        self.widget.columnconfigure(1, weight=0)

    def selection(self):
        logger.debug('Selection: %s', self._tree.selection())
        return [self._names[iid] for iid in self._tree.selection()]

    def edit(self):
        self._tree.event_generate('<<NameViewEdit>>')

    def search(self):
        if len(self._tree.selection()) == 0:
            self._tree.selection_add(self._tree.focus())
        self._tree.event_generate('<<NameViewSearch>>')

    def append(self, names):
        logger.debug('Append names: %s', names)
        for name in names:
            if name not in self._names.values():
                iid = self._tree.insert('', 'end', text=name)
                self._names[iid] = name
                self._iids[name] = iid

    def delete(self, name):
        self._tree.delete(self._iids[name])
        del self._names[self._iids[name]]
        del self._iids[name]

    def _focus(self, iid):
        self._tree.focus(iid)
        self._tree.see(iid)

    def focus_next(self):
        cur_iid = self._tree.focus()
        next_iid = self._tree.next(cur_iid)
        if next_iid == '':
            iids = self._tree.get_children()
            next_iid = iids[0]
        self._focus(next_iid)

    def focus_prev(self):
        cur_iid = self._tree.focus()
        prev_iid = self._tree.prev(cur_iid)
        if prev_iid == '':
            iids = self._tree.get_children()
            prev_iid = iids[-1]
        self._focus(prev_iid)

    def jump_to(self, name):
        try:
            iid = self._iids[name]
            self._focus(iid)
        except KeyError:
            pass

    def get_names(self):
        return tuple(self._names.values())

    def set(self, names):
        self._tree.delete(*self._iids.values())
        self._iids.clear()
        self._names.clear()
        for name in sorted(names):
            iid = self._tree.insert('', 'end', text=name)
            self._names[iid] = name
            self._iids[name] = iid
Exemple #33
0
class MainWindow:
    """
    Класс главного окна
    """
    def __init__(self, top=None):
        """
        Создание всех элементов окна
        """

        top.geometry("1200x570+120+20")
        top.title("Football Analyser")
        top.configure(background=config.background_color)
        top.configure(highlightbackground=config.background_color)
        top.configure(highlightcolor="black")

        self.tree_view = Treeview(top, show="headings")

        self.first_name_label = Label(top)
        self.last_name_label = Label(top)
        self.country_label = Label(top)
        self.age_label = Label(top)
        self.plays_label = Label(top)
        self.goals_label = Label(top)

        self.first_name_entry = Entry(top)
        self.last_name_entry = Entry(top)
        self.country_entry = Entry(top)
        self.age_entry = Entry(top)
        self.plays_entry = Entry(top)
        self.goals_entry = Entry(top)

        self.entries_list = [
            self.first_name_entry, self.last_name_entry, self.country_entry,
            self.age_entry, self.plays_entry, self.goals_entry
        ]

        self.add_button = Button(top)
        self.delete_button = Button(top)
        self.modify_button = Button(top)
        self.clear_fields_button = Button(top)
        self.analyze_button = Button(top)

        self.configure_tree_view()\
            .configure_labels()\
            .configure_entries()\
            .configure_buttons()\
            .fill_on_start()

    def configure_tree_view(self):
        """
        Настройка treeview для отображения всех записей
        """

        self.tree_view.place(relx=0.008,
                             rely=0.018,
                             relheight=0.837,
                             relwidth=0.754)

        self.tree_view["columns"] = ("First name", "Last name", "Country",
                                     "Age", "Plays", "Goals")

        self.tree_view.column("First name", width=200)
        self.tree_view.column("Last name", width=200)
        self.tree_view.column("Country", width=100)
        self.tree_view.column("Age", width=100)
        self.tree_view.column("Plays", width=100)
        self.tree_view.column("Goals", width=100)

        self.tree_view.heading("First name", text="First name")
        self.tree_view.heading("Last name", text="Last name")
        self.tree_view.heading("Country", text="Country")
        self.tree_view.heading("Age", text="Age")
        self.tree_view.heading("Plays", text="Plays")
        self.tree_view.heading("Goals", text="Goals")

        self.tree_view.bind("<<TreeviewSelect>>",
                            lambda event: self.on_select_item())

        return self

    def configure_labels(self):
        """
        Настройка текста над полями ввода
        """

        self.first_name_label.place(relx=0.775, rely=0.07, height=26, width=74)
        self.first_name_label.configure(background=config.background_color)
        self.first_name_label.configure(text="First name")

        self.last_name_label.place(relx=0.775, rely=0.193, height=26, width=73)
        self.last_name_label.configure(background=config.background_color)
        self.last_name_label.configure(text="Last name")

        self.country_label.place(relx=0.775, rely=0.316, height=26, width=57)
        self.country_label.configure(background=config.background_color)
        self.country_label.configure(text="Country")

        self.age_label.place(relx=0.775, rely=0.439, height=26, width=33)
        self.age_label.configure(background=config.background_color)
        self.age_label.configure(text="Age")

        self.plays_label.place(relx=0.775, rely=0.561, height=26, width=39)
        self.plays_label.configure(background=config.background_color)
        self.plays_label.configure(text="Plays")

        self.goals_label.place(relx=0.775, rely=0.684, height=26, width=43)
        self.goals_label.configure(background=config.background_color)
        self.goals_label.configure(text="Goals")

        return self

    def configure_entries(self):
        """
        Настройка полей ввода
        """

        self.first_name_entry.place(relx=0.775,
                                    rely=0.123,
                                    height=24,
                                    relwidth=0.17)
        self.first_name_entry.configure(font=config.font)

        self.last_name_entry.place(relx=0.775,
                                   rely=0.246,
                                   height=24,
                                   relwidth=0.17)
        self.last_name_entry.configure(font=config.font)

        self.country_entry.place(relx=0.775,
                                 rely=0.368,
                                 height=24,
                                 relwidth=0.17)
        self.country_entry.configure(font=config.font)

        self.age_entry.place(relx=0.775, rely=0.491, height=24, relwidth=0.17)
        self.age_entry.configure(font=config.font)

        self.plays_entry.place(relx=0.775,
                               rely=0.614,
                               height=24,
                               relwidth=0.17)
        self.plays_entry.configure(font=config.font)

        self.goals_entry.place(relx=0.775,
                               rely=0.737,
                               height=24,
                               relwidth=0.17)
        self.goals_entry.configure(font=config.font)

        return self

    def configure_buttons(self):
        """
        Настройка кнопок
        """

        self.add_button.place(relx=0.792, rely=0.807, height=33, width=40)
        self.add_button.configure(background=config.background_color)
        self.add_button.configure(text="Add")
        self.add_button.configure(command=self.add_item)

        self.delete_button.place(relx=0.9, rely=0.807, height=33, width=56)
        self.delete_button.configure(background=config.background_color)
        self.delete_button.configure(text="Delete")
        self.delete_button.configure(command=self.delete_item)

        self.modify_button.place(relx=0.842, rely=0.807, height=33, width=59)
        self.modify_button.configure(background=config.background_color)
        self.modify_button.configure(text="Modify")
        self.modify_button.configure(command=self.modify_item)

        self.clear_fields_button.place(relx=0.8,
                                       rely=0.895,
                                       height=33,
                                       width=166)
        self.clear_fields_button.configure(background=config.background_color)
        self.clear_fields_button.configure(text="Clear fields")
        self.clear_fields_button.configure(command=self.clear_all_entries)

        self.analyze_button.place(relx=0.225, rely=0.877, height=53, width=336)
        self.analyze_button.configure(background=config.background_color)
        self.analyze_button.configure(text="Analyze")
        self.analyze_button.configure(font="-size 18")
        self.analyze_button.configure(command=self.analyze)

        return self

    def fill_on_start(self):
        """
        Заполнение treeview записями из базы данных
        """

        for row in db.get_records():
            self.tree_view.insert("", tk.END, values=row)
        return self

    def on_select_item(self):
        """
        Отображение выбранной записи в полях ввода для редактирования
        """

        values = self.tree_view.item(self.tree_view.focus())["values"]
        for entry, val in zip(self.entries_list, values):
            entry.delete(0, tk.END)
            entry.insert(0, val)

    def clear_all_entries(self):
        """
        Очистка всех полей ввода
        """

        for entry in self.entries_list:
            entry.delete(0, tk.END)

    def delete_item(self):
        """
        Удаление записи
        """

        item = self.tree_view.focus()
        db.delete_record(self.tree_view.index(item))
        self.tree_view.delete(item)
        self.clear_all_entries()

    def add_item(self):
        """
        Добавление записи
        """

        try:
            first_name = validator.validate_text(self.first_name_entry.get())
            last_name = validator.validate_text(self.last_name_entry.get())
            country = validator.validate_text(self.country_entry.get())
            age = validator.validate_number(self.age_entry.get())
            plays = validator.validate_number(self.plays_entry.get())
            goals = validator.validate_number(self.goals_entry.get())

            db.insert_record({
                "first_name": first_name,
                "last_name": last_name,
                "country": country,
                "age": age,
                "plays": plays,
                "goals": goals
            })
            self.tree_view.insert("",
                                  tk.END,
                                  values=(first_name, last_name, country, age,
                                          plays, goals))

        except ValueError:
            messagebox.showerror("Invalid input",
                                 "Input are not valid string or number")

        self.on_select_item()

    def modify_item(self):
        """
        Изменение записи
        """

        try:
            item = self.tree_view.focus()
            index = self.tree_view.index(item)

            first_name = validator.validate_text(self.first_name_entry.get())
            last_name = validator.validate_text(self.last_name_entry.get())
            country = validator.validate_text(self.country_entry.get())
            age = validator.validate_number(self.age_entry.get())
            plays = validator.validate_number(self.plays_entry.get())
            goals = validator.validate_number(self.goals_entry.get())

            db.update_record(
                index, (first_name, last_name, country, age, plays, goals))
            self.tree_view.item(item,
                                values=(first_name, last_name, country, age,
                                        plays, goals))

        except ValueError:
            messagebox.showerror("Invalid input",
                                 "Input are not valid string or number")

        self.on_select_item()

    def analyze(self):
        """
        Вызов анализа
        """

        analyse.full_analysis()
        messagebox.showinfo("Done",
                            "Файлы отчета сохранены в output и graphics")
Exemple #34
0
class report:
    def showit(self):
        try:
            global con
            dt1 = self.fromdate.get()
            dt1 = datetime.datetime.strptime(dt1,'%m/%d/%y').strftime('%Y-%m-%d')
            dt2 = self.todate.get()
            dt2 = datetime.datetime.strptime(dt2,'%m/%d/%y').strftime('%Y-%m-%d')

            print(dt1)
            print(dt2)

            cr = con.cursor()
            s = "select * from billtable where date1>='"+str(dt1)+"' and date1<='"+str(dt2)+"'"
            print(s)
            cr.execute(s)
            res = cr.fetchall()
            print(list(res))

            for child in self.tr.get_children():
                self.tr.delete(child)

            count = 0
            for i in res:
                self.tr.insert('',index=count,values=i)
                count+=1
        except Exception as e:
            print(e)

    def __init__(self):
        self.window = Tk()
        self.window.title("Report")
        #self.window.geometry("900x500+200+100")
        self.window.resizable(0,0)
        img = PhotoImage(file="57635230-portrait-of-an-happy-couple-they-are-laughing-and-eating-pizza-and-having-a-great-time-.png")
        Label(self.window, image=img).place(x=0, y=0)

        #this code is for labels
        self.todaysday_lb = Label(self.window,text="From",font=('Arial',18)).grid(row=0,column=0,ipadx=10,pady=30,padx=10,ipady=5)
        self.day_lb = Label(self.window,text="To",font=('Arial',18)).grid(row=0,column=2,ipadx=10,pady=30,padx=10,ipady=5)

        # this code is for entry box
        d = datetime.datetime.now()
        self.ans = StringVar()
        self.ans.set(str(d.date()))
        self.fromdate = DateEntry(self.window,textvariable=self.ans,font=('Arial',12))
        self.fromdate.grid(row=0, column=1,ipadx=5,pady=30,padx=10,ipady=5)
        self.todate = DateEntry(self.window)
        self.todate.grid(row=0, column=3,ipadx=10,pady=30,padx=10,ipady=5)

        # this code is for button
        self.showme = Button(self.window,text="Show",command=self.showit,bd=10,width=10).grid(row=0, column=4,ipadx=10,pady=20,padx=20,ipady=5)
        self.tr = Treeview(self.window,
                           columns=("id", "date1", "total", "gst", "netamount", "customername", "mobileno", "email"))
        self.tr.column("0",width=130)
        self.tr.column("1",width=130)
        self.tr.column("2",width=130)
        self.tr.column("3",width=130)
        self.tr.column("4",width=130)
        self.tr.column("5",width=130)
        self.tr.column("6",width=130)
        self.tr.column("7",width=180)


        self.tr.heading("id", text="ID")
        self.tr.heading("date1", text="Date")
        self.tr.heading("total", text="Total")
        self.tr.heading("gst", text="GST")
        self.tr.heading("netamount", text="Net Amount")
        self.tr.heading("customername", text="Customer Name")
        self.tr.heading("mobileno", text="Mobile No.")
        self.tr.heading("email", text="Email")
        self.tr['show'] = "headings"


        self.tr.grid(row=1, column=0,columnspan=6,ipadx=10,pady=30,padx=10,ipady=5)
        self.close = Button(self.window, text="Cancel", command=self.window.destroy,width=15,height=3,bd=10).grid(row=2,column=2)



        self.window.mainloop()
class Booked:
    """Booked class: A Booked window.
     - Can view your see your booking history
     - Can remove your booking (only future booking)
     - View Movie detail
     - See your tickets information
    "window": it is a Tk() object (tkinter object) that is passed around so we do not need to create it every single
    time
    old_window: reference to the tk() object (Login window)
    username: User's username -_-"""
    def __init__(self, window, old_window, username):
        self.username = username
        self.old_window = old_window

        self.window = window
        self.window.title("Booked")

        # Customers Options
        self.home = Button(self.window, text="Home", font=("Arial", 30), bd=0, bg="#CBFBB5", command=self.goto_home)
        self.home.grid(row=0, column=0, padx=(15, 10))
        self.booking = Button(self.window, text=" Booking ", font=("Arial", 30), bd=0, bg="#CA65F5",
                              command=self.goto_booking)
        self.booking.grid(row=0, column=1, padx=(0, 10))
        self.booked = Button(self.window, text=" Booked ", font=("Arial", 30), bd=0, bg="#1F8BF3")
        self.booked.grid(row=0, column=2, padx=(0, 10))
        self.user = Button(self.window, text=" User ", font=("Comic Sans", 30), bd=0, bg="#BDC3C7", command=self.goto_user)
        self.user.grid(row=0, column=3, padx=(0, 10))
        self.sign_out = Button(self.window, text=" Sign Out ", font=("Comic Sans", 30), bd=0, bg="#FF916E",
                               command=self.goto_sign_out)
        self.sign_out.grid(row=0, column=4, padx=(0, 10))

        self.heading = Label(self.window, text="Your movie Tickets", font=("Arial", 20))
        self.heading.grid(row=1, column=0, columnspan=20, pady=(30, 15))

        # all_info structure is : name, date, time, hall, tickets, num_tickets
        self.all_info, self.print_info = [None, None]

        # Table of booked tickets
        self.table = Treeview(self.window)
        self.table.grid(row=2, column=0, columnspan=30, padx=(10, 0))
        # Scroll bar for the table
        self.scroll_y = Scrollbar(self.window, orient="vertical", command=self.table.yview)
        self.scroll_y.place(x=860, y=159)

        self.create_table()  # Creates the table

        # Movie Info Button
        self.movie_info_btn = Button(self.window, text="Movie Info", font=("Arial", 18), command=self.movie_info,
                                     bg="#F69898")
        self.movie_info_btn.place(x=150, y=398)
        # Ticket Info Button
        self.ticket_info_btn = Button(self.window, text="Ticket Info", font=("Arial", 18), command=self.ticket_info,
                                      bg="#788EB2")
        self.ticket_info_btn.place(x=360, y=398)

        # Remove tickets
        self.remove_booking_btn = Button(self.window, text="Remove Booking", font=("Arial", 18), bg="#B28078",
                                         command=self.remove_booking)
        self.remove_booking_btn.place(x=550, y=398)

        # All the widget I created, I store it here. So i can easily destroy them later.
        self.widgets = [self.home, self.booked, self.booking, self.user, self.sign_out, self.heading, self.table,
                        self.scroll_y, self.movie_info_btn, self.ticket_info_btn, self.remove_booking_btn]



    def goto_home(self):
        """Takes you to the Home window"""

        self.destroy_all()
        self.window.Home(window=self.window, old_window=self.old_window, username=self.username)

    def goto_booking(self):
        """Takes you to the booking window"""

        self.destroy_all()
        self.window.Booking(window=self.window, old_window=self.old_window, username=self.username)

    def goto_user(self):
        """Takes you to the user window"""

        self.destroy_all()
        self.window.User(window=self.window, old_window=self.old_window, username=self.username, customer=True)

    def goto_sign_out(self):
        """Signs out the user and takes the user back to the Login menu. It also logs the date and the time when the
              user signs out"""
        logging.basicConfig(level=logging.INFO, filename="logging.log")
        logging.info(f"Username: {self.username} Sign-out {datetime.datetime.now()}")
        self.window.destroy()
        self.old_window.deiconify()

    def destroy_all(self):
        """ destroy_all() Destroys all the widget (Clears the window, so I can use the same window for adding new
         widgets) """

        [widget.destroy() for widget in self.widgets]

    def remove_booking(self):
        """ remove_booking() ---> remove future booking
        - If the it is an old booking, you can not remove it
        - If you don't choose any tickets, you will get a message saying "Please choose the ticket first"
        - If you remove the tickets, it updates the database.
        - Updates the available seats, the cinema seats layout and remove your booking from the database"""

        num = self.table.focus()
        id = self.table.item(num)["values"]
        if id:
            year, month, day = [int(num) for num in id[2].split("-")]
            hour, min = [int(time) for time in id[3].split(":")]
            booked_date = datetime.datetime(year=year, month=month, day=day, hour=hour, minute=min)
            now = datetime.datetime.now()
            if booked_date >= now:
                if messagebox.askyesno("Confirm", f"Are you sure that you want to delete this ticket?"
                f"\n{self.print_info[id[0]]}"):
                    global cinemaDB_path
                    cinemaDB_path = os.path.abspath(os.path.join(os.path.dirname(__file__), "..", f"{id[4]}.db"))
                    db = sqlite3.connect(cinemaDB_path)
                    cursor = db.cursor()
                    cursor.execute("""SELECT sp.cinema_layout, c.user_tickets, c.num_tickets, sp.available_seats, sp.seating_planID, c.ID
                    FROM seating_plan sp, customer_tickets c, schedule s
                    WHERE sp.scheduleID = c.scheduleID
                    AND sp.scheduleID = s.scheduleID
                    AND s.date=? AND s.time=? AND s.cinema_hall=? """, (id[2], id[3], self.all_info[id[0] - 1][3]))
                    temp = cursor.fetchone()
                    cinema_layout = temp[0]
                    user_tickets = temp[1]
                    new_available_seats = temp[3] + temp[2]
                    seating_planID = temp[4]
                    unique_customerID = temp[5]

                    # Update the seating plan beacuse there are free seats now
                    updated_layout = remove_seats(list_layout=cinema_layout, user_tickets=user_tickets)

                    # Update the database
                    cursor.execute("""UPDATE seating_plan SET available_seats=?, cinema_layout=? 
                    WHERE seating_planID=?""", (new_available_seats, updated_layout, seating_planID))
                    cursor.execute("""DELETE FROM customer_tickets WHERE ID=?""", (unique_customerID,))
                    db.commit()

                    self.create_table(update=True)  # Updates the table

            else:
                messagebox.showwarning("Invalid", "You can not delete this ticket")

        else:
            messagebox.showinfo("Invalid", "Please choose the ticket first.")

    def ticket_info(self):
        """ticket_info() --> show the message on your tickets
        Movie name, location, date, time, cinema hall, number of seats, adult tickets, child tickets, seat location,
        cost
        If you don't choose any tickets, you will get a message saying "Please choose the ticket first"  """

        num = self.table.focus()
        id = self.table.item(num)["values"]

        if id:
            messagebox.showinfo("Your ticket", self.print_info[id[0]])
        else:
            messagebox.showinfo("Invalid", "Please choose the ticket first.")

    def movie_info(self):
        """
        movie_into() --> take you the movie information page
        If you don't choose any tickets, you will get a message saying "Please choose the ticket first"
        """
        num = self.table.focus()
        id = self.table.item(num)["values"]
        if id:
            self.window.withdraw()
            MovieInfo(movie_name=id[1], old_window=self.window, location=id[4])
        else:
            messagebox.showinfo("Invalid", "Please choose the ticket first.")

    def create_table(self, update=False):
        """create_table(update) --> create the table with the user booked history
        if the argument update=False, then the table is created from scratch
        if the argument update=True, then if will only update the information on the table
        Using method get_booked_tickets() to get the user booked information
        """

        # all_info structure: name, date, time, hall, tickets, num_tickets
        self.all_info, self.print_info = get_booked_tickets(username=self.username)

        # Create the table from scratch
        if not update:
            heading_name = ["Num", "Movie", "Date", "Time", "Location"]     # Heading for my table

            self.table["show"] = "headings"
            self.table["columns"] = list(range(len(heading_name)))

            for i in range(len(heading_name)):
                self.table.heading(i, text=heading_name[i])

            for i in range(len(self.all_info)):
                self.table.insert("", 'end', text="L1", values=(i + 1, self.all_info[i][0], self.all_info[i][1],
                                                                self.all_info[i][2], self.all_info[i][9]))

            # I am adjusting the table structure
            self.table.column(0, anchor="center", width=60)
            self.table.column(1, anchor="center", width=250)
            self.table.column(2, anchor="center", width=150)
            self.table.column(3, anchor="center", width=120)
            self.table.column(4, anchor="center")
        else:
            # Clear the table first before adding to the table
            for i in self.table.get_children():
                self.table.delete(i)

            # Fill in the table with new data
            for i in range(len(self.all_info)):
                self.table.insert("", 'end', text="L1", values=(i + 1, self.all_info[i][0], self.all_info[i][1],
                                                                self.all_info[i][2], self.all_info[i][9]))
Exemple #36
0
class main:
    def __init__(self):
        self.tk = Toplevel()
        height = self.tk.winfo_screenheight()
        width = self.tk.winfo_screenwidth()

        y = (height - 650) // 2
        x = (width - 650) // 2
        self.tk.geometry('650x650+' + str(x) + '+' + str(y))

        self.tk.resizable(height=False, width=False)
        self.tk.title("manage patient")

        self.f = Frame(self.tk, height="650", width="650", bg="#CEE3F6")
        self.f.place(x=0, y=0)

        self.f1 = Frame(self.f, height="100", width="650", bg="#070719")
        self.f1.place(x=0, y=0)

        self.l = Label(self.f1,
                       text="Manage Patient",
                       font=('cooper black', 35),
                       fg="#CEE3F6",
                       bg="#070719")
        self.l.place(x=150, y=20)

        self.fr = Frame(self.f, height="70", width="650", bg="#070719")
        self.fr.place(x=0, y=580)
        self.fr1 = Frame(self.f, height="10", width="650", bg="#070719")
        self.fr1.place(x=0, y=560)

        self.table = Treeview(self.f,
                              column=("#0", "#1", "#2", "#3", "#4", "#5", "#6",
                                      "#7", "#8", "#9"))
        style = ttk.Style()
        style.theme_use("alt")
        ttk.Style().configure("Treeview.heading", font=('', 30))
        self.table.heading("#0", text="sno")
        self.table.column("#0", width="30")
        self.table.heading("#1", text="Name")
        self.table.column("#1", width="60")
        self.table.heading("#2", text="Gender")
        self.table.column("#2", width="60")
        self.table.heading("#3", text="Age")
        self.table.column("#3", width="60")
        self.table.heading("#4", text="contact")
        self.table.column("#4", width="70")
        self.table.heading("#5", text="Address")
        self.table.column("#5", width="70")
        self.table.heading("#6", text="Email")
        self.table.column("#6", width="90")
        self.table.heading("#7", text="History")
        self.table.column("#7", width="70")

        self.table.heading("#8", text="Edit")
        self.table.column("#8", width="70")
        self.table.heading("#9", text="Delete")
        self.table.column("#9", width="70")
        self.table.place(x=0, y=200)

        s = database_queries.database()
        res = s.view_patient()
        print(res)
        for i in res:

            self.table.insert('',
                              'end',
                              text=i[0],
                              value=(i[1], i[2], i[3], i[4], i[5], i[6],
                                     "History", "Edit", "Delete"))
            self.table.bind("<Double Button>", self.trigger)
            self.table.place()

        self.tk.mainloop()

    def trigger(self, e):
        #print(e)
        d = self.table.focus()
        g = (self.table.item(d))
        col = self.table.identify_column(e.x)
        if col == "#8":
            y = editp.main(g["text"])
            print("edit")

        elif col == "#9":
            print("delete")
            f = del_appoint()
Exemple #37
0
#滚动条

scrollBar = tkinter.Scrollbar(frame)

scrollBar.pack(side=tkinter.RIGHT, fill=tkinter.Y)

#Treeview组件,6列,显示表头,带垂直滚动条
tree = Treeview(frame,
                columns=('c1', 'c2', 'c3', 'c4', 'c5', 'c6', 'c7', 'c8'),
                show="headings",
                yscrollcommand=scrollBar.set,
                height=50)

#设置每列宽度和对齐方式

tree.column('c1', width=70, anchor='center')

tree.column('c2', width=40, anchor='center')

tree.column('c3', width=40, anchor='center')

tree.column('c4', width=120, anchor='center')

tree.column('c5', width=100, anchor='center')

tree.column('c6', width=90, anchor='center')

#设置每列表头标题文本

tree.heading('c1', text='姓名')
Exemple #38
0
 def CreateUI(self):
     self.frame1 = Frame(self)
     self.frame2 = Frame(self)
     from tkinter.ttk import Treeview
     tv = Treeview(self)
     tv['columns'] = ('address', 'phone_no', 'check_in', 'waiter', 'table',
                      'bill')
     tv.heading("#0", text='Customer Name', anchor='w')
     tv.column("#0", anchor="w")
     tv.heading('address', text='Address')
     tv.column('address', anchor='center', width=100)
     tv.heading('phone_no', text='Phone No.')
     tv.column('phone_no', anchor='center', width=100)
     tv.heading('check_in', text='Check In To')
     tv.column('check_in', anchor='center', width=100)
     tv.heading('waiter', text='Waiter')
     tv.column('waiter', anchor='center', width=100)
     tv.heading('table', text='Table No.')
     tv.column('table', anchor='center', width=100)
     tv.heading('bill', text='Current Bill')
     tv.column('bill', anchor='center', width=100)
     tv.grid(sticky=(N, S, W, E))
     self.frame1.treeview = tv
     self.frame1.grid_rowconfigure(0, weight=1)
     self.frame1.grid_columnconfigure(0, weight=1)
     self.frame2.grid(row=0, column=1, sticky=N)
     self.button = Button(self.frame2, text="Add")
     self.button.grid(row=0, column=0)
     self.button1 = Button(self.frame2, text="Modify")
     self.button1.grid(row=1, column=0)
     self.button2 = Button(self.frame2, text="Delete")
     self.button2.grid(row=2, column=0)
     self.button3 = Button(self.frame2, text="Delete All")
     self.button3.grid(row=3, column=0)
class RssPage(tk.Frame):  # 继承Frame类
    def __init__(self, parent, controller):
        tk.Frame.__init__(self, parent)
        self.controller = controller

        self.rss_list = []

        self.rss_path = './conf/rss_config.pickle'

        if not os.path.isfile(self.rss_path):
            self.create_config()

        self.var_rss_link = StringVar()
        self.var_rss_site = StringVar()
        self.var_rss_name = StringVar()

        self.label_link = Label(self, text='链接:', anchor=W)
        self.label_name = Label(self, text='别名:', anchor=W)
        self.label_site = Label(self, text='站点:', anchor=W)

        self.entry_rss_link = tk.Entry(self,
                                       textvariable=self.var_rss_link,
                                       width=58,
                                       borderwidth=2,
                                       font=('Helvetica', '12'))
        self.entry_rss_name = tk.Entry(self,
                                       textvariable=self.var_rss_name,
                                       width=58,
                                       borderwidth=2,
                                       font=('Helvetica', '12'))
        self.entry_rss_site = tk.Entry(self,
                                       textvariable=self.var_rss_site,
                                       width=58,
                                       borderwidth=2,
                                       font=('Helvetica', '12'))
        self.button_add = tk.Button(self,
                                    text='添加',
                                    width=6,
                                    command=self.add_to_list)

        self.frame_m = Frame(self)
        self.scrollBar = Scrollbar(self.frame_m)
        self.tree = Treeview(self.frame_m,
                             columns=('c1', 'c2', 'c3'),
                             show="headings",
                             yscrollcommand=self.scrollBar.set)

        self.button_delete = tk.Button(self,
                                       text='删除',
                                       command=self.delete_rss)
        self.button_save = tk.Button(self, text='保存', command=self.save_config)

        self.create_page()
        self.load_config()

    def load_config(self):
        try:
            with open(self.rss_path, "rb") as rss_file:
                rss_list = pickle.load(rss_file)
                for item in rss_list:
                    self.tree.insert('',
                                     'end',
                                     values=[item[0], item[1], item[2]])
        except FileNotFoundError:
            pass

    def create_config(self):
        with open(self.rss_path, 'wb') as rss_file:
            self.rss_list = []
            pickle.dump(self.rss_list, rss_file)

    def save_config(self):
        rss_all = self.tree.get_children()
        self.rss_list.clear()
        for item in rss_all:
            value_rss_link = self.tree.item(item, 'values')[0]
            value_rss_name = self.tree.item(item, 'values')[1]
            value_rss_site = self.tree.item(item, 'values')[2]
            rss_tuple = (value_rss_link, value_rss_name, value_rss_site)
            self.rss_list.append(rss_tuple)

        with open(self.rss_path, 'wb') as rss_file:
            pickle.dump(self.rss_list, rss_file)

    def create_page(self):

        self.label_link.place(x=32, y=30, width=80, height=30)
        self.label_name.place(x=32, y=70, width=80, height=30)
        self.label_site.place(x=330, y=70, width=80, height=30)

        self.entry_rss_link.place(x=80, y=30, width=610, height=30)
        self.entry_rss_name.place(x=80, y=70, width=200, height=30)
        self.entry_rss_site.place(x=380, y=70, width=200, height=30)

        self.button_add.place(x=610, y=70, width=80, height=30)

        self.frame_m.place(x=32, y=120, width=680, height=420)

        # 在Frame容器中创建滚动条
        self.scrollBar.pack(side=RIGHT, fill=Y)

        # 在Frame容器中使用Treeview组件实现表格功能
        # Treeview组件,三列,显示表头,带垂直滚动条

        # 设置每列宽度和对齐方式
        self.tree.column('c1', width=400, anchor='center')
        self.tree.column('c2', width=140, anchor='center')
        self.tree.column('c3', width=120, anchor='center')

        # 设置每列表头标题文本
        self.tree.heading(
            'c1',
            text='链接',
            command=lambda: self.treeview_sort_column(self.tree, 'c1', False))
        self.tree.heading(
            'c2',
            text='别名',
            command=lambda: self.treeview_sort_column(self.tree, 'c2', False))
        self.tree.heading(
            'c3',
            text='站点名称',
            command=lambda: self.treeview_sort_column(self.tree, 'c3', False))

        # 左对齐,纵向填充
        self.tree.pack(side=LEFT, fill=Y)
        self.tree.bind('<Double-1>', self.treeviewclick)

        # Treeview组件与垂直滚动条结合
        self.scrollBar.config(command=self.tree.yview)

        # 删除按钮
        self.button_delete.place(x=160, y=555, width=120, height=30)

        # 刷新按钮
        self.button_save.place(x=460, y=555, width=120, height=30)

    def treeview_sort_column(self, tv, col, reverse):  # Treeview、列名、排列方式
        ll = [(tv.set(k, col), k) for k in tv.get_children('')]
        ll.sort(reverse=reverse)  # 排序方式
        for index, (val, k) in enumerate(ll):  # 根据排序后索引移动
            tv.move(k, '', index)
        tv.heading(col,
                   command=lambda: self.treeview_sort_column(
                       tv, col, not reverse))  # 重写标题,使之成为再点倒序的标题

    def add_to_list(self):
        value_rss_site = self.var_rss_site.get()
        value_rss_name = self.var_rss_name.get()
        value_rss_link = self.var_rss_link.get()
        values = [value_rss_link, value_rss_name, value_rss_site]
        self.tree.insert('', 'end', values=values)
        self.var_rss_link.set('')
        self.var_rss_name.set('')
        self.var_rss_site.set('')

    def delete_rss(self):
        if not self.tree.selection():
            tk.messagebox.showerror('抱歉', '你还没有选择,不能删除')
            return
        for item in self.tree.selection():
            self.tree.delete(item)

    def treeviewclick(self, event):
        selected_item = self.tree.selection()[0]
        link = self.tree.item(selected_item, 'values')[0]
        webbrowser.open(link)
Exemple #40
0
 def CreateUI(self):
     self.frame1 = Frame(self)
     self.frame2 = Frame(self)
     from tkinter.ttk import Treeview
     tv = Treeview(self)
     tv['columns'] = ('location', 'city', 'cutomer_count', 'total_table',
                      'total_waiter', 'sales')
     tv.heading("#0", text='Restaurant name', anchor='w')
     tv.column("#0", anchor="w")
     tv.heading('location', text='Location')
     tv.column('location', anchor='center', width=100)
     tv.heading('city', text='City')
     tv.column('city', anchor='center', width=100)
     tv.heading('cutomer_count', text='Customer Count')
     tv.column('cutomer_count', anchor='center', width=100)
     tv.heading('total_table', text='Total Table')
     tv.column('total_table', anchor='center', width=100)
     tv.heading('total_waiter', text='Total Waiter')
     tv.column('total_waiter', anchor='center', width=100)
     tv.heading('sales', text='Sales')
     tv.column('sales', anchor='center', width=100)
     tv.grid(sticky=(N, S, W, E))
     self.frame1.treeview = tv
     self.frame1.grid_rowconfigure(0, weight=1)
     self.frame1.grid_columnconfigure(0, weight=1)
     self.frame2.grid(row=0, column=1, sticky=N)
     self.button = Button(self.frame2, text="Add")
     self.button.grid(row=0, column=0)
     self.button1 = Button(self.frame2, text="Modify")
     self.button1.grid(row=1, column=0)
     self.button2 = Button(self.frame2, text="Delete")
     self.button2.grid(row=2, column=0)
     self.button3 = Button(self.frame2, text="Delete All")
     self.button3.grid(row=3, column=0)
Exemple #41
0
class SuperUser:

    def __init__(self):
        self.win = Tk()
        self.win.title("The Hive")
        self.win.geometry('{}x{}'.format(1000, 450))
        self.canvas = Canvas(self.win, bg='#454b54')
        self.acceptButton = Button(self.canvas, text="Accept", font='Arial 15 bold', bg='#454b54',
                                   fg="#f7cc35", command=self.accept)
        self.rejectButton = Button(self.canvas, text="Reject", font='Arial 15 bold', bg='#454b54',
                                   fg="#f7cc35", command=self.reject)
        self.list = Treeview(self.canvas, columns=(1, 2, 3, 4, 5, 6, 7, 8), show="headings", height="15")

    def main(self):
        self.canvas.pack(expand=TRUE, fill=BOTH)

        self.list.pack()
        self.list.heading(1, text="ID")
        self.list.column(1, width=20)
        self.list.heading(2, text="Name")
        self.list.column(2, width=100)
        self.list.heading(3, text="Email")
        self.list.column(3, width=150)
        self.list.heading(4, text="Reference")
        self.list.column(4, width=100)
        self.list.heading(5, text="Interest")
        self.list.column(5, width=100)
        self.list.heading(6, text="Credential")
        self.list.column(6, width=100)
        self.list.heading(7, text="Rejected #")
        self.list.column(7, width=120)
        self.list.heading(8, text="Appeal")
        self.list.column(8, width=300)

        db.cursor.execute('SELECT * FROM pending_users')
        for row in db.cursor.fetchall():
            self.list.insert('', END, values=row)

        self.acceptButton.pack(expand=TRUE, side=LEFT)
        self.rejectButton.pack(expand=TRUE, side=LEFT)

        self.win.mainloop()

    def accept(self):
        password = ''.join(random.choice(string.ascii_lowercase) for i in range(6))

        for selected_item in self.list.selection():
            a, b, c, d, e, f, g, h = self.list.item(selected_item, 'values')
            email = c
            username = generate_username(b)
            self.list.delete(selected_item)

        db.cursor.execute('INSERT INTO users (email, username, password, reputation_score, user_type, login_time) VALUES (%s, %s, %s, 10, "OU", "FIRST")',
                          (email, username, password))
        db.cursor.execute("DELETE FROM pending_users WHERE email = %s", (email,))

        subject = "Application Accepted!"
        content = '''\
            Congratz! Please change your password once you log in with the following credentials. \n
            Username: {username} \n
            Password: {password} \
            '''.format(username=username, password=password)
        send_email(subject, content, email)

    def reject(self):
        for selected_item in self.list.selection():
            email = self.list.item(selected_item, 'values')[2]
            self.list.delete(selected_item)

        db.cursor.execute("SELECT rejected FROM pending_users WHERE email = %s", (email,))
        rejNum = db.cursor.fetchone()[0]

        if rejNum == 0:
            rejNum += 1
            db.cursor.execute("UPDATE pending_users SET rejected = %s WHERE email = %s", (rejNum,email))

            subject = "Application Denied"
            content = '''\
                Sorry, but your application has been denied. \n
                You have one chance to appeal and the SU will make a final decision to \n
                reverse the rejection. If you receive another rejection, then you \n
                will be put in blacklist forever.  \
                '''
            send_email(subject, content, email)
        elif rejNum == 1:
            db.cursor.execute("DELETE FROM pending_users WHERE email = %s", (email,))
            db.cursor.execute("INSERT INTO black_list VALUES (%s, %s)", (db.getName(), email))
Exemple #42
0
class FensterTrans(GuiTemplate):
    def __init__(self, master):
        super().__init__(master)
        self.grid()

        tv_column_width_id = 50
        tv_column_width = 200
        tv_column_width_min = 200
        self.__pd_PLQuelle = Punkt_Dic()
        self.__pd_PLZiel = Punkt_Dic()
        self.__pd_PLTrans = Punkt_Dic()

        self.__dict_para = {}

        self.str_filePathSource = StringVar()
        self.str_filePathDest = StringVar()
        self.int_radioTrans = IntVar(value=0)

        self.dbl_ParaMY = DoubleVar()
        self.dbl_ParaMX = DoubleVar()
        self.dbl_ParaRotY = DoubleVar()
        self.dbl_ParaRotX = DoubleVar()
        self.dbl_ParaTransY = DoubleVar()
        self.dbl_ParaTransX = DoubleVar()

        lf_transType = LabelFrame(self, text="Ebene Transformationen")
        lf_transType.grid(row=0, column=0, padx=3, pady=3, sticky="w")
        lf_Source = LabelFrame(self, text="Quellsystem")
        lf_Source.grid(row=1,
                       column=0,
                       padx=3,
                       pady=3,
                       sticky="w",
                       columnspan=2)
        lf_Dest = LabelFrame(
            self,
            text=
            "Zielsystem (Markierung: Nichtbeachtung des Passpunktes bei der Transformation)"
        )
        lf_Dest.grid(row=1, column=3, padx=3, pady=3, sticky="w", columnspan=2)
        lf_Parameter = LabelFrame(self, text="Parameter")
        lf_Parameter.grid(row=2,
                          column=2,
                          padx=3,
                          pady=3,
                          sticky="",
                          columnspan=3)
        lf_Trans = LabelFrame(self, text="Zielsystem / transformiert")
        lf_Trans.grid(row=4, column=0, padx=3, pady=3, sticky="", columnspan=4)

        Radiobutton(lf_transType,text="Helmerttransformation", variable=self.int_radioTrans, value=0)\
            .grid(row=0, column=0, padx=3, pady=3)
        Radiobutton(lf_transType,text="Affintransformation", variable=self.int_radioTrans, value=1)\
            .grid(row=0, column=1, padx=3, pady=3)
        Button(self,text="Lade Punkte",command=self.BtnPressedLoadPoints)\
            .grid(row=0, column=1, padx=3, pady=3, sticky="w")
        Button(self,text="Berechnen",command=self.BtnPressedCalc)\
            .grid(row=2, column=0, padx=3, pady=3, columnspan=1,sticky="e")
        Button(self,text="Zeige Grafik",command=self.BtnPressedPlot)\
            .grid(row=2, column=1, padx=3, pady=3, columnspan=1,sticky="w")

        self.tv_punktListSource = Treeview(lf_Source, selectmode="none")
        self.tv_punktListSource.grid(row=0, column=0, padx=3, pady=3)
        self.tv_punktListSource["columns"] = ("y", "x")
        self.tv_punktListSource.column("#0",
                                       width=tv_column_width_id,
                                       minwidth=tv_column_width_id)
        self.tv_punktListSource.column("y",
                                       width=tv_column_width,
                                       minwidth=tv_column_width_min)
        self.tv_punktListSource.column("x",
                                       width=tv_column_width,
                                       minwidth=tv_column_width_min)
        self.tv_punktListSource.heading("#0", text="id")
        self.tv_punktListSource.heading("y", text="y")
        self.tv_punktListSource.heading("x", text="x")
        self.scr_punktListSourceScroll = Scrollbar(
            lf_Source,
            orient="vertical",
            command=self.tv_punktListSource.yview)
        self.scr_punktListSourceScroll.grid(row=0, column=1, sticky="nse")
        self.tv_punktListSource.configure(
            yscrollcommand=self.scr_punktListSourceScroll.set)

        self.tv_punktListDest = Treeview(lf_Dest)
        self.tv_punktListDest.grid(row=0, column=0, padx=3, pady=3)
        self.tv_punktListDest["columns"] = ("Y", "X")
        self.tv_punktListDest.column("#0",
                                     width=tv_column_width_id,
                                     minwidth=tv_column_width_id)
        self.tv_punktListDest.column("Y",
                                     width=tv_column_width,
                                     minwidth=tv_column_width_min)
        self.tv_punktListDest.column("X",
                                     width=tv_column_width,
                                     minwidth=tv_column_width_min)
        self.tv_punktListDest.heading("#0", text="id")
        self.tv_punktListDest.heading("Y", text="Y")
        self.tv_punktListDest.heading("X", text="X")
        self.scr_punktListDestScroll = Scrollbar(
            lf_Dest, orient="vertical", command=self.tv_punktListDest.yview)
        self.scr_punktListDestScroll.grid(row=0, column=1, sticky="nse")
        self.tv_punktListDest.configure(
            yscrollcommand=self.scr_punktListDestScroll.set)

        Label(lf_Parameter, text="Maßstab Y").grid(row=0,
                                                   column=0,
                                                   padx=3,
                                                   pady=3,
                                                   sticky="w")
        Label(lf_Parameter, text="Maßstab X").grid(row=0,
                                                   column=3,
                                                   padx=3,
                                                   pady=3,
                                                   sticky="e")
        Label(lf_Parameter, text="Rotation Y / gon").grid(row=1,
                                                          column=0,
                                                          padx=3,
                                                          pady=3,
                                                          sticky="w")
        Label(lf_Parameter, text="Rotation X / gon").grid(row=1,
                                                          column=3,
                                                          padx=3,
                                                          pady=3,
                                                          sticky="e")
        Label(lf_Parameter, text="Translation Y").grid(row=2,
                                                       column=0,
                                                       padx=3,
                                                       pady=3,
                                                       sticky="w")
        Label(lf_Parameter, text="Translation X").grid(row=2,
                                                       column=3,
                                                       padx=3,
                                                       pady=3,
                                                       sticky="e")

        Entry(lf_Parameter, textvariable=self.dbl_ParaMY,
              state="readonly").grid(row=0, column=1, padx=3, pady=3)
        Entry(lf_Parameter, textvariable=self.dbl_ParaMX,
              state="readonly").grid(row=0, column=2, padx=3, pady=3)
        Entry(lf_Parameter, textvariable=self.dbl_ParaRotY,
              state="readonly").grid(row=1, column=1, padx=3, pady=3)
        Entry(lf_Parameter, textvariable=self.dbl_ParaRotX,
              state="readonly").grid(row=1, column=2, padx=3, pady=3)
        Entry(lf_Parameter, textvariable=self.dbl_ParaTransY,
              state="readonly").grid(row=2, column=1, padx=3, pady=3)
        Entry(lf_Parameter, textvariable=self.dbl_ParaTransX,
              state="readonly").grid(row=2, column=2, padx=3, pady=3)

        self.tv_punktListTrans = Treeview(lf_Trans, selectmode="none")
        self.tv_punktListTrans.grid(row=0, column=0, padx=3, pady=3)
        self.tv_punktListTrans["columns"] = ("Y", "X", "Rk Y", "Rk X")
        self.tv_punktListTrans.column("#0",
                                      width=tv_column_width_id,
                                      minwidth=tv_column_width_id)
        self.tv_punktListTrans.column("Y",
                                      width=tv_column_width,
                                      minwidth=tv_column_width_min)
        self.tv_punktListTrans.column("X",
                                      width=tv_column_width,
                                      minwidth=tv_column_width_min)
        self.tv_punktListTrans.column("Rk Y",
                                      width=tv_column_width,
                                      minwidth=tv_column_width_min)
        self.tv_punktListTrans.column("Rk X",
                                      width=tv_column_width,
                                      minwidth=tv_column_width_min)
        self.tv_punktListTrans.heading("#0", text="id")
        self.tv_punktListTrans.heading("Y", text="Y")
        self.tv_punktListTrans.heading("X", text="X")
        self.tv_punktListTrans.heading("Rk Y", text="Restklaffe Y")
        self.tv_punktListTrans.heading("Rk X", text="Restklaffe X")
        self.scr_punktListTransScroll = Scrollbar(
            lf_Trans, orient="vertical", command=self.tv_punktListTrans.yview)
        self.scr_punktListTransScroll.grid(row=0, column=1, sticky="nse")
        self.tv_punktListTrans.configure(
            yscrollcommand=self.scr_punktListTransScroll.set)

    def loadPoints(self, text, sepDec, sepVal, systemtype):
        if systemtype == 0:
            self.__pd_PLQuelle.clear()
            self.__pd_PLQuelle.einlesenListe(text, sepDec, sepVal)
            self.showPoints(systemtype, self.__pd_PLQuelle)
        else:
            self.__pd_PLZiel.clear()
            self.__pd_PLZiel.einlesenListe(text, sepDec, sepVal)
            self.showPoints(systemtype, self.__pd_PLZiel)

    def showPoints(self, systemtype, dP):
        if systemtype == 0:
            self.fillTree(self.tv_punktListSource, dP)
        elif systemtype == 1:
            self.fillTree(self.tv_punktListDest, dP)
        else:
            self.fillTree(self.tv_punktListTrans, dP)

    def showParam(self, parameter):
        self.dbl_ParaMY.set(self.runde(parameter["m_Y"]))
        self.dbl_ParaRotY.set(
            self.runde(Winkel(parameter["rot_Y"], "rad").get_w("gon")))
        self.dbl_ParaTransY.set(self.runde(parameter["Y0"]))
        self.dbl_ParaTransX.set(self.runde(parameter["X0"]))
        if "m_X" in parameter:
            self.dbl_ParaMX.set(self.runde(parameter["m_X"]))
            self.dbl_ParaRotX.set(
                self.runde(Winkel(parameter["rot_X"], "rad").get_w("gon")))
        else:
            self.dbl_ParaMX.set(self.runde(parameter["m_Y"]))
            self.dbl_ParaRotX.set(
                self.runde(Winkel(parameter["rot_Y"], "rad").get_w("gon")))

    def fillTree(self, treename, dP):
        for row in treename.get_children():
            treename.delete(row)
        dP = dP.get_dic()
        keys = list(dP.keys())
        for i in range(len(dP)):
            pId = keys[i]
            y = self.runde(dP[pId]["coord"].get_y())
            x = self.runde(dP[pId]["coord"].get_x())
            if "w" in dP[pId]:
                wy = self.runde(dP[pId]["w"].get_y())
                wx = self.runde(dP[pId]["w"].get_x())
                treename.insert("", i + 1, text=pId, values=(y, x, wy, wx))
            else:
                treename.insert("", i + 1, text=pId, values=(y, x))

    def BtnPressedLoadPoints(self):
        top = Toplevel()
        top.title("Punkte laden")
        self.F_loadPList = Fenster_loadPList(top, self)

    def BtnPressedCalc(self):
        l_p1exclude = []
        for i in self.tv_punktListDest.selection():
            l_p1exclude.append(self.tv_punktListDest.item(i, "text"))
        if self.int_radioTrans.get() == 0:
            self.__pd_PLTrans, self.__dict_para = HelmertTrans(
                self.__pd_PLQuelle, self.__pd_PLZiel,
                l_p1exclude).get_result()
        else:
            self.__pd_PLTrans, self.__dict_para = AffinTrans(
                self.__pd_PLQuelle, self.__pd_PLZiel,
                l_p1exclude).get_result()
        self.showPoints(2, self.__pd_PLTrans)
        self.showParam(self.__dict_para)

    def load_json(self, s):
        pDic = json.loads(s)
        for k, v in pDic.items():
            if k == "source":
                self.__pd_PLQuelle.from_json(v)
            elif k == "dest":
                self.__pd_PLZiel.from_json(v)
            elif k == "trans":
                self.__pd_PLTrans.from_json(v)
            elif k == "parameter":
                self.__dict_para = v

        self.showPoints(0, self.__pd_PLQuelle)
        self.showPoints(1, self.__pd_PLZiel)
        self.showPoints(2, self.__pd_PLTrans)
        self.showParam(self.__dict_para)

    def save_json(self):
        return json.dumps(
            {
                "source": self.__pd_PLQuelle.get_json(),
                "dest": self.__pd_PLZiel.get_json(),
                "trans": self.__pd_PLTrans.get_json(),
                "parameter": self.__dict_para
            },
            default=lambda obj: obj.get_json(),
            sort_keys=True,
            indent=4)

    def BtnPressedPlot(self):
        fig = plt.figure()
        ax = fig.add_subplot()
        ax.set_aspect("equal")

        pl_plot = []
        for k in self.__pd_PLTrans.get_dic().values():
            pl_plot.append(k)

        l_y = []
        l_x = []
        l_id = []
        for p in pl_plot:
            l_y.append(p["coord"].get_y())
            l_x.append(p["coord"].get_x())
            l_id.append(p["coord"].get_id())

        for i in range(len(l_y)):
            ax.text(l_y[i] + 10, l_x[i] + 10, l_id[i])

        plt.plot(l_y, l_x, '.', color='black')

        ax.relim()
        ax.autoscale_view()
        ax.set_xlabel("Y")
        ax.set_ylabel("X")
        ax.grid(True)
        plt.show()
Exemple #43
0
class TkSqlit3:
    def __init__(self, root):
        self.root = root
        self.frame = Frame(root)
        self.frame.pack(fill="both")
        #sql结果展示
        self.treeviewResult = None
        #存储db路径
        self.db3 = None
        self.varSql = StringVar()
        #数据库操作对象
        self.conn = None
        self.cursor = None
        #添加菜单
        menubar = Menu(root)
        menubar.add_command(label='打开', command=self.openSelectDialog)
        root.config(menu=menubar)
        #sql输入窗口
        sqlInput = Entry(self.frame, textvariable=self.varSql)
        sqlInput.pack(fill=X)
        sqlInput.bind('<Return>', self.showSQLResult)
        #表名列表
        self.lbTable = Listbox(self.frame, height=100)
        self.lbTable.pack(side=LEFT, fill=Y)
        self.lbTable.bind("<<ListboxSelect>>", self.tableSelect)
        #滚动条
        self.scrollBarX = Scrollbar(self.frame, orient="horizontal")
        self.scrollBarX.pack(side=BOTTOM, fill=X)
        self.scrollBarY = Scrollbar(self.frame, orient="vertical")
        self.scrollBarY.pack(side=RIGHT, fill=Y)

    def openSelectDialog(self):
        self.db3 = askopenfilename(filetypes=[('db', '*.db')], initialdir='.')
        self.conn = sqlite3.connect(self.db3)
        self.cursor = self.conn.cursor()
        self.root.title(self.db3)
        self.cursor.execute(
            "select name from sqlite_master where type='table'")
        for item in self.cursor.fetchall():
            self.lbTable.insert(END, item[0])

    def showSQLResult(self, event):
        result = self.cursor.execute(self.varSql.get())
        heads = [x[0] for x in self.cursor.description]
        result = self.cursor.fetchall()
        self.showDataTable(heads, result)

    def tableSelect(self, event):
        idx = self.lbTable.curselection()[0]
        tableSelect = self.lbTable.get(idx)
        self.cursor.execute(f"select * from {tableSelect}")
        heads = [x[0] for x in self.cursor.description]
        result = self.cursor.fetchall()
        self.showDataTable(heads, result)

    def showDataTable(self, heads, result):
        if self.treeviewResult:
            self.treeviewResult.destroy()
        self.treeviewResult = Treeview(
            self.frame,
            height=len(result),
            columns=[str(i) for i in range(len(heads))],
            show='headings',
            xscrollcommand=self.scrollBarX.set,
            yscrollcommand=self.scrollBarY.set)
        self.scrollBarX.config(command=self.treeviewResult.xview)
        self.scrollBarY.config(command=self.treeviewResult.yview)
        for i, text in enumerate(heads):
            self.treeviewResult.column(str(i), width=100, anchor="w")
            self.treeviewResult.heading(str(i), text=text)
        for i, row in enumerate(result):
            self.treeviewResult.insert('', i, values=row)
        self.treeviewResult.pack(side=LEFT, fill=BOTH, expand=True)
Exemple #44
0
# StudentTable.tag_configure("odd", background="yellow")
scroll_x.pack(side=BOTTOM, fill=X)
scroll_y.pack(side=RIGHT, fill=Y)
scroll_x.config(command=StudentTable.xview)
scroll_y.config(command=StudentTable.yview)
StudentTable.heading('ID', text='ID')
StudentTable.heading('Name', text='Name')
StudentTable.heading('Mobile No.', text='Mobile No.')
StudentTable.heading('Email ID', text='Email ID')
StudentTable.heading('Address', text='Address')
StudentTable.heading('Gender', text='Gender')
StudentTable.heading('D.O.B.', text='D.O.B.')
StudentTable.heading('Added Date', text='Added Date')
StudentTable.heading('Added Time', text='Added Time')

StudentTable['show'] = 'headings'

StudentTable.column('ID', width=60)
StudentTable.column('Name', width=200)
StudentTable.column('Mobile No.', width=200)
StudentTable.column('Email ID', width=200)
StudentTable.column('Address', width=300)
StudentTable.column('Gender', width=80)
StudentTable.column('D.O.B.', width=150)
StudentTable.column('Added Date', width=150)
StudentTable.column('Added Time', width=150)

StudentTable.pack(fill=BOTH, expand=1)

root.mainloop()
Exemple #45
0
Entry(s_search, textvariable=searchname).grid(row=0, column=1)

Label(s_search, text='family').grid(row=1, column=0)
searchfamily = StringVar()
Entry(s_search, textvariable=searchfamily).grid(row=1, column=1)

Button(s_search, text='search', command=student_search).grid(row=0,
                                                             column=2,
                                                             rowspan=2)
tree = Treeview(s_search, selectmode='browse')
vsb = Scrollbar(s_search, orient="vertical", command=tree.yview)
vsb.grid(row=2, column=3)
tree.configure(yscrollcommand=vsb.set)

tree["column"] = ("one", "two", "three")
tree.column("#0", width=30)
tree.column("one", width=120)
tree.column("two", width=120)
tree.column("three", width=90)

tree.heading("#0", text="ID", anchor=W)
tree.heading("one", text="NAME")
tree.heading("two", text="FAMILY")
tree.heading("three", text="CODE", anchor=W)
person = StudentSelect().get()
for person in person:
    tree.insert("",
                person[0],
                text=person[0],
                values=(person[1], person[2], person[4]))
tree.grid(row=2, column=0, columnspan=3)
Exemple #46
0
###################################### Table frame
table_frame = Frame(text_fill, borderwidth="3", relief=GROOVE, bg="white")
table_frame.place(x=10, y=55, height=560, width=905)
scroll_x = Scrollbar(table_frame, orient=HORIZONTAL)
scroll_y = Scrollbar(table_frame, orient=VERTICAL)
login_table = Treeview(table_frame,
                       columns=("aid", "eid", "name", "post", "status", "date",
                                "time"),
                       xscrollcommand=scroll_x.set,
                       yscrollcommand=scroll_y.set)
scroll_x.pack(side=BOTTOM, fill=X)
scroll_y.pack(side=RIGHT, fill=Y)
scroll_x.config(command=login_table.xview)
scroll_y.config(command=login_table.yview)
login_table.heading("aid", text="Attendance ID")
login_table.heading("eid", text="Employee ID")
login_table.heading('name', text="Name")
login_table.heading("post", text="post")
login_table.heading("status", text="Attendance Status")
login_table.heading("date", text="Date")
login_table.heading("time", text="Time")
login_table['show'] = 'headings'
login_table.column("aid", width=119)
login_table.column("eid", width=119)
login_table.column("name", width=119)
login_table.column("post", width=119)
login_table.column("status", width=119)
login_table.column("date", width=119)
login_table.column("time", width=119)
login_table.pack(fill=BOTH, expand=1)
report.mainloop()
Exemple #47
0
class DialogOpenArchive(Toplevel):
    def __init__(self, mainWin, openType, filesource, filenames, title, colHeader, showAltViewButton=False):
        parent = mainWin.parent
        super(DialogOpenArchive, self).__init__(parent)
        self.parent = parent
        self.showAltViewButton = showAltViewButton
        parentGeometry = re.match("(\d+)x(\d+)[+]?([-]?\d+)[+]?([-]?\d+)", parent.geometry())
        dialogX = int(parentGeometry.group(3))
        dialogY = int(parentGeometry.group(4))
        self.accepted = False

        self.transient(self.parent)
        
        frame = Frame(self)

        treeFrame = Frame(frame, width=500)
        vScrollbar = Scrollbar(treeFrame, orient=VERTICAL)
        hScrollbar = Scrollbar(treeFrame, orient=HORIZONTAL)
        self.treeView = Treeview(treeFrame, xscrollcommand=hScrollbar.set, yscrollcommand=vScrollbar.set)
        self.treeView.grid(row=0, column=0, sticky=(N, S, E, W))
        hScrollbar["command"] = self.treeView.xview
        hScrollbar.grid(row=1, column=0, sticky=(E,W))
        vScrollbar["command"] = self.treeView.yview
        vScrollbar.grid(row=0, column=1, sticky=(N,S))
        treeFrame.columnconfigure(0, weight=1)
        treeFrame.rowconfigure(0, weight=1)
        treeFrame.grid(row=0, column=0, columnspan=4, sticky=(N, S, E, W), padx=3, pady=3)
        self.treeView.focus_set()
        
        mainWin.showStatus(_("loading archive {0}").format(filesource.url))
        self.filesource = filesource
        self.filenames = filenames
        self.selection = filesource.selection
        self.hasToolTip = False
        selectedNode = None

        if openType == ENTRY_POINTS:
            try:
                metadataFiles = filesource.taxonomyPackageMetadataFiles
                if len(metadataFiles) > 1:
                    raise IOError(_("Taxonomy package contained more than one metadata file: {0}.")
                                  .format(', '.join(metadataFiles)))
                metadataFile = metadataFiles[0]
                metadata = filesource.file(filesource.url + os.sep + metadataFile)[0]
                self.metadataFilePrefix = os.sep.join(os.path.split(metadataFile)[:-1])
                if self.metadataFilePrefix:
                    self.metadataFilePrefix += os.sep
        
                self.nameToUrls, self.remappings = parseTxmyPkg(mainWin, metadata)
            except Exception as e:
                self.close()
                err = _("Failed to parse metadata; the underlying error was: {0}").format(e)
                messagebox.showerror(_("Malformed taxonomy package"), err)
                mainWin.addToLog(err)
                return
    
        mainWin.showStatus(None)
        
        if openType == DISCLOSURE_SYSTEM:
            y = 3
        else:
            y = 1

        okButton = Button(frame, text=_("OK"), command=self.ok)
        cancelButton = Button(frame, text=_("Cancel"), command=self.close)
        okButton.grid(row=y, column=2, sticky=(S,E,W), pady=3)
        cancelButton.grid(row=y, column=3, sticky=(S,E,W), pady=3, padx=3)
        
        if showAltViewButton:
            self.altViewButton = Button(frame, command=self.showAltView)
            self.altViewButton.grid(row=y, column=0, sticky=(S,W), pady=3, padx=3)
        
        self.loadTreeView(openType, colHeader, title)

        frame.grid(row=0, column=0, sticky=(N,S,E,W))
        frame.columnconfigure(0, weight=1)
        window = self.winfo_toplevel()
        window.columnconfigure(0, weight=1)
        self.geometry("+{0}+{1}".format(dialogX+50,dialogY+100))
        
        self.bind("<Return>", self.ok)
        self.bind("<Escape>", self.close)
        
        self.toolTipText = StringVar()
        if self.hasToolTip:
            self.treeView.bind("<Motion>", self.motion, '+')
            self.treeView.bind("<Leave>", self.leave, '+')
            self.toolTipText = StringVar()
            self.toolTip = ToolTip(self.treeView, 
                                   textvariable=self.toolTipText, 
                                   wraplength=640, 
                                   follow_mouse=True,
                                   state="disabled")
            self.toolTipRowId = None

        self.protocol("WM_DELETE_WINDOW", self.close)
        self.grab_set()
        self.wait_window(self)
        
    def loadTreeView(self, openType, title, colHeader):
        self.title(title)
        self.openType = openType
        selectedNode = None

        # clear previous treeview entries
        for previousNode in self.treeView.get_children(""): 
            self.treeView.delete(previousNode)

        # set up treeView widget and tabbed pane
        if openType in (ARCHIVE, DISCLOSURE_SYSTEM):
            self.treeView.column("#0", width=500, anchor="w")
            self.treeView.heading("#0", text=colHeader)
            try:
                self.isRss = self.filesource.isRss
                if self.isRss:
                    self.treeView.column("#0", width=350, anchor="w")
                    self.treeView["columns"] = ("descr", "date", "instDoc")
                    self.treeView.column("descr", width=50, anchor="center", stretch=False)
                    self.treeView.heading("descr", text="Form")
                    self.treeView.column("date", width=170, anchor="w", stretch=False)
                    self.treeView.heading("date", text="Pub Date")
                    self.treeView.column("instDoc", width=200, anchor="w", stretch=False)
                    self.treeView.heading("instDoc", text="Instance Document")
            except AttributeError:
                self.isRss = False
                self.treeView["columns"] = tuple()
        
            loadedPaths = []
            for i, filename in enumerate(self.filenames):
                if isinstance(filename,tuple):
                    if self.isRss:
                        form, date, instDoc = filename[2:5]
                    filename = filename[0] # ignore tooltip
                    self.hasToolTip = True
                if filename.endswith("/"):
                    filename = filename[:-1]
                path = filename.split("/")
                if not self.isRss and len(path) > 1 and path[:-1] in loadedPaths:
                    parent = "file{0}".format(loadedPaths.index(path[:-1]))
                else:
                    parent = "" 
                node = self.treeView.insert(parent, "end", "file{0}".format(i), text=path[-1])
                if self.isRss:
                    self.treeView.set(node, "descr", form)
                    self.treeView.set(node, "date", date)
                    self.treeView.set(node, "instDoc", os.path.basename(instDoc))
                if self.selection == filename:
                    selectedNode = node
                loadedPaths.append(path)

        elif openType == ENTRY_POINTS:
            self.treeView.column("#0", width=150, anchor="w")
            self.treeView.heading("#0", text="Name")
    
            self.treeView["columns"] = ("url",)
            self.treeView.column("url", width=350, anchor="w")
            self.treeView.heading("url", text="URL")
            
            for name, urls in self.nameToUrls.items():
                displayUrl = urls[1] # display the canonical URL
                self.treeView.insert("", "end", name, values=[displayUrl], text=name)
                
            self.hasToolTip = True
        else: # unknown openType
            return None
        if selectedNode:
            self.treeView.see(selectedNode)
            self.treeView.selection_set(selectedNode)

        if self.showAltViewButton:
            self.altViewButton.config(text=_("Show Files") if openType == ENTRY_POINTS else _("Show Entries"))

        
    def ok(self, event=None):
        selection = self.treeView.selection()
        if len(selection) > 0:
            if self.openType in (ARCHIVE, DISCLOSURE_SYSTEM):
                filename = self.filenames[int(selection[0][4:])]
                if isinstance(filename,tuple):
                    if self.isRss:
                        filename = filename[4]
                    else:
                        filename = filename[0]
                if not filename.endswith("/"):
                    self.filesource.select(filename)
                    self.accepted = True
                    self.close()
            elif self.openType == ENTRY_POINTS:
                epName = selection[0]
                #index 0 is the remapped Url, as opposed to the canonical one used for display
                urlOrFile = self.nameToUrls[epName][0]
                
                # load file source remappings
                self.filesource.mappedPaths = \
                    dict((prefix, 
                          remapping if isHttpUrl(remapping)
                          else (self.filesource.baseurl + os.sep + self.metadataFilePrefix +remapping.replace("/", os.sep)))
                          for prefix, remapping in self.remappings.items())
    
                if not urlOrFile.endswith("/"):
                    # check if it's an absolute URL rather than a path into the archive
                    if isHttpUrl(urlOrFile):
                        self.filesource.select(urlOrFile)  # absolute path selection
                    else:
                        # assume it's a path inside the archive:
                        self.filesource.select(self.metadataFilePrefix + urlOrFile)
                    self.accepted = True
                    self.close()
        
    def close(self, event=None):
        self.parent.focus_set()
        self.destroy()
        
    def showAltView(self, event=None):
        if self.openType == ENTRY_POINTS:
            self.loadTreeView(ARCHIVE, _("Select Entry Point"), _("File"))
        else:
            self.loadTreeView(ENTRY_POINTS, _("Select Archive File"), _("File"))
        
    def leave(self, *args):
        self.toolTipRowId = None

    def motion(self, *args):
        tvRowId = self.treeView.identify_row(args[0].y)
        if tvRowId != self.toolTipRowId:
            text = None
            if self.openType in (ARCHIVE, DISCLOSURE_SYSTEM):
                self.toolTipRowId = tvRowId
                if tvRowId and len(tvRowId) > 4:
                    try:
                        text = self.filenames[ int(tvRowId[4:]) ]
                        if isinstance(text, tuple):
                            text = text[1].replace("\\n","\n")
                    except (KeyError, ValueError):
                        pass
            elif self.openType == ENTRY_POINTS:
                try:
                    epUrl = self.nameToUrls[tvRowId][1]
                    text = "{0}\n{1}".format(tvRowId, epUrl)
                except KeyError:
                    pass
            self.setToolTip(text)
                
    def setToolTip(self, text):
        self.toolTip._hide()
        if text:
            self.toolTipText.set(text)
            self.toolTip.configure(state="normal")
            self.toolTip._schedule()
        else:
            self.toolTipText.set("")
            self.toolTip.configure(state="disabled")
Exemple #48
0
class App_test(object):
    def __init__(self, master, fuc, query, next, pre):
        self.win = master
        self.win.title('笔趣阁阅读_v1.0   by: 孤月')
        self.win.iconbitmap('./ico/gui_text_proce.ico')  # 指定界面图标
        curWidth = self.win.winfo_width()
        curHeight = self.win.winfo_height()
        scnWidth, scnHeight = self.win.maxsize()
        tmpcnf = '1340x640+500+300'  # % ((scnWidth - curWidth) / 2, (scnHeight - curHeight) / 2)
        self.win.geometry(tmpcnf)
        self.creat_res()
        self.set_position()
        self.add_train_info()
        self.res_config(fuc, query, next, pre)
        self.train_message = {}
        self.gettime()  # 系统时间

    def creat_res(self):
        self.v = IntVar()  # 书籍查询
        self.v.set(True)
        self.temp = StringVar()  # 书名/作者 录入
        self.temp2 = StringVar()  # 章节名录入
        self.sys_time = StringVar()  # 系统时间

        self.E_startstation = Entry(self.win, textvariable=self.temp)
        self.E_endstation = Entry(self.win, textvariable=self.temp2)

        self.La_startstation = Label(self.win, text="根据书名/作者搜索:")
        self.La_endstation = Label(self.win, text="根据章节名搜索:")
        self.La_directory = Label(self.win, text="目录")
        self.La_text = Label(self.win, text="正文")
        self.La_sys_time = Label(self.win, textvariable=self.sys_time, fg='blue', font=("黑体", 20))  # 设置字体大小颜色

        self.B_search = Button(self.win, text="搜索")
        self.B_buy_tick = Button(self.win, text="阅读")
        self.B_pre_chapter = Button(self.win, text="上一章")
        self.B_next_chapter = Button(self.win, text="下一章")

        self.R_site = Radiobutton(self.win, text="书名查询", variable=self.v, value=True)
        self.R_price = Radiobutton(self.win, text="章节查询", variable=self.v, value=False)

        self.init_data_Text = Text(self.win)  # 原始数据录入框
        self.S_move = Scrollbar(self.win)  # 目录滚动条
        self.S_text_move = Scrollbar(self.win)  # 创建文本框滚动条

    # 设置位置
    def set_position(self):
        self.init_data_Text.place(x=430, y=40, width=870, height=550)
        self.E_startstation.place(x=10, y=50, width=145, height=30)
        self.E_startstation.insert(10, "星辰变")
        self.E_endstation.place(x=10, y=140, width=145, height=30)
        self.E_endstation.insert(10, "第一章 秦羽")
        self.La_startstation.place(x=10, y=10, width=130, height=30)
        self.La_endstation.place(x=10, y=100, width=120, height=30)
        self.La_sys_time.place(x=1150, y=600, width=160, height=30)
        self.B_search.place(x=10, y=220, width=80, height=40)
        self.B_pre_chapter.place(x=950, y=600, width=80, height=40)
        self.B_next_chapter.place(x=1050, y=600, width=80, height=40)
        self.S_move.place(x=380, y=40, width=30, height=550)
        self.S_text_move.place(x=1300, y=40, width=30, height=550)
        self.B_buy_tick.place(x=90, y=220, width=80, height=40)
        self.R_site.place(x=10, y=180, width=90, height=30)
        self.R_price.place(x=100, y=180, width=90, height=30)
        self.La_directory.place(x=180, y=7, width=90, height=30)
        self.La_text.place(x=420, y=7, width=70, height=30)

    # 为按钮绑定事件
    def res_config(self, fuc, query, next_, pre):
        self.B_search.config(command=fuc)  # 搜索
        self.B_buy_tick.config(command=query)  # 阅读
        self.B_pre_chapter.config(command=pre)  # 上一章
        self.B_next_chapter.config(command=next_)  # 下一章
        self.S_move.config(command=self.tree.yview)  # 目录滚动条
        self.tree.config(yscrollcommand=self.S_move.set)
        self.S_text_move.config(command=self.init_data_Text.yview)  # 文本框滚动条
        self.init_data_Text.config(yscrollcommand=self.S_text_move.set)

    def add_train_info(self):
        lis_train = ["C" + str(x) for x in range(0, 2)]
        tuple_train = tuple(lis_train)
        self.tree = Treeview(self.win, columns=tuple_train, height=30, show="headings")
        self.tree.place(x=200, y=40, width=180, height=550)
        train_info = [' 书名 ', ' 作者 ']
        for i in range(0, len(lis_train)):
            self.tree.column(lis_train[i], width=len(train_info[i]) * 11,
                             anchor='w')  # must be n, ne, e, se, s, sw, w, nw, or center
            self.tree.heading(lis_train[i], text=train_info[i])

    # 实时显示时钟
    def gettime(self):
        # 获取当前时间
        self.sys_time.set(time.strftime("%H:%M:%S"))
        # 每隔一秒调用函数自身获取时间
        self.win.after(1000, self.gettime)
class DialogPluginManager(Toplevel):
    def __init__(self, mainWin, modulesWithNewerFileDates):
        super(DialogPluginManager, self).__init__(mainWin.parent)
        
        self.ENABLE = _("Enable")
        self.DISABLE = _("Disable")
        self.parent = mainWin.parent
        self.cntlr = mainWin
        
        # copy plugins for temporary display
        self.pluginConfig = PluginManager.pluginConfig
        self.pluginConfigChanged = False
        self.uiClassMethodsChanged = False
        self.modulesWithNewerFileDates = modulesWithNewerFileDates
        
        parentGeometry = re.match("(\d+)x(\d+)[+]?([-]?\d+)[+]?([-]?\d+)", self.parent.geometry())
        dialogX = int(parentGeometry.group(3))
        dialogY = int(parentGeometry.group(4))

        self.title(_("Plug-in Manager"))
        frame = Frame(self)
        
        # left button frame
        buttonFrame = Frame(frame, width=40)
        buttonFrame.columnconfigure(0, weight=1)
        addLabel = Label(buttonFrame, text=_("Find plug-in modules:"), wraplength=60, justify="center")
        addLocalButton = Button(buttonFrame, text=_("Locally"), command=self.findLocally)
        ToolTip(addLocalButton, text=_("File chooser allows selecting python module files to add (or reload) plug-ins, from the local file system."), wraplength=240)
        addWebButton = Button(buttonFrame, text=_("On Web"), command=self.findOnWeb)
        ToolTip(addWebButton, text=_("Dialog to enter URL full path to load (or reload) plug-ins, from the web or local file system."), wraplength=240)
        addLabel.grid(row=0, column=0, pady=4)
        addLocalButton.grid(row=1, column=0, pady=4)
        addWebButton.grid(row=2, column=0, pady=4)
        buttonFrame.grid(row=0, column=0, rowspan=2, sticky=(N, S, W), padx=3, pady=3)
        
        # right tree frame (plugins already known to arelle)
        modulesFrame = Frame(frame, width=700)
        vScrollbar = Scrollbar(modulesFrame, orient=VERTICAL)
        hScrollbar = Scrollbar(modulesFrame, orient=HORIZONTAL)
        self.modulesView = Treeview(modulesFrame, xscrollcommand=hScrollbar.set, yscrollcommand=vScrollbar.set, height=7)
        self.modulesView.grid(row=0, column=0, sticky=(N, S, E, W))
        self.modulesView.bind('<<TreeviewSelect>>', self.moduleSelect)
        hScrollbar["command"] = self.modulesView.xview
        hScrollbar.grid(row=1, column=0, sticky=(E,W))
        vScrollbar["command"] = self.modulesView.yview
        vScrollbar.grid(row=0, column=1, sticky=(N,S))
        modulesFrame.columnconfigure(0, weight=1)
        modulesFrame.rowconfigure(0, weight=1)
        modulesFrame.grid(row=0, column=1, columnspan=4, sticky=(N, S, E, W), padx=3, pady=3)
        self.modulesView.focus_set()

        self.modulesView.column("#0", width=120, anchor="w")
        self.modulesView.heading("#0", text=_("Name"))
        self.modulesView["columns"] = ("author", "ver", "status", "date", "update", "descr", "license")
        self.modulesView.column("author", width=100, anchor="w", stretch=False)
        self.modulesView.heading("author", text=_("Author"))
        self.modulesView.column("ver", width=50, anchor="w", stretch=False)
        self.modulesView.heading("ver", text=_("Version"))
        self.modulesView.column("status", width=50, anchor="w", stretch=False)
        self.modulesView.heading("status", text=_("Status"))
        self.modulesView.column("date", width=70, anchor="w", stretch=False)
        self.modulesView.heading("date", text=_("File Date"))
        self.modulesView.column("update", width=50, anchor="w", stretch=False)
        self.modulesView.heading("update", text=_("Update"))
        self.modulesView.column("descr", width=200, anchor="w", stretch=False)
        self.modulesView.heading("descr", text=_("Description"))
        self.modulesView.column("license", width=70, anchor="w", stretch=False)
        self.modulesView.heading("license", text=_("License"))

        classesFrame = Frame(frame)
        vScrollbar = Scrollbar(classesFrame, orient=VERTICAL)
        hScrollbar = Scrollbar(classesFrame, orient=HORIZONTAL)
        self.classesView = Treeview(classesFrame, xscrollcommand=hScrollbar.set, yscrollcommand=vScrollbar.set, height=5)
        self.classesView.grid(row=0, column=0, sticky=(N, S, E, W))
        hScrollbar["command"] = self.classesView.xview
        hScrollbar.grid(row=1, column=0, sticky=(E,W))
        vScrollbar["command"] = self.classesView.yview
        vScrollbar.grid(row=0, column=1, sticky=(N,S))
        classesFrame.columnconfigure(0, weight=1)
        classesFrame.rowconfigure(0, weight=1)
        classesFrame.grid(row=1, column=1, columnspan=4, sticky=(N, S, E, W), padx=3, pady=3)
        self.classesView.focus_set()
        
        self.classesView.column("#0", width=200, anchor="w")
        self.classesView.heading("#0", text=_("Class"))
        self.classesView["columns"] = ("modules")
        self.classesView.column("modules", width=500, anchor="w", stretch=False)
        self.classesView.heading("modules", text=_("Modules"))
        
        # bottom frame module info details
        moduleInfoFrame = Frame(frame, width=700)
        moduleInfoFrame.columnconfigure(1, weight=1)
        
        self.moduleNameLabel = Label(moduleInfoFrame, wraplength=600, justify="left", 
                                     font=font.Font(family='Helvetica', size=12, weight='bold'))
        self.moduleNameLabel.grid(row=0, column=0, columnspan=4, sticky=W)
        self.moduleAuthorHdr = Label(moduleInfoFrame, text=_("author:"), state=DISABLED)
        self.moduleAuthorHdr.grid(row=1, column=0, sticky=W)
        self.moduleAuthorLabel = Label(moduleInfoFrame, wraplength=600, justify="left")
        self.moduleAuthorLabel.grid(row=1, column=1, columnspan=3, sticky=W)
        self.moduleDescrHdr = Label(moduleInfoFrame, text=_("description:"), state=DISABLED)
        self.moduleDescrHdr.grid(row=2, column=0, sticky=W)
        self.moduleDescrLabel = Label(moduleInfoFrame, wraplength=600, justify="left")
        self.moduleDescrLabel.grid(row=2, column=1, columnspan=3, sticky=W)
        self.moduleClassesHdr = Label(moduleInfoFrame, text=_("classes:"), state=DISABLED)
        self.moduleClassesHdr.grid(row=3, column=0, sticky=W)
        self.moduleClassesLabel = Label(moduleInfoFrame, wraplength=600, justify="left")
        self.moduleClassesLabel.grid(row=3, column=1, columnspan=3, sticky=W)
        ToolTip(self.moduleClassesLabel, text=_("List of classes that this plug-in handles."), wraplength=240)
        self.moduleUrlHdr = Label(moduleInfoFrame, text=_("URL:"), state=DISABLED)
        self.moduleUrlHdr.grid(row=4, column=0, sticky=W)
        self.moduleUrlLabel = Label(moduleInfoFrame, wraplength=600, justify="left")
        self.moduleUrlLabel.grid(row=4, column=1, columnspan=3, sticky=W)
        ToolTip(self.moduleUrlLabel, text=_("URL of plug-in module (local file path or web loaded file)."), wraplength=240)
        self.moduleDateHdr = Label(moduleInfoFrame, text=_("date:"), state=DISABLED)
        self.moduleDateHdr.grid(row=5, column=0, sticky=W)
        self.moduleDateLabel = Label(moduleInfoFrame, wraplength=600, justify="left")
        self.moduleDateLabel.grid(row=5, column=1, columnspan=3, sticky=W)
        ToolTip(self.moduleDateLabel, text=_("Date of currently loaded module file (with parenthetical node when an update is available)."), wraplength=240)
        self.moduleLicenseHdr = Label(moduleInfoFrame, text=_("license:"), state=DISABLED)
        self.moduleLicenseHdr.grid(row=6, column=0, sticky=W)
        self.moduleLicenseLabel = Label(moduleInfoFrame, wraplength=600, justify="left")
        self.moduleLicenseLabel.grid(row=6, column=1, columnspan=3, sticky=W)
        self.moduleEnableButton = Button(moduleInfoFrame, text=self.ENABLE, state=DISABLED, command=self.moduleEnable)
        ToolTip(self.moduleEnableButton, text=_("Enable/disable plug in."), wraplength=240)
        self.moduleEnableButton.grid(row=7, column=1, sticky=E)
        self.moduleReloadButton = Button(moduleInfoFrame, text=_("Reload"), state=DISABLED, command=self.moduleReload)
        ToolTip(self.moduleReloadButton, text=_("Reload/update plug in."), wraplength=240)
        self.moduleReloadButton.grid(row=7, column=2, sticky=E)
        self.moduleRemoveButton = Button(moduleInfoFrame, text=_("Remove"), state=DISABLED, command=self.moduleRemove)
        ToolTip(self.moduleRemoveButton, text=_("Remove plug in from plug in table (does not erase the plug in's file)."), wraplength=240)
        self.moduleRemoveButton.grid(row=7, column=3, sticky=E)
        moduleInfoFrame.grid(row=2, column=0, columnspan=5, sticky=(N, S, E, W), padx=3, pady=3)
        moduleInfoFrame.config(borderwidth=4, relief="groove")
        
        okButton = Button(frame, text=_("Close"), command=self.ok)
        ToolTip(okButton, text=_("Accept and changes (if any) and close dialog."), wraplength=240)
        cancelButton = Button(frame, text=_("Cancel"), command=self.close)
        ToolTip(cancelButton, text=_("Cancel changes (if any) and close dialog."), wraplength=240)
        okButton.grid(row=3, column=3, sticky=(S,E), pady=3)
        cancelButton.grid(row=3, column=4, sticky=(S,E), pady=3, padx=3)
        
        self.loadTreeViews()

        frame.grid(row=0, column=0, sticky=(N,S,E,W))
        frame.columnconfigure(0, weight=1)
        frame.columnconfigure(1, weight=1)
        window = self.winfo_toplevel()
        window.columnconfigure(0, weight=1)
        self.geometry("+{0}+{1}".format(dialogX+50,dialogY+100))
        
        self.bind("<Return>", self.ok)
        self.bind("<Escape>", self.close)
        
        self.protocol("WM_DELETE_WINDOW", self.close)
        self.grab_set()
        self.wait_window(self)
        
    def loadTreeViews(self):
        self.selectedModule = None

        # clear previous treeview entries
        for previousNode in self.modulesView.get_children(""): 
            self.modulesView.delete(previousNode)

        for i, moduleItem in enumerate(sorted(self.pluginConfig.get("modules", {}).items())):
            moduleInfo = moduleItem[1]
            name = moduleInfo.get("name", moduleItem[0])
            node = self.modulesView.insert("", "end", name, text=name)
            self.modulesView.set(node, "author", moduleInfo.get("author"))
            self.modulesView.set(node, "ver", moduleInfo.get("version"))
            self.modulesView.set(node, "status", moduleInfo.get("status"))
            self.modulesView.set(node, "date", moduleInfo.get("fileDate"))
            if name in self.modulesWithNewerFileDates:
                self.modulesView.set(node, "update", _("available"))
            self.modulesView.set(node, "descr", moduleInfo.get("description"))
            self.modulesView.set(node, "license", moduleInfo.get("license"))
        
        # clear previous treeview entries
        for previousNode in self.classesView.get_children(""): 
            self.classesView.delete(previousNode)

        for i, classItem in enumerate(sorted(self.pluginConfig.get("classes", {}).items())):
            className, moduleList = classItem
            node = self.classesView.insert("", "end", className, text=className)
            self.classesView.set(node, "modules", ', '.join(moduleList))
            
        self.moduleSelect()  # clear out prior selection

    def ok(self, event=None):
        if self.pluginConfigChanged:
            PluginManager.pluginConfig = self.pluginConfig
            PluginManager.pluginConfigChanged = True
            PluginManager.reset()  # force reloading of modules
        if self.uiClassMethodsChanged:  # may require reloading UI
            if messagebox.askyesno(_("User interface plug-in change"),
                                   _("A change in plug-in class methods may have affected the menus "
                                     "of the user interface.  It may be necessary to restart Arelle to "
                                     "access the menu entries or the changes to their plug-in methods.  \n\n"
                                     "Should Arelle restart with changed user interface language, "
                                     "(if there are any unsaved changes they would be lost!)?"),
                                   parent=self):
                self.cntlr.uiThreadQueue.put((self.cntlr.quit, [None, True]))
        self.close()
        
    def close(self, event=None):
        self.parent.focus_set()
        self.destroy()
                
    def moduleSelect(self, *args):
        node = (self.modulesView.selection() or (None,))[0]
        moduleInfo = self.pluginConfig.get("modules", {}).get(node)
        if moduleInfo:
            self.selectedModule = node
            name = moduleInfo["name"]
            self.moduleNameLabel.config(text=name)
            self.moduleAuthorHdr.config(state=ACTIVE)
            self.moduleAuthorLabel.config(text=moduleInfo["author"])
            self.moduleDescrHdr.config(state=ACTIVE)
            self.moduleDescrLabel.config(text=moduleInfo["description"])
            self.moduleClassesHdr.config(state=ACTIVE)
            self.moduleClassesLabel.config(text=', '.join(moduleInfo["classMethods"]))
            self.moduleUrlHdr.config(state=ACTIVE)
            self.moduleUrlLabel.config(text=moduleInfo["moduleURL"])
            self.moduleDateHdr.config(state=ACTIVE)
            self.moduleDateLabel.config(text=moduleInfo["fileDate"] + " " +
                    (_("(an update is available)") if name in self.modulesWithNewerFileDates else ""))
            self.moduleLicenseHdr.config(state=ACTIVE)
            self.moduleLicenseLabel.config(text=moduleInfo["license"])
            self.moduleEnableButton.config(state=ACTIVE,
                                           text={"enabled":self.DISABLE,
                                                 "disabled":self.ENABLE}[moduleInfo["status"]])
            self.moduleReloadButton.config(state=ACTIVE)
            self.moduleRemoveButton.config(state=ACTIVE)
        else:
            self.selectedModule = None
            self.moduleNameLabel.config(text="")
            self.moduleAuthorHdr.config(state=DISABLED)
            self.moduleAuthorLabel.config(text="")
            self.moduleDescrHdr.config(state=DISABLED)
            self.moduleDescrLabel.config(text="")
            self.moduleClassesHdr.config(state=DISABLED)
            self.moduleClassesLabel.config(text="")
            self.moduleUrlHdr.config(state=DISABLED)
            self.moduleUrlLabel.config(text="")
            self.moduleDateHdr.config(state=DISABLED)
            self.moduleDateLabel.config(text="")
            self.moduleLicenseHdr.config(state=DISABLED)
            self.moduleLicenseLabel.config(text="")
            self.moduleEnableButton.config(state=DISABLED, text=self.ENABLE)
            self.moduleReloadButton.config(state=DISABLED)
            self.moduleRemoveButton.config(state=DISABLED)
        
    def findLocally(self):
        filename = self.cntlr.uiFileDialog("open",
                                           owner=self,
                                           title=_("Choose plug-in module file"),
                                           initialdir=self.cntlr.config.setdefault("pluginOpenDir","."),
                                           filetypes=[(_("Python files"), "*.py")],
                                           defaultextension=".py")
        if filename:
            self.cntlr.config["pluginOpenDir"] = os.path.dirname(filename)
            moduleInfo = PluginManager.moduleModuleInfo(filename)
            self.loadFoundModuleInfo(moduleInfo, filename)
                

    def findOnWeb(self):
        url = DialogURL.askURL(self)
        if url:  # url is the in-cache or local file
            moduleInfo = PluginManager.moduleModuleInfo(url)
            self.cntlr.showStatus("") # clear web loading status
            self.loadFoundModuleInfo(moduleInfo, url)
                
    def loadFoundModuleInfo(self, moduleInfo, url):
        if moduleInfo and moduleInfo.get("name"):
            self.addPluginConfigModuleInfo(moduleInfo)
            self.loadTreeViews()
        else:
            messagebox.showwarning(_("Module is not a plug-in"),
                                   _("File does not contain a python program with an appropriate __pluginInfo__ declaration: \n\n{0}")
                                   .format(url),
                                   parent=self)
            
    def removePluginConfigModuleInfo(self, name):
        moduleInfo = self.pluginConfig["modules"].get(name)
        if moduleInfo:
            for classMethod in moduleInfo["classMethods"]:
                classMethods = self.pluginConfig["classes"].get(classMethod)
                if classMethods and name in classMethods:
                    classMethods.remove(name)
                    if not classMethods: # list has become unused
                        del self.pluginConfig["classes"][classMethod] # remove class
                    if classMethod.startswith("CntlrWinMain.Menu"):
                        self.uiClassMethodsChanged = True  # may require reloading UI
            del self.pluginConfig["modules"][name]
            self.pluginConfigChanged = True

    def addPluginConfigModuleInfo(self, moduleInfo):
        name = moduleInfo["name"]
        self.removePluginConfigModuleInfo(name)  # remove any prior entry for this module
        self.modulesWithNewerFileDates.discard(name) # no longer has an update available
        self.pluginConfig["modules"][name] = moduleInfo
        # add classes
        for classMethod in moduleInfo["classMethods"]:
            classMethods = self.pluginConfig["classes"].setdefault(classMethod, [])
            if name not in classMethods:
                classMethods.append(name)
            if classMethod.startswith("CntlrWinMain.Menu"):
                self.uiClassMethodsChanged = True  # may require reloading UI
        self.pluginConfigChanged = True

    def moduleEnable(self):
        if self.selectedModule in self.pluginConfig["modules"]:
            moduleInfo = self.pluginConfig["modules"][self.selectedModule]
            if self.moduleEnableButton['text'] == self.ENABLE:
                moduleInfo["status"] = "enabled"
                self.moduleEnableButton['text'] = self.DISABLE
            elif self.moduleEnableButton['text'] == self.DISABLE:
                moduleInfo["status"] = "disabled"
                self.moduleEnableButton['text'] = self.ENABLE
            self.pluginConfigChanged = True
            self.loadTreeViews()
            
    def moduleReload(self):
        if self.selectedModule in self.pluginConfig["modules"]:
            url = self.pluginConfig["modules"][self.selectedModule].get("moduleURL")
            if url:
                moduleInfo = PluginManager.moduleModuleInfo(url, reload=True)
                if moduleInfo:
                    self.addPluginConfigModuleInfo(moduleInfo)
                    self.loadTreeViews()
                    self.cntlr.showStatus(_("{0} reloaded").format(moduleInfo.get("name")), clearAfter=5000)
                else:
                    messagebox.showwarning(_("Module error"),
                                           _("File or module cannot be reloaded: \n\n{0}")
                                           .format(url),
                                           parent=self)

    def moduleRemove(self):
        if self.selectedModule in self.pluginConfig["modules"]:
            self.removePluginConfigModuleInfo(self.selectedModule)
            self.pluginConfigChanged = True
            self.loadTreeViews()
Exemple #50
0
class Tree:
    def __init__(self, fra, csvFile, csvDelimiter=',', renew=False):
        self.fra = fra
        self.csvFile = csvFile
        self.csvDelimiter = csvDelimiter
        self.renew = renew
        s = Style()
        s.theme_use('clam')
        def_font = font.nametofont('TkDefaultFont')
        font_family = def_font.actual()['family']
        font_size = def_font.actual()['size'] + 3
        s.configure('font.Treeview.Heading',
                    font=(font_family, font_size, 'bold'))
        fact = font.Font(font="TkDefaultFont").metrics('linespace')
        s.configure('font.Treeview',
                    rowheight=fact,
                    font=font.nametofont("TkDefaultFont"))
        self.treeColumns = []
        self.treeData = []
        if renew:
            del self.treeColumns[:]
            del self.treeData[:]

        with open(self.csvFile, newline='', encoding='utf-8-sig') as csvfile:
            treeCsv = csv.reader(csvfile, delimiter=csvDelimiter)

            for ix, row in enumerate(treeCsv):
                if ix == 0:
                    self.treeColumns = row
                else:
                    self.treeData.append(row)

        self.build_tree()

    def build_tree(self):
        try:
            self.fr.destroy()
        except (NameError, AttributeError):
            pass

        self.fr = Frame(self.fra)
        self.fr.pack(fill='both', expand=False)

        lbl = Label(self.fr, text=self.csvFile)
        lbl.grid(column=0, row=0, sticky='n')

        self.tree = Treeview(self.fr,
                             columns=self.treeColumns,
                             show="headings",
                             style='font.Treeview')
        self.tree.grid(column=0, row=1, sticky='ns')

        vsb = Scrollbar(self.fr, orient="vertical", command=self.tree.yview)
        vsb.grid(column=1, row=1, sticky='ns')
        hsb = Scrollbar(self.fr, orient="horizontal", command=self.tree.xview)
        hsb.grid(column=0, row=2, sticky='ew')
        self.tree.configure(xscrollcommand=hsb.set, yscrollcommand=vsb.set)
        self.fr.grid_columnconfigure(0, weight=1)
        self.fr.grid_rowconfigure(0, weight=1)

        if self.renew:
            for row in self.tree.get_children():
                self.tree.delete(row)

        for col in self.treeColumns:
            #print(treeColumns,col,col.title())
            self.tree.heading(col, text=col.title())
            self.tree.column(
                col,
                width=font.Font(family="Segoe UI", size=12,
                                weight="bold").measure(col.title()) + 10,
                stretch=False)

        for item in self.treeData:
            self.tree.insert('', 'end', values=item)

            for indx, val in enumerate(item):
                ilen = font.nametofont('TkDefaultFont').measure(val)
                if self.tree.column(self.treeColumns[indx],
                                    width=None) < ilen + 10:
                    self.tree.column(self.treeColumns[indx], width=ilen + 10)
def retailer_homePage():
    def analysis_page():
        def get_selected_date(selection):
            selected_date = selection
            print(selected_date)

        def change_piechart():
            z1 = con.cursor()
            z1.execute("select sum(pprice) as inventory_total from inventory;")
            f1 = z1.fetchone()

            z2 = con.cursor()
            z2.execute(
                "select sum(pprice) as sales_total from inventory , sales where inventory.pid = sales.pid and sales.date = ? ;",
                (selected_date.get(), ))
            f2 = z2.fetchone()

            for x in f1:
                val1 = x

            for y in f2:
                val2 = y

            labels = [val1, val2]

            fig2 = matplotlib.figure.Figure(figsize=(4, 3))
            ax = fig2.add_subplot(111)
            ax.pie([f1, f2], labels=labels, startangle=90)
            ax.legend(["Total", "Gain"])
            circle = matplotlib.patches.Circle((0, 0), 0.7, color='white')
            ax.add_artist(circle)
            fig2.set_facecolor("#4fc3f7")

            canvas2 = FigureCanvasTkAgg(fig2, master=rootan)
            canvas2.get_tk_widget().place(x=270, y=330)
            canvas2.draw()

        rootan = Tk()
        rootan.geometry("940x610+100+50")
        rootan.title("Retailer Analysis")
        rootan.config(bg="#4fc3f7")
        selected_date = StringVar(rootan)

        x = []
        y = []

        analysislabel = Label(rootan,
                              text="Retailer Analysis",
                              font=("Lobster Two", 20, "bold"),
                              fg="#ffffff",
                              bg="#4fc3f7")
        analysislabel.pack()
        # navbar = Frame(rootan,bg="#212121",height=50,width=920)
        # navbar.place(x=0,y=0)
        g1 = con.cursor()
        g1.execute(
            "select pcategory as purchased from inventory,sales where inventory.pid = sales.pid GROUP by pcategory;"
        )
        fetch = g1.fetchall()

        for data in fetch:
            x.extend(data)

        g2 = con.cursor()
        g2.execute(
            "select count(sales.pid) as purchased from inventory,sales where inventory.pid = sales.pid GROUP by pcategory;"
        )
        fet = g2.fetchall()

        for dat in fet:
            y.extend(dat)

        fig = Figure(figsize=(5, 3), dpi=90)
        fig.suptitle('Category - wise', fontsize=16)
        axes = fig.add_subplot(111)
        axes.plot(x, y)

        canvas = FigureCanvasTkAgg(fig, rootan)
        canvas.get_tk_widget().pack(side=LEFT,
                                    anchor=NW,
                                    pady=(20, 0),
                                    padx=(10, 0))
        fig.set_facecolor("#81d4fa")

        top5 = Label(rootan,
                     text="Top 5 items :",
                     font=("Oxygen", 14, "bold"),
                     fg="#212121",
                     bg="#4fc3f7")
        top5.place(x=650, y=60)

        c = con.cursor()
        top = c.execute(
            "select pname,pcategory,count(pname) from inventory,sales where inventory.pid = sales.pid group by pname order by count(pname) DESC LIMIT 5;"
        )
        fetc = c.fetchall()

        tree = Treeview(rootan, columns=('pname', 'pcategory', 'count(pname)'))
        tree.heading('pname', text='Product Name')
        tree.heading('pcategory', text='Category')
        tree.heading('count(pname)', text='Purchased count')
        tree.column("pname", width=90)
        tree.column("pcategory", width=90)
        tree.column("count(pname)", width=90)
        tree.pack(side=RIGHT, anchor=NE, pady=(52, 0), padx=(0, 10))
        tree['show'] = 'headings'

        for data in fetc:
            tree.insert('', 'end', values=(data))

        options = []

        d = con.cursor()
        d.execute("select distinct(date) from sales;")
        val = d.fetchall()

        for data in val:
            options.extend(data)

        selected_date.set(options[1])

        w = OptionMenu(rootan,
                       selected_date,
                       *options,
                       command=get_selected_date)
        w.place(x=100, y=460)
        w.configure(background="#ffffff", relief="flat")

        date_show_pie = Button(rootan,
                               text="Show",
                               font=("Nunito", 10, "bold"),
                               bg="#ff5722",
                               fg="#000000",
                               relief="flat",
                               width=8,
                               activebackground="#ff5722",
                               command=change_piechart)
        date_show_pie.place(x=100, y=500)

        rootan.mainloop()

    def updateStock():
        a = con.cursor()
        a.execute("UPDATE stock SET total_quantity = ? WHERE pid =?", (
            updateNewQuantity.get(),
            updateStockId.get(),
        ))
        a.execute("UPDATE inventory SET pprice = ? WHERE pid = ?", (
            updateStockPrice.get(),
            updateStockId.get(),
        ))
        con.commit()
        rootm.destroy()
        retailer_homePage()

    def addItem():
        c = con.cursor()
        x = con.cursor()
        c.execute("INSERT INTO inventory (pname,pprice) VALUES(?,?)", (
            itemName.get(),
            itemPrice.get(),
        ))
        x.execute("INSERT INTO stock(total_quantity) VALUES(?)",
                  (itemStock.get(), ))
        con.commit()
        rootm.destroy()
        retailer_homePage()

    def removeItem():
        a = con.cursor()
        b = con.cursor()
        a.execute("DELETE FROM inventory where pid = ?",
                  (removeItemId.get(), ))
        b.execute("DELETE FROM stock where pid = ?", (removeItemId.get(), ))
        con.commit()
        rootm.destroy()
        retailer_homePage()

    rootm = Tk()
    rootm.geometry("920x570+100+50")
    rootm.title("Home")
    rootm.config(bg="#ffe0b2")

    itemName = StringVar(rootm)
    itemPrice = IntVar(rootm)
    itemStock = IntVar(rootm)
    removeItemId = IntVar(rootm)
    updateStockId = IntVar(rootm)
    updateNewQuantity = IntVar(rootm)
    updateStockPrice = IntVar(rootm)

    searchVar = StringVar(rootm)
    treeVals = []

    c = con.cursor()

    def command(self, *args):
        selections = []

        for i in range(len(treeVals)):
            if searchVar.get() != "" and searchVar.get(
            ) == treeVals[i][:len(searchVar.get())]:
                selections.append(ids[i])
                print(
                    selections
                )  #if it matches it appends the id to the selections list

        tree.selection_set(selections)  # Highlights the name in treeview

    c.execute(
        "SELECT inventory.pid,pname,pprice,total_quantity FROM `inventory`,`stock`  where stock.pid=inventory.pid ORDER BY inventory.pid ASC"
    )
    fetch = c.fetchall()

    tree = Treeview(rootm,
                    columns=('pid', 'pname', 'pprice', 'total_quantity'))
    tree.heading('pid', text='Product ID')
    tree.heading('pname', text='Product Name')
    tree.heading('pprice', text='Price')
    tree.heading('total_quantity', text='Stock Quantity')
    tree.column("pid", width=90)
    tree.column("pname", width=90)
    tree.column("pprice", width=90)
    tree.column("total_quantity", width=90)
    tree.pack(side=RIGHT, anchor=NE, fill='y', pady=(52, 0))
    tree['show'] = 'headings'

    ids = []
    for data in fetch:
        ids.append(tree.insert('', 'end', values=(data)))

    for child in tree.get_children():
        treeVals.append(tree.item(child)['values'][1])

    navbar = Frame(rootm, bg="#212121", height=50, width=920)
    navbar.place(x=0, y=0)

    searchVar.trace("w", command)
    search = Entry(rootm,
                   width=34,
                   relief="flat",
                   bg="#ffffff",
                   textvariable=searchVar,
                   font=("Oxygen", 10))
    search.insert(0, 'Quick Search')
    search.place(x=500, y=15)

    print(ids)
    print(treeVals)

    analysisbtn = Button(navbar,
                         text="Analysis",
                         font=("Noto sans", 12, "bold"),
                         fg="#ffffff",
                         bg="#2979ff",
                         relief="flat",
                         command=lambda: analysis_page())
    analysisbtn.place(x=230, y=5)

    outbtn = Button(navbar,
                    text="Back",
                    font=("Noto sans", 12, "bold"),
                    fg="#ffffff",
                    bg="#c62828",
                    relief="flat",
                    command=rootm.destroy)
    outbtn.place(x=830, y=5)

    addFrame = Frame(rootm, bg="#03a9f4", height=160, width=520)
    addFrame.place(x=10, y=55)

    removeFrame = Frame(rootm, bg="#03a9f4", height=160, width=520)
    removeFrame.place(x=10, y=230)

    updateFrame = Frame(rootm, bg="#03a9f4", height=160, width=520)
    updateFrame.place(x=10, y=405)

    #-----------------------------------------Update Stock Button------------------------------------------------------------------------------------------------

    update_button = Button(updateFrame,
                           text='Update',
                           font=("Nunito", 10, "italic"),
                           bg="#ffb300",
                           fg="#000000",
                           relief="flat",
                           width=7,
                           activebackground="#ffb300",
                           command=lambda: updateStock())
    update_button.place(x=450, y=125)

    updateHeadingLabel = Label(updateFrame,
                               text="Update Item :",
                               font=("Roboto", 12, "underline"),
                               fg="#212121",
                               bg="#03a9f4")
    updateHeadingLabel.place(x=5, y=10)

    updateitemLabel = Label(updateFrame,
                            text="Enter item id  : ",
                            font=("Noto sans", 10, "bold"),
                            fg="#212121",
                            bg="#03a9f4")
    updateitemLabel.place(x=5, y=70)

    updateitemEntry = Entry(updateFrame,
                            width=34,
                            relief="flat",
                            bg="#ffffff",
                            textvariable=updateStockId,
                            font=("Oxygen", 10))
    updateitemEntry.place(x=200, y=70)

    updateitemLabel = Label(updateFrame,
                            text="Enter item price  : ",
                            font=("Noto sans", 10, "bold"),
                            fg="#212121",
                            bg="#03a9f4")
    updateitemLabel.place(x=5, y=100)

    updateitemEntry = Entry(updateFrame,
                            width=34,
                            relief="flat",
                            bg="#ffffff",
                            textvariable=updateStockPrice,
                            font=("Oxygen", 10))
    updateitemEntry.place(x=200, y=100)

    updateitemLabel = Label(updateFrame,
                            text="Enter  new quantity  : ",
                            font=("Noto sans", 10, "bold"),
                            fg="#212121",
                            bg="#03a9f4")
    updateitemLabel.place(x=5, y=130)

    updateitemEntry = Entry(updateFrame,
                            width=34,
                            relief="flat",
                            bg="#ffffff",
                            textvariable=updateNewQuantity,
                            font=("Oxygen", 10))
    updateitemEntry.place(x=200, y=130)

    #-----------------------------------------Add Button-------------------------------------------------------------------------------------------

    add_button = Button(addFrame,
                        text='Add',
                        font=("Nunito", 10, "italic"),
                        bg="#ffb300",
                        fg="#000000",
                        relief="flat",
                        width=7,
                        activebackground="#ffb300",
                        command=lambda: addItem())
    add_button.place(x=450, y=125)

    addLabel = Label(addFrame,
                     text="Add New Item : ",
                     font=("Roboto", 12, "underline"),
                     fg="#212121",
                     bg="#03a9f4")
    addLabel.place(x=5, y=10)

    newitemLabel = Label(addFrame,
                         text="New Item Name : ",
                         font=("Noto sans", 10, "bold"),
                         fg="#212121",
                         bg="#03a9f4")
    newitemLabel.place(x=5, y=40)

    newitemEntry = Entry(addFrame,
                         width=34,
                         relief="flat",
                         bg="#ffffff",
                         textvariable=itemName,
                         font=("Oxygen", 10))
    newitemEntry.place(x=200, y=40)

    newitemPriceLabel = Label(addFrame,
                              text="New Item Price : ",
                              font=("Noto sans", 10, "bold"),
                              fg="#212121",
                              bg="#03a9f4")
    newitemPriceLabel.place(x=5, y=70)

    newitemPriceEntry = Entry(addFrame,
                              width=34,
                              relief="flat",
                              bg="#ffffff",
                              textvariable=itemPrice,
                              font=("Oxygen", 10))
    newitemPriceEntry.place(x=200, y=70)

    newitemStockLabel = Label(addFrame,
                              text="New Item Quantity/Stock : ",
                              font=("Noto sans", 10, "bold"),
                              fg="#212121",
                              bg="#03a9f4")
    newitemStockLabel.place(x=5, y=100)

    newitemStockEntry = Entry(addFrame,
                              width=34,
                              relief="flat",
                              bg="#ffffff",
                              textvariable=itemStock,
                              font=("Oxygen", 10))
    newitemStockEntry.place(x=200, y=100)

    #-------------------------------------------------Remove Button-------------------------------------------------------------------------------------------
    remove_button = Button(removeFrame,
                           text='Remove',
                           font=("Nunito", 10, "italic"),
                           bg="#ffb300",
                           fg="#000000",
                           relief="flat",
                           width=7,
                           activebackground="#ffb300",
                           command=lambda: removeItem())
    remove_button.place(x=450, y=125)

    removeHeadingLabel = Label(removeFrame,
                               text="Remove item :",
                               font=("Roboto", 12, "underline"),
                               fg="#212121",
                               bg="#03a9f4")
    removeHeadingLabel.place(x=5, y=10)

    removeitemLabel = Label(removeFrame,
                            text="Enter item id  : ",
                            font=("Noto sans", 10, "bold"),
                            fg="#212121",
                            bg="#03a9f4")
    removeitemLabel.place(x=5, y=70)

    removeitemEntry = Entry(removeFrame,
                            width=34,
                            relief="flat",
                            bg="#ffffff",
                            textvariable=removeItemId,
                            font=("Oxygen", 10))
    removeitemEntry.place(x=200, y=70)

    rootm.mainloop()
    def analysis_page():
        def get_selected_date(selection):
            selected_date = selection
            print(selected_date)

        def change_piechart():
            z1 = con.cursor()
            z1.execute("select sum(pprice) as inventory_total from inventory;")
            f1 = z1.fetchone()

            z2 = con.cursor()
            z2.execute(
                "select sum(pprice) as sales_total from inventory , sales where inventory.pid = sales.pid and sales.date = ? ;",
                (selected_date.get(), ))
            f2 = z2.fetchone()

            for x in f1:
                val1 = x

            for y in f2:
                val2 = y

            labels = [val1, val2]

            fig2 = matplotlib.figure.Figure(figsize=(4, 3))
            ax = fig2.add_subplot(111)
            ax.pie([f1, f2], labels=labels, startangle=90)
            ax.legend(["Total", "Gain"])
            circle = matplotlib.patches.Circle((0, 0), 0.7, color='white')
            ax.add_artist(circle)
            fig2.set_facecolor("#4fc3f7")

            canvas2 = FigureCanvasTkAgg(fig2, master=rootan)
            canvas2.get_tk_widget().place(x=270, y=330)
            canvas2.draw()

        rootan = Tk()
        rootan.geometry("940x610+100+50")
        rootan.title("Retailer Analysis")
        rootan.config(bg="#4fc3f7")
        selected_date = StringVar(rootan)

        x = []
        y = []

        analysislabel = Label(rootan,
                              text="Retailer Analysis",
                              font=("Lobster Two", 20, "bold"),
                              fg="#ffffff",
                              bg="#4fc3f7")
        analysislabel.pack()
        # navbar = Frame(rootan,bg="#212121",height=50,width=920)
        # navbar.place(x=0,y=0)
        g1 = con.cursor()
        g1.execute(
            "select pcategory as purchased from inventory,sales where inventory.pid = sales.pid GROUP by pcategory;"
        )
        fetch = g1.fetchall()

        for data in fetch:
            x.extend(data)

        g2 = con.cursor()
        g2.execute(
            "select count(sales.pid) as purchased from inventory,sales where inventory.pid = sales.pid GROUP by pcategory;"
        )
        fet = g2.fetchall()

        for dat in fet:
            y.extend(dat)

        fig = Figure(figsize=(5, 3), dpi=90)
        fig.suptitle('Category - wise', fontsize=16)
        axes = fig.add_subplot(111)
        axes.plot(x, y)

        canvas = FigureCanvasTkAgg(fig, rootan)
        canvas.get_tk_widget().pack(side=LEFT,
                                    anchor=NW,
                                    pady=(20, 0),
                                    padx=(10, 0))
        fig.set_facecolor("#81d4fa")

        top5 = Label(rootan,
                     text="Top 5 items :",
                     font=("Oxygen", 14, "bold"),
                     fg="#212121",
                     bg="#4fc3f7")
        top5.place(x=650, y=60)

        c = con.cursor()
        top = c.execute(
            "select pname,pcategory,count(pname) from inventory,sales where inventory.pid = sales.pid group by pname order by count(pname) DESC LIMIT 5;"
        )
        fetc = c.fetchall()

        tree = Treeview(rootan, columns=('pname', 'pcategory', 'count(pname)'))
        tree.heading('pname', text='Product Name')
        tree.heading('pcategory', text='Category')
        tree.heading('count(pname)', text='Purchased count')
        tree.column("pname", width=90)
        tree.column("pcategory", width=90)
        tree.column("count(pname)", width=90)
        tree.pack(side=RIGHT, anchor=NE, pady=(52, 0), padx=(0, 10))
        tree['show'] = 'headings'

        for data in fetc:
            tree.insert('', 'end', values=(data))

        options = []

        d = con.cursor()
        d.execute("select distinct(date) from sales;")
        val = d.fetchall()

        for data in val:
            options.extend(data)

        selected_date.set(options[1])

        w = OptionMenu(rootan,
                       selected_date,
                       *options,
                       command=get_selected_date)
        w.place(x=100, y=460)
        w.configure(background="#ffffff", relief="flat")

        date_show_pie = Button(rootan,
                               text="Show",
                               font=("Nunito", 10, "bold"),
                               bg="#ff5722",
                               fg="#000000",
                               relief="flat",
                               width=8,
                               activebackground="#ff5722",
                               command=change_piechart)
        date_show_pie.place(x=100, y=500)

        rootan.mainloop()
class MainWindow(Frame):
    def __init__(self, parent):
        Frame.__init__(self, parent)
        self.eventHandler = EventHandler(self)
        self.parent = parent
        self.initUI()

    def initUI(self):

        self.parent.title("File synchronizer")

        Style().configure("TButton", padding=(0, 5, 0, 5), font="serif 10")

        # 3X3 Grid
        self.columnconfigure(0, pad=3, weight=1)
        self.columnconfigure(1, pad=3)
        self.columnconfigure(2, pad=3, weight=1)
        self.rowconfigure(0, pad=3)
        self.rowconfigure(1, pad=3, weight=1)
        self.rowconfigure(2, pad=3)

        ltf = Frame(self)
        ltf.grid(row=0, column=0, sticky=W + E)
        # 1X4 Grid
        ltf.columnconfigure(0, pad=3)
        ltf.columnconfigure(1, pad=3, weight=1)
        ltf.columnconfigure(2, pad=3, weight=1)
        ltf.columnconfigure(3, pad=3)
        ltf.rowconfigure(0, pad=3, weight=1)
        llabel = Label(ltf, text="Direcotry:")
        llabel.grid(row=0, column=0, sticky=W + E)
        self.leftDir = Entry(ltf)
        self.leftDir.bind("<Return>", self.eventHandler.leftDirChanged)
        self.leftDir.grid(row=0, column=1, columnspan=2, sticky=W + E)
        # Left browse button
        lBtn = Button(ltf, text="browse...", command=self.eventHandler.chooseLeftDirectory)
        lBtn.grid(row=0, column=3, sticky=E)

        rtf = Frame(self)
        rtf.grid(row=0, column=2, sticky=W + E)
        # 1X4 Grid
        rtf.columnconfigure(0, pad=3)
        rtf.columnconfigure(1, pad=3, weight=1)
        rtf.columnconfigure(2, pad=3, weight=1)
        rtf.columnconfigure(3, pad=3)
        rtf.rowconfigure(0, pad=3, weight=1)
        rlabel = Label(rtf, text="Direcotry:")
        rlabel.grid(row=0, column=0, sticky=W + E)
        self.rightDir = Entry(rtf)
        self.rightDir.bind("<Return>", self.eventHandler.rightDirChanged)
        self.rightDir.grid(row=0, column=1, columnspan=2, sticky=W + E)
        # Right browse button
        rBtn = Button(rtf, text="browse...", command=self.eventHandler.chooseRightDirectory)
        rBtn.grid(row=0, column=3, sticky=E)

        # Left TreeView frame
        ltf1 = Frame(self)
        ltf1.grid(row=1, column=0, sticky=N + S + W + E)
        # 2 X 2 Grid
        ltf1.columnconfigure(0, pad=3, weight=1)
        ltf1.columnconfigure(1, pad=3)
        ltf1.rowconfigure(0, pad=3, weight=1)
        ltf1.rowconfigure(1, pad=3)
        self.ltree = Treeview(ltf1, columns=("fullpath", "type", "size"), displaycolumns="size")
        self.ltree.grid(row=0, column=0, sticky=E + W + S + N)
        lysb = ttk.Scrollbar(ltf1, orient=VERTICAL, command=self.ltree.yview)
        lysb.grid(row=0, column=1, sticky=NS)
        lxsb = ttk.Scrollbar(ltf1, orient=HORIZONTAL, command=self.ltree.xview)
        lxsb.grid(row=1, column=0, columnspan=3, sticky=EW)
        self.ltree["yscroll"] = lysb.set
        self.ltree["xscroll"] = lxsb.set
        self.ltree.heading("#0", text="Directory Structure", anchor="w")
        self.ltree.heading("size", text="File Size", anchor="w")
        self.ltree.column("size", stretch=0, width=100)
        self.ltree.bind("<<TreeviewOpen>>", self.eventHandler.openTree)

        # Right TreeView frame
        rtf1 = Frame(self)
        rtf1.grid(row=1, column=2, sticky=N + S + W + E)
        # 2 X 2 Grid
        rtf1.columnconfigure(0, pad=3, weight=1)
        rtf1.columnconfigure(1, pad=3)
        rtf1.rowconfigure(0, pad=3, weight=1)
        rtf1.rowconfigure(1, pad=3)
        self.rtree = Treeview(rtf1, columns=("fullpath", "type", "size"), displaycolumns="size")
        self.rtree.grid(row=0, column=0, sticky=E + W + S + N)
        rysb = ttk.Scrollbar(rtf1, orient=VERTICAL, command=self.ltree.yview)
        rysb.grid(row=0, column=1, sticky=NS)
        rxsb = ttk.Scrollbar(rtf1, orient=HORIZONTAL, command=self.ltree.xview)
        rxsb.grid(row=1, column=0, columnspan=3, sticky=EW)
        self.rtree["yscroll"] = rysb.set
        self.rtree["xscroll"] = rxsb.set
        self.rtree.heading("#0", text="Directory Structure", anchor="w")
        self.rtree.heading("size", text="File Size", anchor="w")
        self.rtree.column("size", stretch=0, width=100)
        self.rtree.bind("<<TreeviewOpen>>", self.eventHandler.openTree)

        # Command Button frame
        btnf = Frame(self)
        btnf.grid(row=1, column=1, sticky=W + E + N + S)
        btnf.columnconfigure(0, pad=3, weight=1)
        btnf.rowconfigure(0, pad=3, weight=1)
        btnf.rowconfigure(1, pad=3, weight=1)
        btnf.rowconfigure(2, pad=3, weight=1)
        btnf.rowconfigure(3, pad=3, weight=1)
        btnf.rowconfigure(4, pad=3, weight=1)
        btnf.rowconfigure(5, pad=3, weight=1)
        btnf.rowconfigure(6, pad=3, weight=1)
        btnf.rowconfigure(7, pad=3, weight=1)
        l2rBtn = Button(btnf, text="Left >> Right", command=self.eventHandler.left2RightSynch)
        l2rBtn.grid(row=1, column=0, sticky=W + E)

        syncBtn = Button(btnf, text="<< Sync >>", command=self.eventHandler.leftRightSynch)
        syncBtn.grid(row=3, column=0, sticky=W + E)

        r2lBtn = Button(btnf, text="Left << Right", command=self.eventHandler.right2LeftSynch)
        r2lBtn.grid(row=5, column=0, sticky=W + E)

        closeBtn = Button(self, text="Close", command=self.eventHandler.quit)
        closeBtn.grid(row=2, column=2, sticky=E)

        self.pack(fill=BOTH, expand=1)
class DialogPluginManager(Toplevel):
    def __init__(self, mainWin, modulesWithNewerFileDates):
        super(DialogPluginManager, self).__init__(mainWin.parent)
        
        self.ENABLE = _("Enable")
        self.DISABLE = _("Disable")
        self.parent = mainWin.parent
        self.cntlr = mainWin
        
        # copy plugins for temporary display
        self.pluginConfig = PluginManager.pluginConfig
        self.pluginConfigChanged = False
        self.uiClassMethodsChanged = False
        self.modelClassesChanged = False
        self.disclosureSystemTypesChanged = False
        self.hostSystemFeaturesChanged = False
        self.modulesWithNewerFileDates = modulesWithNewerFileDates
        
        parentGeometry = re.match("(\d+)x(\d+)[+]?([-]?\d+)[+]?([-]?\d+)", self.parent.geometry())
        dialogX = int(parentGeometry.group(3))
        dialogY = int(parentGeometry.group(4))

        self.title(_("Plug-in Manager"))
        frame = Frame(self)
        
        # left button frame
        buttonFrame = Frame(frame, width=40)
        buttonFrame.columnconfigure(0, weight=1)
        addLabel = Label(buttonFrame, text=_("Find plug-in modules:"), wraplength=60, justify="center")
        addLocalButton = Button(buttonFrame, text=_("Locally"), command=self.findLocally)
        ToolTip(addLocalButton, text=_("File chooser allows selecting python module files to add (or reload) plug-ins, from the local file system."), wraplength=240)
        addWebButton = Button(buttonFrame, text=_("On Web"), command=self.findOnWeb)
        ToolTip(addWebButton, text=_("Dialog to enter URL full path to load (or reload) plug-ins, from the web or local file system."), wraplength=240)
        addLabel.grid(row=0, column=0, pady=4)
        addLocalButton.grid(row=1, column=0, pady=4)
        addWebButton.grid(row=2, column=0, pady=4)
        buttonFrame.grid(row=0, column=0, rowspan=2, sticky=(N, S, W), padx=3, pady=3)
        
        # right tree frame (plugins already known to arelle)
        modulesFrame = Frame(frame, width=700)
        vScrollbar = Scrollbar(modulesFrame, orient=VERTICAL)
        hScrollbar = Scrollbar(modulesFrame, orient=HORIZONTAL)
        self.modulesView = Treeview(modulesFrame, xscrollcommand=hScrollbar.set, yscrollcommand=vScrollbar.set, height=7)
        self.modulesView.grid(row=0, column=0, sticky=(N, S, E, W))
        self.modulesView.bind('<<TreeviewSelect>>', self.moduleSelect)
        hScrollbar["command"] = self.modulesView.xview
        hScrollbar.grid(row=1, column=0, sticky=(E,W))
        vScrollbar["command"] = self.modulesView.yview
        vScrollbar.grid(row=0, column=1, sticky=(N,S))
        modulesFrame.columnconfigure(0, weight=1)
        modulesFrame.rowconfigure(0, weight=1)
        modulesFrame.grid(row=0, column=1, columnspan=4, sticky=(N, S, E, W), padx=3, pady=3)
        self.modulesView.focus_set()

        self.modulesView.column("#0", width=120, anchor="w")
        self.modulesView.heading("#0", text=_("Name"))
        self.modulesView["columns"] = ("author", "ver", "status", "date", "update", "descr", "license")
        self.modulesView.column("author", width=100, anchor="w", stretch=False)
        self.modulesView.heading("author", text=_("Author"))
        self.modulesView.column("ver", width=50, anchor="w", stretch=False)
        self.modulesView.heading("ver", text=_("Version"))
        self.modulesView.column("status", width=50, anchor="w", stretch=False)
        self.modulesView.heading("status", text=_("Status"))
        self.modulesView.column("date", width=70, anchor="w", stretch=False)
        self.modulesView.heading("date", text=_("File Date"))
        self.modulesView.column("update", width=50, anchor="w", stretch=False)
        self.modulesView.heading("update", text=_("Update"))
        self.modulesView.column("descr", width=200, anchor="w", stretch=False)
        self.modulesView.heading("descr", text=_("Description"))
        self.modulesView.column("license", width=70, anchor="w", stretch=False)
        self.modulesView.heading("license", text=_("License"))

        classesFrame = Frame(frame)
        vScrollbar = Scrollbar(classesFrame, orient=VERTICAL)
        hScrollbar = Scrollbar(classesFrame, orient=HORIZONTAL)
        self.classesView = Treeview(classesFrame, xscrollcommand=hScrollbar.set, yscrollcommand=vScrollbar.set, height=5)
        self.classesView.grid(row=0, column=0, sticky=(N, S, E, W))
        hScrollbar["command"] = self.classesView.xview
        hScrollbar.grid(row=1, column=0, sticky=(E,W))
        vScrollbar["command"] = self.classesView.yview
        vScrollbar.grid(row=0, column=1, sticky=(N,S))
        classesFrame.columnconfigure(0, weight=1)
        classesFrame.rowconfigure(0, weight=1)
        classesFrame.grid(row=1, column=1, columnspan=4, sticky=(N, S, E, W), padx=3, pady=3)
        self.classesView.focus_set()
        
        self.classesView.column("#0", width=200, anchor="w")
        self.classesView.heading("#0", text=_("Class"))
        self.classesView["columns"] = ("modules",)
        self.classesView.column("modules", width=500, anchor="w", stretch=False)
        self.classesView.heading("modules", text=_("Modules"))
        
        # bottom frame module info details
        moduleInfoFrame = Frame(frame, width=700)
        moduleInfoFrame.columnconfigure(1, weight=1)
        
        self.moduleNameLabel = Label(moduleInfoFrame, wraplength=600, justify="left", 
                                     font=font.Font(family='Helvetica', size=12, weight='bold'))
        self.moduleNameLabel.grid(row=0, column=0, columnspan=4, sticky=W)
        self.moduleAuthorHdr = Label(moduleInfoFrame, text=_("author:"), state=DISABLED)
        self.moduleAuthorHdr.grid(row=1, column=0, sticky=W)
        self.moduleAuthorLabel = Label(moduleInfoFrame, wraplength=600, justify="left")
        self.moduleAuthorLabel.grid(row=1, column=1, columnspan=3, sticky=W)
        self.moduleDescrHdr = Label(moduleInfoFrame, text=_("description:"), state=DISABLED)
        self.moduleDescrHdr.grid(row=2, column=0, sticky=W)
        self.moduleDescrLabel = Label(moduleInfoFrame, wraplength=600, justify="left")
        self.moduleDescrLabel.grid(row=2, column=1, columnspan=3, sticky=W)
        self.moduleClassesHdr = Label(moduleInfoFrame, text=_("classes:"), state=DISABLED)
        self.moduleClassesHdr.grid(row=3, column=0, sticky=W)
        self.moduleClassesLabel = Label(moduleInfoFrame, wraplength=600, justify="left")
        self.moduleClassesLabel.grid(row=3, column=1, columnspan=3, sticky=W)
        ToolTip(self.moduleClassesLabel, text=_("List of classes that this plug-in handles."), wraplength=240)
        self.moduleUrlHdr = Label(moduleInfoFrame, text=_("URL:"), state=DISABLED)
        self.moduleUrlHdr.grid(row=4, column=0, sticky=W)
        self.moduleUrlLabel = Label(moduleInfoFrame, wraplength=600, justify="left")
        self.moduleUrlLabel.grid(row=4, column=1, columnspan=3, sticky=W)
        ToolTip(self.moduleUrlLabel, text=_("URL of plug-in module (local file path or web loaded file)."), wraplength=240)
        self.moduleDateHdr = Label(moduleInfoFrame, text=_("date:"), state=DISABLED)
        self.moduleDateHdr.grid(row=5, column=0, sticky=W)
        self.moduleDateLabel = Label(moduleInfoFrame, wraplength=600, justify="left")
        self.moduleDateLabel.grid(row=5, column=1, columnspan=3, sticky=W)
        ToolTip(self.moduleDateLabel, text=_("Date of currently loaded module file (with parenthetical node when an update is available)."), wraplength=240)
        self.moduleLicenseHdr = Label(moduleInfoFrame, text=_("license:"), state=DISABLED)
        self.moduleLicenseHdr.grid(row=6, column=0, sticky=W)
        self.moduleLicenseLabel = Label(moduleInfoFrame, wraplength=600, justify="left")
        self.moduleLicenseLabel.grid(row=6, column=1, columnspan=3, sticky=W)
        self.moduleImportsHdr = Label(moduleInfoFrame, text=_("imports:"), state=DISABLED)
        self.moduleImportsHdr.grid(row=7, column=0, sticky=W)
        self.moduleImportsLabel = Label(moduleInfoFrame, wraplength=600, justify="left")
        self.moduleImportsLabel.grid(row=7, column=1, columnspan=3, sticky=W)
        self.moduleEnableButton = Button(moduleInfoFrame, text=self.ENABLE, state=DISABLED, command=self.moduleEnable)
        ToolTip(self.moduleEnableButton, text=_("Enable/disable plug in."), wraplength=240)
        self.moduleEnableButton.grid(row=8, column=1, sticky=E)
        self.moduleReloadButton = Button(moduleInfoFrame, text=_("Reload"), state=DISABLED, command=self.moduleReload)
        ToolTip(self.moduleReloadButton, text=_("Reload/update plug in."), wraplength=240)
        self.moduleReloadButton.grid(row=8, column=2, sticky=E)
        self.moduleRemoveButton = Button(moduleInfoFrame, text=_("Remove"), state=DISABLED, command=self.moduleRemove)
        ToolTip(self.moduleRemoveButton, text=_("Remove plug in from plug in table (does not erase the plug in's file)."), wraplength=240)
        self.moduleRemoveButton.grid(row=8, column=3, sticky=E)
        moduleInfoFrame.grid(row=2, column=0, columnspan=5, sticky=(N, S, E, W), padx=3, pady=3)
        moduleInfoFrame.config(borderwidth=4, relief="groove")
        
        okButton = Button(frame, text=_("Close"), command=self.ok)
        ToolTip(okButton, text=_("Accept and changes (if any) and close dialog."), wraplength=240)
        cancelButton = Button(frame, text=_("Cancel"), command=self.close)
        ToolTip(cancelButton, text=_("Cancel changes (if any) and close dialog."), wraplength=240)
        okButton.grid(row=3, column=3, sticky=(S,E), pady=3)
        cancelButton.grid(row=3, column=4, sticky=(S,E), pady=3, padx=3)
        
        enableDisableFrame = Frame(frame)
        enableDisableFrame.grid(row=3, column=1, sticky=(S,W), pady=3)
        enableAllButton = Button(enableDisableFrame, text=_("Enable All"), command=self.enableAll)
        ToolTip(enableAllButton, text=_("Enable all plug ins."), wraplength=240)
        disableAllButton = Button(enableDisableFrame, text=_("Disable All"), command=self.disableAll)
        ToolTip(disableAllButton, text=_("Disable all plug ins."), wraplength=240)
        enableAllButton.grid(row=1, column=1)
        disableAllButton.grid(row=1, column=2)
        
        self.loadTreeViews()

        self.geometry("+{0}+{1}".format(dialogX+50,dialogY+100))
        frame.grid(row=0, column=0, sticky=(N,S,E,W))
        frame.columnconfigure(0, weight=0)
        frame.columnconfigure(1, weight=1)
        frame.rowconfigure(0, weight=1)
        window = self.winfo_toplevel()
        window.columnconfigure(0, weight=1)
        window.rowconfigure(0, weight=1)
        
        self.bind("<Return>", self.ok)
        self.bind("<Escape>", self.close)
        
        self.protocol("WM_DELETE_WINDOW", self.close)
        self.grab_set()
        self.wait_window(self)
        
    def loadTreeViews(self):
        self.selectedModule = None

        # clear previous treeview entries
        for previousNode in self.modulesView.get_children(""): 
            self.modulesView.delete(previousNode)
            
        def loadSubtree(parentNode, moduleItems):
            for moduleItem in sorted(moduleItems, key=lambda item: item[0]):
                moduleInfo = moduleItem[1]
                if parentNode or not moduleInfo.get("isImported"):
                    nodeName = moduleItem[0]
                    if parentNode:
                        nodeName = parentNode + GROUPSEP + nodeName
                    name = moduleInfo.get("name", nodeName)
                    node = self.modulesView.insert(parentNode, "end", nodeName, text=name)
                    self.modulesView.set(node, "author", moduleInfo.get("author"))
                    self.modulesView.set(node, "ver", moduleInfo.get("version"))
                    self.modulesView.set(node, "status", moduleInfo.get("status"))
                    self.modulesView.set(node, "date", moduleInfo.get("fileDate"))
                    if name in self.modulesWithNewerFileDates:
                        self.modulesView.set(node, "update", _("available"))
                    self.modulesView.set(node, "descr", moduleInfo.get("description"))
                    self.modulesView.set(node, "license", moduleInfo.get("license"))
                    if moduleInfo.get("imports"):
                        loadSubtree(node, [(importModuleInfo["name"],importModuleInfo)
                                           for importModuleInfo in moduleInfo["imports"]])
            
        loadSubtree("", self.pluginConfig.get("modules", {}).items())
        
        # clear previous treeview entries
        for previousNode in self.classesView.get_children(""): 
            self.classesView.delete(previousNode)

        for i, classItem in enumerate(sorted(self.pluginConfig.get("classes", {}).items())):
            className, moduleList = classItem
            node = self.classesView.insert("", "end", className, text=className)
            self.classesView.set(node, "modules", ', '.join(moduleList))
            
        self.moduleSelect()  # clear out prior selection

    def ok(self, event=None):
        if self.pluginConfigChanged:
            PluginManager.pluginConfig = self.pluginConfig
            PluginManager.pluginConfigChanged = True
            PluginManager.reset()  # force reloading of modules
        if self.uiClassMethodsChanged or self.modelClassesChanged or self.disclosureSystemTypesChanged or self.hostSystemFeaturesChanged:  # may require reloading UI
            affectedItems = ""
            if self.uiClassMethodsChanged:
                affectedItems += _("menus of the user interface")
            if self.modelClassesChanged:
                if affectedItems:
                    affectedItems += _(" and ")
                affectedItems += _("model objects of the processor")
            if self.disclosureSystemTypesChanged:
                if affectedItems:
                    affectedItems += _(" and ")
                affectedItems += _("disclosure system types")
            if self.hostSystemFeaturesChanged:
                if affectedItems:
                    affectedItems += _(" and ")
                affectedItems += _("host system features")
            if messagebox.askyesno(_("User interface plug-in change"),
                                   _("A change in plug-in class methods may have affected {0}.  " 
                                     "Please restart Arelle to due to these changes.  \n\n"
                                     "Should Arelle restart itself now "
                                     "(if there are any unsaved changes they would be lost!)?"
                                     ).format(affectedItems),
                                   parent=self):
                self.cntlr.uiThreadQueue.put((self.cntlr.quit, [None, True]))
        self.close()
        
    def close(self, event=None):
        self.parent.focus_set()
        self.destroy()
                
    def moduleSelect(self, *args):
        node = (self.modulesView.selection() or (None,))[0]
        if node:
            node = node.rpartition(GROUPSEP)[2] # drop leading path names for module name
        moduleInfo = self.pluginConfig.get("modules", {}).get(node)
        if moduleInfo:
            self.selectedModule = node
            name = moduleInfo["name"]
            self.moduleNameLabel.config(text=name)
            self.moduleAuthorHdr.config(state=ACTIVE)
            self.moduleAuthorLabel.config(text=moduleInfo["author"])
            self.moduleDescrHdr.config(state=ACTIVE)
            self.moduleDescrLabel.config(text=moduleInfo["description"])
            self.moduleClassesHdr.config(state=ACTIVE)
            self.moduleClassesLabel.config(text=', '.join(moduleInfo["classMethods"]))
            self.moduleUrlHdr.config(state=ACTIVE)
            self.moduleUrlLabel.config(text=moduleInfo["moduleURL"])
            self.moduleDateHdr.config(state=ACTIVE)
            self.moduleDateLabel.config(text=moduleInfo["fileDate"] + " " +
                    (_("(an update is available)") if name in self.modulesWithNewerFileDates else ""))
            self.moduleLicenseHdr.config(state=ACTIVE)
            self.moduleLicenseLabel.config(text=moduleInfo["license"])
            if moduleInfo.get("imports"):
                self.moduleImportsHdr.config(state=ACTIVE)
                _text = ", ".join(mi["name"] for mi in moduleInfo["imports"][:3])
                if len(moduleInfo["imports"]) >= 3:
                    _text += ", ..."
                self.moduleImportsLabel.config(text=_text)
            _buttonState = DISABLED if moduleInfo.get("isImported") else ACTIVE
            self.moduleEnableButton.config(state=_buttonState,
                                           text={"enabled":self.DISABLE,
                                                 "disabled":self.ENABLE}[moduleInfo["status"]])
            self.moduleReloadButton.config(state=_buttonState)
            self.moduleRemoveButton.config(state=_buttonState)
        else:
            self.selectedModule = None
            self.moduleNameLabel.config(text="")
            self.moduleAuthorHdr.config(state=DISABLED)
            self.moduleAuthorLabel.config(text="")
            self.moduleDescrHdr.config(state=DISABLED)
            self.moduleDescrLabel.config(text="")
            self.moduleClassesHdr.config(state=DISABLED)
            self.moduleClassesLabel.config(text="")
            self.moduleUrlHdr.config(state=DISABLED)
            self.moduleUrlLabel.config(text="")
            self.moduleDateHdr.config(state=DISABLED)
            self.moduleDateLabel.config(text="")
            self.moduleLicenseHdr.config(state=DISABLED)
            self.moduleLicenseLabel.config(text="")
            self.moduleImportsHdr.config(state=DISABLED)
            self.moduleImportsLabel.config(text="")
            self.moduleEnableButton.config(state=DISABLED, text=self.ENABLE)
            self.moduleReloadButton.config(state=DISABLED)
            self.moduleRemoveButton.config(state=DISABLED)
        
    def findLocally(self):
        initialdir = self.cntlr.pluginDir # default plugin directory
        if not self.cntlr.isMac: # can't navigate within app easily, always start in default directory
            initialdir = self.cntlr.config.setdefault("pluginOpenDir", initialdir)
        filename = self.cntlr.uiFileDialog("open",
                                           parent=self,
                                           title=_("Choose plug-in module file"),
                                           initialdir=initialdir,
                                           filetypes=[(_("Python files"), "*.py")],
                                           defaultextension=".py")
        if filename:
            # check if a package is selected (any file in a directory containing an __init__.py
            #if (os.path.basename(filename) == "__init__.py" and os.path.isdir(os.path.dirname(filename)) and
            #    os.path.isfile(filename)):
            #    filename = os.path.dirname(filename) # refer to the package instead
            self.cntlr.config["pluginOpenDir"] = os.path.dirname(filename)
            moduleInfo = PluginManager.moduleModuleInfo(filename)
            self.loadFoundModuleInfo(moduleInfo, filename)
                

    def findOnWeb(self):
        url = DialogURL.askURL(self)
        if url:  # url is the in-cache or local file
            moduleInfo = PluginManager.moduleModuleInfo(url)
            self.cntlr.showStatus("") # clear web loading status
            self.loadFoundModuleInfo(moduleInfo, url)
                
    def loadFoundModuleInfo(self, moduleInfo, url):
        if moduleInfo and moduleInfo.get("name"):
            self.addPluginConfigModuleInfo(moduleInfo)
            self.loadTreeViews()
        else:
            messagebox.showwarning(_("Module is not itself a plug-in or in a directory with package __init__.py plug-in.  "),
                                   _("File does not itself contain a python program with an appropriate __pluginInfo__ declaration: \n\n{0}")
                                   .format(url),
                                   parent=self)
        
    def checkIfImported(self, moduleInfo):
        if moduleInfo.get("isImported"):
            messagebox.showwarning(_("Plug-in is imported by a parent plug-in.  "),
                                   _("Plug-in has a parent, please request operation on the parent: \n\n{0}")
                                   .format(moduleInfo.get("name")),
                                   parent=self)
            return True
        return False
    
    def removePluginConfigModuleInfo(self, name):
        moduleInfo = self.pluginConfig["modules"].get(name)
        if moduleInfo:
            if self.checkIfImported(moduleInfo):
                return;
            def _removePluginConfigModuleInfo(moduleInfo):
                _name = moduleInfo.get("name")
                if _name:
                    for classMethod in moduleInfo["classMethods"]:
                        classMethods = self.pluginConfig["classes"].get(classMethod)
                        if classMethods and _name in classMethods:
                            classMethods.remove(_name)
                            if not classMethods: # list has become unused
                                del self.pluginConfig["classes"][classMethod] # remove class
                            if classMethod.startswith("CntlrWinMain.Menu"):
                                self.uiClassMethodsChanged = True  # may require reloading UI
                            elif classMethod == "ModelObjectFactory.ElementSubstitutionClasses":
                                self.modelClassesChanged = True # model object factor classes changed
                            elif classMethod == "DisclosureSystem.Types":
                                self.disclosureSystemTypesChanged = True # disclosure system types changed
                            elif classMethod.startswith("Proxy."):
                                self.hostSystemFeaturesChanged = True # system features (e.g., proxy) changed
                    for importModuleInfo in moduleInfo.get("imports", EMPTYLIST):
                        _removePluginConfigModuleInfo(importModuleInfo)
                    self.pluginConfig["modules"].pop(_name, None)
            _removePluginConfigModuleInfo(moduleInfo)
            self.pluginConfigChanged = True

    def addPluginConfigModuleInfo(self, moduleInfo):
        if self.checkIfImported(moduleInfo):
            return;
        name = moduleInfo.get("name")
        self.removePluginConfigModuleInfo(name)  # remove any prior entry for this module
        def _addPlugin(moduleInfo):
            _name = moduleInfo.get("name")
            if _name:
                self.modulesWithNewerFileDates.discard(_name) # no longer has an update available
                self.pluginConfig["modules"][_name] = moduleInfo
                # add classes
                for classMethod in moduleInfo["classMethods"]:
                    classMethods = self.pluginConfig["classes"].setdefault(classMethod, [])
                    if name not in classMethods:
                        classMethods.append(_name)
                    if classMethod.startswith("CntlrWinMain.Menu"):
                        self.uiClassMethodsChanged = True  # may require reloading UI
                    elif classMethod == "ModelObjectFactory.ElementSubstitutionClasses":
                        self.modelClassesChanged = True # model object factor classes changed
                    elif classMethod == "DisclosureSystem.Types":
                        self.disclosureSystemTypesChanged = True # disclosure system types changed
                    elif classMethod.startswith("Proxy."):
                        self.hostSystemFeaturesChanged = True # system features (e.g., proxy) changed
            for importModuleInfo in moduleInfo.get("imports", EMPTYLIST):
                _addPlugin(importModuleInfo)
        _addPlugin(moduleInfo)
        self.pluginConfigChanged = True

    def moduleEnable(self):
        if self.selectedModule in self.pluginConfig["modules"]:
            moduleInfo = self.pluginConfig["modules"][self.selectedModule]
            if self.checkIfImported(moduleInfo):
                return;
            def _moduleEnable(moduleInfo):
                if self.moduleEnableButton['text'] == self.ENABLE:
                    moduleInfo["status"] = "enabled"
                elif self.moduleEnableButton['text'] == self.DISABLE:
                    moduleInfo["status"] = "disabled"
                for importModuleInfo in moduleInfo.get("imports", EMPTYLIST):
                    _moduleEnable(importModuleInfo)
            _moduleEnable(moduleInfo)
            if self.moduleEnableButton['text'] == self.ENABLE:
                self.moduleEnableButton['text'] = self.DISABLE
            elif self.moduleEnableButton['text'] == self.DISABLE:
                self.moduleEnableButton['text'] = self.ENABLE
            self.pluginConfigChanged = True
            self.loadTreeViews()
            
    def moduleReload(self):
        if self.selectedModule in self.pluginConfig["modules"]:
            url = self.pluginConfig["modules"][self.selectedModule].get("moduleURL")
            if url:
                moduleInfo = PluginManager.moduleModuleInfo(url, reload=True)
                if moduleInfo:
                    if self.checkIfImported(moduleInfo):
                        return;
                    self.addPluginConfigModuleInfo(moduleInfo)
                    self.loadTreeViews()
                    self.cntlr.showStatus(_("{0} reloaded").format(moduleInfo["name"]), clearAfter=5000)
                else:
                    messagebox.showwarning(_("Module error"),
                                           _("File or module cannot be reloaded: \n\n{0}")
                                           .format(url),
                                           parent=self)

    def moduleRemove(self):
        if self.selectedModule in self.pluginConfig["modules"]:
            self.removePluginConfigModuleInfo(self.selectedModule)
            self.pluginConfigChanged = True
            self.loadTreeViews()
                    
    def enableAll(self):
        self.enableDisableAll(True)
                    
    def disableAll(self):
        self.enableDisableAll(False)
                    
    def enableDisableAll(self, doEnable):
        for module in self.pluginConfig["modules"]:
            if not module.get("isImported"):
                moduleInfo = self.pluginConfig["modules"][module]
                def _enableDisableAll(moduleInfo):
                    if doEnable:
                        moduleInfo["status"] = "enabled"
                    else:
                        moduleInfo["status"] = "disabled"
                    for importModuleInfo in moduleInfo.get("imports", EMPTYLIST):
                        _enableDisableAll(importModuleInfo)
                _enableDisableAll(moduleInfo)
                if doEnable:
                    self.moduleEnableButton['text'] = self.DISABLE
                else:
                    self.moduleEnableButton['text'] = self.ENABLE
        self.pluginConfigChanged = True
        self.loadTreeViews()