modde_games/oblivion_remastered/
scanner.rs1use anyhow::Result;
4
5use crate::scanner_patterns::{FileGroupRule, SingleFileModRule};
6use crate::traits::{DiscoveredMod, ModScanner, ScanContext};
7
8pub struct OblivionRemasteredScanner;
10
11pub static OBLIVION_REMASTERED_SCANNER: OblivionRemasteredScanner = OblivionRemasteredScanner;
12
13const GROUP_EXTENSIONS: &[&str] = &["pak", "ucas", "utoc"];
14
15impl ModScanner for OblivionRemasteredScanner {
16 fn scan_directories(&self) -> &[&str] {
17 &["Content/Paks/~mods", "Data"]
18 }
19
20 fn scan_filesystem(&self, ctx: &ScanContext<'_>) -> Result<Vec<DiscoveredMod>> {
21 let mut out = Vec::new();
22 let paks = super::paks_root(ctx.install_dir).join("~mods");
23 FileGroupRule {
24 rel_dir: "",
25 extensions: GROUP_EXTENSIONS,
26 mod_id_prefix: "pak",
27 source_location: "paks-mods",
28 confidence: 0.9,
29 }
30 .scan_dir(ctx.install_dir, &paks, &mut out);
31
32 SingleFileModRule {
33 rel_dir: "Data",
34 extension: "esp",
35 ignored_prefixes: &[],
36 mod_id_prefix: "plugin",
37 source_location: "Data",
38 confidence: 0.8,
39 }
40 .scan(ctx.install_dir, &mut out)?;
41 Ok(out)
42 }
43
44 fn mod_id_footprint(&self, mod_id: &str) -> Option<modde_core::scanner::ModFootprint> {
45 if let Some(stem) = mod_id.strip_prefix("pak/") {
46 return Some(modde_core::scanner::ModFootprint::File(format!(
47 "oblivionremastered/content/paks/~mods/{}.pak",
48 stem.to_lowercase()
49 )));
50 }
51 let stem = mod_id.strip_prefix("plugin/")?.to_lowercase();
52 Some(modde_core::scanner::ModFootprint::File(format!(
53 "data/{stem}.esp"
54 )))
55 }
56}