1use super::NanonisClient;
2use crate::error::NanonisError;
3use crate::types::NanonisValue;
4
5#[derive(Debug, Clone, Copy, PartialEq, Eq, Default)]
7pub enum SpectrumFFTWindow {
8 #[default]
9 None = 0,
10 Hanning = 1,
11 Hamming = 2,
12 BlackmanHarris = 3,
13 ExactBlackman = 4,
14 Blackman = 5,
15 FlatTop = 6,
16 FourTermBHarris = 7,
17 SevenTermBHarris = 8,
18 LowSidelobe = 9,
19}
20
21impl From<SpectrumFFTWindow> for u16 {
22 fn from(window: SpectrumFFTWindow) -> Self {
23 window as u16
24 }
25}
26
27impl TryFrom<u16> for SpectrumFFTWindow {
28 type Error = NanonisError;
29
30 fn try_from(value: u16) -> Result<Self, Self::Error> {
31 match value {
32 0 => Ok(Self::None),
33 1 => Ok(Self::Hanning),
34 2 => Ok(Self::Hamming),
35 3 => Ok(Self::BlackmanHarris),
36 4 => Ok(Self::ExactBlackman),
37 5 => Ok(Self::Blackman),
38 6 => Ok(Self::FlatTop),
39 7 => Ok(Self::FourTermBHarris),
40 8 => Ok(Self::SevenTermBHarris),
41 9 => Ok(Self::LowSidelobe),
42 _ => Err(NanonisError::Protocol(format!(
43 "Invalid FFT window: {}",
44 value
45 ))),
46 }
47 }
48}
49
50#[derive(Debug, Clone, Copy, PartialEq, Eq, Default)]
52pub enum SpectrumAveragingMode {
53 #[default]
54 None = 0,
55 Vector = 1,
56 RMS = 2,
57 PeakHold = 3,
58}
59
60impl From<SpectrumAveragingMode> for u16 {
61 fn from(mode: SpectrumAveragingMode) -> Self {
62 mode as u16
63 }
64}
65
66impl TryFrom<u16> for SpectrumAveragingMode {
67 type Error = NanonisError;
68
69 fn try_from(value: u16) -> Result<Self, Self::Error> {
70 match value {
71 0 => Ok(Self::None),
72 1 => Ok(Self::Vector),
73 2 => Ok(Self::RMS),
74 3 => Ok(Self::PeakHold),
75 _ => Err(NanonisError::Protocol(format!(
76 "Invalid averaging mode: {}",
77 value
78 ))),
79 }
80 }
81}
82
83#[derive(Debug, Clone, Copy, PartialEq, Eq, Default)]
85pub enum SpectrumWeightingMode {
86 #[default]
87 Linear = 0,
88 Exponential = 1,
89}
90
91impl From<SpectrumWeightingMode> for u16 {
92 fn from(mode: SpectrumWeightingMode) -> Self {
93 mode as u16
94 }
95}
96
97impl TryFrom<u16> for SpectrumWeightingMode {
98 type Error = NanonisError;
99
100 fn try_from(value: u16) -> Result<Self, Self::Error> {
101 match value {
102 0 => Ok(Self::Linear),
103 1 => Ok(Self::Exponential),
104 _ => Err(NanonisError::Protocol(format!(
105 "Invalid weighting mode: {}",
106 value
107 ))),
108 }
109 }
110}
111
112#[derive(Debug, Clone, Copy, PartialEq, Eq, Default)]
114pub enum SpectrumCursorType {
115 #[default]
116 XY = 0,
117 DxDy = 1,
118 X1X2Dx = 2,
119 Y1Y2Dy = 3,
120 RMSDf = 4,
121 NoChange = 5,
122}
123
124impl From<SpectrumCursorType> for u16 {
125 fn from(cursor: SpectrumCursorType) -> Self {
126 cursor as u16
127 }
128}
129
130impl TryFrom<u16> for SpectrumCursorType {
131 type Error = NanonisError;
132
133 fn try_from(value: u16) -> Result<Self, Self::Error> {
134 match value {
135 0 => Ok(Self::XY),
136 1 => Ok(Self::DxDy),
137 2 => Ok(Self::X1X2Dx),
138 3 => Ok(Self::Y1Y2Dy),
139 4 => Ok(Self::RMSDf),
140 5 => Ok(Self::NoChange),
141 _ => Err(NanonisError::Protocol(format!(
142 "Invalid cursor type: {}",
143 value
144 ))),
145 }
146 }
147}
148
149#[derive(Debug, Clone, Copy, PartialEq, Eq, Default)]
151pub enum SpectrumAnalyzerInstance {
152 #[default]
153 Analyzer1 = 1,
154 Analyzer2 = 2,
155}
156
157impl From<SpectrumAnalyzerInstance> for i32 {
158 fn from(instance: SpectrumAnalyzerInstance) -> Self {
159 instance as i32
160 }
161}
162
163#[derive(Debug, Clone, Default)]
165pub struct SpectrumFreqRange {
166 pub selected_index: i32,
168 pub available_ranges_hz: Vec<f32>,
170}
171
172#[derive(Debug, Clone, Default)]
174pub struct SpectrumFreqResolution {
175 pub selected_index: u16,
177 pub available_resolutions_hz: Vec<f32>,
179}
180
181#[derive(Debug, Clone, Copy, Default)]
183pub struct SpectrumAveraging {
184 pub mode: SpectrumAveragingMode,
186 pub weighting: SpectrumWeightingMode,
188 pub count: u32,
190}
191
192#[derive(Debug, Clone, Copy, Default)]
194pub struct SpectrumCursorPos {
195 pub cursor1_x_hz: f64,
197 pub cursor2_x_hz: f64,
199 pub cursor1_y: f64,
201}
202
203#[derive(Debug, Clone, Copy, Default)]
205pub struct SpectrumBandRMS {
206 pub rms: f64,
208 pub min_freq_hz: f64,
210 pub max_freq_hz: f64,
212}
213
214#[derive(Debug, Clone, Default)]
216pub struct SpectrumData {
217 pub f0_hz: f32,
219 pub df_hz: f32,
221 pub data: Vec<f32>,
223}
224
225impl NanonisClient {
226 pub fn spectrum_anlzr_ch_set(
237 &mut self,
238 instance: SpectrumAnalyzerInstance,
239 channel_index: i32,
240 ) -> Result<(), NanonisError> {
241 self.quick_send(
242 "SpectrumAnlzr.ChSet",
243 vec![
244 NanonisValue::I32(instance.into()),
245 NanonisValue::I32(channel_index),
246 ],
247 vec!["i", "i"],
248 vec![],
249 )?;
250 Ok(())
251 }
252
253 pub fn spectrum_anlzr_ch_get(
264 &mut self,
265 instance: SpectrumAnalyzerInstance,
266 ) -> Result<i32, NanonisError> {
267 let result = self.quick_send(
268 "SpectrumAnlzr.ChGet",
269 vec![NanonisValue::I32(instance.into())],
270 vec!["i"],
271 vec!["i"],
272 )?;
273
274 result[0].as_i32()
275 }
276
277 pub fn spectrum_anlzr_freq_range_set(
288 &mut self,
289 instance: SpectrumAnalyzerInstance,
290 range_index: i32,
291 ) -> Result<(), NanonisError> {
292 self.quick_send(
293 "SpectrumAnlzr.FreqRangeSet",
294 vec![
295 NanonisValue::I32(instance.into()),
296 NanonisValue::I32(range_index),
297 ],
298 vec!["i", "i"],
299 vec![],
300 )?;
301 Ok(())
302 }
303
304 pub fn spectrum_anlzr_freq_range_get(
315 &mut self,
316 instance: SpectrumAnalyzerInstance,
317 ) -> Result<SpectrumFreqRange, NanonisError> {
318 let result = self.quick_send(
319 "SpectrumAnlzr.FreqRangeGet",
320 vec![NanonisValue::I32(instance.into())],
321 vec!["i"],
322 vec!["i", "i", "*f"],
323 )?;
324
325 Ok(SpectrumFreqRange {
326 selected_index: result[0].as_i32()?,
327 available_ranges_hz: result[2].as_f32_array()?.to_vec(),
328 })
329 }
330
331 pub fn spectrum_anlzr_freq_res_set(
342 &mut self,
343 instance: SpectrumAnalyzerInstance,
344 resolution_index: u16,
345 ) -> Result<(), NanonisError> {
346 self.quick_send(
347 "SpectrumAnlzr.FreqResSet",
348 vec![
349 NanonisValue::I32(instance.into()),
350 NanonisValue::U16(resolution_index),
351 ],
352 vec!["i", "H"],
353 vec![],
354 )?;
355 Ok(())
356 }
357
358 pub fn spectrum_anlzr_freq_res_get(
369 &mut self,
370 instance: SpectrumAnalyzerInstance,
371 ) -> Result<SpectrumFreqResolution, NanonisError> {
372 let result = self.quick_send(
373 "SpectrumAnlzr.FreqResGet",
374 vec![NanonisValue::I32(instance.into())],
375 vec!["i"],
376 vec!["H", "i", "*f"],
377 )?;
378
379 Ok(SpectrumFreqResolution {
380 selected_index: result[0].as_u16()?,
381 available_resolutions_hz: result[2].as_f32_array()?.to_vec(),
382 })
383 }
384
385 pub fn spectrum_anlzr_fft_window_set(
394 &mut self,
395 instance: SpectrumAnalyzerInstance,
396 window: SpectrumFFTWindow,
397 ) -> Result<(), NanonisError> {
398 self.quick_send(
399 "SpectrumAnlzr.FFTWindowSet",
400 vec![
401 NanonisValue::I32(instance.into()),
402 NanonisValue::U16(window.into()),
403 ],
404 vec!["i", "H"],
405 vec![],
406 )?;
407 Ok(())
408 }
409
410 pub fn spectrum_anlzr_fft_window_get(
421 &mut self,
422 instance: SpectrumAnalyzerInstance,
423 ) -> Result<SpectrumFFTWindow, NanonisError> {
424 let result = self.quick_send(
425 "SpectrumAnlzr.FFTWindowGet",
426 vec![NanonisValue::I32(instance.into())],
427 vec!["i"],
428 vec!["H"],
429 )?;
430
431 SpectrumFFTWindow::try_from(result[0].as_u16()?)
432 }
433
434 pub fn spectrum_anlzr_averag_set(
443 &mut self,
444 instance: SpectrumAnalyzerInstance,
445 averaging: &SpectrumAveraging,
446 ) -> Result<(), NanonisError> {
447 self.quick_send(
448 "SpectrumAnlzr.AveragSet",
449 vec![
450 NanonisValue::I32(instance.into()),
451 NanonisValue::U16(averaging.mode.into()),
452 NanonisValue::U16(averaging.weighting.into()),
453 NanonisValue::U32(averaging.count),
454 ],
455 vec!["i", "H", "H", "I"],
456 vec![],
457 )?;
458 Ok(())
459 }
460
461 pub fn spectrum_anlzr_averag_get(
472 &mut self,
473 instance: SpectrumAnalyzerInstance,
474 ) -> Result<SpectrumAveraging, NanonisError> {
475 let result = self.quick_send(
476 "SpectrumAnlzr.AveragGet",
477 vec![NanonisValue::I32(instance.into())],
478 vec!["i"],
479 vec!["H", "H", "I"],
480 )?;
481
482 Ok(SpectrumAveraging {
483 mode: SpectrumAveragingMode::try_from(result[0].as_u16()?)?,
484 weighting: SpectrumWeightingMode::try_from(result[1].as_u16()?)?,
485 count: result[2].as_u32()?,
486 })
487 }
488
489 pub fn spectrum_anlzr_ac_coupling_set(
500 &mut self,
501 instance: SpectrumAnalyzerInstance,
502 enabled: bool,
503 ) -> Result<(), NanonisError> {
504 self.quick_send(
505 "SpectrumAnlzr.ACCouplingSet",
506 vec![
507 NanonisValue::I32(instance.into()),
508 NanonisValue::U32(if enabled { 1 } else { 0 }),
509 ],
510 vec!["i", "I"],
511 vec![],
512 )?;
513 Ok(())
514 }
515
516 pub fn spectrum_anlzr_ac_coupling_get(
527 &mut self,
528 instance: SpectrumAnalyzerInstance,
529 ) -> Result<bool, NanonisError> {
530 let result = self.quick_send(
531 "SpectrumAnlzr.ACCouplingGet",
532 vec![NanonisValue::I32(instance.into())],
533 vec!["i"],
534 vec!["I"],
535 )?;
536
537 Ok(result[0].as_u32()? != 0)
538 }
539
540 pub fn spectrum_anlzr_cursor_pos_set(
553 &mut self,
554 instance: SpectrumAnalyzerInstance,
555 cursor_type: SpectrumCursorType,
556 cursor1_x_hz: f64,
557 cursor2_x_hz: f64,
558 ) -> Result<(), NanonisError> {
559 self.quick_send(
560 "SpectrumAnlzr.CursorPosSet",
561 vec![
562 NanonisValue::I32(instance.into()),
563 NanonisValue::U16(cursor_type.into()),
564 NanonisValue::F64(cursor1_x_hz),
565 NanonisValue::F64(cursor2_x_hz),
566 ],
567 vec!["i", "H", "d", "d"],
568 vec![],
569 )?;
570 Ok(())
571 }
572
573 pub fn spectrum_anlzr_cursor_pos_get(
585 &mut self,
586 instance: SpectrumAnalyzerInstance,
587 cursor_type: SpectrumCursorType,
588 ) -> Result<SpectrumCursorPos, NanonisError> {
589 let result = self.quick_send(
590 "SpectrumAnlzr.CursorPosGet",
591 vec![
592 NanonisValue::I32(instance.into()),
593 NanonisValue::U16(cursor_type.into()),
594 ],
595 vec!["i", "H"],
596 vec!["d", "d", "d"],
597 )?;
598
599 Ok(SpectrumCursorPos {
600 cursor1_x_hz: result[0].as_f64()?,
601 cursor2_x_hz: result[1].as_f64()?,
602 cursor1_y: result[2].as_f64()?,
603 })
604 }
605
606 pub fn spectrum_anlzr_band_rms_get(
619 &mut self,
620 instance: SpectrumAnalyzerInstance,
621 ) -> Result<SpectrumBandRMS, NanonisError> {
622 let result = self.quick_send(
623 "SpectrumAnlzr.BandRMSGet",
624 vec![NanonisValue::I32(instance.into())],
625 vec!["i"],
626 vec!["d", "d", "d"],
627 )?;
628
629 Ok(SpectrumBandRMS {
630 rms: result[0].as_f64()?,
631 min_freq_hz: result[1].as_f64()?,
632 max_freq_hz: result[2].as_f64()?,
633 })
634 }
635
636 pub fn spectrum_anlzr_dc_get(
649 &mut self,
650 instance: SpectrumAnalyzerInstance,
651 ) -> Result<f64, NanonisError> {
652 let result = self.quick_send(
653 "SpectrumAnlzr.DCGet",
654 vec![NanonisValue::I32(instance.into())],
655 vec!["i"],
656 vec!["d"],
657 )?;
658
659 result[0].as_f64()
660 }
661
662 pub fn spectrum_anlzr_run(
673 &mut self,
674 instance: SpectrumAnalyzerInstance,
675 ) -> Result<(), NanonisError> {
676 self.quick_send(
677 "SpectrumAnlzr.Run",
678 vec![NanonisValue::I32(instance.into())],
679 vec!["i"],
680 vec![],
681 )?;
682 Ok(())
683 }
684
685 pub fn spectrum_anlzr_data_get(
696 &mut self,
697 instance: SpectrumAnalyzerInstance,
698 ) -> Result<SpectrumData, NanonisError> {
699 let result = self.quick_send(
700 "SpectrumAnlzr.DataGet",
701 vec![NanonisValue::I32(instance.into())],
702 vec!["i"],
703 vec!["f", "f", "i", "*f"],
704 )?;
705
706 Ok(SpectrumData {
707 f0_hz: result[0].as_f32()?,
708 df_hz: result[1].as_f32()?,
709 data: result[3].as_f32_array()?.to_vec(),
710 })
711 }
712}