Replies: 97 comments 14 replies
-
Yes, I did it dirty and used the random number gen instead of "the smart way". Now I just need to figure out how to read this. I would just think, use the recursion strategy and have it hit every node with a known max depth. And the whole "Good" direction thing is not needed for most, except for puzzles that have a fixed direction. |
Beta Was this translation helpful? Give feedback.
-
I've played and refactored a bunch. Fewer setup calls and it finds the best solution.
|
Beta Was this translation helpful? Give feedback.
-
I did some work, think it is better now, and it doesn't check everything |
Beta Was this translation helpful? Give feedback.
-
I can rewrite it in mostly any language you like. And actually add comments. /**
* A possibility that we'll explore in the breadth-first search
*/
class State {
/**
* Which cubes did we touch to get to this state?
*/
steps = [];
/**
* How are the cubes arranged? I'm using numbers (0,1,2,3)
*/
cubes = [];
constructor(steps, cubes) {
this.steps = steps;
this.cubes = cubes;
}
}
/**
* Applies a rotation to some cubes. A rotation just describes which cubes get rotated.
* It then returns a new array of cubes.
*/
function applyRotation(rotation, cubes) {
if (rotation.length != cubes.length)
throw new Error("There has to be one rotation for every cube.");
let newCubes = cubes.slice(); // Copy the array
for (let i = 0; i < rotation.length; i++) {
newCubes[i] = mod(cubes[i] + rotation[i], 4);
}
return newCubes;
}
function applyAllRotations(possibleRotations, state) {
// We take every single rotation, and create a new state
return possibleRotations.map(
(rotation, i) =>
new State(state.steps.concat(i), applyRotation(rotation, state.cubes))
);
}
/**
* states: We explore all possibilities at the same time. Could be improved by only visiting actually new states.
* possibleRotations: If we touch cube n, which cubes get rotated
*/
function solvePuzzle(states, possibleRotations) {
// Solutions are those possibilities where every cube is 0 (facing in the desired direction, could be made better)
let solutions = states.filter((state) => state.cubes.every((cube) => cube == 0));
if (solutions.length == 0) {
// Keep searching
const newStates = states
.map((state) => applyAllRotations(possibleRotations, state))
.flat();
return solvePuzzle(newStates, possibleRotations);
} else {
// Yay, we found a solution
return solutions[0].steps;
}
}
function mod(a, b) {
// Most languages don't implement a proper modulo that handles negative numbers
// Instead they implement a division-remainder. Ew.
return ((a % b) + b) % b;
}
solvePuzzle(
// We haven't done anything yet
// And the cube at index 1 has been rotated 2 times
[new State([], [0, 2, 0, 0])],
// And if we hit the cube at index N, it will get rotated accordingly
[
[1, 1, 0, 1],
[1, 1, 1, 0],
[0, 1, 1, 1],
[1, 0, 1, 1],
],
);
I think the easiest way is to have a function that checks if a solution is valid. That way, you could easily switch out which variant to use at runtime.
Yeah, the max depth variant works. But doing it breadth-first, where you first check all solutions with a max depth of 0, then with a max depth of 1, then with a max depth of 2, and so on is neater. It guarantees that the first solution you find is also the best one.
Very nice indeed! |
Beta Was this translation helpful? Give feedback.
-
Oh lol, I also have a super simplistic one that assumes cubes will only ever rotate in one direction |
Beta Was this translation helpful? Give feedback.
-
I keep thinking, need to add drag and drop somewhere, or pre-program all the puzzle configurations, but if you just showed up to the puzzle, the pieces are in a fixed direction, here is the answer. |
Beta Was this translation helpful? Give feedback.
-
This puzzle is why I wrote it. |
Beta Was this translation helpful? Give feedback.
-
I think the easiest option is to code in every puzzle in the game. Writing something that lets you configure a puzzle seems like it'd be more trouble than it's worth. The only part that should be configure-able is the initial state of the puzzle, since I bet people are going to go to a puzzle, attempt it themselves, give up and look at the tool. Which makes me wonder: Is there a list of all such puzzles somewhere? |
Beta Was this translation helpful? Give feedback.
-
On the official map it has every cube puzzle listed. But I already solved them, so I can't play with them again to get the X triggers Y logic and initial diection. |
Beta Was this translation helpful? Give feedback.
-
But I could easily change up the code and have it start at a lower max depth, and then on failure, increase it until it works / max. |
Beta Was this translation helpful? Give feedback.
-
I suppose there are a few reasonable options for getting puzzles:
Also, how do you feel about turning this into a website? As in, boring old JavaScript, HTML, CSS, a bunch of images and hosting it on Github Pages. Costs nothing, is easy to make, and saves people the trouble of downloading something. |
Beta Was this translation helpful? Give feedback.
-
It would not be that hard to make simple js page version, since it would just be all client side. Use a worker. I thought about making a simple site, but I forgot about github pages, then it could have a crude map of all the puzzles to click to see the root solution and if you messed with it, enter the current facing. I still have one of my kids accounts that hasn't don't anything yet in inazuma. |
Beta Was this translation helpful? Give feedback.
-
Yep, fully agreed. It's always nice when a web-development project boils down to client side Javascript. No complicated servers involved, haha.
Sweet! Then that beautifully solves that. |
Beta Was this translation helpful? Give feedback.
-
Just need to worry about copyrights, Jenshin Impact is always pretty memeable. |
Beta Was this translation helpful? Give feedback.
-
Bwahaha yes indeed. I also propose drawing the Inazuma map instead of using the official, probably copyrighted one. |
Beta Was this translation helpful? Give feedback.
-
Interesting observation indeed. Judging from this video, there seem to be a lot of puzzles that have something like that. I suppose one would have to play around with the puzzles more to figure out what exactly they mean. |
Beta Was this translation helpful? Give feedback.
-
I checked the puzzle at https://mgatelabs.github.io/GenshinSolvers/puzzle?id=x14197 and the 3 back cubes have no interactions, so they will have empty connections and should be skipped when checking. |
Beta Was this translation helpful? Give feedback.
-
Interesting indeed. Then I'm glad that the algorithm I whipped up doesn't assume that hitting a cube will cause it to rotate. Like, if we had an imaginary 2 cube puzzle where the user can only touch the second cube: solvePuzzle({
initialState: [3, 0],
isFinalState: customSolution([3, 3]),
maximumNumber: 4,
stateTransitions: [
[], // Nothing happens when hitting cube 0
[1], // Cube 1 rotates when cube 1 gets hit
]
}); |
Beta Was this translation helpful? Give feedback.
-
Cube 1 still causes [0,1,2] and curb 3 causes [2,3,4]. Just 0,2,4 have not user interaction. Technically cube 0 and 1 will always face the same way. Cube 3 & 4 also do the same. |
Beta Was this translation helpful? Give feedback.
-
In other news, I just found out that there are a few other Genshin Impact puzzle solvers.
What they all have in common is that the user has to configure the puzzles themselves. I might reach out to some of them, mainly to say: "Look, we've also built a solver. What do you think?" |
Beta Was this translation helpful? Give feedback.
-
Nice to know we're not the only ones building an overly complex solution to a simple problem. But from what i've witnessed, we might be the simplest, but we have to put in all the leg work. |
Beta Was this translation helpful? Give feedback.
-
Switching to ortho view for Light up puzzles, to hide the other sides. Also new fav icon. |
Beta Was this translation helpful? Give feedback.
-
Yes indeed, I was quite amused to see what other people have tried. I personally really enjoyed the mathematical approach, even if it is like using an industrial jackhammer to tighten a screw. And yes again, we're definitely building the simplest one. In fact, I'd go so far as to say that we're building the only one that's use-able enough to actually consider using. After all, it has to compete with simplistic alternatives like
|
Beta Was this translation helpful? Give feedback.
-
But watching that video, there are cubes with the thing on top and the user can hit them. Maybe by the time they made those, they were like thing on top pretty, screw the rules. So we really can't just look at the picture, but need to manually test each one and see what happens. The hard part is not solving it too early. |
Beta Was this translation helpful? Give feedback.
-
Finally implemented the puzzle that was presented before. |
Beta Was this translation helpful? Give feedback.
-
Started to test the app on iPhone, it crashed the browser, but all the buttons work. Should have the click magic working soon. Think I setup a no win config and it didn't like it. Made a change so it skips dead ends. Cubes are clickable. Navbar works |
Beta Was this translation helpful? Give feedback.
-
I moved the issue to discussion, since it is all over the place. |
Beta Was this translation helpful? Give feedback.
-
Quick heads up: It looks like the current configuration can't handle URLs like https://mgatelabs.github.io/GenshinSolvers/puzzle/x14197 I think the reason for that is that
|
Beta Was this translation helpful? Give feedback.
-
Just figured out something, there is no "0" for light puzzles. Just 1,2,3. I need to mess with the solver input, have it convert 1 > 0, 2 > 1, 3 > 2. Then reverse it when showing. Got it working. |
Beta Was this translation helpful? Give feedback.
-
Maybe it's time to make a new discussion topic, like a "Weekly Bread Topic 2/27" and each week choose a new bread for the title. |
Beta Was this translation helpful? Give feedback.
-
The fact that this solver is calling a random number generator makes me think that it simply tries out stuff until something works. Is that assessment correct?
An even more
overblownwell engineered approach would be to try out all possibilities in a breadth-first manner. In fact, I did write something like this. And since nobody said anything about being reasonable, I wrote it in Haskell.Pro:
It's super short and works beautifully
Con:
It's in Haskell. Not sure if that's better or worse than Java.
Feel free to use the code. Though, if one wants to make something actually usable, I'd recommend writing it in Typescript and having a proper, static website. I'd totally be willing to help if you're interested.
Beta Was this translation helpful? Give feedback.
All reactions