1
0
Fork 0
mirror of https://github.com/gwm17/spspy.git synced 2024-11-26 20:18:50 -05:00

Compare commits

..

2 Commits

3 changed files with 23 additions and 19 deletions

View File

@ -89,7 +89,6 @@ class Reaction:
beamRxnEnergy = self.params.beamEnergy - self.targetMaterial.get_incoming_energyloss(self.params.projectile.Z, self.params.projectile.mass, self.params.beamEnergy, self.rxnLayer, 0.0) beamRxnEnergy = self.params.beamEnergy - self.targetMaterial.get_incoming_energyloss(self.params.projectile.Z, self.params.projectile.mass, self.params.beamEnergy, self.rxnLayer, 0.0)
beamRxnP = sqrt(beamRxnEnergy * (beamRxnEnergy + 2.0 * self.params.projectile.mass)) beamRxnP = sqrt(beamRxnEnergy * (beamRxnEnergy + 2.0 * self.params.projectile.mass))
residRxnEnergy = beamRxnEnergy + self.params.projectile.mass + self.params.target.mass - ejectileRxnEnergy - self.params.ejectile.mass residRxnEnergy = beamRxnEnergy + self.params.projectile.mass + self.params.target.mass - ejectileRxnEnergy - self.params.ejectile.mass
residRxnP2 = beamRxnP**2.0 + ejectileRxnP**2.0 - 2.0 * ejectileRxnP * beamRxnP * cos(self.params.spsAngle) residRxnP2 = beamRxnP**2.0 + ejectileRxnP**2.0 - 2.0 * ejectileRxnP * beamRxnP * cos(self.params.spsAngle)
return sqrt(residRxnEnergy**2.0 - residRxnP2) - self.residual.mass return sqrt(residRxnEnergy**2.0 - residRxnP2) - self.residual.mass

View File

@ -43,10 +43,10 @@ def get_reverse_energyloss(projectile: catima.Projectile, material: catima.Mater
e_step = catima.dedx(projectile, material)*x_step e_step = catima.dedx(projectile, material)*x_step
e_initial += e_step*A_recip e_initial += e_step*A_recip
projectile.T(e_initial) projectile.T(e_initial)
return (e_initial - e_out)*projectile.A() return (e_initial - e_out)
elif depth == ADAPTIVE_DEPTH_MAX: elif depth == ADAPTIVE_DEPTH_MAX:
return e_out*projectile.A() return e_out
else: else:
e_step = catima.dedx(projectile, material)*x_step e_step = catima.dedx(projectile, material)*x_step
e_initial += e_step*A_recip e_initial += e_step*A_recip
@ -80,10 +80,10 @@ def get_energyloss(projectile: catima.Projectile, material: catima.Material) ->
e_step = catima.dedx(projectile, material)*x_step*A_recip e_step = catima.dedx(projectile, material)*x_step*A_recip
e_final -= e_step e_final -= e_step
projectile.T(e_final) projectile.T(e_final)
return (e_in - e_final)*projectile.A() return (e_in - e_final)
elif depth == ADAPTIVE_DEPTH_MAX: elif depth == ADAPTIVE_DEPTH_MAX:
return e_in*projectile.A() return e_in
else: else:
e_step = catima.dedx(projectile, material)*x_step*A_recip e_step = catima.dedx(projectile, material)*x_step*A_recip
@ -94,6 +94,7 @@ def get_energyloss(projectile: catima.Projectile, material: catima.Material) ->
class SPSTarget: class SPSTarget:
MEV2U: float = 1.0/931.493614838475
UG2G: float = 1.0e-6 #convert ug to g UG2G: float = 1.0e-6 #convert ug to g
def __init__(self, layers: list[TargetLayer], name: str = "default"): def __init__(self, layers: list[TargetLayer], name: str = "default"):
self.layer_details = layers self.layer_details = layers
@ -114,31 +115,33 @@ class SPSTarget:
if angle == pi*0.5: if angle == pi*0.5:
return e_initial return e_initial
projectile = catima.Projectile(ap, zp) ap_u = ap * self.MEV2U
e_current = e_initial/ap projectile = catima.Projectile(ap_u, zp)
e_current = e_initial/ap_u
for (idx, layer) in enumerate(self.layer_details): for (idx, layer) in enumerate(self.layer_details):
material = catima.Material([(global_nuclear_data.get_data(z, a).mass, z, float(s)) for (z, a, s) in layer.compound_list]) material = catima.Material([(global_nuclear_data.get_data(z, a).mass * self.MEV2U, z, float(s)) for (z, a, s) in layer.compound_list])
projectile.T(e_current) #catima wants MeV/u projectile.T(e_current) #catima wants MeV/u
if idx == rxn_layer: if idx == rxn_layer:
material.thickness(self.layer_details[idx].thickness * self.UG2G / (2.0 * abs(cos(angle)))) material.thickness(self.layer_details[idx].thickness * self.UG2G / (2.0 * abs(cos(angle))))
e_current -= get_energyloss(projectile, material) e_current -= get_energyloss(projectile, material)
return e_initial - e_current*ap return e_initial - e_current*ap_u
else: else:
material.thickness(self.layer_details[idx].thickness * self.UG2G / abs(cos(angle))) material.thickness(self.layer_details[idx].thickness * self.UG2G / abs(cos(angle)))
e_current -= get_energyloss(projectile, material) e_current -= get_energyloss(projectile, material)
return e_initial - e_current*ap return e_initial - e_current*ap_u
#Calculate energy loss for a particle leaving the target, from rxn layer (halfway through rxn layer) to end #Calculate energy loss for a particle leaving the target, from rxn layer (halfway through rxn layer) to end
def get_outgoing_energyloss(self, zp: int, ap: float, e_initial: float, rxn_layer: int, angle: float) -> float: def get_outgoing_energyloss(self, zp: int, ap: float, e_initial: float, rxn_layer: int, angle: float) -> float:
if angle == pi*0.5: if angle == pi*0.5:
return e_initial return e_initial
projectile = catima.Projectile(ap, zp) ap_u = ap * self.MEV2U
e_current = e_initial/ap projectile = catima.Projectile(ap_u, zp)
e_current = e_initial/ap_u
for (idx, layer) in enumerate(self.layer_details[rxn_layer:], start=rxn_layer): for (idx, layer) in enumerate(self.layer_details[rxn_layer:], start=rxn_layer):
material = catima.Material([(global_nuclear_data.get_data(z, a).mass, z, float(s)) for (z, a, s) in layer.compound_list]) material = catima.Material([(global_nuclear_data.get_data(z, a).mass * self.MEV2U, z, float(s)) for (z, a, s) in layer.compound_list])
projectile.T(e_current) #catima wants MeV/u projectile.T(e_current) #catima wants MeV/u
if idx == rxn_layer: if idx == rxn_layer:
material.thickness(self.layer_details[idx].thickness * self.UG2G / (2.0 * abs(cos(angle)))) material.thickness(self.layer_details[idx].thickness * self.UG2G / (2.0 * abs(cos(angle))))
@ -146,19 +149,20 @@ class SPSTarget:
material.thickness(self.layer_details[idx].thickness * self.UG2G / abs(cos(angle))) material.thickness(self.layer_details[idx].thickness * self.UG2G / abs(cos(angle)))
e_current -= get_energyloss(projectile, material) e_current -= get_energyloss(projectile, material)
return e_initial - e_current*ap return e_initial - e_current*ap_u
#Calculate reverse energy loss (energy gain) for a particle that left the target after a reaction (end -> rxn_layer) #Calculate reverse energy loss (energy gain) for a particle that left the target after a reaction (end -> rxn_layer)
def get_outgoing_reverse_energyloss(self, zp: int, ap: float, e_final: float, rxn_layer: int, angle: float) -> float: def get_outgoing_reverse_energyloss(self, zp: int, ap: float, e_final: float, rxn_layer: int, angle: float) -> float:
if angle == pi*0.5: if angle == pi*0.5:
return 0.0 return 0.0
projectile = catima.Projectile(ap, zp) ap_u = ap * self.MEV2U
e_current = e_final/ap projectile = catima.Projectile(ap_u, zp)
e_current = e_final/ap_u
sublist = self.layer_details[rxn_layer:] #only care about rxn_layer -> exit sublist = self.layer_details[rxn_layer:] #only care about rxn_layer -> exit
reveresedRxnLayer = len(sublist) -1 #when reversed rxn_layer is the last layer reveresedRxnLayer = len(sublist) -1 #when reversed rxn_layer is the last layer
for (idx, layer) in reversed(list(enumerate(sublist))): for (idx, layer) in reversed(list(enumerate(sublist))):
material = catima.Material([(global_nuclear_data.get_data(z, a).mass, z, float(s)) for (z, a, s) in layer.compound_list]) material = catima.Material([(global_nuclear_data.get_data(z, a).mass * self.MEV2U, z, float(s)) for (z, a, s) in layer.compound_list])
projectile.T(e_current) #catima wants MeV/u projectile.T(e_current) #catima wants MeV/u
if idx == reveresedRxnLayer: if idx == reveresedRxnLayer:
material.thickness(self.layer_details[idx].thickness * self.UG2G / (2.0 * abs(cos(angle)))) material.thickness(self.layer_details[idx].thickness * self.UG2G / (2.0 * abs(cos(angle))))
@ -166,5 +170,5 @@ class SPSTarget:
material.thickness(self.layer_details[idx].thickness * self.UG2G / abs(cos(angle))) material.thickness(self.layer_details[idx].thickness * self.UG2G / abs(cos(angle)))
e_current += get_reverse_energyloss(projectile, material) e_current += get_reverse_energyloss(projectile, material)
return e_current*ap - e_final return e_current*ap_u - e_final

View File

@ -5,6 +5,7 @@ from PySide6.QtWidgets import QVBoxLayout, QFormLayout, QGroupBox
from PySide6.QtWidgets import QSpinBox, QDoubleSpinBox, QComboBox from PySide6.QtWidgets import QSpinBox, QDoubleSpinBox, QComboBox
from PySide6.QtWidgets import QDialog, QDialogButtonBox from PySide6.QtWidgets import QDialog, QDialogButtonBox
from PySide6.QtCore import Signal from PySide6.QtCore import Signal
from numpy import rad2deg
MAXIMUM_NUCLEAR_Z: int = 110 MAXIMUM_NUCLEAR_Z: int = 110
MAXIMUM_NUCLEAR_A: int = 270 MAXIMUM_NUCLEAR_A: int = 270
@ -116,6 +117,6 @@ class ReactionDialog(QDialog):
self.aeInput.setValue(rxn.params.ejectile.A) self.aeInput.setValue(rxn.params.ejectile.A)
self.aeInput.setEnabled(False) self.aeInput.setEnabled(False)
self.bkeInput.setValue(rxn.params.beamEnergy) self.bkeInput.setValue(rxn.params.beamEnergy)
self.thetaInput.setValue(rxn.params.spsAngle) self.thetaInput.setValue(rad2deg(rxn.params.spsAngle))
self.bfieldInput.setValue(rxn.params.magneticField) self.bfieldInput.setValue(rxn.params.magneticField)