show solutions with no matching level under a 'missing levels' chapter
This commit is contained in:
parent
522a027f7a
commit
563c819900
4 changed files with 49 additions and 4 deletions
|
@ -3,6 +3,7 @@ Game store page: https://crispypin.itch.io/marble-machinations
|
||||||
|
|
||||||
## [unreleased]
|
## [unreleased]
|
||||||
### added
|
### added
|
||||||
|
- create "missing levels" section allowing access to solutions to levels that are no longer available
|
||||||
- click to collapse chapters in level list
|
- click to collapse chapters in level list
|
||||||
### fixed
|
### fixed
|
||||||
- When two input bindings had the same trigger but one has a strict subset of the others modifiers, both would activate when the one with more modifiers was pressed. For example (Ctrl+S -> Save) would also trigger (S -> Wire Tool). Now, Shift+S will still trigger Wire Tool, unless Shift+S (or eg. Shift+Ctrl+S) is bound to something else.
|
- When two input bindings had the same trigger but one has a strict subset of the others modifiers, both would activate when the one with more modifiers was pressed. For example (Ctrl+S -> Save) would also trigger (S -> Wire Tool). Now, Shift+S will still trigger Wire Tool, unless Shift+S (or eg. Shift+Ctrl+S) is bound to something else.
|
||||||
|
|
|
@ -21,7 +21,6 @@ logic mostly like https://git.crispypin.cc/CrispyPin/marble
|
||||||
- UI layout engine
|
- UI layout engine
|
||||||
- global scale setting
|
- global scale setting
|
||||||
#### unspecified
|
#### unspecified
|
||||||
- show orphaned solutions
|
|
||||||
- comments
|
- comments
|
||||||
- editing
|
- editing
|
||||||
- add to all intro levels
|
- add to all intro levels
|
||||||
|
|
14
src/level.rs
14
src/level.rs
|
@ -49,6 +49,20 @@ impl IOData {
|
||||||
}
|
}
|
||||||
|
|
||||||
impl Level {
|
impl Level {
|
||||||
|
pub fn new_orphan(id: &str) -> Self {
|
||||||
|
Self {
|
||||||
|
id: id.to_owned(),
|
||||||
|
name: id.to_owned(),
|
||||||
|
description: String::from(
|
||||||
|
"No level with this id was found, but there are saved solutions pointing to it.\n
|
||||||
|
Because input values and expected output is not available, this functions as a sandbox.\n
|
||||||
|
This allows you to recover any machines you have built here.",
|
||||||
|
),
|
||||||
|
init_board: None,
|
||||||
|
stages: Vec::new(),
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
pub fn id(&self) -> &str {
|
pub fn id(&self) -> &str {
|
||||||
&self.id
|
&self.id
|
||||||
}
|
}
|
||||||
|
|
35
src/main.rs
35
src/main.rs
|
@ -10,7 +10,7 @@ use marble_machinations::*;
|
||||||
|
|
||||||
use config::Config;
|
use config::Config;
|
||||||
use editor::{Editor, ExitState};
|
use editor::{Editor, ExitState};
|
||||||
use level::Chapter;
|
use level::{Chapter, Level};
|
||||||
use solution::Solution;
|
use solution::Solution;
|
||||||
use theme::*;
|
use theme::*;
|
||||||
use ui::{simple_option_button, tex32_button, text_button, text_input, ShapedText, Tooltip};
|
use ui::{simple_option_button, tex32_button, text_button, text_input, ShapedText, Tooltip};
|
||||||
|
@ -46,8 +46,11 @@ fn main() {
|
||||||
|
|
||||||
impl Game {
|
impl Game {
|
||||||
fn new(rl: &mut RaylibHandle, thread: &RaylibThread) -> Self {
|
fn new(rl: &mut RaylibHandle, thread: &RaylibThread) -> Self {
|
||||||
let chapters = get_chapters();
|
let mut chapters = get_chapters();
|
||||||
let solutions = get_solutions();
|
let solutions = get_solutions();
|
||||||
|
if let Some(orphans) = find_orphans(&chapters, &solutions) {
|
||||||
|
chapters.push(orphans);
|
||||||
|
}
|
||||||
|
|
||||||
Self {
|
Self {
|
||||||
chapters,
|
chapters,
|
||||||
|
@ -407,9 +410,37 @@ fn get_solutions() -> HashMap<String, Vec<Solution>> {
|
||||||
}
|
}
|
||||||
solutions.sort_unstable_by_key(Solution::id);
|
solutions.sort_unstable_by_key(Solution::id);
|
||||||
}
|
}
|
||||||
|
if !solutions.is_empty() {
|
||||||
by_level.insert(level_name, solutions);
|
by_level.insert(level_name, solutions);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
}
|
||||||
by_level
|
by_level
|
||||||
}
|
}
|
||||||
|
|
||||||
|
fn find_orphans(
|
||||||
|
chapters: &[Chapter],
|
||||||
|
solutions: &HashMap<String, Vec<Solution>>,
|
||||||
|
) -> Option<Chapter> {
|
||||||
|
let mut orphan_levels = Vec::new();
|
||||||
|
'outer: for id in solutions.keys() {
|
||||||
|
for c in chapters {
|
||||||
|
for l in &c.levels {
|
||||||
|
if l.id() == id {
|
||||||
|
continue 'outer;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
orphan_levels.push(Level::new_orphan(id))
|
||||||
|
}
|
||||||
|
if orphan_levels.is_empty() {
|
||||||
|
None
|
||||||
|
} else {
|
||||||
|
Some(Chapter {
|
||||||
|
title: "Missing levels".into(),
|
||||||
|
levels: orphan_levels,
|
||||||
|
visible: false,
|
||||||
|
})
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
Loading…
Add table
Reference in a new issue