JAPAn
Just Another Parity Analyzer
Loading...
Searching...
No Matches
VQwBPM.cc
Go to the documentation of this file.
1/*!
2 * \file VQwBPM.cc
3 * \brief Virtual base class implementation for beam position monitors
4 *
5 * Base helper implementations for BPMs (beam position monitors). Contains
6 * small utility methods shared by concrete BPM types plus factory helpers.
7 * Documentation-only edits; runtime behavior unchanged.
8 */
9
10#include "VQwBPM.h"
11
12// System headers
13#include <stdexcept>
14
15// Qweak headers
16#include "QwLog.h"
17#include "QwBPMStripline.h"
18#include "QwLinearDiodeArray.h"
19#include "QwCombinedBPM.h"
20#include "QwVQWK_Channel.h"
21#include "QwScaler_Channel.h"
22#include "QwMollerADC_Channel.h"
23
24
25/* With X being vertical up and Z being the beam direction toward the beamdump */
26const TString VQwBPM::kAxisLabel[2]={"X","Y"};
27
28
29/*!
30 * \brief Initialize common BPM state and set the element name.
31 * \param name Element name to assign to this BPM.
32 *
33 * Initializes position center array to zero and sets the element name.
34 * This is the base initialization common to all BPM types.
35 */
36void VQwBPM::InitializeChannel(TString name)
37{
38 Short_t i = 0;
39
40 for(i=0;i<3;i++) fPositionCenter[i] = 0.0;
41
42 SetElementName(name);
43
44 return;
45}
46
47/*!
48 * \brief Store geometry/survey offsets for absolute position calibration.
49 * \param Xoffset X-axis survey offset in mm.
50 * \param Yoffset Y-axis survey offset in mm.
51 * \param Zoffset Z-axis survey offset in mm.
52 *
53 * Reads position offsets from geometry map file for absolute position
54 * calibration. These offsets correct for known mechanical installation
55 * differences from ideal positions.
56 */
57void VQwBPM::GetSurveyOffsets(Double_t Xoffset, Double_t Yoffset, Double_t Zoffset)
58{
59 // Read in the position offsets from the geometry map file
60 for(Short_t i=0;i<3;i++) fPositionCenter[i]=0.0;
61 fPositionCenter[0]=Xoffset;
62 fPositionCenter[1]=Yoffset;
63 fPositionCenter[2]=Zoffset;
64 return;
65}
66
67
68/*!
69 * \brief Apply per-detector electronic calibration and relative gains.
70 * \param BSENfactor Beam sensitivity factor for position calibration.
71 * \param AlphaX Relative gain correction factor for X position.
72 * \param AlphaY Relative gain correction factor for Y position.
73 *
74 * Reads electronic factors from calibration file and applies stripline-specific
75 * calibrations. BSENfactor is scaled by 18.81 to convert to mm/V, and a
76 * correction factor of 0.250014 is applied for stripline geometry.
77 */
78void VQwBPM::GetElectronicFactors(Double_t BSENfactor, Double_t AlphaX, Double_t AlphaY)
79{
80 // Read in the electronic factors from the file
81 Bool_t ldebug = kFALSE;
82
83 fQwStriplineCalibration = BSENfactor*18.81;
84 fQwStriplineCorrection = 0.250014;
85
86 fRelativeGains[0]=AlphaX;
87 fRelativeGains[1]=AlphaY;
88
89 if(ldebug){
90 std::cout<<"\n%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%\n";
91 std::cout<<this->GetElementName();
92 std::cout<<"\nfQwStriplineCalibration = "<<fQwStriplineCalibration<<std::endl;
93 std::cout<<"\nfQwStriplineCorrection = "<<fQwStriplineCorrection<<std::endl;
94 std::cout<<"AlphaX = "<<fRelativeGains[0]<<std::endl;
95 std::cout<<"AlphaY = "<<fRelativeGains[1]<<std::endl;
96
97 }
98 return;
99}
100
101/*!
102 * \brief Set detector rotation angle and update cached trigonometric values.
103 * \param rotation_angle Rotation angle in degrees (positive = clockwise from beam's perspective).
104 *
105 * Sets the BPM rotation angle and pre-computes sin/cos values for efficient
106 * coordinate transformations. Rotation is applied to correct for mechanical
107 * installation angles that differ from ideal orientation.
108 */
109void VQwBPM::SetRotation(Double_t rotation_angle){
110 // Read the rotation angle in degrees (to beam right)
111 Bool_t ldebug = kFALSE;
112 fSinRotation = 0;
113 fCosRotation = 0;
114 fRotationAngle = rotation_angle;
115 fSinRotation = TMath::Sin(fRotationAngle*(TMath::DegToRad()));
116 fCosRotation = TMath::Cos(fRotationAngle*(TMath::DegToRad()));
117
118 if(ldebug){
119 std::cout<<"\n%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%\n";
120 std::cout<<this->GetElementName();
121 std::cout<<" is rotated by angle = "<<rotation_angle<<std::endl;
122
123 }
124}
125
126/** Disable rotation, restoring accelerator coordinates (0 degrees). */
128 // Turn off rotation. This object is already in accelerator coordinates.
129 fRotationAngle = 0.0;
131 bRotated=kFALSE;
132}
133
134/** Configure position-dependent gains (X or Y). */
135void VQwBPM::SetGains(TString pos, Double_t value){
136 if(pos.Contains("X")) fGains[0] = value;
137 if(pos.Contains("Y")) fGains[1] = value;
138}
139
140void VQwBPM::SetSingleEventCuts(TString ch_name, Double_t minX, Double_t maxX)
141{
142 VQwHardwareChannel* tmpptr = GetSubelementByName(ch_name);
143 QwMessage << GetElementName() << " " << ch_name
144 << " LL " << minX <<" UL " << maxX <<QwLog::endl;
145 tmpptr->SetSingleEventCuts(minX,maxX);
146}
147
148void VQwBPM::SetSingleEventCuts(TString ch_name, UInt_t errorflag,Double_t minX, Double_t maxX, Double_t stability, Double_t burplevel)
149{
150 VQwHardwareChannel* tmpptr = GetSubelementByName(ch_name);
151 errorflag|=kBPMErrorFlag;//update the device flag
152 QwMessage << GetElementName() << " " << ch_name
153 << " LL " << minX <<" UL " << maxX <<QwLog::endl;
154 tmpptr->SetSingleEventCuts(errorflag,minX,maxX,stability,burplevel);
155}
156
158{
159 if (GetElementName()!=""){
162 bRotated = value.bRotated;
166 fGoodEvent = value.fGoodEvent;
167 // fDeviceErrorCode = value.fDeviceErrorCode;
168 // bFullSave = value.bFullSave;
169 for(size_t axis=kXAxis;axis<kNumAxes;axis++){
172 }
173 // Copy Z center position
174 this->fPositionCenter[2]=value.fPositionCenter[2];
175 }
176 return *this;
177}
178
179// VQwBPM& VQwBPM::operator+= (const VQwBPM &value)
180// {
181// if (GetElementName()!=""){
182// this->fEffectiveCharge+=value.fEffectiveCharge;
183// for(Short_t i=kXAxis;i<kNumAxes;i++) this->fAbsPos[i]+=value.fAbsPos[i];
184// }
185// return *this;
186// }
187
188// VQwBPM& VQwBPM::operator-= (const VQwBPM &value)
189// {
190// if (GetElementName()!=""){
191// this->fEffectiveCharge-=value.fEffectiveCharge;
192// for(Short_t i=kXAxis;i<kNumAxes;i++) this->fAbsPos[i]-=value.fAbsPos[i];
193// }
194// return *this;
195// }
196
197
198// void VQwBPM::Sum(VQwBPM &value1, VQwBPM &value2)
199// {
200// *this = value1;
201// *this += value2;
202// }
203
204// void VQwBPM::Difference(VQwBPM &value1, VQwBPM &value2)
205// {
206// *this = value1;
207// *this -= value2;
208// }
209
210
211// void VQwBPM::Scale(Double_t factor)
212// {
213// fEffectiveCharge_base->Scale(factor);
214// for(Short_t i = 0;i<2;i++)fAbsPos_base[i]->Scale(factor);
215// return;
216// }
217
218
219
220
221void VQwBPM::SetRootSaveStatus(TString &prefix)
222{
223 if(prefix.Contains("diff_")||prefix.Contains("yield_")|| prefix.Contains("asym_"))
224 bFullSave=kFALSE;
225
226 return;
227}
228
229// void VQwBPM::PrintValue() const
230// {
231// Short_t i;
232// for (i = 0; i < 2; i++) fAbsPos_base[i]->PrintValue();
233// fEffectiveCharge_base->PrintValue();
234
235// return;
236// }
237
238// void VQwBPM::PrintInfo() const
239// {
240// Short_t i = 0;
241// for (i = 0; i < 4; i++) fAbsPos_base[i]->PrintInfo();
242// fEffectiveCharge_base->PrintInfo();
243// }
244
245
246// void VQwBPM::CalculateRunningAverage()
247// {
248// Short_t i = 0;
249// for (i = 0; i < 2; i++) fAbsPos_base[i]->CalculateRunningAverage();
250// fEffectiveCharge_base->CalculateRunningAverage();
251
252// return;
253// }
254
255
256// void VQwBPM::AccumulateRunningSum(const VQwBPM& value)
257// {
258// // TODO This is unsafe, see QwBeamline::AccumulateRunningSum
259// Short_t i = 0;
260// for (i = 0; i < 2; i++) fAbsPos_base[i]->AccumulateRunningSum(value.fAbsPos_base[i]);
261// fEffectiveCharge_base->AccumulateRunningSum(value.fEffectiveCharge_base);
262// return;
263// }
264
265/**
266 * \brief A fast way of creating a BPM stripline of specified type
267 */
268VQwBPM* VQwBPM::CreateStripline(TString subsystemname, TString name, TString type)
269{
270 Bool_t localDebug = kFALSE;
271 type.ToUpper();
272 if( localDebug ) QwMessage<<"Creating BPM of type: "<<type<<" with name: "<<
273 name<<". Subsystem Name: " <<subsystemname<<"\n";
274 // (jc2) As a first try, let's do this the ugly way (but rather very
275 // simple), just list out the types of BPM's supported by this code!!!
276 if( type == "VQWK") {
277 return new QwBPMStripline<QwVQWK_Channel>(subsystemname,name,type);
278 } else if ( type == "SIS3801" ) {
279 return new QwBPMStripline<QwSIS3801_Channel>(subsystemname,name,type);
280 } else if ( type == "SCALER" || type == "SIS3801D24" ) {
281 return new QwBPMStripline<QwSIS3801D24_Channel>(subsystemname,name,type);
282 } else if ( type == "MOLLERADC" ) {
283 return new QwBPMStripline<QwMollerADC_Channel>(subsystemname,name,type);
284 } else { // Unsupported one!
285 QwWarning << "BPM of type="<<type<<" is UNSUPPORTED!!\n";
286 exit(-1);
287 }
288}
289
291{
292 Bool_t localDebug = kFALSE;
293 TString type = source.GetModuleType();
294 type.ToUpper();
295 if( localDebug ) QwMessage<<"Creating BPM of type: "<<type << QwLog::endl;
296 // (jc2) As a first try, let's do this the ugly way (but rather very
297 // simple), just list out the types of BPM's supported by this code!!!
298 if( type == "VQWK") {
299 return new QwBPMStripline<QwVQWK_Channel>(dynamic_cast<const QwBPMStripline<QwVQWK_Channel>&>(source));
300 } else if ( type == "SIS3801" ) {
301 return new QwBPMStripline<QwSIS3801_Channel>(dynamic_cast<const QwBPMStripline<QwSIS3801_Channel>&>(source));
302 } else if ( type == "SCALER" || type == "SIS3801D24" ) {
303 return new QwBPMStripline<QwSIS3801D24_Channel>(dynamic_cast<const QwBPMStripline<QwSIS3801D24_Channel>&>(source));
304 } else if ( type == "MOLLERADC" ) {
305 return new QwBPMStripline<QwMollerADC_Channel>(dynamic_cast<const QwBPMStripline<QwMollerADC_Channel>&>(source));
306 } else { // Unsupported one!
307 QwWarning << "BPM of type="<<type<<" is UNSUPPORTED!!\n";
308 exit(-1);
309 }
310}
311
312VQwBPM* VQwBPM::CreateLinearDiodeArray(TString subsystemname, TString name, TString type) {
313 Bool_t localdebug = kFALSE;
314 type.ToUpper();
315 if( localdebug ) QwMessage<<"Create Linear Diode Array of type: "<<type<<". Subsystem Name: "<<subsystemname<<"\n";
316 if( type == "VQWK") {
317 return new QwLinearDiodeArray<QwVQWK_Channel>(subsystemname, name, type);
318 } else if( type == "MOLLERADC" ) {
319 return new QwLinearDiodeArray<QwMollerADC_Channel>(subsystemname, name, type);
320 } else {
321 QwWarning<<"Linear Diode Array of type="<<type<<" is UNSUPPORTED!!\n";
322 exit(-1);
323 }
324}
325
327 Bool_t localdebug = kFALSE;
328 TString type = source.GetModuleType();
329 type.ToUpper();
330 if( localdebug ) QwMessage<<"Create Linear Diode Array of type: "<<type<<QwLog::endl;
331 if( type == "VQWK") {
332 return new QwLinearDiodeArray<QwVQWK_Channel>(dynamic_cast<const QwLinearDiodeArray<QwVQWK_Channel>&>(source));
333 } else if( type == "MOLLERADC" ) {
335 } else {
336 QwWarning<<"Linear Diode Array of type="<<type<<" is UNSUPPORTED!!\n";
337 exit(-1);
338 }
339}
340
341/**
342 * \brief A fast way of creating a BPM stripline of specified type
343 */
344VQwBPM* VQwBPM::CreateCombo(TString subsystemname, TString name,
345 TString type)
346{
347 Bool_t localDebug = kFALSE;
348 type.ToUpper();
349 if( localDebug ) QwMessage<<"Creating CombinedBPM of type: "<<type<<" with name: "<<
350 name<<". Subsystem Name: " <<subsystemname<<"\n";
351 // (jc2) As a first try, let's do this the ugly way (but rather very
352 // simple), just list out the types of BPM's supported by this code!!!
353 if( type == "VQWK") {
354 return new QwCombinedBPM<QwVQWK_Channel>(subsystemname,name,type);
355 } else if (type == "SIS3801" ) { // Default SCALER channel
356 return new QwCombinedBPM<QwSIS3801_Channel>(subsystemname,name,type);
357 } else if ( type == "SCALER" || type == "SIS3801D24" ) {
358 return new QwCombinedBPM<QwSIS3801D24_Channel>(subsystemname,name,type);
359 } else if ( type == "MOLLERADC" ) {
360 return new QwCombinedBPM<QwMollerADC_Channel>(subsystemname,name,type);
361 } else { // Unsupported one!
362 QwWarning << "BPM of type="<<type<<" is UNSUPPORTED!!\n";
363 exit(-1);
364 }
365}
366
368{
369 Bool_t localDebug = kFALSE;
370 TString type = source.GetModuleType();
371 type.ToUpper();
372 if( localDebug ) QwMessage<<"Creating CombinedBCM of type: "<<type<< QwLog::endl;
373 // (jc2) As a first try, let's do this the ugly way (but rather very
374 // simple), just list out the types of BCM's supported by this code!!!
375 if( type == "VQWK") {
376 return new QwCombinedBPM<QwVQWK_Channel>(dynamic_cast<const QwCombinedBPM<QwVQWK_Channel>&>(source));
377 } else if ( type == "SIS3801" ) { // Default SCALER channel
378 return new QwCombinedBPM<QwSIS3801_Channel>(dynamic_cast<const QwCombinedBPM<QwSIS3801_Channel>&>(source));
379 } else if ( type == "SCALER" || type == "SIS3801D24" ) {
380 return new QwCombinedBPM<QwSIS3801D24_Channel>(dynamic_cast<const QwCombinedBPM<QwSIS3801D24_Channel>&>(source));
381 } else if ( type == "MOLLERADC" ) {
382 return new QwCombinedBPM<QwMollerADC_Channel>(dynamic_cast<const QwCombinedBPM<QwMollerADC_Channel>&>(source));
383 } else { // Unsupported one!
384 QwWarning << "BPM of type="<<type<<" is UNSUPPORTED!!\n";
385 exit(-1);
386 }
387}
Decoding and management for VQWK ADC channels (6x32-bit datawords)
static const UInt_t kBPMErrorFlag
Definition QwTypes.h:170
A logfile class, based on an identical class in the Hermes analyzer.
#define QwWarning
Predefined log drain for warnings.
Definition QwLog.h:44
#define QwMessage
Predefined log drain for regular messages.
Definition QwLog.h:49
Base and derived classes for scaler channel data handling.
Decoding and management for Moller ADC channels (6x32-bit datawords)
Virtual base class for beam position monitors.
Stripline beam position monitor implementation.
Linear diode array beam position monitor implementation.
Combined beam position monitor using weighted average.
static std::ostream & endl(std::ostream &)
End of the line.
Definition QwLog.cc:297
virtual const TString & GetElementName() const
Get the name of this element.
void SetElementName(const TString &name)
Set the name of this element.
TString GetModuleType() const
Return the type of the beam instrument.
Abstract base for concrete hardware channels implementing dual-operator pattern.
void SetSingleEventCuts(Double_t min, Double_t max)
Set the upper and lower limits (fULimit and fLLimit) for this channel.
Linear diode array beam position monitor implementation.
Double_t fPositionCenter[3]
Definition VQwBPM.h:330
friend class QwCombinedBPM
Definition VQwBPM.h:66
@ kXAxis
Definition VQwBPM.h:72
@ kNumAxes
Definition VQwBPM.h:72
friend class QwBPMStripline
Definition VQwBPM.h:65
void GetSurveyOffsets(Double_t Xoffset, Double_t Yoffset, Double_t Zoffset)
Store geometry/survey offsets for absolute position calibration.
Definition VQwBPM.cc:57
void SetRotation(Double_t)
Set detector rotation angle and update cached trigonometric values.
Definition VQwBPM.cc:109
Double_t fQwStriplineCalibration
Definition VQwBPM.h:331
void SetRootSaveStatus(TString &prefix)
Definition VQwBPM.cc:221
static const TString kAxisLabel[2]
Definition VQwBPM.h:26
Double_t fGains[2]
Definition VQwBPM.h:334
Double_t fRotationAngle
Definition VQwBPM.h:339
static VQwBPM * CreateCombo(TString subsystemname, TString name, TString type)
A fast way of creating a BPM stripline of specified type.
Definition VQwBPM.cc:344
Double_t fCosRotation
Definition VQwBPM.h:340
void SetSingleEventCuts(TString, Double_t, Double_t)
Definition VQwBPM.cc:140
Double_t fRelativeGains[2]
Definition VQwBPM.h:333
void InitializeChannel(TString name)
Initialize common BPM state and set the element name.
Definition VQwBPM.cc:36
Bool_t fGoodEvent
Definition VQwBPM.h:347
static VQwBPM * CreateLinearDiodeArray(TString subsystemname, TString name, TString type)
Definition VQwBPM.cc:312
void SetRotationOff()
Definition VQwBPM.cc:127
void GetElectronicFactors(Double_t BSENfactor, Double_t AlphaX, Double_t AlphaY)
Apply per-detector electronic calibration and relative gains.
Definition VQwBPM.cc:78
virtual VQwHardwareChannel * GetSubelementByName(TString ch_name)=0
void SetGains(TString pos, Double_t value)
Definition VQwBPM.cc:135
Bool_t bFullSave
Definition VQwBPM.h:350
Double_t fQwStriplineCorrection
Definition VQwBPM.h:332
static VQwBPM * CreateStripline(TString subsystemname, TString name, TString type)
A fast way of creating a BPM stripline of specified type.
Definition VQwBPM.cc:268
static const TString axis[3]
Definition VQwBPM.h:335
virtual VQwBPM & operator=(const VQwBPM &value)=0
Definition VQwBPM.cc:157
Bool_t bRotated
Definition VQwBPM.h:338
VQwBPM()
Definition VQwBPM.h:76
Double_t fSinRotation
Definition VQwBPM.h:341