create variable name from list using a loop in python - python

I am trying to generate a bunch of variables from a list, which will be called from another function.
If I create them separately(as in the commented part of the code), everything is working fine(by fine, I mean, I can access the date using get_data function listed below). But, when I am using the loop, the get_data is giving error:
File "main.py", line 97, in get_data
dAu = self.Author.get_text()
AttributeError: 'MyWindow' object has no attribute 'Author'
So, it is obvious that inside the loop, EDITI am expecting, for field[0],
self.field = self.field[0]=self.Author
but this is not the case.EDIT COMPLETE
self.field != self.Author
as I wished.
How can I get that?
The code in question is:
# Generate the Entry fields
self.notebook = Gtk.Notebook()
# self.LAuthor = Gtk.Label("Author")
# self.EAuthor = Gtk.Entry()
# self.page = Gtk.Grid()
# self.page.attach(self.LAuthor, 0, 0, 2, 1)
# self.page.attach_next_to(self.EAuthor, self.LAuthor, Gtk.PositionType.RIGHT, 1, 1)
# self.notebook.append_page(self.page, Gtk.Label("Trial"))
xpos = 0
minf = 0
fields = ["Author", "Year", "Journal", "Title", "Publisher", "Page",
"Address", "Annote", " Booktitle", "Chapter", "Crossred",
"Edition", "Editor", "HowPublished", "Institution", "Month",
"Note", "Number", "Organization", "Pages", "Publishers",
"School", "Series", "Type"]
Tabs = ["Essential", "Publishers", "Extra I", "Extra II"]
for note in range(int(len(fields)/6)):
ypos = 0
self.npage = "page"+str(note)
self.npage = Gtk.Grid()
self.npage.set_border_width(10)
maxf = minf+6
for field in fields[minf:maxf]:
print(field)
self.lfield = "L" + field
self.lfield = Gtk.Label(field)
self.field = Gtk.Entry()
self.field.set_placeholder_text(field)
self.npage.attach(self.lfield, xpos, ypos, 2, 1)
self.npage.attach_next_to(self.field, self.lfield,
Gtk.PositionType.RIGHT, 1, 1)
ypos += 1
self.notebook.append_page(self.npage, Gtk.Label(Tabs[note]))
minf = maxf
And the get_data function is just:
def get_data(self, widget):
dAu = self.Author.get_text()
print(dAu)
Kindly help.

Use dictionary - for example:
self.all_fields = dict()
field = "Author"
self.all_fields[field] = ...
# self.all_fields["Author"] = ...
and then you can use
def get_data(self, widget):
dAu = self.all_fields["Author"].get_text()
print(dAu)

Related

Tkinter delete not working on referenced entry when referenceing lenth of entry

I have a tkinter window class that I've made and my delete function is not working properly.
my_window = tk.Tk()
class QuoteForm():
def __init__(self,master):
self.file_data = ''
self.master = master
self.master.rowconfigure(0, weight=1)
self.master.rowconfigure(1, weight= 1)
self.master.rowconfigure(2, weight = 1)
master.geometry('600x400')
master.resizable(False,False)
#create the frames
self.directory_frm = tk.Frame(master=master)
self.directory_frm.grid(row=0) #this is the frame for the directory
self.add_on_frm = tk.Frame(master=master)
self.add_on_frm.grid(row=1) #this is the frame for add-ons input
self.button_frm = tk.Frame(master=master)
self.button_frm.grid(row=2) #this is the frame for
#creates buttons, entries, labels
self.load_directory_frame() #creates and grids the directory button
self.load_add_on_frame() #creates and grids the entry buttons and labels
self.load_button_frame() #creates and grids the buttons
my_window.mainloop()
def load_add_on_frame(self):
vcmd = (self.master.register(self.validate_ent), '%S')
#create inputs and labels for add-ons
self.trip_ent = tk.Entry(master=self.add_on_frm,validate = 'key', validatecommand = vcmd, name='trip_ent')
self.trip_ent.grid(column= 1, row = 0)
self.raw_cutouts_ent = tk.Entry(master=self.add_on_frm,validate = 'key', validatecommand = vcmd)
self.raw_cutouts_ent.grid(column= 3, row = 0)
def clear_entries(self):
entries = (self.trip_ent, self.raw_cutouts_ent) #list of entries to loop (there are a total of 12 in the actual code)
for entry in entries:
entry.delete(0,len(entry.get())) #this is where the trouble seems to happen
new_quote = QuoteForm(my_window)
My problem is that the on the second to last line of code (starting with 'entry.delete')
Typically you would do 'entry.delete(0,END)' but because entry is a variable the code won't run with END.
'END' is an invalid index, and 'end' just does the same as pulling the length, and so i tried to make it dynamic by making the 'end' the length of whatever is in the entry.
When i do that however, it deletes nothing [i also tried forcing it with int(len(entry.get()))]. If i manually enter an integer it will delete everything up to that integer, including if it's the same as the length of that entry, and I put breaks to confirm that i'm getting an int return and I am.
I realize i could just write a line of code to delete each entry individually, but there's a totaly of 12 and I would like to clean it up.
I'm adding the full code to be able to run below
import os
import re
import tkinter as tk
from tkinter import filedialog as fd
from tkinter import messagebox
import pandas as pd
my_window = tk.Tk()
class QuoteForm():
def __init__(self,master):
self.file_data = ''
self.master = master
self.master.rowconfigure(0, weight=1)
self.master.rowconfigure(1, weight= 1)
self.master.rowconfigure(2, weight = 1)
master.geometry('600x400')
master.resizable(False,False)
self.directory_frm = tk.Frame(master=master)
self.directory_frm.grid(row=0) #this is the frame for the directory
self.add_on_frm = tk.Frame(master=master)
self.add_on_frm.grid(row=1) #this is the frame for add-ons input
self.button_frm = tk.Frame(master=master)
self.button_frm.grid(row=2) #this is the frame for
self.load_directory_frame()
self.load_add_on_frame()
self.load_button_frame()
my_window.mainloop()
#staticmethod
def get_quote_data(filepath):
#read csv to get job infomation for pricing
try:
if filepath:
job_info = pd.read_csv(filepath,
index_col=0, #set index column
skiprows=range(4), #skip first 4 rows
usecols=['Item','Quan'])
job_info = job_info.drop(labels='Grand Total:', axis= 0)
customer_info = pd.read_csv(filepath, header=None,
skiprows= lambda x: x not in range(2), #skip any row beyond first two rows
usecols=[0,1]) #use first two columns
customer_info = {customer_info.at[0,0].replace(':',''): customer_info.at[0,1], ##formatting the data for legibility
customer_info.at[1,0].replace(':','') : customer_info.at[1,1]}
return [customer_info, job_info]
except:
messagebox.showerror("Data Invalid", "Please make sure you select a valid estimate CSV file.")
def sink_check(self):
####this is to be used at the submit buttons to confirm that there are not more sinks than cutouts
cutouts = self.um_sink_inst_ent.get()
sink_quan_list = (self.std_sink_ent.get(),self.upgrd_sink_ent.get(),self.van_sink_ent.get(),self.cust_sink_temp_ent.get())
sinks = sum(sink_quan_list)
if sinks > cutouts:
return False
###check that the sinks included does not exceed the number of sinks charged for install
return True
def validate_ent(self,input):
if not input:
return True
elif re.fullmatch(r'[0-9]',input):
return True
return False
def open_file(self):
file = fd.askopenfile(mode='r', filetypes=[('CSV Files', '*.csv')])
if file:
filepath = os.path.abspath(file.name)
file_data = self.get_quote_data(filepath)
cust_name = file_data[0]['Name']
job_addr = file_data[0]['Addr']
self.file_select_text['text'] = f"{job_addr} for {cust_name} is currently selected"
def load_directory_frame(self):
file_select_btn = tk.Button(master=self.directory_frm,text= "Select a file",command=self.open_file)
file_select_btn.grid(column=0, row=0)
self.file_select_text = tk.Label(master=self.directory_frm, text = "No File Selected")
self.file_select_text.grid(column=1, row=0)
def load_add_on_frame(self):
vcmd = (self.master.register(self.validate_ent), '%S')
#create inputs and labels for add-ons
self.trip_ent = tk.Entry(master=self.add_on_frm,validate = 'key', validatecommand = vcmd, name='trip_ent')
self.trip_ent.grid(column= 1, row = 0)
self.raw_cutouts_ent = tk.Entry(master=self.add_on_frm,validate = 'key', validatecommand = vcmd)
self.raw_cutouts_ent.grid(column= 3, row = 0)
self.radii_ent = tk.Entry(master=self.add_on_frm,validate = 'key', validatecommand = vcmd)
self.radii_ent.grid(column= 1, row = 1)
self.arcs_ent = tk.Entry(master=self.add_on_frm,validate = 'key', validatecommand = vcmd)
self.arcs_ent.grid(column= 3, row = 1)
self.splay_ent = tk.Entry(master=self.add_on_frm,validate = 'key', validatecommand = vcmd)
self.splay_ent.grid(column= 1, row = 2)
self.wtrfall_ent = tk.Entry(master=self.add_on_frm,validate = 'key', validatecommand = vcmd)
self.wtrfall_ent.grid(column= 3, row = 2)
self.um_sink_inst_ent = tk.Entry(master=self.add_on_frm,validate = 'key', validatecommand = vcmd)
self.um_sink_inst_ent.grid(column= 1, row = 3)
self.farm_sink_co_ent = tk.Entry(master=self.add_on_frm,validate = 'key', validatecommand = vcmd)
self.farm_sink_co_ent.grid(column= 3, row = 3)
self.std_sink_ent = tk.Entry(master=self.add_on_frm,validate = 'key', validatecommand = vcmd)
self.std_sink_ent.grid(column= 1, row = 4)
self.upgrd_sink_ent = tk.Entry(master=self.add_on_frm,validate = 'key', validatecommand = vcmd)
self.upgrd_sink_ent.grid(column= 3, row = 4)
self.van_sink_ent = tk.Entry(master=self.add_on_frm,validate = 'key', validatecommand = vcmd)
self.van_sink_ent.grid(column= 1, row = 5)
self.cust_sink_temp_ent = tk.Entry(master=self.add_on_frm,validate = 'key', validatecommand = vcmd)
self.cust_sink_temp_ent.grid(column= 3, row = 5)
trip_lbl = tk.Label(master=self.add_on_frm,text = "Extra Trip(s)")
trip_lbl.grid(column= 0, row = 0)
raw_cutouts_lbl = tk.Label(master=self.add_on_frm,text = "Unpolished Cutout(s)")
raw_cutouts_lbl.grid(column= 2, row = 0)
radii_lbl = tk.Label(master=self.add_on_frm,text = "Radii")
radii_lbl.grid(column= 0, row = 1)
arcs_lbl = tk.Label(master=self.add_on_frm,text = "Arc(s)")
arcs_lbl.grid(column= 2, row = 1)
splay_lbl = tk.Label(master=self.add_on_frm,text = "Splay(s)")
splay_lbl.grid(column= 0, row = 2)
wtrfall_lbl = tk.Label(master=self.add_on_frm,text = "Waterfal Leg(s)")
wtrfall_lbl.grid(column= 2, row = 2)
um_sink_inst_lbl = tk.Label(master=self.add_on_frm,text = "Install of UM Sink(s)")
um_sink_inst_lbl.grid(column= 0, row = 3)
farm_sink_co_lbl = tk.Label(master=self.add_on_frm,text = "Farm Sink C/O")
farm_sink_co_lbl.grid(column= 2, row = 3)
std_sink_lbl = tk.Label(master=self.add_on_frm,text = "Standard 18ga Sink(s)")
std_sink_lbl.grid(column= 0, row = 4)
upgrd_sink_lbl = tk.Label(master=self.add_on_frm,text = "Upgrade 18ga Sink(s)")
upgrd_sink_lbl.grid(column= 2, row = 4)
van_sink_lbl = tk.Label(master=self.add_on_frm,text = "Vanity Sink(s)")
van_sink_lbl.grid(column= 0, row = 5)
cust_sink_temp_lbl = tk.Label(master=self.add_on_frm,text = "Customer Sink Template(s)")
cust_sink_temp_lbl.grid(column= 2, row = 5)
def load_button_frame(self):
submit_btn = tk.Button(master=self.button_frm, text='Submit')
submit_btn.grid(column=0,row=0)
clear_btn = tk.Button(master=self.button_frm,text='Clear',command=self.clear_entries)
clear_btn.grid(column=1, row=0)
advanced_btn = tk.Button(master=self.button_frm,text='Advanced')
advanced_btn.grid(column=2, row=0)
def clear_entries(self):
entries = (self.trip_ent, self.raw_cutouts_ent, self.radii_ent, self.arcs_ent, self.splay_ent, #list of entry boxes on the form
self.wtrfall_ent, self.um_sink_inst_ent, self.um_sink_inst_ent, self.farm_sink_co_ent,
self.std_sink_ent, self.upgrd_sink_ent, self.van_sink_ent, self.cust_sink_temp_ent)
for entry in entries:
entry.delete(0,tk.END)
new_quote = QuoteForm(my_window)
It's all about yourvalidate_ent function. Only when it returns true then your entry text can change. While typing tkinter just sent single chars like '1','2','a'. Even when you remove with backspace, this function gets the character you are trying to remove. However when you try to clear it function gets as an input whole string like '123543123'. This is not takes place inside r'[0-9]' reguler expression and you return false so tkinter denies removing it.
There is two simple solution to fix this.
First one add another condition for longer input like:
def validate_ent(self,input):
if not input:
return True
elif re.fullmatch(r'[0-9]',input):
return True
if(len(input)>2):
return True
return False
However I do not recommend this one because if someone copy paste longer inputs then it can write letters inside entry boxes.
def validate_ent(self,input):
if not input:
return True
elif re.fullmatch(r'[0-9]*',input):
return True
return False
In here we added a asteriks to reguler expression. Now it's accepting numbers bigger then 9. Now people can also paste numbers that fits into this rule. Also removing works as expected!

How do you query an object inside of a text field, to do something with it?

I would like to know how to query a selection entered into a text field group, so I can do something with it. I have created a window to just translate an object that I loaded in the text field. The error is that cont is not defined.
import maya.cmds as cmds
import maya.mel as ml
def set_selected_name (text_field):
cont = cmds.ls (selection = True)
text_field = cmds.textFieldButtonGrp (text_field, edit = True,
text = ''.join (cont),
buttonLabel = '<<<<',
backgroundColor = [0.5098039215686274,
0.5098039215686274,
0.5098039215686274])
return text_field
def translate_x(cont):
cmds.setAttr( cont[0] + '.translateX', 10)
def translate_y():
cmds.setAttr( cont[0] + '.translateY', 10)
def translate_z(*Args):
cmds.setAttr( cont[0] + '.translateZ', 10)
if cmds.window ('window1', q = 1, ex = 1):
cmds.deleteUI ('window1')
cmds.window ('window1',
title = 'Translate Attr',
sizeable = 0,
resizeToFitChildren = True,
menuBar = 1)
cmds.rowLayout (numberOfColumns = 3)
cmds.separator (style = 'double',
height = 6)
cmds.rowLayout (parent = 'window1',
numberOfColumns = 4)
ddd = cmds.textFieldButtonGrp (editable = False,
text = 'Obj',
backgroundColor = [0.029495689326314183,
0.5488975356679637,
0.5488975356679637],
buttonLabel = '<<<<')
cmds.textFieldButtonGrp (ddd, edit = True,
buttonCommand = 'set_selected_name (ddd)')
cmds.separator (style = 'double',
height = 6)
cmds.rowLayout (parent = 'window1',
numberOfColumns = 6)
cmds.separator (style = 'double',
height = 6)
cmds.button (command = 'translate_y()',
backgroundColor = [1.0,
0.7300068665598535,
0.7300068665598535],
label = 'Translate Y')
cmds.separator (style = 'double',
height = 6)
cmds.button (command = 'translate_x(cont)',
backgroundColor = [1.0,
0.9733272297245746,
0.7333333333333333],
label = 'Translate X')
cmds.separator (style = 'double',
height = 6)
cmds.button (command = 'translate_z()',
backgroundColor = [0.7333333333333333,
1.0,
0.7600061036087586],
label = 'Translate Z')
cmds.columnLayout (parent = 'window1')
cmds.separator (style = 'double',
height = 3)
cmds.showWindow ('window1')
# ~ BABLAAM ~
Create any object you like, loaded into the text field and then try to translate with buttons.
You have several problems in your code.
In the translate commands you always use cont[0]. cont is only used in the function set_selected_name() and is a local variable what means it is deleted as soon as the function is completed.
You can use a string as command in the button command, but this only works with static values. You should use lambdas to use functions with arguments.
The cont Problem can be solved by using a global variable, but it shouldn't since global variables are the source of all evil. A much more elegant way would be to enclose you UI in one python class and use instance variables to get the selection.
I have adjusted the code to add the class as you recommended but still having the same issue. By not using the quotes in the button command I get this error when I try to run the script, instead of getting it when I press the button.
Error: NameError: file line 28: name 'translate_x' is not defined
Can you please write a workable version, or place a link from the internet that shows a method using the class and calling methods using buttons? Nothing I have found from my internet search has anything like this and I'm just guessing where thigs should go.
import maya.cmds as cmds
import maya.mel as ml
class move_obj(object):
def __int__(self, *args):
self.cont = cont
self.trans = trans
def set_selected_name(self, *args):
cont = cmds.ls (selection = True)
return cont
def translate_x(self, *args):
trans = cmds.setAttr( cont[0] + '.translateX', 10)
print trans
if cmds.window ('window1', q = 1, ex = 1):
cmds.deleteUI ('window1')
cmds.window ('window1',
title = 'Translate Attr',
sizeable = 0,
resizeToFitChildren = True,
menuBar = 1)
cmds.rowLayout (numberOfColumns = 3)
cmds.button (command = translate_x,
backgroundColor = [1.0,
0.7300068665598535,
0.7300068665598535],
label = 'Translate X')
cmds.showWindow ('window1')

Why wont my code return a value for the data input into a tkinter text box

I have written this code and for some reason it refuses to return any sort of value or input for slef.REV when used in the function post(self) however it will return a value when I try and return a value in the getlen() function which is used to reurn the number of characters in the review.I dont have this problem for any other variables that I retrieve data from within this class. Below is the relevant code, any help would be appreciated. the lines where this problem occures is the first functio calld post(lines 1-5) and 4 lines up from the bottom
def post(self):
MovieID = self.MovID
REV = self.REV
AddReview(conn,cursor,Add_Review,MovieID,REV)
print(REV)
def shrek_film(self):
self.title = "Shrek"
self.MovID = 1
self.root4 = tk.Toplevel()
self.root4.title("Watch Shreck")
self.root4.geometry("1400x800")
frame_4 = tk.Frame(self.root4, bg = "black")
frame_4.pack(fill = tk.BOTH, expand = True, padx=0 , pady=0)
frame_4.grid_columnconfigure(1,weight=1)
self.Create_canvas = tk.Canvas(frame_4, width=2000, height=1080)
self.Create_canvas.place(x=-50, y=-50)
self.Create_img = PhotoImage(file="shrek-landscape.gif")
self.Create_canvas.create_image(20, 20, anchor = NW, image=self.Create_img)
play_button= tk.Button(frame_4,bg="orange",text="play", command = self.addHistory)
play_button.place(x=700,y=400)
play_button.config(font=("Ariel","30"))
def gtelen():
Review = reviewbox.get('1.0',END)
REVLEN = len(Review)
REVLENLEFT = (231-len(Review))
if REVLEN >=230:
lenbox = tk.Label(frame_4 ,text="No words left",bg="orange")
lenbox.place(x=360,y=460)
lenbox.config(font=("Ariel","15"))
else:
lenbox = tk.Label(frame_4 ,text=REVLENLEFT,bg="orange")
lenbox.place(x=360,y=460)
lenbox.config(font=("Ariel","15"))
print(Review)
Words_button = tk.Button(frame_4, bg="orange",text="check number of words remaining", command=gtelen)
Words_button.place(x=150,y=460)
Words_button.config(font=("Ariel","10"))
reviewlable=tk.Label(frame_4,text="Write a review",bg="orange")
reviewlable.place(x=10,y=460)
reviewlable.config(font=("ariel","15"))
Review_button= tk.Button(frame_4,bg="orange",text="See Reviews")#, command = self.ViewReviews)
Review_button.place(x=490,y=450)
Review_button.config(font=("Ariel","15"))
reviewbox= Text(frame_4,width=100,height=12)
reviewbox.place(x=10,y=500)
self.REV = reviewbox.get('1.0',END)
post_button = tk.Button(frame_4,bg="orange",text="Post Review", command = self.post)
post_button.place(x=830,y=650)
post_button.config(font=("Ariel","15"))
You can use Entry instead and use a StringVar
v = StringVar() # Create StringVar
reviewbox = Entry(frame_4, width = 100, height = 12, textvariable = v) # Create Entry widget
reviewbox.place(x = 10, y = 500) # Place Entry widget
self.REV = v.get() # Get contents of StringVar
The line self.REV = reviewbox.get('1.0',END) is being called about a millisecond after creating the text widget. The user will not even have seen the widget yet, much less have had time to type in it.
You can't call the get() method until after the user has had a chance to enter data, such as inside the post method.
def post(self):
MovieID = self.MovID
REV = reviewbox.get("1.0", "end")
AddReview(conn,cursor,Add_Review,MovieID,REV)
print(REV)

Embedding visvis figure in a wx application

The code bellow try to embed visvis figure in a wx application to make a movie with 3D data. The problem is that everytime I rum the code, I get the error
"./src/unix/glx11.cpp(86): assert "xid" failed in SetCurrent(): window
must be shown" right after calling Figure = app.GetFigureClass()
self.fig = Figure(self)
I spent some time researching this error, but none of the answers suited me. Does anyone knows how to fix it?
import wx
import h5py
import numpy as np
import visvis as vv
app = vv.use('wx')
class CPlot3D (wx.Frame) :
"""
Class for plotting 3D Dirac
"""
def data_for_plotting (self, frame_number) :
"""
Load the data to be plotted for the frame with the frame_number
"""
frame = str(self.frame_names[frame_number])
return self.f[frame][...]
def draw_curent_frame (self, event=None) :
"""
Display the current frame
"""
# Load data
data = self.data_for_plotting (self.frame_number.GetValue())
try :
self.volume_plot.SetData (data)
except AttributeError :
vv.clf()
self.volume_plot = vv.volshow (data, clim=(self.global_min, self.global_max), renderStyle='mip', cm=vv.CM_JET)
a = vv.gca()
vv.ColormapEditor(a)
def GetTicks (axis_num, min_val, max_val, label_format="%.2f") :
size = data.shape[axis_num]
# Number of ticks
nticks = int(np.ceil(np.log2(size)))
nticks += 1 - nticks % 2 # Make <nticks> odd
ticks_position = np.linspace(0, size-1, nticks)
ticks_label = map( lambda x : label_format % x, np.linspace(min_val, max_val, nticks) )
return dict( zip(ticks_position, ticks_label) )
a.axis.xTicks = GetTicks(0, self.x_min, self.x_max)
a.axis.xLabel = "x (rel. units)"
a.axis.yTicks = GetTicks(1, self.y_min, self.y_max)
a.axis.yLabel = "y (rel. units)"
a.axis.zTicks = GetTicks(2, self.z_min, self.z_max)
a.axis.zLabel = "z (rel. units)"
self.fig.Draw()
def __init__ (self, parent, file_name, title="Plot Dirac 3D") :
# Open files
self.f = h5py.File (file_name, 'r')
# Extract the dimension
self.x_gridDIM = int(self.f['x_gridDIM'][...])
self.y_gridDIM = int(self.f['y_gridDIM'][...])
self.z_gridDIM = int(self.f['z_gridDIM'][...])
self.dx = self.f['dx'][...]
self.x_min = self.f['x_min'][...]
self.x_max = self.x_min + self.x_gridDIM * self.dx
self.y_min = self.f['y_min'][...]
self.y_max = self.y_min + self.y_gridDIM * self.dx
self.z_min = self.f['z_min'][...]
self.z_max = self.z_min + self.z_gridDIM * self.dx
# Collect the frame names
self.frame_names = []
for key in self.f.keys () :
try : self.frame_names.append (int(key))
except ValueError: pass
self.frame_names.sort ()
print "\nGet global maximum and minimum..."
# Find the min and max values in all the frames
for frame_number in range(len(self.frame_names)) :
data = self.data_for_plotting (frame_number)
try :
self.global_min = min( self.global_min, data.min() )
self.global_max = max( self.global_max, data.max() )
except AttributeError :
self.global_min = data.min()
self.global_max = data.max()
print "\nStart animation..."
# Create GUI
dw, dh = wx.DisplaySize()
wx.Frame.__init__ (self, parent, title=title, size=(0.4*dw, 0.6*dh) )
self.ConstructGUI ()
self.Center()
self.Show ()
wx.EVT_CLOSE(self, self.on_close)
self.On_animation_button ()
def on_close (self, event) :
try : self.animation_timer.Stop()
except AttributeError : pass
self.Destroy()
def ConstructGUI (self) :
"""
Make a GUI
"""
######################### Navigation bar ##############################
panel = wx.Panel(self)
boxsizer = wx.BoxSizer (wx.HORIZONTAL)
# Frame number indicator
boxsizer.Add (wx.StaticText(panel, label="Frame Number:"))
self.frame_number = wx.SpinCtrl (panel, value="0", min=0, max=len(self.frame_names)-1)
self.frame_number.Bind (wx.EVT_SPINCTRL, self.draw_curent_frame )
boxsizer.Add (self.frame_number)
# Go to the beginning button
self.go_beginnign_button = wx.Button (panel, label="<<")
self.Bind (wx.EVT_BUTTON, self.go_to_beginning, self.go_beginnign_button)
boxsizer.Add (self.go_beginnign_button)
# Animation button
self.animation_button_start_label = "Play animation "
self.animation_button_stop_label = "STOP animation"
self.animation_button = wx.Button (panel, label=self.animation_button_start_label)
self.Bind (wx.EVT_BUTTON, self.On_animation_button, self.animation_button)
boxsizer.Add (self.animation_button)
# Go to the end button
self.go_end_button = wx.Button (panel, label=">>")
self.Bind (wx.EVT_BUTTON, self.go_to_end, self.go_end_button)
boxsizer.Add (self.go_end_button)
panel.SetSizer (boxsizer)
############################# Setting up visvis binding #######################################
Figure = app.GetFigureClass()
self.fig = Figure(self)
################################### Layout #####################################################
sizer = wx.BoxSizer (wx.VERTICAL)
sizer.Add (panel, flag=wx.CENTER)
sizer.Add(self.fig._widget, 1, flag=wx.EXPAND)
self.SetSizer(sizer)
self.SetAutoLayout(True)
self.Layout()
def On_animation_button (self, event=None) :
"""
<self.animation_button> was clicked
"""
if self.animation_button.GetLabel() == self.animation_button_start_label :
# Begin playing animation
# Set up timer for animation
timer_id = wx.NewId ()
self.animation_timer = wx.Timer (self, timer_id)
self.animation_timer.Start (200)
def on_animation_timer (event) :
self.draw_curent_frame()
position = self.frame_number.GetValue()
if position > len(self.frame_names)-2 : self.On_animation_button ()
else : self.frame_number.SetValue (position+1)
wx.EVT_TIMER (self, timer_id, on_animation_timer)
# Channing the button's label
self.animation_button.SetLabel(self.animation_button_stop_label)
else : # Stop playing animation
self.animation_timer.Stop ()
del self.animation_timer
# Channing the button's label
self.animation_button.SetLabel(self.animation_button_start_label)
def go_to_beginning (self, event) :
"""
<self.go_beginnign_button> was clicked
"""
self.frame_number.SetValue (0)
self.draw_curent_frame()
def go_to_end (self, event) :
"""
<self.go_end_button> was clicked
"""
self.frame_number.SetValue (len(self.frame_names)-1)
self.draw_curent_frame()
if __name__ == '__main__' :
import sys
app.Create()
# Loading files
if len(sys.argv) <> 2 :
openFileDialog = wx.FileDialog(None, "Open HDF5 file to load 3D Dirac", "", "",
"HDF5 files (*.hdf5)|*.hdf5", wx.FD_OPEN | wx.FD_FILE_MUST_EXIST | wx.FD_CHANGE_DIR)
# Check whether user canceled
if openFileDialog.ShowModal() == wx.ID_CANCEL:
print "Error: file name is needed as argument"
exit()
else : filename = openFileDialog.GetPath()
else : filename = sys.argv[1]
CPlot3D (None, filename)
app.Run ()
When you call On_animation_button() manually, your frame is not actually shown yet, even though you had called Show() on it because, at least with X11, showing happens asynchronously. So you need to delay calling it until later. This can be done by e.g. binding a lambda doing this to EVT_SIZE event (because by the time you get it, the window is already initialized) or just by using CallAfter().

Get ItemWidget from QTreeWidget on DoubleClick event

I created a QTreeWidget now when i click on an item, i want to get the widget data.
I fill my QTreeWidget that way :
def addNodeToTreeview(self, data):
self.panelInfoPatientUi.treeWidgetDevices.clear()
for item in data:
mainWidgetItem = QtGui.QTreeWidgetItem(self.panelInfoPatientUi.treeWidgetDevices)
widgetContainer = QtWidgets.QWidget()
widgetContainer.setObjectName("widgetContainer")
deviceWidget = Ui_DeviceListviewWidget()
deviceWidget.setupUi(widgetContainer)
deviceWidget.labelSerialNumber.setText(item.serialNumber)
deviceWidget.labelModel.setText(item.model)
deviceWidget.labelInstallationDate.setText(item.installDate)
mainWidgetItem.setSizeHint(0, widgetContainer.sizeHint())
self.panelInfoPatientUi.treeWidgetDevices.addTopLevelItem(mainWidgetItem)
self.panelInfoPatientUi.treeWidgetDevices.setItemWidget(mainWidgetItem, 0, widgetContainer)
for files in item.listFile:
#Files
fileWidgetItem = QtGui.QTreeWidgetItem(mainWidgetItem)
widgetContainerFiles = QtWidgets.QWidget()
widgetContainerFiles.setObjectName("widgetContainerFiles")
fileWidget = Ui_FileListWidgetItem()
fileWidget.setupUi(widgetContainerFiles)
fileWidgetItem.setText(0, "BLABLBALA")
fileWidget.labelFileName.setText(files.fileName)
fileWidget.labelDateFile.setText(files.dateFile)
fileWidgetItem.setSizeHint(0, widgetContainerFiles.sizeHint())
mainWidgetItem.addChild(fileWidgetItem)
self.panelInfoPatientUi.treeWidgetDevices.setItemWidget(fileWidgetItem, 0, widgetContainerFiles)
i connect the widget that way :
def connectSignalTreeWidget(self):
self.view.panelInfoPatientUi.treeWidgetDevices.itemDoubleClicked.connect(self.testest)
and when i receive the Click event i can't access to my widget i tried several way :
def testest(self, item, col):
print(self.view.panelInfoPatientUi.treeWidgetDevices.itemWidget(item, 0))
#print([method for method in dir(item) if callable(getattr(item, method))])
#print(str(item.ItemType()))
#print(str(item.text(col)))
#print(str(item.child(0)))
#print(str(item.childCount()))
#print(str(item.child(1).text(0)))
#print(str(self.view.panelInfoPatientUi.treeWidgetDevices.currentItem()))
# titi = .itemWidget(item, columnIndex)
# print(str(titi))
# titi.text(0)
# titi.data()
#print(str(titi.labelFileName.text()))
'''selectedItems = self.view.panelInfoPatientUi.treeWidgetDevices.selectedItems()
for selectedItem in selectedItems:
print(str(selectedItem.text(0)))
print(str(selectedItem.text(1)))
print(str(selectedItem.text(2))) '''
'''
print(item.data(1, 0))
print("column count " + str(data.columnCount()))
print("AHYAAAAAAAAAA")'''
As i use "setItemWidget" method i expect to get a getItemWidget method and retreive data from it but no. How can i access to fileWidget.labelFileName ?
Thanks
I found the solution :
I changed my creation methode :
def addNodeToTreeview(self, data):
self.panelInfoPatientUi.treeWidgetDevices.clear()
for item in data:
mainWidgetItem = QtGui.QTreeWidgetItem(self.panelInfoPatientUi.treeWidgetDevices)
widgetContainer = QtWidgets.QWidget()
widgetContainer.setObjectName("widgetContainer")
deviceWidget = Ui_DeviceListviewWidget()
deviceWidget.setupUi(widgetContainer)
deviceWidget.labelSerialNumber.setText(item.serialNumber)
deviceWidget.labelModel.setText(item.model)
deviceWidget.labelInstallationDate.setText(item.installDate)
mainWidgetItem.setSizeHint(0, widgetContainer.sizeHint())
self.panelInfoPatientUi.treeWidgetDevices.addTopLevelItem(mainWidgetItem)
self.panelInfoPatientUi.treeWidgetDevices.setItemWidget(mainWidgetItem, 0, widgetContainer)
for files in item.listFile:
#Files
fileWidgetItem = QtGui.QTreeWidgetItem(mainWidgetItem)
widgetContainerFiles = QtWidgets.QWidget()
widgetContainerFiles.setObjectName("widgetContainerFiles")
widgetContainerFiles.ui = Ui_FileListWidgetItem()
widgetContainerFiles.ui.setupUi(widgetContainerFiles)
widgetContainerFiles.ui.labelFileName.setText(files.fileName)
widgetContainerFiles.ui.labelDateFile.setText(files.dateFile)
fileWidgetItem.setSizeHint(0, widgetContainerFiles.sizeHint())
mainWidgetItem.addChild(fileWidgetItem)
self.panelInfoPatientUi.treeWidgetDevices.setItemWidget(fileWidgetItem, 0, widgetContainerFiles)
and i can get my data like that :
def testest(self, item, col):
print(str(item.treeWidget().itemWidget(item, col).ui.labelFileName.text()))

Categories