for some reason, when I try to call the python script alone it does not
open. I have to be in Pycharm in order to open.
Also, I was able to turn another python script into exe but I gave it to
somebody else to run who was working another windows version, it could open
but did not do anything
Le lun. 9 nov. 2020 à 15:16, Nurul Carvalho <[email protected]> a
écrit :
> haham i'm seeing.. i thought this guide could help u...
> but i want too..
> please send screenshot of ur code..
> i'm working with linux and my compile process is lil bit different
> but anyway u just need to check if ur script (source code) is running like
> ur compiled program..
> (in the same folder with the same file locations)
>
> don't worry i'm here to help with anything that i can...
>
>
> melissa makonga <[email protected]> escreveu no dia segunda,
> 9/11/2020 à(s) 20:58:
>
>> I am still getting the same output. Maybe it is because the file that I
>> am working are on an external hard drive. Do you think that would cause an
>> issue because I also tried to run it on powershell but got the same output
>>
>> On Mon, Nov 9, 2020, 1:05 PM Nurul Carvalho <[email protected]>
>> wrote:
>>
>>> definitely, it's very strange...
>>> but are u sure that u didn't use any extra file in ur script?
>>> anyway, u can put the PressureGauge.exe file in the same folder as ur
>>> PressureGauge.py script and rerun it to see what's going next...
>>>
>>> melissa makonga <[email protected]> escreveu no dia segunda,
>>> 9/11/2020 à(s) 19:22:
>>>
>>>> No, I am only using --onefile but to package the exe I am using Pycharm.
>>>> This is what happen when I try to run it using command line
>>>>
>>>> On Mon, Nov 9, 2020, 11:42 AM Brenainn Woodsend <[email protected]>
>>>> wrote:
>>>>
>>>>> It sounds like you are using the `--windowed` option? If you are then
>>>>> don't. It means no output meaning you can never see any errors. Or
>>>>> possibly
>>>>> you are using Conda?
>>>>>
>>>>> --
>>>>> You received this message because you are subscribed to a topic in the
>>>>> Google Groups "PyInstaller" group.
>>>>> To unsubscribe from this topic, visit
>>>>> https://groups.google.com/d/topic/pyinstaller/HYmG_zasD6o/unsubscribe.
>>>>> To unsubscribe from this group and all its topics, send an email to
>>>>> [email protected].
>>>>> To view this discussion on the web visit
>>>>> https://groups.google.com/d/msgid/pyinstaller/CAFLMo5_Yei_wTihS_YKdENLWnQFftPObAzVO5MKrrOd%3DBpjtLw%40mail.gmail.com
>>>>> <https://groups.google.com/d/msgid/pyinstaller/CAFLMo5_Yei_wTihS_YKdENLWnQFftPObAzVO5MKrrOd%3DBpjtLw%40mail.gmail.com?utm_medium=email&utm_source=footer>
>>>>> .
>>>>>
>>>> --
>>>> You received this message because you are subscribed to the Google
>>>> Groups "PyInstaller" group.
>>>> To unsubscribe from this group and stop receiving emails from it, send
>>>> an email to [email protected].
>>>> To view this discussion on the web visit
>>>> https://groups.google.com/d/msgid/pyinstaller/CAF13mUwgv7utAytG3W_z1qfeU%3DvWd5c9cuw%2BSm-JPX6KN7ObuQ%40mail.gmail.com
>>>> <https://groups.google.com/d/msgid/pyinstaller/CAF13mUwgv7utAytG3W_z1qfeU%3DvWd5c9cuw%2BSm-JPX6KN7ObuQ%40mail.gmail.com?utm_medium=email&utm_source=footer>
>>>> .
>>>>
>>> --
>>> You received this message because you are subscribed to a topic in the
>>> Google Groups "PyInstaller" group.
>>> To unsubscribe from this topic, visit
>>> https://groups.google.com/d/topic/pyinstaller/HYmG_zasD6o/unsubscribe.
>>> To unsubscribe from this group and all its topics, send an email to
>>> [email protected].
>>> To view this discussion on the web visit
>>> https://groups.google.com/d/msgid/pyinstaller/CADcH5neOJ8y7_7OohfdS6B_Wn0CPsYj1vZfaDhCUo_z9zYab_Q%40mail.gmail.com
>>> <https://groups.google.com/d/msgid/pyinstaller/CADcH5neOJ8y7_7OohfdS6B_Wn0CPsYj1vZfaDhCUo_z9zYab_Q%40mail.gmail.com?utm_medium=email&utm_source=footer>
>>> .
>>>
>> --
>> You received this message because you are subscribed to the Google Groups
>> "PyInstaller" group.
>> To unsubscribe from this group and stop receiving emails from it, send an
>> email to [email protected].
>> To view this discussion on the web visit
>> https://groups.google.com/d/msgid/pyinstaller/CAF13mUwFPYguc%3DR1NNDB2sQWm%3DdpX%3Dbwiv__V10uffY7R%3DZTvA%40mail.gmail.com
>> <https://groups.google.com/d/msgid/pyinstaller/CAF13mUwFPYguc%3DR1NNDB2sQWm%3DdpX%3Dbwiv__V10uffY7R%3DZTvA%40mail.gmail.com?utm_medium=email&utm_source=footer>
>> .
>>
> --
> You received this message because you are subscribed to a topic in the
> Google Groups "PyInstaller" group.
> To unsubscribe from this topic, visit
> https://groups.google.com/d/topic/pyinstaller/HYmG_zasD6o/unsubscribe.
> To unsubscribe from this group and all its topics, send an email to
> [email protected].
> To view this discussion on the web visit
> https://groups.google.com/d/msgid/pyinstaller/CADcH5neMLmynQ9n7P%2B%2BKJR%2BoYQvXXMtNqHOn8mp3nJnbeFS44Q%40mail.gmail.com
> <https://groups.google.com/d/msgid/pyinstaller/CADcH5neMLmynQ9n7P%2B%2BKJR%2BoYQvXXMtNqHOn8mp3nJnbeFS44Q%40mail.gmail.com?utm_medium=email&utm_source=footer>
> .
>
--
You received this message because you are subscribed to the Google Groups
"PyInstaller" group.
To unsubscribe from this group and stop receiving emails from it, send an email
to [email protected].
To view this discussion on the web visit
https://groups.google.com/d/msgid/pyinstaller/CAF13mUyVa4%3D9m4Nj-yEcgrTJVvznQX426Qq_Vm%2BMbJyR8HoM-A%40mail.gmail.com.
"""
Michael Fusco - 12/14/2018
This script is intended to read data from certain pressure gauges and
continuously plot pressure data.
This script also generates a GUI with several buttons for starting and stopping
data aquisition/plotting
and also for recording pressure data to a text file. Currently supported
pressure gauge controllers include:
-Granville-Phillips 275 Mini-Convectron Module (RS485)
-MKS 650 series Baratron controller (RS232)
-MKS PDR2500 Baratron controller (RS232)
More pressure gauge options may be added at a later date
The type of controller should be specified in the Pgauge_info.txt file within
the Configuration Files folder.
Accepted designations are: '275c' for 275 Mini-Convectron, '650b' for 650
series Baratron, and
'2500b' for pdr2500 series Baratron controller.
*Note: the 275 convectron module uses RS485 communication. The COM port must be
set to a baud rate of 19200 and
2-Wire Auto setting. Otherwise, communication with the unit will fail.
The data recording module is connected to the valve control GUI using the
python socketserver module.
When a recipe is started in the valve control program, pressure data recording
will begin, provided the PressureGauge.py
script is running. This data will be written to a file located in the Pressure
Data folder within the Pressure_Gauge
folder.
"""
# ------------Imports ------------------------------------------
from Pressure_Gauge.Config import get_inst, get_press_dir, get_press_lim
import visa
import os
import tornado
import datetime
import threading
import collections
import matplotlib
from matplotlib.backends.backend_tkagg import FigureCanvasTkAgg
import tkinter.messagebox
import tkinter as tk
from tkinter import ttk
import matplotlib.pyplot as plt
import matplotlib.animation as animation
import socketserver
import socket
# -------------- End of Imports --------------------------------------
# ---------------- Functions ----------------------------------------
def exit_handler():
"""
Function to handle times when python exits. Shuts down the communication
server and closes and saves the data file
(if open). This function is only called if python exits normally. It does
not handle program crashes
"""
global stop, data_file, record, server
stop = True
server.shutdown()
if record:
data_file.close()
root.destroy()
def read_data(j):
"""
Function to communicate with several types of pressure gauge controllers.
The instrument is queried each time this
function is called, returning the time elapsed since data recording began
and the current measured pressure.
"""
global t_init
try:
if gauge_type[j].lower() == '275c':
try:
p_str = p_inst[j].query('#01RD')
p_vals = p_str.split(" ")
pressure = float(p_vals[1])
except visa.VisaIOError:
pressure = None
print('IO Error')
elif gauge_type[j].lower() == '650b':
try:
p_str = p_inst[j].query('R5')
p_val = p_str.split('+')
pressure = p_max[j] * float(p_val[1]) / 100
except visa.VisaIOError:
pressure = None
print('IO Error')
elif gauge_type[j].lower() == '146': #TODO - make this work
"""RS-232 communication is found on page 255 of manual
Commands are on 259 (!Commands)
Error coes are on 287 (!Error messages)
checksum note on 280 (annotated with !Checksum)"""
try:
p_str = p_inst[j].query('@6021?\r') #Which channel? (1,2,3,4 -
5 (Dual 1), 6 (dual 2))
#Original: p_str = p_inst[j].query('@602<para>?')
#is carriage retun in ascii he same as \r?
p_val = p_str.split('\r')
pressure = p_max[j] * float(p_val[1]) / 100
except visa.VisaIOError:
pressure = None
print('IO Error')
elif gauge_type[j].lower() == '2500b':
try:
p_str = p_inst[j].query('p')
p_vals = p_str.split(' ')
pressure = float(p_vals[1])
except visa.VisaIOError:
pressure = None
print('IO Error')
t_elapsed = datetime.datetime.now() - t_init
mins, sec = divmod(t_elapsed.days * 86400 + t_elapsed.seconds, 60)
microsec = t_elapsed.microseconds / 1000
t = mins * 60 + sec + round(microsec / 1000, 2)
except TypeError:
t = None
pressure = None
return t, pressure
def queue_data():
"""
Function to get data from the controller and place it in a queue to be
accessed by the update_graph function.
This function runs continuously while the play button is active. The
read_data function is called to get data from
the controller.
"""
def update_queue():
"""
This function continuously updates the data queue and writes that data
to a file if recording is active.
Recording only takes place every 5th? data point to prevent files from
becoming too large.
"""
global t_rec_int, t_rec_start, press_file_path
pressure = []
for j in range(len(p_inst)):
t, press = read_data(j)
pressure.append(press)
if pressure is None:
pass
else:
data_queue.append((t, pressure))
if record:
if (t - t_rec_start) >= t_rec_int-.003: #Data collection loop,
with lag factor
data_file.write(str(round(t, 2)))
for j in range(len(p_inst)):
data_file.write("\t" + str(round(pressure[j], 3)))
data_file.write("\n")
t_rec_start += t_rec_int
if os.path.getsize(press_file_path) >= 1e7:
data_file.close()
open_p_file()
global stop, record, data_file
while not stop:
update_queue()
def gen():
"""
Generator function to generate frame numbers for the plot animation. When
the pause button is pressed, the
generator continues yielding the same number over and over, effectively
pausing the plot animation. When play is
resumed, the generator continues incrementing n
"""
global stop
n = 0
while True:
if not stop:
n += 1
yield n
def update_graph(n):
"""
Function to update the graph with newly-collected data every 100 ms. Only
120 seconds worth of data is kept at
a time. Beyond that, earlier data is replaced with the most recent data.
:param n: Keeps track of the graph frames; n is passed to this function via
a generator
"""
global xlist, ylist_t, ylist_m, ax_scale, p_scale
try:
(t, pressure) = data_queue.popleft()
for j in range(len(p_inst)):
if pressure[j] <= 0:
pressure[j] = 1e-6
if len(xlist) > 2 and xlist[-1] - xlist[0] > 120:
xlist.popleft()
ylist_t.popleft()
ylist_m.popleft()
xlist.append(t)
ylist_t.append([round(pressure[j], 3) for j in range(len(p_inst))])
ylist_m.append([round(pressure[j]*1000, 1) for j in range(len(p_inst))])
except IndexError:
pressure = [0.0]
if p_scale == 'Torr':
p_val.config(text=str(round(pressure[0], 3)) + " " + p_scale)
line.set_data(xlist, ylist_t)
else:
p_val.config(text=str(round(pressure[0] * 1000, 1)) + " " + p_scale)
line.set_data(xlist, ylist_m)
ax.set_ylabel('Pressure (' + p_scale + ')')
ax.set_xlabel('Time (s)')
ax.set_yscale(ax_scale)
ax.relim()
ax.autoscale_view(True, True, True)
return line,
def record_click():
"""
Records time and pressure data to a text file. File name is the date with a
number appended at the end:
i.e. 2019-01-04_1
"""
global data_file, record, t_rec_int, t_rec_start
if record:
data_file.close()
record = False
record_button.config(bg='green', text='Record')
else:
try:
t_rec_int = float(rec_int_entry.get().replace(' ', ""))
except ValueError as ve:
print(ve)
t_rec_int = 0.2 # Record interval defaults to 0.2 s
open_p_file()
record_button.config(bg='lime green', text='Recording')
record = True
t_rec_start = 0.0
clear_click()
play_click()
def open_p_file():
global data_file, press_file_path
date = datetime.date.today()
a = False
h = 0
while not a:
h += 1
press_file_name = str(date) + "_" + str(h) + ".txt"
press_file_path = os.path.join(press_dir, press_file_name)
if os.path.exists(press_file_path):
pass
else:
a = True
data_file = open(press_file_path, 'w')
data_file.write(str(datetime.datetime.now()) + "\n")
data_file.write('Time (s)' + "\t" + 'Pressure (Torr)' + "\n")
def pause_click():
"""
Pauses data collection and plotting.
"""
global stop
if not stop:
stop = True
data_queue.clear()
play_button.config(state='normal')
pause_button.config(state='disabled')
else:
pass
def play_click():
"""
Starts or resumes data collection and plotting. If the graph was paused,
plotting will begin from the time at
which it was paused plus the time elapsed during the pause.
"""
global stop
if stop:
stop = False
play_button.config(state='disabled')
pause_button.config(state='normal')
# Start communicating with pressure controller to collect data
data_thread = threading.Thread(target=queue_data)
data_thread.start()
# Monitor pressure and compare to limit
alarm_thread = threading.Thread(target=monitor_pressure)
alarm_thread.start()
else:
pass
def clear_click():
"""
Clears the graphs and restarts from time 0
"""
global xlist, ylist_t, ylist_m, t_init
data_queue.clear()
xlist.clear()
ylist_t.clear()
ylist_m.clear()
t_init = datetime.datetime.now()
def axis_select(event=None):
"""
Function to change axis type of graph between linear and log pressure. It
gets the ax_type from a combobox in the
interface
"""
global ax_scale
ax_scale = axis_type.get()
def p_scale_select(event=None):
"""
Function to change axis type of graph between linear and log pressure. It
gets the ax_type from a combobox in the
interface
"""
global p_scale
p_scale = p_scale_cb.get()
def monitor_server():
"""
Function to create a local server for communication with another python
program.
Specifically, this function receives messages from the ALD sequencer
(Main.py) telling this program when to
record pressure data.
"""
global server
class MyHandler(socketserver.BaseRequestHandler):
def handle(self):
self.msg = self.request.recv(1024)
if self.msg.decode("utf-8") == 'start' or self.msg.decode("utf-8")
== 'stop':
record_click()
server = socketserver.TCPServer(("localhost", 9999), MyHandler)
server.socket.setsockopt(socket.SOL_SOCKET, socket.SO_REUSEADDR, 1)
server.serve_forever()
def feedback_server(msg):
try:
sock = socket.socket(socket.AF_INET, socket.SOCK_STREAM)
sock.settimeout(2)
sock.connect(('localhost', 8888))
sock.send(msg.encode('utf-8'))
sock.close()
except ConnectionRefusedError as e:
print(e)
def monitor_pressure():
global stop, alarm
alarm_count = 0
while not stop:
try:
pressure = ylist_t[-1]
except IndexError as ie:
print(ie)
if pressure > press_lim:
alarm_count += 1
if not alarm and alarm_count >= 3:
msg = 'alarm'
feedback_server(msg)
alarm = True
else:
if alarm:
msg = 'normal'
feedback_server(msg)
alarm = False
alarm_count = 0
# ----------------------------- End of Functions
---------------------------------------
# ----------------------------- Main program
--------------------------------------------
if __name__ == "__main__":
# Initialize instrument communication and directories
p_inst, gauge_type, p_max = get_inst()
press_dir = get_press_dir()
press_lim = get_press_lim()
# Initialize matplotlib properties
matplotlib.use('TkAgg')
matplotlib.interactive(False)
# Initialize variables
t_init = datetime.datetime.now()
ax_scale = 'linear'
p_scale = 'Torr'
stop = True
record = False
# Create deques (double-sided queues)
data_queue = collections.deque(maxlen=3)
xlist = collections.deque()
ylist_t = collections.deque()
ylist_m = collections.deque()
# -------------------- Create Tkinter window
---------------------------------
root = tk.Tk()
root.title('Pressure Monitor')
# --------------------- Create figure --------------------------------------
fig = plt.Figure()
ax = fig.add_subplot(111)
ax.set_ylabel('Pressure (Torr)')
ax.set_xlabel('Time (s)')
line, = ax.plot([], [])
# ---------------------- Create figure canvas
---------------------------------
canvas = FigureCanvasTkAgg(fig, master=root)
canvas.get_tk_widget().pack(expand=True, side=tk.BOTTOM)
# ------------------ Create the remaining Tk window features
----------------------
frame2 = tk.Frame(root)
frame2.pack(expand=True, side=tk.BOTTOM)
button_frame = tk.Frame(root)
button_frame.pack(expand=True, side=tk.BOTTOM)
record_button = tk.Button(button_frame, text='Record', width=10,
bg='green', command=record_click)
pause_button = tk.Button(button_frame, text='Pause', width=6, bg='yellow',
state='disabled', command=pause_click)
play_button = tk.Button(button_frame, text='Play', width=6,
command=play_click)
clear_button = tk.Button(button_frame, text='Clear Graph',
command=clear_click)
# check_button = tk.Checkbutton(button_frame)
ax_type_label = tk.Label(button_frame, text='Axis Type: ')
axis_type = ttk.Combobox(button_frame, values=["linear", "log"],
state='readonly')
axis_type.set('linear')
axis_type.bind("<<ComboboxSelected>>", axis_select)
p_scale_label = tk.Label(button_frame, text='Pressure Scale: ')
p_scale_cb = ttk.Combobox(button_frame, values=["Torr", "mTorr"],
state='readonly')
p_scale_cb.set('Torr')
p_scale_cb.bind("<<ComboboxSelected>>", p_scale_select)
p_val = tk.Label(button_frame, bg='white', relief=tk.SUNKEN, width=13)
rec_int_label = tk.Label(frame2, text='Record interval (s): ')
rec_int_entry = tk.Entry(frame2, text=' ', width=7, justify='center')
play_button.grid(row=0, column=0)
pause_button.grid(row=0, column=1)
record_button.grid(row=0, column=2)
clear_button.grid(row=0, column=3)
ax_type_label.grid(row=1, column=0, pady=5)
axis_type.grid(row=1, column=1, columnspan=2, pady=5)
p_val.grid(row=2, column=3, pady=5, padx=5)
p_scale_label.grid(row=2, column=0, pady=5)
p_scale_cb.grid(row=2, column=1, columnspan=2, pady=5)
rec_int_label.grid(row=0, column=0, padx=5, pady=5)
rec_int_entry.grid(row=0, column=1, padx=5, pady=5)
# ----------------------- Create thread to monitor external server
---------------------------
server_thread = threading.Thread(target=monitor_server)
server_thread.start()
# --------------------- Start animating pressure vs. time plot
-------------------------------------
ani = animation.FuncAnimation(fig, update_graph, frames=gen, interval=100,
blit=False, repeat=True, save_count=None)
# Check if instrument was detected
if p_inst == 0:
tkinter.messagebox.showinfo('Warning', 'No Instrument Detected! Check
COM port.')
rec_int_entry.focus_force()
# ---------------------- Call exit_handler when Tkinter window is closed
---------------------------
root.protocol('WM_DELETE_WINDOW', exit_handler)
root.mainloop()
# ------------------------------------- End of Program
--------------------------------------