use crate::utils::{KEY_DUBBLE_MONITOR, KEY_DUBBLE_PHOTO};
use cryiorust::cbf;
use cryiorust::frame::{Array, Frame, Header, HeaderEntry};
pub struct FrameToAverage<'a> {
pub frame: Box<dyn Frame>,
pub name: &'a str,
pub transmission: f64,
pub monitor: f64,
pub photo: f64,
}
impl<'a> FrameToAverage<'a> {
pub fn new(frame: Box<dyn Frame>, name: &'a str) -> FrameToAverage<'a> {
FrameToAverage {
frame,
name,
transmission: 0.0,
monitor: 0.0,
photo: 0.0,
}
}
}
pub struct AveragedFrame {
pub array: Array,
pub monitor: f64,
pub transmission: f64,
pub photo: f64,
pub done: usize,
pub errors: Vec<String>,
pub header: Header,
}
impl AveragedFrame {
pub fn new(frames: &[FrameToAverage], coefficient: f64) -> AveragedFrame {
let (dim1, dim2) = frames[0].frame.array().dims();
let mut af = AveragedFrame {
array: Array::with_data(dim1, dim2, vec![0.; dim1 * dim2]),
monitor: 0.0,
transmission: 0.0,
photo: 0.0,
done: 0,
errors: vec![],
header: Header::new(),
};
let mut array = &mut af.array;
for frame in frames {
if frame.frame.array() != array {
af.errors
.push(format!("File {} has different dimensions", frame.name));
continue;
}
array += frame.frame.array();
af.transmission += frame.transmission;
af.monitor += frame.monitor;
af.photo += frame.photo;
af.done += 1;
}
if af.done > 0 {
let done = af.done as f64;
array *= coefficient / done;
af.transmission /= done;
af.monitor /= done;
af.photo /= done;
}
af.header
.insert(cbf::KEY_FLUX.to_string(), HeaderEntry::Float(af.monitor));
af.header.insert(
KEY_DUBBLE_MONITOR.to_string(),
HeaderEntry::Float(af.monitor),
);
af.header
.insert(KEY_DUBBLE_PHOTO.to_string(), HeaderEntry::Float(af.photo));
af
}
pub fn set_array(&mut self, array: Array) {
self.array = array;
}
}
impl Frame for AveragedFrame {
fn array(&self) -> &Array {
&self.array
}
fn header(&self) -> &Header {
&self.header
}
fn header_mut(&mut self) -> &mut Header {
&mut self.header
}
fn array_mut(&mut self) -> &mut Array {
&mut self.array
}
fn set_array(&mut self, array: Array) {
self.set_array(array);
}
}