basically ok, need to polish the Plotlu plot style

This commit is contained in:
Ryan@Home 2024-11-03 22:43:52 -05:00
parent 8dbdb424d8
commit 056c55e01c
2 changed files with 173 additions and 26 deletions

View File

@ -1,20 +1,99 @@
#!/usr/bin/python3 #!/usr/bin/python3
import os import os
import datetime import platform
import csv
import subprocess import subprocess
import sys import sys
import time
from functools import partial from functools import partial
from PyQt6.QtWidgets import ( from PyQt6.QtWidgets import (
QApplication, QMainWindow, QGridLayout, QPushButton, QApplication, QMainWindow, QGridLayout, QPushButton,
QComboBox, QWidget, QLabel, QLineEdit, QTextEdit, QCheckBox, QComboBox, QWidget, QLabel, QLineEdit, QTextEdit, QCheckBox,
QFileDialog, QGroupBox, QVBoxLayout, QSpinBox, QDoubleSpinBox QFileDialog, QGroupBox, QVBoxLayout, QSpinBox, QDoubleSpinBox
) )
from PyQt6.QtCore import Qt, QPoint from PyQt6.QtCore import Qt, QUrl
from PyQt6.QtGui import QFont from PyQt6.QtGui import QFont
from PyQt6.QtWebEngineWidgets import QWebEngineView
import plotly.graph_objects as go
import tempfile
class PlotWindow(QWidget):
def __init__(self, XsecFile):
super().__init__()
self.setWindowTitle("DWBA Plot")
self.setGeometry(100, 100, 800, 600)
self.x = []
self.data = []
self.headers = []
self.x, self.data, self.headers = self.read_data(XsecFile)
layout = QVBoxLayout(self)
self.web_view = QWebEngineView()
layout.addWidget(self.web_view)
self.plot_plotly_graph()
def read_data(self,file_path):
x = [] # List for the first column
data = [] # 2D list for other columns
headers = [] # List to store headers
with open(file_path, 'r') as file:
header_found = False # Flag to indicate if the header has been found
for line in file:
# Skip lines that start with '#' and empty lines
if line.startswith('#') or not line.strip():
continue
if not header_found:
parts = line.split('ELab')
elab_parts = [parts[0]] # Start with the first part
for part in parts[1:]:
elab_parts.append('ELab' + part) # Prepend 'ELab' to each subsequent part
headers = elab_parts # Use the split parts as headers
header_found = True # Set the flag to True to skip this block in future iterations
print(f"ELab parts found: {elab_parts}") # Print or process this as needed
continue
# Split the line by whitespace
parts = line.split()
if len(parts) > 0: # Make sure there is at least one column
x.append(float(parts[0])) # First column
# Append the rest of the columns to data
if len(data) == 0:
# Initialize the data array with the right number of sublists
data = [[] for _ in range(len(parts) - 1)]
for i in range(len(parts) - 1):
data[i].append(float(parts[i + 1])) # Rest of the columns
print(headers)
return x, data, headers
def plot_plotly_graph(self):
# Create a Plotly figure
fig = go.Figure()
# Add traces for each column in data against x
for i, y in enumerate(self.data):
fig.add_trace(go.Scatter(x=self.x, y=y, mode='lines+markers', name=self.headers[i + 1])) # Use headers for names
# Update layout for better presentation
fig.update_layout(
xaxis_title="Angle_CM [Deg]",
yaxis_title="Values",
template="plotly"
)
# Save the plot as an HTML file in a temporary location
with tempfile.NamedTemporaryFile(delete=False, suffix=".html") as tmp_file:
fig.write_html(tmp_file.name)
html_file = tmp_file.name
# Load the HTML file in QWebEngineView
self.web_view.setUrl(QUrl.fromLocalFile(html_file))
class MyWindow(QMainWindow): class MyWindow(QMainWindow):
def __init__(self): def __init__(self):
@ -24,7 +103,9 @@ class MyWindow(QMainWindow):
self.setGeometry(100, 100, 1000, 700) self.setGeometry(100, 100, 1000, 700)
self.setMinimumSize(400, 600) self.setMinimumSize(400, 600)
self.DWBAFileName = "../DWBA" self.DWBAFileName = "DWBA"
self.bashResult = ""
self.plot_window = None
# Set up Group Box for DWBA Control # Set up Group Box for DWBA Control
self.gbDWBA = QGroupBox("DWBA") self.gbDWBA = QGroupBox("DWBA")
@ -32,15 +113,14 @@ class MyWindow(QMainWindow):
group_layout.setAlignment(Qt.AlignmentFlag.AlignTop) group_layout.setAlignment(Qt.AlignmentFlag.AlignTop)
self.gbDWBA.setLayout(group_layout) self.gbDWBA.setLayout(group_layout)
self.bnOpenDWBA = QPushButton("Open DWBA Source") self.bnOpenDWBA = QPushButton("Open DWBA")
self.bnOpenDWBA.clicked.connect(self.OpenDWBASourceFile) self.bnOpenDWBA.clicked.connect(lambda: self.LoadFileToTextBox(self.DWBAFileName))
self.bnOpenInFile = QPushButton("Open *.in File") self.bnOpenInFile = QPushButton("Open *.in File")
self.bnOpenInFile.clicked.connect(partial(self.LoadFileToTextBox, self.DWBAFileName + ".in")) self.bnOpenInFile.clicked.connect(lambda: self.LoadFileToTextBox(self.DWBAFileName + ".in"))
self.bnOpenOutFile = QPushButton("Open *.out File") self.bnOpenOutFile = QPushButton("Open *.out File")
self.bnOpenInFile.clicked.connect(partial(self.LoadFileToTextBox, self.DWBAFileName + ".out")) self.bnOpenOutFile.clicked.connect(lambda: self.LoadFileToTextBox(self.DWBAFileName + ".out"))
self.bnOpenXsecFile = QPushButton("Open X-sec File") self.bnOpenXsecFile = QPushButton("Open X-sec File")
self.bnOpenInFile.clicked.connect(partial(self.LoadFileToTextBox, self.DWBAFileName + ".txt")) self.bnOpenXsecFile.clicked.connect(lambda: self.LoadFileToTextBox(self.DWBAFileName + ".Xsec.txt"))
lbAngMin = QLabel("angMin") lbAngMin = QLabel("angMin")
lbAngMax = QLabel("angMax") lbAngMax = QLabel("angMax")
@ -60,15 +140,21 @@ class MyWindow(QMainWindow):
self.sbAngSize.setSingleStep(0.5) self.sbAngSize.setSingleStep(0.5)
self.chkCreateInFile = QCheckBox("Create InFile") self.chkCreateInFile = QCheckBox("Create InFile")
self.chkCreateInFile.setChecked(True)
self.chkRunPtolemy = QCheckBox("Run Ptolemy") self.chkRunPtolemy = QCheckBox("Run Ptolemy")
self.chkRunPtolemy.setChecked(True)
self.chkExtracrXsec = QCheckBox("Extract Xsec") self.chkExtracrXsec = QCheckBox("Extract Xsec")
self.chkPlot = QCheckBox("Plot") self.chkExtracrXsec.setChecked(True)
self.chkExtracrXsec.stateChanged.connect(self.OnOffXsecOption)
self.cbXsec = QComboBox() self.cbXsec = QComboBox()
self.cbXsec.addItem("XSec") self.cbXsec.addItem("XSec")
self.cbXsec.addItem("Ratio to Ruth.") self.cbXsec.addItem("Ratio to Ruth.")
self.cbXsec.addItem("Ruth.") self.cbXsec.addItem("Ruth.")
self.chkPlot = QCheckBox("Plot")
self.chkPlot.setChecked(True)
self.bnCalDWBA = QPushButton("Calculate DWBA") self.bnCalDWBA = QPushButton("Calculate DWBA")
self.bnCalDWBA.setFixedHeight(50) self.bnCalDWBA.setFixedHeight(50)
self.bnCalDWBA.clicked.connect(self.CalDWBA) self.bnCalDWBA.clicked.connect(self.CalDWBA)
@ -89,13 +175,16 @@ class MyWindow(QMainWindow):
group_layout.addWidget(self.chkRunPtolemy, 8, 0, 1, 2) group_layout.addWidget(self.chkRunPtolemy, 8, 0, 1, 2)
group_layout.addWidget(self.chkExtracrXsec, 9, 0, 1, 2) group_layout.addWidget(self.chkExtracrXsec, 9, 0, 1, 2)
group_layout.addWidget(self.chkPlot, 10, 0) group_layout.addWidget(self.cbXsec, 10, 0, 1, 2)
group_layout.addWidget(self.cbXsec, 10, 1) group_layout.addWidget(self.chkPlot, 11, 0, 1, 2)
group_layout.addWidget(self.bnCalDWBA, 11, 0, 1, 2) group_layout.addWidget(self.bnCalDWBA, 12, 0, 1, 2)
# Set up the Right Side # Set up the Right Side
self.bnOpenDWBASource = QPushButton("Open DWBA Source")
self.bnOpenDWBASource.clicked.connect(self.OpenDWBASourceFile)
self.leFileName = QLineEdit("") self.leFileName = QLineEdit("")
self.leFileName.setReadOnly(True) self.leFileName.setReadOnly(True)
self.leFileName.setText(self.DWBAFileName) self.leFileName.setText(self.DWBAFileName)
@ -116,7 +205,9 @@ class MyWindow(QMainWindow):
# Set up the layout # Set up the layout
layout = QGridLayout() layout = QGridLayout()
layout.addWidget(self.gbDWBA, 0, 0, 7, 1) layout.addWidget(self.gbDWBA, 0, 0, 7, 1)
layout.addWidget(self.leFileName, 0, 1, 1, 4)
layout.addWidget(self.bnOpenDWBASource, 0, 1)
layout.addWidget(self.leFileName, 0, 2, 1, 3)
layout.addWidget(self.bnSaveFile, 0, 5) layout.addWidget(self.bnSaveFile, 0, 5)
layout.addWidget(self.text_edit, 1, 1, 5, 5) layout.addWidget(self.text_edit, 1, 1, 5, 5)
layout.addWidget(self.leStatus, 6, 1, 1, 5) layout.addWidget(self.leStatus, 6, 1, 1, 5)
@ -127,6 +218,9 @@ class MyWindow(QMainWindow):
self.setCentralWidget(container) self.setCentralWidget(container)
####################################### methods ####################################### methods
def OnOffXsecOption(self):
self.cbXsec.setEnabled(self.chkExtracrXsec.isChecked())
def OpenDWBASourceFile(self): def OpenDWBASourceFile(self):
file_path, _ = QFileDialog.getOpenFileName(self, "Open File", "", "All Files (*)") file_path, _ = QFileDialog.getOpenFileName(self, "Open File", "", "All Files (*)")
if file_path: if file_path:
@ -135,11 +229,13 @@ class MyWindow(QMainWindow):
self.LoadFileToTextBox(self.DWBAFileName) self.LoadFileToTextBox(self.DWBAFileName)
def LoadFileToTextBox(self, fileName): def LoadFileToTextBox(self, fileName):
# print(fileName)
try: try:
with open(fileName, 'r') as file: with open(fileName, 'r') as file:
content = file.read() content = file.read()
self.text_edit.setText(content) self.text_edit.setText(content)
self.leStatus.setText(f"Loaded file : {fileName}") self.leStatus.setText(f"Loaded file : {fileName}")
self.leFileName.setText(fileName)
except Exception as e: except Exception as e:
self.text_edit.setText(f"Failed to load file:\n{e}") self.text_edit.setText(f"Failed to load file:\n{e}")
self.leStatus.setText(f"Failed to load file:\n{e}") self.leStatus.setText(f"Failed to load file:\n{e}")
@ -150,24 +246,71 @@ class MyWindow(QMainWindow):
file.write(self.text_edit.toPlainText()) file.write(self.text_edit.toPlainText())
self.leStatus.setText(f"File saved to: {file_path}") self.leStatus.setText(f"File saved to: {file_path}")
def MakePrograms(self): def BashCommand(self, cmd):
result = subprocess.run("cd ../Cleopatra; make;cd ../PyGUIQt6", shell=True, capture_output=True, text=True) print("Bash Command : |" + cmd + "|")
self.bashResult = subprocess.run(cmd, shell=True, capture_output=True, text=True)
print("Output:", result.stdout) print("Output:", self.bashResult.stdout)
print("Error:", result.stderr) print("Error:", self.bashResult.stderr)
print("Return Code:", result.returncode) print("Return Code:", self.bashResult.returncode)
def file_exists(self,file_path):
return os.path.exists(file_path) and os.path.isfile(file_path)
def CalDWBA(self): def CalDWBA(self):
self.MakePrograms() self.BashCommand("cd ../Cleopatra; make;cd ../PyGUIQt6")
if self.chkCreateInFile.isChecked : print(" Is Create InFile : " + str(self.chkCreateInFile.isChecked() ))
aMin = self.sbAngMin.value() print(" Is Run Ptolemy : " + str(self.chkRunPtolemy.isChecked() ))
aMax = self.sbAngMax.value() print(" Is Extract XSec : " + str(self.chkExtracrXsec.isChecked() ))
aSize = self.sbAngSize.value() print(" Is Plot : " + str(self.chkPlot.isChecked() ))
if self.chkCreateInFile.isChecked() :
aMin = " " + str(self.sbAngMin.value())
aMax = " " + str(self.sbAngMax.value())
aSize = " " + str(self.sbAngSize.value())
self.BashCommand("../Cleopatra/InFileCreator " + self.DWBAFileName + aMin + aMax + aSize)
isRunOK = False
if self.chkRunPtolemy.isChecked() :
os_name = platform.system()
if os_name == "Linux" :
self.BashCommand("../Cleopatra/ptolemy <" + self.DWBAFileName + ".in>" + " " + self.DWBAFileName + ".out")
if os_name == "Darwin":
self.BashCommand("../Cleopatra/ptolemy_mac <" + self.DWBAFileName + ".in>" + " " + self.DWBAFileName + ".out")
if self.bashResult.returncode == 0 :
isRunOK = True
else:
self.leStatus.setText("Ptolemy Run Error. Should check the out File.")
if isRunOK and self.chkExtracrXsec.isChecked() and self.file_exists(self.DWBAFileName + ".out") :
option = str(self.cbXsec.currentIndex())
self.BashCommand("../Cleopatra/ExtractXSec " + self.DWBAFileName + ".out " + option)
### Plot ##
if self.chkPlot.isChecked() and self.file_exists(self.DWBAFileName + ".Xsec.txt") :
print("dasdsadsa")
self.open_plot_window()
def open_plot_window(self):
print("dsadasdsadafkal;k;lkl;kdasdsadsa")
if self.plot_window is None :
self.plot_window = PlotWindow(self.DWBAFileName + ".Xsec.txt")
self.plot_window.show()
self.plot_window.setAttribute(Qt.WA_DeleteOnClose) # Optional: Automatically delete when closed
else:
self.plot_window.read_data(self.DWBAFileName + ".Xsec.txt")
self.plot_window.plot_plotly_graph()
def closeEvent(self, event):
if self.plot_window:
self.plot_window.close() # Close the PlotWindow when MainWindow closes
event.accept() # Accept the event to proceed with closing the main window
################################################## Main ################################################## Main

4
PyGUIQt6/README.md Normal file
View File

@ -0,0 +1,4 @@
~>sudo apt install python3-pyqt6 python3-pip
~>python3 -m pip install pyqt6 PyQt6-WebEngine Plotly