use super::taggroup_entries::{Key, Tag, TagGroup};
use super::taggroup_entries::Tag::*;
use super::dmtypes::{SORTED, OPEN};
const VERSION: Option<&'static str> = option_env!("CARGO_PKG_VERSION");
const AUTHORS: Option<&'static str> = option_env!("CARGO_PKG_AUTHORS");
const PKGNAME: Option<&'static str> = option_env!("CARGO_PKG_NAME");
pub fn document_object_list() -> Tag {
let mut dol = TagGroup::new(!SORTED, !OPEN);
let mut tg0 = TagGroup::new(SORTED, !OPEN);
let agl = TagGroup::new(!SORTED, OPEN);
tg0.insert(Key::from_str("AnnotationGroupList"), TagGroupEntry(agl));
tg0.insert(Key::from_str("AnnotationType"), Long(20));
tg0.insert(
Key::from_str("BackgroundColor"),
Struct(vec![Short(-1), Short(-1), Short(-1)]),
);
tg0.insert(Key::from_str("BackgroundMode"), Short(2));
tg0.insert(Key::from_str("FillMode"), Short(1));
tg0.insert(
Key::from_str("ForegroundColor"),
Struct(vec![Short(-1), Short(0), Short(0)]),
);
tg0.insert(Key::from_str("HasBackground"), Boolean(true));
tg0.insert(Key::from_str("ImageDisplayInfo"), image_display_info());
tg0.insert(Key::from_str("ImageDisplayType"), Long(1));
tg0.insert(Key::from_str("ImageSource"), ULong(0));
tg0.insert(Key::from_str("IsMoveable"), Boolean(true));
tg0.insert(Key::from_str("IsResizable"), Boolean(true));
tg0.insert(Key::from_str("IsSelectable"), Boolean(true));
tg0.insert(Key::from_str("IsTranslatable"), Boolean(true));
tg0.insert(Key::from_str("IsVisible"), Boolean(true));
let ot = TagGroup::new(SORTED, !OPEN);
tg0.insert(Key::from_str("ObjectTags"), TagGroupEntry(ot));
tg0.insert(
Key::from_str("Rectangle"),
Struct(vec![Float(0.0), Float(0.0), Float(128.0), Float(128.0)]),
);
tg0.insert(Key::from_str("UniqueID"), ULong(8));
dol.insert(Key::Index(0), TagGroupEntry(tg0));
TagGroupEntry(dol)
}
fn image_display_info() -> Tag {
let mut idi = TagGroup::new(SORTED, !OPEN);
idi.insert(
Key::from_str("BrightColor"),
Struct(vec![Short(-1), Short(-1), Short(-1)]),
);
idi.insert(Key::from_str("CaptionOn"), Boolean(false));
idi.insert(Key::from_str("CaptionSize"), UShort(10));
idi.insert(Key::from_str("Brightness"), Float(0.5));
idi.insert(Key::from_str("CLUT"), new_clut());
idi.insert(
Key::from_str("CLUTName"),
ArrayUShort(vec![71, 114, 101, 121, 115, 99, 97, 108, 101]),
);
idi.insert(Key::from_str("ComplexMode"), ULong(4));
idi.insert(Key::from_str("ComplexRange"), Float(1000.0));
idi.insert(Key::from_str("Contrast"), Float(0.5));
idi.insert(Key::from_str("ContrastMode"), ULong(1));
let mut dim_labels = TagGroup::new(!SORTED, !OPEN);
dim_labels.insert(Key::Index(0), ArrayUShort(vec![]));
idi.insert(Key::from_str("DimensionLabels"), TagGroupEntry(dim_labels));
idi.insert(Key::from_str("DoAutoSurvey"), Boolean(true));
idi.insert(Key::from_str("EstimatedMax"), Float(0.0));
idi.insert(Key::from_str("EstimatedMaxTrimPercentage"), Float(0.001));
idi.insert(Key::from_str("EstimatedMin"), Float(0.0));
idi.insert(Key::from_str("EstimatedMinTrimPercentage"), Float(0.001));
idi.insert(Key::from_str("Gamma"), Float(0.5));
idi.insert(
Key::from_str("HiLimitContrastDeltaTriggerPercentage"),
Float(0.0),
);
idi.insert(Key::from_str("HighLimit"), Float(0.0));
idi.insert(Key::from_str("IsInverted"), Boolean(false));
idi.insert(Key::from_str("LowLimit"), Float(0.0));
idi.insert(
Key::from_str("LowLimitContrastDeltaTriggerPercentage"),
Float(0.0),
);
let mut main_slice_id = TagGroup::new(!SORTED, !OPEN);
main_slice_id.insert(Key::Index(0), ULong(0));
idi.insert(Key::from_str("MainSliceId"), TagGroupEntry(main_slice_id));
idi.insert(Key::from_str("MinimumContrast"), Float(0.0));
idi.insert(Key::from_str("RangeAdjust"), Float(1.0));
idi.insert(Key::from_str("SparseSurvey_GridSize"), ULong(16));
idi.insert(Key::from_str("SparseSurvey_NumberPixels"), ULong(32));
idi.insert(Key::from_str("SparseSurvey_UseNumberPixels"), Boolean(true));
idi.insert(Key::from_str("SurveyTechique"), ULong(2));
TagGroupEntry(idi)
}
fn new_clut() -> Tag {
let mut clut = Vec::new();
for i in 0..256 {
let val = (i * 257usize) as i16;
let st = Struct(vec![Short(val), Short(val), Short(val)]);
clut.push(st);
}
ComplexArray(clut)
}
pub fn image_behavior() -> Tag {
let mut ib = TagGroup::new(SORTED, !OPEN);
ib.insert(Key::from_str("DoIntegralZoom"), Boolean(true));
ib.insert(
Key::from_str("ImageDisplayBounds"),
Struct(vec![Float(0.0), Float(0.0), Float(128.0), Float(128.0)]),
);
ib.insert(Key::from_str("IsZoomedToWindow"), Boolean(false));
let mut unscaled_transform = TagGroup::new(SORTED, !OPEN);
unscaled_transform.insert(
Key::from_str("Offset"),
Struct(vec![Float(0.0), Float(0.0)]),
);
unscaled_transform.insert(Key::from_str("Scale"), Struct(vec![Float(1.0), Float(1.0)]));
ib.insert(
Key::from_str("UnscaledTransform"),
TagGroupEntry(unscaled_transform),
);
ib.insert(Key::from_str("ViewDisplayID"), ULong(0));
ib.insert(
Key::from_str("WindowRect"),
Struct(vec![Float(0.0), Float(0.0), Float(128.0), Float(128.0)]),
);
let mut zoom_and_move_transform = TagGroup::new(SORTED, !OPEN);
zoom_and_move_transform.insert(
Key::from_str("Offset"),
Struct(vec![Float(0.0), Float(0.0)]),
);
zoom_and_move_transform.insert(Key::from_str("Scale"), Struct(vec![Float(1.0), Float(1.0)]));
ib.insert(
Key::from_str("ZoomAndMoveTransform"),
TagGroupEntry(zoom_and_move_transform),
);
TagGroupEntry(ib)
}
pub fn image_list(shape: &[usize], image_type: u32) -> Tag {
let mut il = TagGroup::new(!SORTED, !OPEN);
let mut tg0 = TagGroup::new(SORTED, !OPEN);
tg0.insert(Key::from_str("ImageData"), new_image_data(&[128, 128], 23));
tg0.insert(Key::from_str("ImageTags"), new_image_tags());
tg0.insert(
Key::from_str("Name"),
ArrayUShort(vec![73, 109, 97, 103, 101, 32, 79, 102, 32, 50, 68]),
);
tg0.insert(Key::from_str("UniqueID"), get_uniqueid_thumb());
il.insert(Key::Index(0), TagGroupEntry(tg0));
let mut tg1 = TagGroup::new(SORTED, !OPEN);
tg1.insert(
Key::from_str("ImageData"),
new_image_data(shape, image_type),
);
tg1.insert(Key::from_str("ImageTags"), new_image_tags());
tg1.insert(Key::from_str("Name"), ArrayUShort(vec![50, 68]));
tg1.insert(Key::from_str("UniqueID"), get_uniqueid());
il.insert(Key::Index(1), TagGroupEntry(tg1));
TagGroupEntry(il)
}
pub fn image_source_list() -> Tag {
let mut isl = TagGroup::new(!SORTED, !OPEN);
let mut tg0 = TagGroup::new(SORTED, !OPEN);
tg0.insert(
Key::from_str("ClassName"),
ArrayUShort(vec![
73,
109,
97,
103,
101,
83,
111,
117,
114,
99,
101,
58,
83,
105,
109,
112,
108,
101,
]),
);
let mut id = TagGroup::new(!SORTED, !OPEN);
id.insert(Key::Index(0), ULong(0));
tg0.insert(Key::from_str("Id"), TagGroupEntry(id));
tg0.insert(Key::from_str("ImageRef"), ULong(1));
isl.insert(Key::Index(0), TagGroupEntry(tg0));
TagGroupEntry(isl)
}
pub fn min_version_list() -> Tag {
let mut mvl = TagGroup::new(!SORTED, !OPEN);
let mut tg0 = TagGroup::new(SORTED, !OPEN);
tg0.insert(Key::from_str("RequiredVersion"), ULong(50_659_328));
mvl.insert(Key::Index(0), TagGroupEntry(tg0));
TagGroupEntry(mvl)
}
pub fn page_behavior() -> Tag {
let mut pb = TagGroup::new(SORTED, !OPEN);
pb.insert(Key::from_str("DoIntegralZoom"), Boolean(false));
pb.insert(Key::from_str("DrawMargins"), Boolean(false));
pb.insert(Key::from_str("DrawPaper"), Boolean(false));
pb.insert(Key::from_str("IsFixedInPageMode"), Boolean(false));
pb.insert(Key::from_str("IsZoomedToWindow"), Boolean(false));
pb.insert(Key::from_str("LayedOut"), Boolean(false));
let mut page_transform = TagGroup::new(SORTED, !OPEN);
page_transform.insert(
Key::from_str("Offset"),
Struct(vec![Float(0.0), Float(0.0)]),
);
page_transform.insert(Key::from_str("Scale"), Struct(vec![Float(1.0), Float(1.0)]));
pb.insert(
Key::from_str("PageTransform"),
TagGroupEntry(page_transform),
);
pb.insert(
Key::from_str("RestoreImageDisplayBounds"),
Struct(vec![Float(0.0), Float(0.0), Float(100.0), Float(100.0)]),
);
pb.insert(Key::from_str("RestoreImageDisplayID"), ULong(0));
pb.insert(Key::from_str("TargetDisplayID"), ULong(0));
TagGroupEntry(pb)
}
pub fn page_setup() -> Tag {
let ps = TagGroup::new(SORTED, !OPEN);
TagGroupEntry(ps)
}
pub fn thumbnails() -> Tag {
let mut t = TagGroup::new(!SORTED, !OPEN);
let mut tg0 = TagGroup::new(SORTED, !OPEN);
tg0.insert(Key::from_str("ImageIndex"), ULong(0));
tg0.insert(
Key::from_str("SourceSize_Pixels"),
Struct(vec![Long(128), Long(128)]),
);
t.insert(Key::Index(0), TagGroupEntry(tg0));
TagGroupEntry(t)
}
fn new_image_data(shape: &[usize], image_type: u32) -> Tag {
let mut image_data = TagGroup::new(SORTED, !OPEN);
image_data.insert(Key::from_str("Calibrations"), new_calibration(shape.len()));
let data_len = shape.iter().product();
let data = match image_type {
2 => ArrayFloat(vec![0.0; data_len]),
23 => ArrayLong(vec![0; data_len]),
_ => panic!("Unknown type"),
};
image_data.insert(Key::from_str("Data"), data);
image_data.insert(Key::from_str("DataType"), ULong(image_type));
image_data.insert(Key::from_str("Dimensions"), new_dim(shape));
image_data.insert(Key::from_str("PixelDepth"), ULong(4));
TagGroupEntry(image_data)
}
fn new_calibration(n_dim: usize) -> Tag {
let mut calibrations = TagGroup::new(SORTED, !OPEN);
calibrations.insert(Key::from_str("Brightness"), new_dim_cal());
let mut dimension = TagGroup::new(!SORTED, !OPEN);
for i in 0..n_dim {
dimension.insert(Key::Index(i), new_dim_cal());
}
calibrations.insert(Key::from_str("Dimension"), TagGroupEntry(dimension));
calibrations.insert(Key::from_str("DisplayCalibratedUnits"), Boolean(true));
TagGroupEntry(calibrations)
}
fn new_dim_cal() -> Tag {
let mut dim_cal = TagGroup::new(SORTED, !OPEN);
dim_cal.insert(Key::from_str("Origin"), Float(0.0));
dim_cal.insert(Key::from_str("Scale"), Float(1.0));
dim_cal.insert(Key::from_str("Units"), ArrayUShort(Vec::new()));
TagGroupEntry(dim_cal)
}
fn new_dim(shape: &[usize]) -> Tag {
let mut dim = TagGroup::new(!SORTED, !OPEN);
for (ind, &size) in shape.iter().enumerate() {
dim.insert(Key::Index(ind), ULong(size as u32));
}
TagGroupEntry(dim)
}
fn new_image_tags() -> Tag {
let mut img_tags = TagGroup::new(SORTED, !OPEN);
let mut tg_ver = TagGroup::new(SORTED, !OPEN);
let version = VERSION.unwrap_or("unknown").encode_utf16().collect();
tg_ver.insert(Key::from_str("Version"), ArrayUShort(version));
let authors = AUTHORS.unwrap_or("unknown").encode_utf16().collect();
tg_ver.insert(Key::from_str("Authors"), ArrayUShort(authors));
let mut description = "Image created by ".to_string();
description.push_str(PKGNAME.unwrap_or("dm3io"));
img_tags.insert(Key::Label(description), TagGroupEntry(tg_ver));
TagGroupEntry(img_tags)
}
fn get_uniqueid_thumb() -> Tag {
let mut uniqueid = TagGroup::new(!SORTED, !OPEN);
uniqueid.insert(Key::Index(0), ULong(843_787_323));
uniqueid.insert(Key::Index(1), ULong(725_888_012));
uniqueid.insert(Key::Index(2), ULong(853_419_723));
uniqueid.insert(Key::Index(3), ULong(192_158_838));
TagGroupEntry(uniqueid)
}
fn get_uniqueid() -> Tag {
let mut uniqueid = TagGroup::new(!SORTED, !OPEN);
uniqueid.insert(Key::Index(0), ULong(22_810_150));
uniqueid.insert(Key::Index(1), ULong(1_405_054_737));
uniqueid.insert(Key::Index(2), ULong(893_145_621));
uniqueid.insert(Key::Index(3), ULong(538_509_487));
TagGroupEntry(uniqueid)
}