Skip to content

Commit

Permalink
Merge branch 'master' into 'marge'
Browse files Browse the repository at this point in the history
  • Loading branch information
volatile-static committed Nov 15, 2024
1 parent cffb480 commit e65dd9f
Show file tree
Hide file tree
Showing 147 changed files with 7,538 additions and 7,069 deletions.
573 changes: 6 additions & 567 deletions README.md

Large diffs are not rendered by default.

10 changes: 5 additions & 5 deletions autotuning/autotuning.py
Original file line number Diff line number Diff line change
Expand Up @@ -45,7 +45,7 @@ def findPort(self):
arduino_port = port.device

if arduino_port is None:
print("\nNo Arduino found for " + self.name)
print("WARNING: No Arduino found for " + self.name)
return False
else:
return arduino_port
Expand All @@ -62,7 +62,7 @@ def connect(self):
return False
else:
self.device = serial.Serial(port=self.port, baudrate=self.baudrate, timeout=self.timeout)
print("\nConnected to Arduino for " + self.name)
print("Connected to Arduino for " + self.name)
time.sleep(1.0)

def disconnect(self):
Expand All @@ -71,7 +71,7 @@ def disconnect(self):
"""
if self.device is not None:
self.device.close()
print("\nDisconnected from Arduino for " + self.name)
print("Disconnected from Arduino for " + self.name)
self.device = None

def send(self, data):
Expand Down Expand Up @@ -123,10 +123,10 @@ def connect(self):
time.sleep(0.1)
self.device = Hardware.get_VNA(self.interface)
self.frequencies = np.array(self.device.readFrequencies()) * 1e-6 # MHz
print("\nConnected to nanoVNA for auto-tuning")
print("Connected to nanoVNA for auto-tuning")
return True
except:
print("\nNo nanoVNA detected for auto-tuning")
print("WARNING: No nanoVNA detected for auto-tuning")
return False

def getFrequency(self):
Expand Down
11 changes: 7 additions & 4 deletions autotuning/autotuning_arduino/autotuning_arduino.ino.copy
Original file line number Diff line number Diff line change
@@ -1,7 +1,10 @@
// Code to control the autotuning circuit with python.
// cPins[] = {S1, S2, S3, S4, S5, T1, T2, T3, T4, T5, M1, M2, M3, M4, M5, TTL}
int cPins[] = {23, 31, 29, 27, 25, 41, 39, 37, 35, 33, 43, 51, 49, 47, 45, 53};
int nPins = 16;
/* Code to control the autotuning circuit with python.
We added two relays to control the VNA. First one selects if the autotuning is connected to the scanner or to the VNA.
Second one switches on or off the VNA to prevent noise coupling to the RF chain in the scanner.
*/
// cPins[] = {S1, S2, S3, S4, S5, T1, T2, T3, T4, T5, M1, M2, M3, M4, M5, VNA, VNA}
int cPins[] = {34, 36, 38, 40, 42, 44, 46, 48, 50, 52, 51, 53, 47, 49, 43, 45, 32};
int nPins = 17;

void setup() {
// Start the Serial communication
Expand Down
6 changes: 5 additions & 1 deletion configs/hw_config.py
Original file line number Diff line number Diff line change
Expand Up @@ -10,7 +10,6 @@
import numpy as np

gFactor = [0.025, 0.040, 0.035] # (X, Y, Z) in T/m/o.u.
max_grad = 80 # mT/m
max_slew_rate = 50e-3 # mT/m/ms
grad_raster_time = 30e-6 # s
grad_rise_time = 400e-6 # s, time for gradient ramps
Expand All @@ -29,16 +28,21 @@
adcFactor = 13.788 # mV/adcUnit
scanner_name = "Physio V1.01"
antenna_dict = {"RF01": np.pi/(0.3*70), "RF02": np.pi/(0.3*70)}
reference_time = 70 # us, reference excitation time to get the amplitude for rabi
fov = [20.0, 20.0, 20.0]
dfov = [0.0, 0.0, 0.0]
bash_path = "D:\Git\git-bash.exe" # use "gnome-terminal" for genome linux
rp_ip_address = "192.168.5.20"
rp_version = "rp-122"
rp_max_input_voltage = 225 # mV
lnaGain = 50 # dB
rf_min_gain = 50 # dB if your rf chain uses a fix gain, set this number equal to lnaGain
rf_max_gain = 76 # dB, if your rf chain uses a fix gain, set this number equal to lnaGain
temperature = 293 # k
shimming_factor = 1e-5
rx_channels = 4

# Arduinos
ard_sn_autotuning = '242353133363518050E0'
ard_sn_interlock = '242353133363518050E1'
ard_sn_attenuator = '242353133363518050E2'
1 change: 0 additions & 1 deletion configs/sys_config.py.copy
Original file line number Diff line number Diff line change
Expand Up @@ -2,4 +2,3 @@ study_case = ["Phantom", "Hand", "Wrist", "Forearm", "Elbow", "Foot", "Ankle", "
projects = ["None", "La Fe", "Ana Ferri"]
side = ["Left", "Right"]
orientation = ["Supine", "Prono"]
screenshot_folder = "experiments/screenshots"
40 changes: 37 additions & 3 deletions controller/controller_console.py
Original file line number Diff line number Diff line change
Expand Up @@ -4,7 +4,7 @@
:affiliation: MRILab, i3M, CSIC, Valencia, Spain
"""

import datetime
import sys
from PyQt5.QtCore import QObject, pyqtSignal, pyqtSlot
from widgets.widget_console import ConsoleWidget
Expand All @@ -28,17 +28,51 @@ class ConsoleController(ConsoleWidget):
def __init__(self):
super().__init__()

def setup_console(self):
# Redirect the output of print to the console widget
sys.stdout = EmittingStream(textWritten=self.write_console)

def write_console(self, text):
cursor = self.console.textCursor()
cursor.movePosition(cursor.End)
cursor.insertText(text)

# Get the current time and format it
current_time = datetime.datetime.now().strftime("%H:%M:%S")
current_time = "<b>" + current_time + "</b>"

# Give format to the text
if "ERROR" in text:
text = f'<span style="color:red;"><b>ERROR</b></span>{text[5:]}'

if "WARNING" in text:
text = f'<span style="color:orange;"><b>WARNING</b></span>{text[7:]}'

if "READY" in text:
text = f'<span style="color:green;"><b>READY</b></span>{text[5:]}'

# Prepend the time to the text
if text == "\n" or text == " ":
formatted_text = text
else:
formatted_text = f"{current_time} - {text}"
formatted_text = formatted_text.replace("\n", "<br>")

# Check if the text contains a marker for bold formatting
if "<b>" in formatted_text and "</b>" in formatted_text:
# Insert the text as HTML to allow formatting
cursor.insertHtml(formatted_text)
else:
# Insert plain text
cursor.insertText(formatted_text)

self.console.setTextCursor(cursor)
self.console.ensureCursorVisible()

def clear_console(self):
"""
Clear the console widget by removing all its contents.
"""
self.console.clear() # Clears the console content

class EmittingStream(QObject):
"""
Emitting stream class.
Expand Down
2 changes: 1 addition & 1 deletion controller/controller_figures.py
Original file line number Diff line number Diff line change
Expand Up @@ -34,7 +34,7 @@ def wellcomeMessage():
Note:
The method does not return any value.
"""
print("\nGraphical User Interface for MaRCoS")
print("Graphical User Interface for MaRCoS")
print("J.M. Algarín, PhD")
print("[email protected]")
print("mriLab @ i3M, CSIC, Valencia, Spain")
Expand Down
75 changes: 49 additions & 26 deletions controller/controller_history_list.py
Original file line number Diff line number Diff line change
Expand Up @@ -20,6 +20,7 @@
from widgets.widget_history_list import HistoryListWidget
from manager.dicommanager import DICOMImage
import numpy as np
import configs.hw_config as hw


class HistoryListController(HistoryListWidget):
Expand Down Expand Up @@ -53,14 +54,16 @@ def __init__(self, *args, **kwargs):
self.itemChanged.connect(self.main.sequence_list.updateSequence)
self.itemEntered.connect(self.main.sequence_list.updateSequence)

def delete_items(self):
while self.count() > 0:
self.deleteTask(item_number=0)

def showContextMenu(self, point):
"""
Displays a context menu at the given point.
:param point: The position where the context menu should be displayed.
"""
# Send printed text to the corresponding console
self.main.console.setup_console()

self.clicked_item = self.itemAt(point)
if self.clicked_item is not None:
Expand All @@ -87,13 +90,24 @@ def openPostGui(self):
self.main.post_gui.showMaximized()
self.main.post_gui.toolbar_image.rawDataLoading(file_path=path + "/mat/", file_name=item_name)

def deleteTask(self):
def deleteTask(self, item_number=None):
"""
Deletes the currently selected task from the list.
This method removes the currently selected task item from the list widget.
"""
self.takeItem(self.row(self.currentItem()))
if item_number is None:
item = self.currentItem()
else:
item = self.item(item_number)
text = item.text()
text = text.split(".", maxsplit=2)
key = text[0] + "." + text[1]
self.takeItem(self.row(item))
if key in self.pending_inputs.keys():
self.pending_inputs.pop(text)
if key in self.inputs.keys():
self.inputs.pop(key)

def addNewFigure(self):
"""
Expand Down Expand Up @@ -177,7 +191,7 @@ def addFigure(self):
label.setText(self.labels[n])
self.main.figures_layout.addWidget(label, row=1, col=col)
self.main.figures_layout.addWidget(image, row=2, col=col)
self.main.figures_layout.addWidget(sub_label, row=0, col=0, colspan=col+1)
self.main.figures_layout.addWidget(sub_label, row=0, col=0, colspan=col + 1)
except:
pass
n += 1
Expand All @@ -196,8 +210,6 @@ def updateHistoryTable(self, item):
:param item: The selected item from which to retrieve the corresponding input data.
"""
# Send printed text to the corresponding console
self.main.console.setup_console()

# Get the corresponding key to get access to the history dictionary
item_time = item.text().split(' | ')[0]
Expand Down Expand Up @@ -237,8 +249,6 @@ def updateHistoryFigure(self, item):
:param item: The selected item from which to retrieve the corresponding output information.
"""
# Send printed text to the corresponding console
self.main.console.setup_console()

# Get the corresponding key to get access to the history dictionary
item_time = item.text().split(' | ')[0]
Expand All @@ -257,7 +267,6 @@ def updateHistoryFigure(self, item):
sequence.rotations = rotations.copy()
sequence.dfovs = shifts.copy()
sequence.fovs = fovs.copy()
print("\nReference system fixed to image %s" % self.current_output)
except:
pass

Expand Down Expand Up @@ -326,20 +335,31 @@ def waitingForRun(self):
seq_name = self.pending_inputs[key][1][0]
sequence = copy.copy(defaultsequences[seq_name])

# Modify input parameters of the sequence
# Modify input parameters of the sequence according to current item
n = 0
for keyParam in sequence.mapKeys:
sequence.mapVals[keyParam] = self.pending_inputs[key][1][n]
n += 1

# Specific tasks for calibration
if "Calibration" in key:
if seq_name == 'Larmor':
sequence.mapVals['larmorFreq'] = hw.larmorFreq
try:
sequence.mapVals['shimming'] = defaultsequences['Shimming'].mapVals['shimming']
except:
pass
if seq_name == 'RabiFlops':
sequence.mapVals['shimming'] = defaultsequences['Shimming'].mapVals['shimming']

# Run the sequence
key_index = keys.index(key)
raw_data_name = key.split('|')[1].split(' ')[1]
output = self.runSequenceInlist(sequence=sequence, key=key, raw_data_name=raw_data_name)
if output == 0:
# There is an error
del self.pending_inputs[key]
print("\n" + key + " sequence finished abruptly with error.")
print("ERROR: " + key + " sequence finished abruptly with error.\n")
else:
# Add item to the history list
file_name = sequence.mapVals['fileName']
Expand All @@ -351,7 +371,7 @@ def waitingForRun(self):
# Delete outputs from the sequence
sequence.resetMapVals()
# self.main.sequence_list.updateSequence()
print("\n" + key + " ready!")
print("READY: " + key + "\n")
time.sleep(0.1)
# Enable acquire button
if self.main.toolbar_marcos.action_server.isChecked():
Expand Down Expand Up @@ -389,13 +409,21 @@ def runSequenceInlist(self, sequence=None, key=None, raw_data_name=""):
self.fovs[key] = sequence.fovs.copy()

# Create and execute selected sequence
if sequence.sequenceRun(0, self.main.demo):
pass
else:
try:
if sequence.sequenceRun(0, self.main.demo):
pass
else:
return 0
except Exception as e:
print(f"An error occurred in sequenceRun method: {e}")
return 0

# Do sequence analysis and get results
return sequence.sequenceAnalysis()
try:
return sequence.sequenceAnalysis()
except Exception as e:
print(f"An erro ocurred in sequenceAnalysis method: {e}")
return 0


class HistoryListControllerPos(HistoryListWidget):
Expand Down Expand Up @@ -535,7 +563,7 @@ def addFigure(self):
label = QLabel(self.labels[n])
label.setAlignment(QtCore.Qt.AlignCenter)
label.setStyleSheet("background-color: black;color: white")
self.main.image_view_widget.addWidget(label, row=2*(idx//4)+1, col=idx%4)
self.main.image_view_widget.addWidget(label, row=2 * (idx // 4) + 1, col=idx % 4)

# Figure
image2show, x_label, y_label, title = self.main.toolbar_image.fixImage(self.figures[n],
Expand All @@ -545,9 +573,9 @@ def addFigure(self):
x_label=x_label,
y_label=y_label,
title=title)
self.main.image_view_widget.addWidget(image, row=2*(idx//4)+2, col=idx%4)
self.main.image_view_widget.addWidget(image, row=2 * (idx // 4) + 2, col=idx % 4)

ncol = np.max([ncol, idx%4+1])
ncol = np.max([ncol, idx % 4 + 1])
self.main.image_view_widget.addWidget(sub_label, row=0, col=0, colspan=ncol)
except:
pass
Expand Down Expand Up @@ -575,7 +603,6 @@ def addNewItem(self, image_key=None, stamp=None, image=None, orientation=None, o
self.operations_hist[self.image_key] = operations
self.main.image_view_widget.image_key = self.image_key


# Update the space dictionary
self.space[self.image_key] = space

Expand All @@ -588,8 +615,6 @@ def updateHistoryFigure(self, item):
Args:
item (QListWidgetItem): The selected item in the history list.
"""
# Send printed text to the corresponding console
self.main.console.setup_console()

image_key = item.text()
if image_key in self.image_hist.keys():
Expand Down Expand Up @@ -650,8 +675,6 @@ def updateHistoryTable(self, item):
Args:
item (QListWidgetItem): The selected item in the history list.
"""
# Send printed text to the corresponding console
self.main.console.setup_console()

# Clear the methods_list table
self.main.methods_list.setText('')
Expand Down Expand Up @@ -724,7 +747,7 @@ def deleteSelectedItem(self):

if selected_item.text() in self.image_hist:
del self.image_hist[selected_item.text()]

if selected_item.text() in self.operations_hist:
del self.operations_hist[selected_item.text()]

Expand Down
Loading

0 comments on commit e65dd9f

Please sign in to comment.