mirror of
https://github.com/nqrduck/quackseq-simulator.git
synced 2025-01-02 18:08:07 +00:00
Updated to new setting access.
This commit is contained in:
parent
fe458ed59e
commit
014bf53efd
4 changed files with 108 additions and 150 deletions
|
@ -15,3 +15,7 @@ class Simulator(Spectrometer):
|
||||||
|
|
||||||
def set_averages(self, value: int):
|
def set_averages(self, value: int):
|
||||||
self.model.average = value
|
self.model.average = value
|
||||||
|
|
||||||
|
@property
|
||||||
|
def settings(self):
|
||||||
|
return self.model.settings
|
||||||
|
|
|
@ -48,7 +48,10 @@ class SimulatorController(SpectrometerController):
|
||||||
result = simulation.simulate()
|
result = simulation.simulate()
|
||||||
|
|
||||||
tdx = (
|
tdx = (
|
||||||
np.linspace(0, float(self.calculate_simulation_length(sequence)), len(result)) * 1e6
|
np.linspace(
|
||||||
|
0, float(self.calculate_simulation_length(sequence)), len(result)
|
||||||
|
)
|
||||||
|
* 1e6
|
||||||
)
|
)
|
||||||
|
|
||||||
rx_begin, rx_stop = self.translate_rx_event(sequence)
|
rx_begin, rx_stop = self.translate_rx_event(sequence)
|
||||||
|
@ -84,48 +87,18 @@ class SimulatorController(SpectrometerController):
|
||||||
sample_length = None
|
sample_length = None
|
||||||
sample_diameter = None
|
sample_diameter = None
|
||||||
|
|
||||||
for samplesetting in model.settings[self.model.SAMPLE]:
|
name = model.settings.sample_name
|
||||||
logger.debug("Sample setting: %s", samplesetting.name)
|
density = model.settings.density
|
||||||
|
molar_mass = model.settings.molar_mass
|
||||||
if samplesetting.name == model.NAME:
|
resonant_frequency = model.settings.resonant_frequency
|
||||||
name = samplesetting.value
|
gamma = model.settings.gamma
|
||||||
elif samplesetting.name == model.DENSITY:
|
nuclear_spin = model.settings.nuclear_spin
|
||||||
density = float(samplesetting.value)
|
spin_factor = model.settings.spin_factor
|
||||||
elif samplesetting.name == model.MOLAR_MASS:
|
powder_factor = model.settings.powder_factor
|
||||||
molar_mass = float(samplesetting.value)
|
filling_factor = model.settings.filling_factor
|
||||||
elif samplesetting.name == model.RESONANT_FREQUENCY:
|
T1 = model.settings.T1
|
||||||
resonant_frequency = float(samplesetting.value)
|
T2 = model.settings.T2
|
||||||
elif samplesetting.name == model.GAMMA:
|
T2_star = model.settings.T2_star
|
||||||
gamma = float(samplesetting.value)
|
|
||||||
elif samplesetting.name == model.NUCLEAR_SPIN:
|
|
||||||
nuclear_spin = float(samplesetting.value)
|
|
||||||
elif samplesetting.name == model.SPIN_FACTOR:
|
|
||||||
spin_factor = float(samplesetting.value)
|
|
||||||
elif samplesetting.name == model.POWDER_FACTOR:
|
|
||||||
powder_factor = float(samplesetting.value)
|
|
||||||
elif samplesetting.name == model.FILLING_FACTOR:
|
|
||||||
filling_factor = float(samplesetting.value)
|
|
||||||
elif samplesetting.name == model.T1:
|
|
||||||
T1 = float(samplesetting.value)
|
|
||||||
elif samplesetting.name == model.T2:
|
|
||||||
T2 = float(samplesetting.value)
|
|
||||||
elif samplesetting.name == model.T2_STAR:
|
|
||||||
T2_star = float(samplesetting.value)
|
|
||||||
elif samplesetting.name == model.ATOM_DENSITY:
|
|
||||||
atom_density = float(samplesetting.value)
|
|
||||||
elif samplesetting.name == model.SAMPLE_VOLUME:
|
|
||||||
sample_volume = float(samplesetting.value)
|
|
||||||
elif samplesetting.name == model.SAMPLE_LENGTH:
|
|
||||||
sample_length = float(samplesetting.value)
|
|
||||||
elif samplesetting.name == model.SAMPLE_DIAMETER:
|
|
||||||
sample_diameter = float(samplesetting.value)
|
|
||||||
else:
|
|
||||||
logger.warning("Unknown sample setting: %s", samplesetting.name)
|
|
||||||
self.module.nqrduck_signal.emit(
|
|
||||||
"notification",
|
|
||||||
["Error", "Unknown sample setting: " + samplesetting.name],
|
|
||||||
)
|
|
||||||
return None
|
|
||||||
|
|
||||||
sample = Sample(
|
sample = Sample(
|
||||||
name=name,
|
name=name,
|
||||||
|
@ -147,7 +120,9 @@ class SimulatorController(SpectrometerController):
|
||||||
)
|
)
|
||||||
return sample
|
return sample
|
||||||
|
|
||||||
def translate_pulse_sequence(self, sequence : QuackSequence, dwell_time: float) -> PulseArray:
|
def translate_pulse_sequence(
|
||||||
|
self, sequence: QuackSequence, dwell_time: float
|
||||||
|
) -> PulseArray:
|
||||||
"""This method translates the pulse sequence from the core to a PulseArray object needed for the simulation.
|
"""This method translates the pulse sequence from the core to a PulseArray object needed for the simulation.
|
||||||
|
|
||||||
Args:
|
Args:
|
||||||
|
@ -221,51 +196,39 @@ class SimulatorController(SpectrometerController):
|
||||||
simulation = Simulation(
|
simulation = Simulation(
|
||||||
sample=sample,
|
sample=sample,
|
||||||
pulse=pulse_array,
|
pulse=pulse_array,
|
||||||
number_isochromats=int(
|
number_isochromats=int(model.settings.number_isochromats),
|
||||||
model.get_setting_by_name(model.NUMBER_ISOCHROMATS).value
|
initial_magnetization=float(model.settings.initial_magnetization),
|
||||||
),
|
gradient=float(model.settings.gradient),
|
||||||
initial_magnetization=float(
|
noise=float(model.settings.noise),
|
||||||
model.get_setting_by_name(model.INITIAL_MAGNETIZATION).value
|
length_coil=float(model.settings.length_coil),
|
||||||
),
|
diameter_coil=float(model.settings.diameter_coil),
|
||||||
gradient=float(model.get_setting_by_name(model.GRADIENT).value),
|
number_turns=float(model.settings.number_turns),
|
||||||
noise=float(model.get_setting_by_name(model.NOISE).value),
|
q_factor_transmit=float(model.settings.q_factor_transmit),
|
||||||
length_coil=float(model.get_setting_by_name(model.LENGTH_COIL).value),
|
q_factor_receive=float(model.settings.q_factor_receive),
|
||||||
diameter_coil=float(model.get_setting_by_name(model.DIAMETER_COIL).value),
|
power_amplifier_power=float(model.settings.power_amplifier_power),
|
||||||
number_turns=float(model.get_setting_by_name(model.NUMBER_TURNS).value),
|
gain=float(model.settings.gain),
|
||||||
q_factor_transmit=float(
|
temperature=float(model.settings.temperature),
|
||||||
model.get_setting_by_name(model.Q_FACTOR_TRANSMIT).value
|
|
||||||
),
|
|
||||||
q_factor_receive=float(
|
|
||||||
model.get_setting_by_name(model.Q_FACTOR_RECEIVE).value
|
|
||||||
),
|
|
||||||
power_amplifier_power=float(
|
|
||||||
model.get_setting_by_name(model.POWER_AMPLIFIER_POWER).value
|
|
||||||
),
|
|
||||||
gain=float(model.get_setting_by_name(model.GAIN).value),
|
|
||||||
temperature=float(model.get_setting_by_name(model.TEMPERATURE).value),
|
|
||||||
averages=int(model.averages),
|
averages=int(model.averages),
|
||||||
loss_TX=float(model.get_setting_by_name(model.LOSS_TX).value),
|
loss_TX=float(model.settings.loss_tx),
|
||||||
loss_RX=float(model.get_setting_by_name(model.LOSS_RX).value),
|
loss_RX=float(model.settings.loss_rx),
|
||||||
conversion_factor=float(
|
conversion_factor=float(model.settings.conversion_factor),
|
||||||
model.get_setting_by_name(model.CONVERSION_FACTOR).value
|
|
||||||
),
|
|
||||||
)
|
)
|
||||||
return simulation
|
return simulation
|
||||||
|
|
||||||
def calculate_dwelltime(self, sequence : QuackSequence) -> float:
|
def calculate_dwelltime(self, sequence: QuackSequence) -> float:
|
||||||
"""This method calculates the dwell time based on the settings and the pulse sequence.
|
"""This method calculates the dwell time based on the settings and the pulse sequence.
|
||||||
|
|
||||||
Returns:
|
Returns:
|
||||||
float: The dwell time in seconds.
|
float: The dwell time in seconds.
|
||||||
"""
|
"""
|
||||||
n_points = int(
|
n_points = int(
|
||||||
self.model.get_setting_by_name(self.model.NUMBER_POINTS).value
|
self.model.get_setting_by_display_name(self.model.NUMBER_POINTS).value
|
||||||
)
|
)
|
||||||
simulation_length = self.calculate_simulation_length(sequence)
|
simulation_length = self.calculate_simulation_length(sequence)
|
||||||
dwell_time = simulation_length / n_points
|
dwell_time = simulation_length / n_points
|
||||||
return dwell_time
|
return dwell_time
|
||||||
|
|
||||||
def calculate_simulation_length(self, sequence : QuackSequence) -> float:
|
def calculate_simulation_length(self, sequence: QuackSequence) -> float:
|
||||||
"""This method calculates the simulation length based on the settings and the pulse sequence.
|
"""This method calculates the simulation length based on the settings and the pulse sequence.
|
||||||
|
|
||||||
Returns:
|
Returns:
|
||||||
|
@ -277,14 +240,14 @@ class SimulatorController(SpectrometerController):
|
||||||
simulation_length += event.duration
|
simulation_length += event.duration
|
||||||
return simulation_length
|
return simulation_length
|
||||||
|
|
||||||
def translate_rx_event(self, sequence : QuackSequence) -> tuple:
|
def translate_rx_event(self, sequence: QuackSequence) -> tuple:
|
||||||
"""This method translates the RX event of the pulse sequence to the limr object.
|
"""This method translates the RX event of the pulse sequence to the limr object.
|
||||||
|
|
||||||
Returns:
|
Returns:
|
||||||
tuple: A tuple containing the start and stop time of the RX event in µs
|
tuple: A tuple containing the start and stop time of the RX event in µs
|
||||||
"""
|
"""
|
||||||
# This is a correction factor for the RX event. The offset of the first pulse is 2.2µs longer than from the specified samples.
|
# This is a correction factor for the RX event. The offset of the first pulse is 2.2µs longer than from the specified samples.
|
||||||
events = sequence.events
|
events = sequence.events
|
||||||
|
|
||||||
previous_events_duration = 0
|
previous_events_duration = 0
|
||||||
# offset = 0
|
# offset = 0
|
||||||
|
@ -314,41 +277,3 @@ class SimulatorController(SpectrometerController):
|
||||||
|
|
||||||
else:
|
else:
|
||||||
return None, None
|
return None, None
|
||||||
|
|
||||||
def set_frequency(self, value: str) -> None:
|
|
||||||
"""This method is called when the set_frequency signal is received from the core.
|
|
||||||
|
|
||||||
For the simulator this just prints a warning that the simulator is selected.
|
|
||||||
|
|
||||||
Args:
|
|
||||||
value (str) : The new frequency in MHz.
|
|
||||||
"""
|
|
||||||
logger.debug("Setting frequency to: %s", value)
|
|
||||||
try:
|
|
||||||
self.module.model.target_frequency = float(value)
|
|
||||||
logger.debug("Successfully set frequency to: %s", value)
|
|
||||||
except ValueError:
|
|
||||||
logger.warning("Could not set frequency to: %s", value)
|
|
||||||
self.module.nqrduck_signal.emit(
|
|
||||||
"notification", ["Error", "Could not set frequency to: " + value]
|
|
||||||
)
|
|
||||||
self.module.nqrduck_signal.emit("failure_set_frequency", value)
|
|
||||||
|
|
||||||
def set_averages(self, value: str) -> None:
|
|
||||||
"""This method is called when the set_averages signal is received from the core.
|
|
||||||
|
|
||||||
It sets the averages in the model used for the simulation.
|
|
||||||
|
|
||||||
Args:
|
|
||||||
value (str): The value to set the averages to.
|
|
||||||
"""
|
|
||||||
logger.debug("Setting averages to: %s", value)
|
|
||||||
try:
|
|
||||||
self.module.model.averages = int(value)
|
|
||||||
logger.debug("Successfully set averages to: %s", value)
|
|
||||||
except ValueError:
|
|
||||||
logger.warning("Could not set averages to: %s", value)
|
|
||||||
self.module.nqrduck_signal.emit(
|
|
||||||
"notification", ["Error", "Could not set averages to: " + value]
|
|
||||||
)
|
|
||||||
self.module.nqrduck_signal.emit("failure_set_averages", value)
|
|
||||||
|
|
|
@ -2,7 +2,11 @@
|
||||||
|
|
||||||
import logging
|
import logging
|
||||||
from quackseq.spectrometer.spectrometer_model import SpectrometerModel
|
from quackseq.spectrometer.spectrometer_model import SpectrometerModel
|
||||||
from quackseq.spectrometer.spectrometer_settings import IntSetting, FloatSetting, StringSetting
|
from quackseq.spectrometer.spectrometer_settings import (
|
||||||
|
IntSetting,
|
||||||
|
FloatSetting,
|
||||||
|
StringSetting,
|
||||||
|
)
|
||||||
from quackseq.pulseparameters import TXPulse, RXReadout
|
from quackseq.pulseparameters import TXPulse, RXReadout
|
||||||
|
|
||||||
logger = logging.getLogger(__name__)
|
logger = logging.getLogger(__name__)
|
||||||
|
@ -33,7 +37,7 @@ class SimulatorModel(SpectrometerModel):
|
||||||
CONVERSION_FACTOR = "Conversion factor"
|
CONVERSION_FACTOR = "Conversion factor"
|
||||||
|
|
||||||
# Sample settings, this will be done in a separate module later on
|
# Sample settings, this will be done in a separate module later on
|
||||||
NAME = "Name"
|
SAMPLE_NAME = "Name"
|
||||||
DENSITY = "Density (g/cm^3)"
|
DENSITY = "Density (g/cm^3)"
|
||||||
MOLAR_MASS = "Molar mass (g/mol)"
|
MOLAR_MASS = "Molar mass (g/mol)"
|
||||||
RESONANT_FREQUENCY = "Resonant freq. (Hz)"
|
RESONANT_FREQUENCY = "Resonant freq. (Hz)"
|
||||||
|
@ -63,241 +67,264 @@ class SimulatorModel(SpectrometerModel):
|
||||||
# Simulation settings
|
# Simulation settings
|
||||||
number_of_points_setting = IntSetting(
|
number_of_points_setting = IntSetting(
|
||||||
self.NUMBER_POINTS,
|
self.NUMBER_POINTS,
|
||||||
|
self.SIMULATION,
|
||||||
8192,
|
8192,
|
||||||
"Number of points used for the simulation. This influences the dwell time in combination with the total event simulation given by the pulse sequence.",
|
"Number of points used for the simulation. This influences the dwell time in combination with the total event simulation given by the pulse sequence.",
|
||||||
min_value=0,
|
min_value=0,
|
||||||
)
|
)
|
||||||
self.add_setting(
|
self.add_setting(
|
||||||
|
"number_points",
|
||||||
number_of_points_setting,
|
number_of_points_setting,
|
||||||
self.SIMULATION,
|
|
||||||
)
|
)
|
||||||
|
|
||||||
number_of_isochromats_setting = IntSetting(
|
number_of_isochromats_setting = IntSetting(
|
||||||
self.NUMBER_ISOCHROMATS,
|
self.NUMBER_ISOCHROMATS,
|
||||||
|
self.SIMULATION,
|
||||||
1000,
|
1000,
|
||||||
"Number of isochromats used for the simulation. This influences the computation time.",
|
"Number of isochromats used for the simulation. This influences the computation time.",
|
||||||
min_value=0,
|
min_value=0,
|
||||||
max_value=10000,
|
max_value=10000,
|
||||||
)
|
)
|
||||||
self.add_setting(number_of_isochromats_setting, self.SIMULATION)
|
self.add_setting("number_isochromats", number_of_isochromats_setting)
|
||||||
|
|
||||||
initial_magnetization_setting = FloatSetting(
|
initial_magnetization_setting = FloatSetting(
|
||||||
self.INITIAL_MAGNETIZATION,
|
self.INITIAL_MAGNETIZATION,
|
||||||
|
self.SIMULATION,
|
||||||
1,
|
1,
|
||||||
"Initial magnetization",
|
"Initial magnetization",
|
||||||
min_value=0,
|
min_value=0,
|
||||||
)
|
)
|
||||||
self.add_setting(initial_magnetization_setting, self.SIMULATION)
|
self.add_setting("initial_magnetization", initial_magnetization_setting)
|
||||||
|
|
||||||
# This doesn't really do anything yet
|
|
||||||
gradient_setting = FloatSetting(
|
gradient_setting = FloatSetting(
|
||||||
self.GRADIENT,
|
self.GRADIENT,
|
||||||
|
self.SIMULATION,
|
||||||
1,
|
1,
|
||||||
"Gradient",
|
"Gradient",
|
||||||
)
|
)
|
||||||
self.add_setting(gradient_setting, self.SIMULATION)
|
self.add_setting("gradient", gradient_setting)
|
||||||
|
|
||||||
noise_setting = FloatSetting(
|
noise_setting = FloatSetting(
|
||||||
self.NOISE,
|
self.NOISE,
|
||||||
|
self.SIMULATION,
|
||||||
2,
|
2,
|
||||||
"Adds a specified level of random noise to the simulation to mimic real-world signal variations.",
|
"Adds a specified level of random noise to the simulation to mimic real-world signal variations.",
|
||||||
min_value=0,
|
min_value=0,
|
||||||
max_value=100,
|
max_value=100,
|
||||||
)
|
)
|
||||||
self.add_setting(noise_setting, self.SIMULATION)
|
self.add_setting("noise", noise_setting)
|
||||||
|
|
||||||
# Hardware settings
|
# Hardware settings
|
||||||
coil_length_setting = FloatSetting(
|
coil_length_setting = FloatSetting(
|
||||||
self.LENGTH_COIL,
|
self.LENGTH_COIL,
|
||||||
|
self.HARDWARE,
|
||||||
30e-3,
|
30e-3,
|
||||||
"The length of the sample coil within the hardware setup.",
|
"The length of the sample coil within the hardware setup.",
|
||||||
min_value=1e-3,
|
min_value=1e-3,
|
||||||
)
|
)
|
||||||
self.add_setting(coil_length_setting, self.HARDWARE)
|
self.add_setting("length_coil", coil_length_setting)
|
||||||
|
|
||||||
coil_diameter_setting = FloatSetting(
|
coil_diameter_setting = FloatSetting(
|
||||||
self.DIAMETER_COIL,
|
self.DIAMETER_COIL,
|
||||||
|
self.HARDWARE,
|
||||||
8e-3,
|
8e-3,
|
||||||
"The diameter of the sample coil.",
|
"The diameter of the sample coil.",
|
||||||
min_value=1e-3,
|
min_value=1e-3,
|
||||||
)
|
)
|
||||||
self.add_setting(coil_diameter_setting, self.HARDWARE)
|
self.add_setting("diameter_coil", coil_diameter_setting)
|
||||||
|
|
||||||
number_turns_setting = FloatSetting(
|
number_turns_setting = FloatSetting(
|
||||||
self.NUMBER_TURNS,
|
self.NUMBER_TURNS,
|
||||||
|
self.HARDWARE,
|
||||||
8,
|
8,
|
||||||
"The total number of turns of the sample coil.",
|
"The total number of turns of the sample coil.",
|
||||||
min_value=1,
|
min_value=1,
|
||||||
)
|
)
|
||||||
self.add_setting(number_turns_setting, self.HARDWARE)
|
self.add_setting("number_turns", number_turns_setting)
|
||||||
|
|
||||||
q_factor_transmit_setting = FloatSetting(
|
q_factor_transmit_setting = FloatSetting(
|
||||||
self.Q_FACTOR_TRANSMIT,
|
self.Q_FACTOR_TRANSMIT,
|
||||||
|
self.HARDWARE,
|
||||||
80,
|
80,
|
||||||
"The quality factor of the transmit path, which has an effect on the field strength for excitation.",
|
"The quality factor of the transmit path, which has an effect on the field strength for excitation.",
|
||||||
min_value=1,
|
min_value=1,
|
||||||
)
|
)
|
||||||
self.add_setting(q_factor_transmit_setting, self.HARDWARE)
|
self.add_setting("q_factor_transmit", q_factor_transmit_setting)
|
||||||
|
|
||||||
q_factor_receive_setting = FloatSetting(
|
q_factor_receive_setting = FloatSetting(
|
||||||
self.Q_FACTOR_RECEIVE,
|
self.Q_FACTOR_RECEIVE,
|
||||||
|
self.HARDWARE,
|
||||||
80,
|
80,
|
||||||
"The quality factor of the receive path, which has an effect on the final SNR.",
|
"The quality factor of the receive path, which has an effect on the final SNR.",
|
||||||
min_value=1,
|
min_value=1,
|
||||||
)
|
)
|
||||||
self.add_setting(q_factor_receive_setting, self.HARDWARE)
|
self.add_setting("q_factor_receive", q_factor_receive_setting)
|
||||||
|
|
||||||
power_amplifier_power_setting = FloatSetting(
|
power_amplifier_power_setting = FloatSetting(
|
||||||
self.POWER_AMPLIFIER_POWER,
|
self.POWER_AMPLIFIER_POWER,
|
||||||
|
self.HARDWARE,
|
||||||
110,
|
110,
|
||||||
"The power output capability of the power amplifier, determines the strength of pulses that can be generated.",
|
"The power output capability of the power amplifier, determines the strength of pulses that can be generated.",
|
||||||
min_value=0.1,
|
min_value=0.1,
|
||||||
)
|
)
|
||||||
self.add_setting(power_amplifier_power_setting, self.HARDWARE)
|
self.add_setting("power_amplifier_power", power_amplifier_power_setting)
|
||||||
|
|
||||||
gain_setting = FloatSetting(
|
gain_setting = FloatSetting(
|
||||||
self.GAIN,
|
self.GAIN,
|
||||||
|
self.HARDWARE,
|
||||||
6000,
|
6000,
|
||||||
"The amplification factor of the receiver chain, impacting the final measured signal amplitude.",
|
"The amplification factor of the receiver chain, impacting the final measured signal amplitude.",
|
||||||
min_value=0.1,
|
min_value=0.1,
|
||||||
)
|
)
|
||||||
self.add_setting(gain_setting, self.HARDWARE)
|
self.add_setting("gain", gain_setting)
|
||||||
|
|
||||||
temperature_setting = FloatSetting(
|
temperature_setting = FloatSetting(
|
||||||
self.TEMPERATURE,
|
self.TEMPERATURE,
|
||||||
|
self.EXPERIMENTAL_Setup,
|
||||||
300,
|
300,
|
||||||
"The absolute temperature during the experiment. This influences the SNR of the measurement.",
|
"The absolute temperature during the experiment. This influences the SNR of the measurement.",
|
||||||
min_value=0.1,
|
min_value=0.1,
|
||||||
max_value=400,
|
max_value=400,
|
||||||
)
|
)
|
||||||
self.add_setting(temperature_setting, self.EXPERIMENTAL_Setup)
|
self.add_setting("temperature", temperature_setting)
|
||||||
|
|
||||||
loss_tx_setting = FloatSetting(
|
loss_tx_setting = FloatSetting(
|
||||||
self.LOSS_TX,
|
self.LOSS_TX,
|
||||||
|
self.EXPERIMENTAL_Setup,
|
||||||
25,
|
25,
|
||||||
"The signal loss occurring in the transmission path, affecting the effective RF pulse power.",
|
"The signal loss occurring in the transmission path, affecting the effective RF pulse power.",
|
||||||
min_value=0.1,
|
min_value=0.1,
|
||||||
max_value=60,
|
max_value=60,
|
||||||
)
|
)
|
||||||
self.add_setting(loss_tx_setting, self.EXPERIMENTAL_Setup)
|
self.add_setting("loss_tx", loss_tx_setting)
|
||||||
|
|
||||||
loss_rx_setting = FloatSetting(
|
loss_rx_setting = FloatSetting(
|
||||||
self.LOSS_RX,
|
self.LOSS_RX,
|
||||||
|
self.EXPERIMENTAL_Setup,
|
||||||
25,
|
25,
|
||||||
"The signal loss in the reception path, which can reduce the signal that is ultimately detected.",
|
"The signal loss in the reception path, which can reduce the signal that is ultimately detected.",
|
||||||
min_value=0.1,
|
min_value=0.1,
|
||||||
max_value=60,
|
max_value=60,
|
||||||
)
|
)
|
||||||
self.add_setting(loss_rx_setting, self.EXPERIMENTAL_Setup)
|
self.add_setting("loss_rx", loss_rx_setting)
|
||||||
|
|
||||||
conversion_factor_setting = FloatSetting(
|
conversion_factor_setting = FloatSetting(
|
||||||
self.CONVERSION_FACTOR,
|
self.CONVERSION_FACTOR,
|
||||||
|
self.EXPERIMENTAL_Setup,
|
||||||
2884,
|
2884,
|
||||||
"Conversion factor (spectrometer units / V)",
|
"Conversion factor (spectrometer units / V)",
|
||||||
)
|
)
|
||||||
self.add_setting(
|
self.add_setting("conversion_factor", conversion_factor_setting) # Conversion factor for the LimeSDR based spectrometer
|
||||||
conversion_factor_setting,
|
|
||||||
self.EXPERIMENTAL_Setup,
|
|
||||||
) # Conversion factor for the LimeSDR based spectrometer
|
|
||||||
|
|
||||||
# Sample settings
|
# Sample settings
|
||||||
sample_name_setting = StringSetting(
|
sample_name_setting = StringSetting(
|
||||||
self.NAME,
|
self.SAMPLE_NAME,
|
||||||
|
self.SAMPLE,
|
||||||
"BiPh3",
|
"BiPh3",
|
||||||
"The name of the sample.",
|
"The name of the sample.",
|
||||||
)
|
)
|
||||||
self.add_setting(sample_name_setting, self.SAMPLE)
|
self.add_setting("sample_name", sample_name_setting)
|
||||||
|
|
||||||
density_setting = FloatSetting(
|
density_setting = FloatSetting(
|
||||||
self.DENSITY,
|
self.DENSITY,
|
||||||
|
self.SAMPLE,
|
||||||
1.585e6,
|
1.585e6,
|
||||||
"The density of the sample. This is used to calculate the number of spins in the sample volume.",
|
"The density of the sample. This is used to calculate the number of spins in the sample volume.",
|
||||||
min_value=0.1,
|
min_value=0.1,
|
||||||
)
|
)
|
||||||
self.add_setting(density_setting, self.SAMPLE)
|
self.add_setting("density", density_setting)
|
||||||
|
|
||||||
molar_mass_setting = FloatSetting(
|
molar_mass_setting = FloatSetting(
|
||||||
self.MOLAR_MASS,
|
self.MOLAR_MASS,
|
||||||
|
self.SAMPLE,
|
||||||
440.3,
|
440.3,
|
||||||
"The molar mass of the sample. This is used to calculate the number of spins in the sample volume.",
|
"The molar mass of the sample. This is used to calculate the number of spins in the sample volume.",
|
||||||
min_value=0.1,
|
min_value=0.1,
|
||||||
)
|
)
|
||||||
self.add_setting(molar_mass_setting, self.SAMPLE)
|
self.add_setting("molar_mass", molar_mass_setting)
|
||||||
|
|
||||||
resonant_frequency_setting = FloatSetting(
|
resonant_frequency_setting = FloatSetting(
|
||||||
self.RESONANT_FREQUENCY,
|
self.RESONANT_FREQUENCY,
|
||||||
|
self.SAMPLE,
|
||||||
83.56e6,
|
83.56e6,
|
||||||
"The resonant frequency of the observed transition.",
|
"The resonant frequency of the observed transition.",
|
||||||
min_value=1e5,
|
min_value=1e5,
|
||||||
)
|
)
|
||||||
self.add_setting(resonant_frequency_setting, self.SAMPLE)
|
self.add_setting("resonant_frequency", resonant_frequency_setting)
|
||||||
|
|
||||||
gamma_setting = FloatSetting(
|
gamma_setting = FloatSetting(
|
||||||
self.GAMMA,
|
self.GAMMA,
|
||||||
|
self.SAMPLE,
|
||||||
4.342e7,
|
4.342e7,
|
||||||
"The gyromagnetic ratio of the sample’s nuclei.",
|
"The gyromagnetic ratio of the sample’s nuclei.",
|
||||||
min_value=0,
|
min_value=0,
|
||||||
)
|
)
|
||||||
self.add_setting(gamma_setting, self.SAMPLE)
|
self.add_setting("gamma", gamma_setting)
|
||||||
|
|
||||||
# This could be updated to a selection setting
|
|
||||||
nuclear_spin_setting = FloatSetting(
|
nuclear_spin_setting = FloatSetting(
|
||||||
self.NUCLEAR_SPIN,
|
self.NUCLEAR_SPIN,
|
||||||
|
self.SAMPLE,
|
||||||
9 / 2,
|
9 / 2,
|
||||||
"The nuclear spin of the sample’s nuclei.",
|
"The nuclear spin of the sample’s nuclei.",
|
||||||
min_value=0,
|
min_value=0,
|
||||||
)
|
)
|
||||||
self.add_setting(nuclear_spin_setting, self.SAMPLE)
|
self.add_setting("nuclear_spin", nuclear_spin_setting)
|
||||||
|
|
||||||
spin_factor_setting = FloatSetting(
|
spin_factor_setting = FloatSetting(
|
||||||
self.SPIN_FACTOR,
|
self.SPIN_FACTOR,
|
||||||
|
self.SAMPLE,
|
||||||
2,
|
2,
|
||||||
"The spin factor represents the scaling coefficient for observable nuclear spin transitions along the x-axis, derived from the Pauli I x 0 -matrix elements.",
|
"The spin factor represents the scaling coefficient for observable nuclear spin transitions along the x-axis, derived from the Pauli I x 0 -matrix elements.",
|
||||||
min_value=0,
|
min_value=0,
|
||||||
)
|
)
|
||||||
self.add_setting(spin_factor_setting, self.SAMPLE)
|
self.add_setting("spin_factor", spin_factor_setting)
|
||||||
|
|
||||||
powder_factor_setting = FloatSetting(
|
powder_factor_setting = FloatSetting(
|
||||||
self.POWDER_FACTOR,
|
self.POWDER_FACTOR,
|
||||||
|
self.SAMPLE,
|
||||||
0.75,
|
0.75,
|
||||||
"A factor representing the crystallinity of the solid sample. A value of 0.75 corresponds to a powder sample.",
|
"A factor representing the crystallinity of the solid sample. A value of 0.75 corresponds to a powder sample.",
|
||||||
min_value=0,
|
min_value=0,
|
||||||
max_value=1,
|
max_value=1,
|
||||||
)
|
)
|
||||||
self.add_setting(powder_factor_setting, self.SAMPLE)
|
self.add_setting("powder_factor", powder_factor_setting)
|
||||||
|
|
||||||
filling_factor_setting = FloatSetting(
|
filling_factor_setting = FloatSetting(
|
||||||
self.FILLING_FACTOR,
|
self.FILLING_FACTOR,
|
||||||
|
self.SAMPLE,
|
||||||
0.7,
|
0.7,
|
||||||
"The ratio of the sample volume that occupies the coil’s sensitive volume.",
|
"The ratio of the sample volume that occupies the coil’s sensitive volume.",
|
||||||
min_value=0,
|
min_value=0,
|
||||||
max_value=1,
|
max_value=1,
|
||||||
)
|
)
|
||||||
self.add_setting(filling_factor_setting, self.SAMPLE)
|
self.add_setting("filling_factor", filling_factor_setting)
|
||||||
|
|
||||||
t1_setting = FloatSetting(
|
t1_setting = FloatSetting(
|
||||||
self.T1,
|
self.T1,
|
||||||
|
self.SAMPLE,
|
||||||
83.5e-5,
|
83.5e-5,
|
||||||
"The longitudinal or spin-lattice relaxation time of the sample, influencing signal recovery between pulses.",
|
"The longitudinal or spin-lattice relaxation time of the sample, influencing signal recovery between pulses.",
|
||||||
min_value=1e-6,
|
min_value=1e-6,
|
||||||
)
|
)
|
||||||
self.add_setting(t1_setting, self.SAMPLE)
|
self.add_setting("T1", t1_setting)
|
||||||
|
|
||||||
t2_setting = FloatSetting(
|
t2_setting = FloatSetting(
|
||||||
self.T2,
|
self.T2,
|
||||||
|
self.SAMPLE,
|
||||||
396e-6,
|
396e-6,
|
||||||
"The transverse or spin-spin relaxation time, determining the rate at which spins dephase and the signal decays in the xy plane",
|
"The transverse or spin-spin relaxation time, determining the rate at which spins dephase and the signal decays in the xy plane",
|
||||||
min_value=1e-6,
|
min_value=1e-6,
|
||||||
)
|
)
|
||||||
self.add_setting(t2_setting, self.SAMPLE)
|
self.add_setting("T2", t2_setting)
|
||||||
|
|
||||||
t2_star_setting = FloatSetting(
|
t2_star_setting = FloatSetting(
|
||||||
self.T2_STAR,
|
self.T2_STAR,
|
||||||
|
self.SAMPLE,
|
||||||
50e-6,
|
50e-6,
|
||||||
"The effective transverse relaxation time, incorporating effects of EFG inhomogeneities and other dephasing factors.",
|
"The effective transverse relaxation time, incorporating effects of EFG inhomogeneities and other dephasing factors.",
|
||||||
min_value=1e-6,
|
min_value=1e-6,
|
||||||
)
|
)
|
||||||
self.add_setting(t2_star_setting, self.SAMPLE)
|
self.add_setting("T2_star", t2_star_setting)
|
||||||
|
|
||||||
self.averages = 1
|
self.averages = 1
|
||||||
self.target_frequency = 100e6
|
self.target_frequency = 100e6
|
||||||
|
|
|
@ -24,6 +24,8 @@ class TestQuackSequence(unittest.TestCase):
|
||||||
sim = Simulator()
|
sim = Simulator()
|
||||||
sim.set_averages(100)
|
sim.set_averages(100)
|
||||||
|
|
||||||
|
sim.settings.noise = 0
|
||||||
|
|
||||||
result = sim.run_sequence(seq)
|
result = sim.run_sequence(seq)
|
||||||
self.assertIsNotNone(result)
|
self.assertIsNotNone(result)
|
||||||
self.assertTrue(hasattr(result, "tdx"))
|
self.assertTrue(hasattr(result, "tdx"))
|
||||||
|
|
Loading…
Reference in a new issue