-
Notifications
You must be signed in to change notification settings - Fork 0
Commit
This commit does not belong to any branch on this repository, and may belong to a fork outside of the repository.
- Loading branch information
1 parent
24bc89c
commit 0cc9e19
Showing
7 changed files
with
13,687 additions
and
0 deletions.
There are no files selected for viewing
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,30 @@ | ||
# This file tracks properties of this Flutter project. | ||
# Used by Flutter tool to assess capabilities and perform upgrades etc. | ||
# | ||
# This file should be version controlled and should not be manually edited. | ||
|
||
version: | ||
revision: "78666c8dc57e9f7548ca9f8dd0740fbf0c658dc9" | ||
channel: "stable" | ||
|
||
project_type: app | ||
|
||
# Tracks metadata for the flutter migrate command | ||
migration: | ||
platforms: | ||
- platform: root | ||
create_revision: 78666c8dc57e9f7548ca9f8dd0740fbf0c658dc9 | ||
base_revision: 78666c8dc57e9f7548ca9f8dd0740fbf0c658dc9 | ||
- platform: windows | ||
create_revision: 78666c8dc57e9f7548ca9f8dd0740fbf0c658dc9 | ||
base_revision: 78666c8dc57e9f7548ca9f8dd0740fbf0c658dc9 | ||
|
||
# User provided section | ||
|
||
# List of Local paths (relative to this file) that should be | ||
# ignored by the migrate tool. | ||
# | ||
# Files that are not part of the templates will be ignored by default. | ||
unmanaged_files: | ||
- 'lib/main.dart' | ||
- 'ios/Runner.xcodeproj/project.pbxproj' |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,4 @@ | ||
include: package:flutter_lints/flutter.yaml | ||
|
||
linter: | ||
rules: |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,179 @@ | ||
import 'dart:math' as math; | ||
|
||
import 'package:characters/characters.dart'; | ||
import 'package:flutter/foundation.dart'; | ||
import 'package:wordle/game/letter.dart'; | ||
import 'package:wordle/game/words.dart'; | ||
|
||
typedef WordMatchResult = List<Letter>; | ||
|
||
enum SubmitResult { | ||
notEnoughLetters, | ||
noSuchWord, | ||
incorrectWord, | ||
lose, | ||
win, | ||
} | ||
|
||
class Game extends ChangeNotifier { | ||
late int _attempts; | ||
late int _currentAttempt; | ||
late String _secretWord; | ||
late List<WordMatchResult> _guesses; | ||
late String _currentWord; | ||
late Map<String, LetterMatch> _usedLetters; | ||
bool _finished = false; | ||
|
||
int get attempts => _attempts; | ||
|
||
int get currentAttempt => _currentAttempt; | ||
|
||
String get currentWord => _currentWord; | ||
|
||
Game() { | ||
restart(); | ||
_randomizeSecretWord(); | ||
} | ||
|
||
Game.withSecretWord(String secretWord) { | ||
restart(); | ||
_setSecretWord(secretWord); | ||
} | ||
|
||
Letter letterAt(int i, int j) { | ||
if (i == _currentAttempt - 1) { | ||
String? character = _currentWord.characters.elementAtOrNull(j); | ||
return character == null ? const Letter.empty() : Letter.unmatched(character); | ||
} | ||
|
||
return _guesses.elementAtOrNull(i)?.elementAt(j) ?? const Letter.empty(); | ||
} | ||
|
||
LetterMatch? matchForLetter(String letter) { | ||
return _usedLetters[letter]; | ||
} | ||
|
||
void pushLetter(String letter) { | ||
if (_finished) { | ||
return; | ||
} | ||
|
||
if (_currentWord.length == 5) { | ||
print("letter limit reached"); | ||
return; | ||
} | ||
|
||
assert(letter.isNotEmpty); | ||
assert(letter.length == 1); | ||
assert(letter.contains(RegExp("\\w"))); | ||
|
||
_currentWord += letter.toUpperCase(); | ||
|
||
print("push: $letter"); | ||
notifyListeners(); | ||
} | ||
|
||
void pushLetters(String letters) { | ||
if (_finished) { | ||
return; | ||
} | ||
|
||
for (var letter in letters.characters) { | ||
pushLetter(letter); | ||
} | ||
} | ||
|
||
void popLetter() { | ||
if (_finished) { | ||
return; | ||
} | ||
|
||
_currentWord = _currentWord.substring(0, math.max(0, _currentWord.length - 1)); | ||
print("(pop)"); | ||
notifyListeners(); | ||
} | ||
|
||
SubmitResult submit() { | ||
if (_finished) { | ||
return SubmitResult.win; | ||
} | ||
|
||
if (_currentWord.length < 5) { | ||
return SubmitResult.notEnoughLetters; | ||
} | ||
|
||
if (_currentWord == _secretWord) { | ||
_finished = true; | ||
_saveCurrentWord(); | ||
notifyListeners(); | ||
return SubmitResult.win; | ||
} | ||
|
||
if (_currentAttempt == _attempts) { | ||
print("Your word was $_secretWord"); | ||
|
||
_finished = true; | ||
_saveCurrentWord(); | ||
notifyListeners(); | ||
return SubmitResult.lose; | ||
} | ||
|
||
if (!_isCurrentWordValid()) { | ||
notifyListeners(); | ||
return SubmitResult.noSuchWord; | ||
} | ||
|
||
_saveCurrentWord(); | ||
notifyListeners(); | ||
return SubmitResult.incorrectWord; | ||
} | ||
|
||
void restart() { | ||
_attempts = 6; | ||
_currentAttempt = 1; | ||
_currentWord = ""; | ||
_secretWord = ""; | ||
_guesses = []; | ||
_finished = false; | ||
_usedLetters = {}; | ||
} | ||
|
||
WordMatchResult? lastGuessLetterMatchResult() { | ||
return _guesses.lastOrNull; | ||
} | ||
|
||
bool _isCurrentWordValid() { | ||
return answers.contains(_currentWord.toLowerCase()) || acceptableWords.contains(_currentWord.toLowerCase()); | ||
} | ||
|
||
void _saveCurrentWord() { | ||
WordMatchResult wordMatch = WordMatchResult.filled(5, const Letter.empty(), growable: false); | ||
|
||
for (int i = 0; i < 5; ++i) { | ||
String character = _currentWord[i]; | ||
LetterMatch letterMatch = LetterMatch.noMatch; | ||
|
||
if (character == _secretWord[i]) { | ||
letterMatch = LetterMatch.fullMatch; | ||
} else if (_secretWord.contains(character)) { | ||
letterMatch = LetterMatch.partialMatch; | ||
} | ||
|
||
wordMatch[i] = Letter(character, letterMatch); | ||
_usedLetters[character] = letterMatch; | ||
} | ||
|
||
_guesses.add(wordMatch); | ||
_currentWord = ""; | ||
_currentAttempt++; | ||
} | ||
|
||
void _setSecretWord(String word) { | ||
assert(word.length == 5); | ||
_secretWord = word.toUpperCase(); | ||
} | ||
|
||
void _randomizeSecretWord() { | ||
_secretWord = answers.elementAt(math.Random().nextInt(answers.length)).toUpperCase(); | ||
} | ||
} |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,30 @@ | ||
enum LetterMatch { | ||
noMatch, | ||
partialMatch, | ||
fullMatch, | ||
} | ||
|
||
class Letter { | ||
const Letter.empty() | ||
: _character = "", | ||
_matchResult = null; | ||
|
||
const Letter.unmatched(String character) | ||
: _character = character, | ||
_matchResult = null; | ||
|
||
const Letter(String character, LetterMatch matchResult) | ||
: _character = character, | ||
_matchResult = matchResult; | ||
|
||
final String _character; | ||
final LetterMatch? _matchResult; | ||
|
||
String get character => _character; | ||
|
||
LetterMatch? get matchResult => _matchResult; | ||
|
||
bool get isEmpty => _character.isEmpty; | ||
|
||
bool get isNotEmpty => _character.isNotEmpty; | ||
} |
Oops, something went wrong.