This branch predates CI on `main`. `cargo fmt --all` only; no behaviour. Co-Authored-By: Claude Opus 5 <noreply@anthropic.com>
78 lines
2.8 KiB
Rust
78 lines
2.8 KiB
Rust
//! Does a primitive's alpha AT t=0 predict the layer it paints on?
|
|
//!
|
|
//! `implied_layer_key` is a measured per-name table. The four entries in it, read
|
|
//! against their own keyframes, suggest a rule derived from the file instead:
|
|
//!
|
|
//! * `palogo_eff0.prm` measured FIRST (0x0000) -- alpha at t=0 = ?
|
|
//! * `pfbase.tbm` measured FIRST (0x0000) -- alpha at t=0 = ?
|
|
//! * `pteff02.prm` measured MIDDLE (0x8030) -- alpha at t=0 = ?
|
|
//! * `pteff00.prm` measured LAST -- alpha at t=0 = ?
|
|
//!
|
|
//! ⚠️ The rule was invented AFTER seeing three of those answers, so it is fitted
|
|
//! on them and only `pfbase.tbm` is out of sample. This prints all four plus a
|
|
//! disc-wide census, so the fit and its reach are visible together.
|
|
use std::collections::BTreeMap;
|
|
use sylpheed_formats::{pak, ratc, ui_layout};
|
|
|
|
fn main() {
|
|
let root = std::env::var("SYLPHEED_DISC").unwrap_or_else(|_| "/disc".into());
|
|
let mut paks: Vec<_> = std::fs::read_dir(format!("{root}/dat"))
|
|
.expect("dat/")
|
|
.flatten()
|
|
.map(|e| e.path())
|
|
.filter(|p| p.extension().and_then(|s| s.to_str()) == Some("pak"))
|
|
.collect();
|
|
paks.sort();
|
|
// name -> (count, set of t=0 alphas, set of "starts at max" flags)
|
|
let mut byname: BTreeMap<String, (usize, BTreeMap<u32, usize>)> = BTreeMap::new();
|
|
for p in &paks {
|
|
let Ok(ar) = pak::PakArchive::open(p) else {
|
|
continue;
|
|
};
|
|
for e in ar.entries() {
|
|
let Ok(by) = ar.read(e) else { continue };
|
|
if !ratc::is_ratc(&by) {
|
|
continue;
|
|
}
|
|
let Some(b) = ui_layout::parse_build(&by) else {
|
|
continue;
|
|
};
|
|
for el in &b.elements {
|
|
// primitives and the keyless: anything with no layer key
|
|
if ui_layout::sprite_layer_key(&b, &by, el).is_some() {
|
|
continue;
|
|
}
|
|
let Some(k0) = el.keyframes.first() else {
|
|
continue;
|
|
};
|
|
let a0 = k0.fade >> 24;
|
|
let ent = byname.entry(el.name.clone()).or_default();
|
|
ent.0 += 1;
|
|
*ent.1.entry(a0).or_default() += 1;
|
|
}
|
|
}
|
|
}
|
|
println!(
|
|
"{:>28} {:>7} alpha at t=0 (count)",
|
|
"keyless element", "n"
|
|
);
|
|
let known = [
|
|
"palogo_eff0.prm",
|
|
"pfbase.tbm",
|
|
"pteff02.prm",
|
|
"pteff00.prm",
|
|
];
|
|
for (n, (c, a)) in &byname {
|
|
let tag = if known.contains(&n.as_str()) {
|
|
" <- IN THE MEASURED TABLE"
|
|
} else {
|
|
""
|
|
};
|
|
if *c < 4 && tag.is_empty() {
|
|
continue;
|
|
}
|
|
let al: Vec<String> = a.iter().map(|(k, v)| format!("{k}x{v}")).collect();
|
|
println!(" {n:>26} {c:>7} {}{tag}", al.join(" "));
|
|
}
|
|
}
|