Skip to content

Commit

Permalink
add files
Browse files Browse the repository at this point in the history
added files for SIMSEF tool. Bruker library and code referring to said library removed due to bruker restrictions
  • Loading branch information
SteffenHeu authored Jun 5, 2023
1 parent dc8e6d9 commit 1c818c5
Show file tree
Hide file tree
Showing 5 changed files with 261 additions and 0 deletions.
Binary file added figures_simsef_pewpew.png
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
Binary file added requirements.txt
Binary file not shown.
46 changes: 46 additions & 0 deletions src/AcquisitionControl.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,46 @@
import os
import shutil

from src.AcquisitionParameters import AcquisitionParameters
from src.InstrumentController import InstrumentController


class AcquisitionControl:
# controller: InstrumentController

def __init__(self):
self.controller = InstrumentController()

def runAcquisition(self, parameters: AcquisitionParameters):
if not os.path.exists(parameters.path):
os.mkdir(parameters.path)

# copy precursor file
shutil.copyfile(parameters.precursorList, "C:/BDalSystemData/timsTOF/maldi/maldi_tims_precursors.csv")

# if acqtype == 'accumulate':
# controller.setAppendAcquisition(True)
# else:
# controller.setAppendAcquisition(False)

if parameters.laserOffsetX is not None and parameters.laserOffsetY is not None:
self.controller.setLaserOffset(parameters.laserOffsetX, parameters.laserOffsetY)

self.controller.directory = parameters.path
self.controller.sampleName = parameters.name

if parameters.geometry is not None:
self.controller.maldiControl.selectGeometry(parameters.geometry)

if parameters.ceTable is not None and os.path.exists(parameters.ceTable):
self.controller.readAndSetCeTable(parameters.ceTable)

if parameters.isowdith is not None:
self.controller.overrideIsolationWidth(parameters.isowdith)

self.controller.moveToSpotAndWait(parameters.spot, parameters.xOffset, parameters.yOffset)
self.controller.singleSpotAcquisition()
if(os.path.isfile("C:/BDalSystemData/timsTOF/maldi/maldi_tims_precursors.csv")):
os.remove("C:/BDalSystemData/timsTOF/maldi/maldi_tims_precursors.csv")

# self.controller.snapshot()
79 changes: 79 additions & 0 deletions src/AcquisitionParameters.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,79 @@
import argparse


class AcquisitionParameters:
# spot: str
# xOffset: int
# yOffset: int
# path: str
# name: str
# geometry: str
# laserOffsetX: int
# laserOffsetY: int
# acqtype: str
# ceTable: str

def __init__(self, args):
parser = argparse.ArgumentParser(description="timsTOF Maldi controller")

parser.add_argument('--spot', required=True, type=str, help="The spot on a 384 target plate to be measured")
parser.add_argument('--xoffset', required=True, type=int, help="The offset in x dimension")
parser.add_argument('--yoffset', required=True, type=int, help="The offset in y dimension")
parser.add_argument('--path', required=True, type=str, help="The parent directory to store the analysis in.")
parser.add_argument('--name', required=True, type=str, help="The name of the analysis.")
parser.add_argument('--acqtype', required=False, choices=['accumulate', 'single'],
help="Specifies how the data shall be handled.\n"
"\"accumulate\" = add to current acquisition.\n" +
"\"single\" = store as single file (default).\n", default='single')
parser.add_argument('--cetable', required=False,
help="Path to csv file with collision energy settings. Must contain columns \'mass\' (decimal), " +
"\'iso_width\' (decimal), \'ce\' (decimal), \'type\' (0=base or 1=fixed) ")
parser.add_argument('--geometry', required=False, type=str,
help="Speficy a sample carrier geometry to select specific spots.")
parser.add_argument('--laseroffsetx', required=False, type=int, help="Specifies a laser offset in x dimension",
default=None)
parser.add_argument('--laseroffsety', required=False, type=int, help="Specifies a laser offset in y dimension",
default=None)
parser.add_argument('--precursorlist', required=True, type=str,
help="Path to csv file containing the list of precursors for this spot")
parser.add_argument('--isolationwidth', required=False, type=float, default=None,
help="Manually sets the isolation width in the MALDI mode. Overrides the isolation given in the CE table (if there is one).")

arguments = parser.parse_args(args)

# make a valid path so we can concatenate
if not arguments.path[len(arguments.path) - 1] == '/':
arguments.path = arguments.path + '/'

self.spot: str = arguments.spot
self.xOffset: int = arguments.xoffset
self.yOffset: int = arguments.yoffset
self.path: str = arguments.path
self.name: str = arguments.name
self.geometry: str = arguments.geometry
self.laserOffsetX: int = arguments.laseroffsetx
self.laserOffsetY: int = arguments.laseroffsety
self.acqtype: str = arguments.acqtype
self.ceTable = arguments.cetable
self.precursorList = arguments.precursorlist
self.isowdith = arguments.isolationwidth

# print(str(arguments))

def fromArgs(spot: str, path: str, name: str, precursorList: str, xOffset: int = 0, yOffset: int = 0,
geometry: str = None, laserOffsetX: int = 0, laserOffsetY: int = 0, acqtype: str = "single",
ceTable: str = None, isowidth: float = None):
# self.ceTable = ceTable
# self.laserOffsetY = laserOffsetY
# self.laserOffsetX = laserOffsetX
# self.yOffset = yOffset
# self.xOffset = xOffset
# self.spot = spot
# self.path = path
# self.geometry = geometry
# self.name = name
# self.acqtype = acqtype
return AcquisitionParameters(
["--spot", spot, "--path", path, "--name", name, "--xoffset", xOffset, "--yoffset", yOffset, "--geometry",
geometry, "--laserOffsetX", laserOffsetX, "--laserOffsetY", laserOffsetY, "--acqtype", acqtype,
"--cetable", ceTable, "--precursorlist", precursorList, "--isolationwidth", isowidth])
136 changes: 136 additions & 0 deletions src/simsef_pewpew.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,136 @@
import subprocess
import sys
import time
import argparse
import os
import shutil
from datetime import datetime
import sys
from PyQt5.QtWidgets import QApplication, QWidget, QTextEdit, QPushButton, QVBoxLayout, QHBoxLayout, QFileDialog
from PyQt5.QtGui import QPalette, QColor
from PyQt5.QtCore import Qt

# instrument specific imports
from src.AcquisitionControl import AcquisitionControl
from src.AcquisitionParameters import AcquisitionParameters

def main():
app = QApplication(sys.argv)

# Create a QWidget object (a window)
window = QWidget()
window.setGeometry(100, 100, 300, 200) # Set the position and size of the window
window.setWindowTitle('SIMSEF pewpew') # Set the window title

# Create a QTextEdit object (a text area)
global text_area
text_area = QTextEdit()
text_area.setPlaceholderText('Please select a file')

# Create two QPushButton objects (buttons)
button1 = QPushButton('Select command file')
button2 = QPushButton('Run acquisition')

# Define a function to handle the button1 click event
def open_file_dialog():
file_dialog = QFileDialog()
file_dialog.setNameFilter("Text file (*.txt)")
file_path = file_dialog.getOpenFileName(window, 'Select command file')[0]
if file_path:
text_area.setText(file_path)

# Connect the button1 click event to the open_file_dialog function
button1.clicked.connect(open_file_dialog)

# Connect the button2 click event to the run_function function
button2.clicked.connect(run_function)

# Create a QVBoxLayout object to arrange the widgets vertically
layout = QVBoxLayout()
layout.addWidget(text_area)
layout.addWidget(button1)

# Create a QHBoxLayout object to arrange the buttons horizontally
button_layout = QHBoxLayout()
button_layout.addWidget(button1)
button_layout.addWidget(button2)
layout.addLayout(button_layout)

# Set the dark mode stylesheet
dark_palette = QPalette()
dark_palette.setColor(QPalette.Window, QColor(53, 53, 53))
dark_palette.setColor(QPalette.WindowText, Qt.white)
dark_palette.setColor(QPalette.Base, QColor(25, 25, 25))
dark_palette.setColor(QPalette.AlternateBase, QColor(53, 53, 53))
dark_palette.setColor(QPalette.ToolTipBase, Qt.white)
dark_palette.setColor(QPalette.ToolTipText, Qt.white)
dark_palette.setColor(QPalette.Text, Qt.white)
dark_palette.setColor(QPalette.Button, QColor(53, 53, 53))
dark_palette.setColor(QPalette.ButtonText, Qt.white)
dark_palette.setColor(QPalette.BrightText, Qt.red)
dark_palette.setColor(QPalette.Link, QColor(42, 130, 218))
dark_palette.setColor(QPalette.Highlight, QColor(42, 130, 218))
dark_palette.setColor(QPalette.HighlightedText, Qt.black)
app.setPalette(dark_palette)

# Apply the stylesheet to the widgets
style_sheet = """
QTextEdit {
background-color: #252525;
color: white;
border: 1px solid #444444;
}
QPushButton {
background-color: #333333;
color: white;
border: 1px solid #444444;
}
QPushButton:hover {
background-color: #444444;
}
"""
window.setStyleSheet(style_sheet)

window.setLayout(layout)

window.show() # Show the window

sys.exit(app.exec_())

def run_function():

# Your code here
# text_area.append('Button 2 was clicked!')
# create Parameters
control = AcquisitionControl()

# parser = argparse.ArgumentParser()
# parser.add_argument('--commandfile', help='the path to command file', type=str, required=True)
# argtable = parser.parse_args()
commandFilePath = text_area.toPlainText()

with open(commandFilePath) as f:
lines = f.readlines()

measured = 0
starttime = datetime.now()
for line in lines:
line = line.strip()
args = line.split(" ")
parameters = AcquisitionParameters(args)
control.runAcquisition(parameters)

control.controller.waitUntilAcqFinished()

measured = measured + 1
elapsedTime = datetime.now() - starttime
text_area.append('Acquired MS/MS in spot ' + parameters.spot + ' ' + str(measured) + '/' + str(len(lines)))

remaining = (elapsedTime / measured) * (len(lines) - measured)
text_area.append('Time elapsed: ' + str(elapsedTime) + ' Remaining: ' + str(remaining))


if __name__ == "__main__":
main()

0 comments on commit 1c818c5

Please sign in to comment.