Skip to content
Snippets Groups Projects
Commit b3d23951 authored by Benoît Harrault's avatar Benoît Harrault
Browse files

Split settings in global/game settings

parent b33877ee
No related branches found
No related tags found
1 merge request!23Resolve "Add "global settings" management"
Pipeline #4974 passed
Showing
with 339 additions and 161 deletions
org.gradle.jvmargs=-Xmx1536M org.gradle.jvmargs=-Xmx1536M
android.useAndroidX=true android.useAndroidX=true
android.enableJetifier=true android.enableJetifier=true
app.versionName=0.0.20 app.versionName=0.0.21
app.versionCode=20 app.versionCode=21
Split parameters in global parameters and game parameters.
Séparation des paramètres en paramètre globaux et paramètres de jeu.
...@@ -2,7 +2,6 @@ class DefaultGameSettings { ...@@ -2,7 +2,6 @@ class DefaultGameSettings {
static const List<String> availableParameters = [ static const List<String> availableParameters = [
'boardSize', 'boardSize',
'colorsCount', 'colorsCount',
'colorsTheme',
]; ];
static const int boardSizeValueSmall = 6; static const int boardSizeValueSmall = 6;
...@@ -31,28 +30,12 @@ class DefaultGameSettings { ...@@ -31,28 +30,12 @@ class DefaultGameSettings {
colorsCountValueVeryHigh, colorsCountValueVeryHigh,
]; ];
static const int defaultColorsThemeValue = 1;
static const List<int> allowedColorsThemeValues = [
// 0, // 0x9D9D9D,0xFFFFFF,0xBE2633,0xE06F8B,0x493C2B,0xA46422,0xEB8931,0xF7E26B,0x2F484E,0x44891A,0xA3CE27,0x1B2632,0x005784,0x31A2F2,0xB2DCEF,// legacy
1, // 0x0e0e12,0x1a1a24,0x333346,0x535373,0x8080a4,0xa6a6bf,0xc1c1d2,0xe6e6ec, // https://lospec.com/palette-list/gothic-bit
2, // 0x615e85,0x9c8dc2,0xd9a3cd,0xebc3a7,0xe0e0dc,0xa3d1af,0x90b4de,0x717fb0, // https://lospec.com/palette-list/sweethope
3, // 0xd9af80,0xb07972,0x524352,0x686887,0x7f9bb0,0xbfd4b0,0x90b870,0x628c70, // https://lospec.com/palette-list/nostalgic-dreams
4, // 0x8bc7bf,0x5796a1,0x524bb3,0x471b6e,0x702782,0xb0455a,0xde8b6f,0xebd694, // https://lospec.com/palette-list/arjibi8
// 5, // 0x40263e,0x5979a6,0x84c2a3,0xefe8c3,0xefefef,0xcbc7d6,0xd06060,0x773971, // https://lospec.com/palette-list/kotomasho-8
// 6, // 0xf0f0eb,0xffff8f,0x7be098,0x849ad8,0xe8b382,0xd8828e,0xa776c1,0x545155, // https://lospec.com/palette-list/desatur8
// 7, // 0x211d38,0x2e2a4f,0x3b405e,0x60556e,0x9a6278,0xc7786f,0xcfa98a,0xcdd4a5, // https://lospec.com/palette-list/purplemorning8
// 8, // 0x332422,0xc95b40,0xff9b5e,0xfcdf76,0x4c2f7f,0x3a66ad,0x39cec2,0xfafff9, // https://lospec.com/palette-list/cold-war-8
// 9, // 0x111323,0x374566,0x50785d,0x8497b3,0xe8dcd8,0xcfb463,0xb35447,0x692e4b, // https://lospec.com/palette-list/low-8
];
static List<int> getAvailableValues(String parameterCode) { static List<int> getAvailableValues(String parameterCode) {
switch (parameterCode) { switch (parameterCode) {
case 'boardSize': case 'boardSize':
return DefaultGameSettings.allowedBoardSizeValues; return DefaultGameSettings.allowedBoardSizeValues;
case 'colorsCount': case 'colorsCount':
return DefaultGameSettings.allowedColorsCountValues; return DefaultGameSettings.allowedColorsCountValues;
case 'colorsTheme':
return DefaultGameSettings.allowedColorsThemeValues;
} }
return []; return [];
......
class DefaultGlobalSettings {
static const List<String> availableParameters = [
'colorsTheme',
];
static const int defaultColorsThemeValue = 1;
static const List<int> allowedColorsThemeValues = [
// 0, // 0x9D9D9D,0xFFFFFF,0xBE2633,0xE06F8B,0x493C2B,0xA46422,0xEB8931,0xF7E26B,0x2F484E,0x44891A,0xA3CE27,0x1B2632,0x005784,0x31A2F2,0xB2DCEF,// legacy
1, // 0x0e0e12,0x1a1a24,0x333346,0x535373,0x8080a4,0xa6a6bf,0xc1c1d2,0xe6e6ec, // https://lospec.com/palette-list/gothic-bit
2, // 0x615e85,0x9c8dc2,0xd9a3cd,0xebc3a7,0xe0e0dc,0xa3d1af,0x90b4de,0x717fb0, // https://lospec.com/palette-list/sweethope
3, // 0xd9af80,0xb07972,0x524352,0x686887,0x7f9bb0,0xbfd4b0,0x90b870,0x628c70, // https://lospec.com/palette-list/nostalgic-dreams
4, // 0x8bc7bf,0x5796a1,0x524bb3,0x471b6e,0x702782,0xb0455a,0xde8b6f,0xebd694, // https://lospec.com/palette-list/arjibi8
// 5, // 0x40263e,0x5979a6,0x84c2a3,0xefe8c3,0xefefef,0xcbc7d6,0xd06060,0x773971, // https://lospec.com/palette-list/kotomasho-8
// 6, // 0xf0f0eb,0xffff8f,0x7be098,0x849ad8,0xe8b382,0xd8828e,0xa776c1,0x545155, // https://lospec.com/palette-list/desatur8
// 7, // 0x211d38,0x2e2a4f,0x3b405e,0x60556e,0x9a6278,0xc7786f,0xcfa98a,0xcdd4a5, // https://lospec.com/palette-list/purplemorning8
// 8, // 0x332422,0xc95b40,0xff9b5e,0xfcdf76,0x4c2f7f,0x3a66ad,0x39cec2,0xfafff9, // https://lospec.com/palette-list/cold-war-8
// 9, // 0x111323,0x374566,0x50785d,0x8497b3,0xe8dcd8,0xcfb463,0xb35447,0x692e4b, // https://lospec.com/palette-list/low-8
];
static List<int> getAvailableValues(String parameterCode) {
switch (parameterCode) {
case 'colorsTheme':
return DefaultGlobalSettings.allowedColorsThemeValues;
}
return [];
}
}
import 'package:equatable/equatable.dart'; import 'package:equatable/equatable.dart';
import 'package:flutter/material.dart'; import 'package:flutter/material.dart';
import 'package:hydrated_bloc/hydrated_bloc.dart'; import 'package:hydrated_bloc/hydrated_bloc.dart';
import 'package:jeweled/config/default_game_settings.dart';
import 'package:jeweled/config/default_game_settings.dart';
import 'package:jeweled/models/game.dart'; import 'package:jeweled/models/game.dart';
import 'package:jeweled/models/cell_location.dart'; import 'package:jeweled/models/cell_location.dart';
import 'package:jeweled/models/game_settings.dart'; import 'package:jeweled/models/settings_game.dart';
import 'package:jeweled/models/settings_global.dart';
part 'game_state.dart'; part 'game_state.dart';
...@@ -24,7 +25,8 @@ class GameCubit extends HydratedCubit<GameState> { ...@@ -24,7 +25,8 @@ class GameCubit extends HydratedCubit<GameState> {
void refresh() { void refresh() {
final Game game = Game( final Game game = Game(
board: state.currentGame.board, board: state.currentGame.board,
settings: state.currentGame.settings, gameSettings: state.currentGame.gameSettings,
globalSettings: state.currentGame.globalSettings,
shuffledColors: state.currentGame.shuffledColors, shuffledColors: state.currentGame.shuffledColors,
isRunning: state.currentGame.isRunning, isRunning: state.currentGame.isRunning,
isFinished: state.currentGame.isFinished, isFinished: state.currentGame.isFinished,
...@@ -74,8 +76,8 @@ class GameCubit extends HydratedCubit<GameState> { ...@@ -74,8 +76,8 @@ class GameCubit extends HydratedCubit<GameState> {
moveCellsDown() { moveCellsDown() {
final Game currentGame = this.state.currentGame; final Game currentGame = this.state.currentGame;
final int boardSizeHorizontal = currentGame.settings.boardSize; final int boardSizeHorizontal = currentGame.gameSettings.boardSize;
final int boardSizeVertical = currentGame.settings.boardSize; final int boardSizeVertical = currentGame.gameSettings.boardSize;
for (int row = 0; row < boardSizeVertical; row++) { for (int row = 0; row < boardSizeVertical; row++) {
for (int col = 0; col < boardSizeHorizontal; col++) { for (int col = 0; col < boardSizeHorizontal; col++) {
...@@ -136,9 +138,13 @@ class GameCubit extends HydratedCubit<GameState> { ...@@ -136,9 +138,13 @@ class GameCubit extends HydratedCubit<GameState> {
} }
} }
void startNewGame(GameSettings settings) { void startNewGame({
required GameSettings gameSettings,
required GlobalSettings globalSettings,
}) {
Game newGame = Game.createNew( Game newGame = Game.createNew(
gameSettings: settings, gameSettings: gameSettings,
globalSettings: globalSettings,
); );
newGame.dump(); newGame.dump();
......
...@@ -2,24 +2,22 @@ import 'package:equatable/equatable.dart'; ...@@ -2,24 +2,22 @@ import 'package:equatable/equatable.dart';
import 'package:flutter/material.dart'; import 'package:flutter/material.dart';
import 'package:hydrated_bloc/hydrated_bloc.dart'; import 'package:hydrated_bloc/hydrated_bloc.dart';
import 'package:jeweled/models/game_settings.dart'; import 'package:jeweled/models/settings_game.dart';
part 'settings_state.dart'; part 'settings_game_state.dart';
class SettingsCubit extends HydratedCubit<SettingsState> { class GameSettingsCubit extends HydratedCubit<GameSettingsState> {
SettingsCubit() : super(SettingsState(settings: GameSettings.createDefault())); GameSettingsCubit() : super(GameSettingsState(settings: GameSettings.createDefault()));
void setValues({ void setValues({
int? boardSize, int? boardSize,
int? colorsCount, int? colorsCount,
int? colorsTheme,
}) { }) {
emit( emit(
SettingsState( GameSettingsState(
settings: GameSettings( settings: GameSettings(
boardSize: boardSize ?? state.settings.boardSize, boardSize: boardSize ?? state.settings.boardSize,
colorsCount: colorsCount ?? state.settings.colorsCount, colorsCount: colorsCount ?? state.settings.colorsCount,
colorsTheme: colorsTheme ?? state.settings.colorsTheme,
), ),
), ),
); );
...@@ -31,48 +29,41 @@ class SettingsCubit extends HydratedCubit<SettingsState> { ...@@ -31,48 +29,41 @@ class SettingsCubit extends HydratedCubit<SettingsState> {
return GameSettings.getBoardSizeValueFromUnsafe(state.settings.boardSize); return GameSettings.getBoardSizeValueFromUnsafe(state.settings.boardSize);
case 'colorsCount': case 'colorsCount':
return GameSettings.getColorsCountValueFromUnsafe(state.settings.colorsCount); return GameSettings.getColorsCountValueFromUnsafe(state.settings.colorsCount);
case 'colorsTheme':
return GameSettings.getColorsThemeValueFromUnsafe(state.settings.colorsTheme);
} }
return 0; return 0;
} }
void setParameterValue(String code, int value) { void setParameterValue(String code, int value) {
print('SettingsCubit.setParameterValue'); print('GameSettingsCubit.setParameterValue');
print('code: ' + code + ' / value: ' + value.toString()); print('code: ' + code + ' / value: ' + value.toString());
int boardSize = code == 'boardSize' ? value : getParameterValue('boardSize'); int boardSize = code == 'boardSize' ? value : getParameterValue('boardSize');
int colorsCount = code == 'colorsCount' ? value : getParameterValue('colorsCount'); int colorsCount = code == 'colorsCount' ? value : getParameterValue('colorsCount');
int colorsTheme = code == 'colorsTheme' ? value : getParameterValue('colorsTheme');
setValues( setValues(
boardSize: boardSize, boardSize: boardSize,
colorsCount: colorsCount, colorsCount: colorsCount,
colorsTheme: colorsTheme,
); );
} }
@override @override
SettingsState? fromJson(Map<String, dynamic> json) { GameSettingsState? fromJson(Map<String, dynamic> json) {
int boardSize = json['boardSize'] as int; int boardSize = json['boardSize'] as int;
int colorsCount = json['colorsCount'] as int; int colorsCount = json['colorsCount'] as int;
int colorsTheme = json['colorsTheme'] as int;
return SettingsState( return GameSettingsState(
settings: GameSettings( settings: GameSettings(
boardSize: boardSize, boardSize: boardSize,
colorsCount: colorsCount, colorsCount: colorsCount,
colorsTheme: colorsTheme,
), ),
); );
} }
@override @override
Map<String, dynamic>? toJson(SettingsState state) { Map<String, dynamic>? toJson(GameSettingsState state) {
return <String, dynamic>{ return <String, dynamic>{
'boardSize': state.settings.boardSize, 'boardSize': state.settings.boardSize,
'colorsCount': state.settings.colorsCount, 'colorsCount': state.settings.colorsCount,
'colorsTheme': state.settings.colorsTheme,
}; };
} }
} }
part of 'settings_cubit.dart'; part of 'settings_game_cubit.dart';
@immutable @immutable
class SettingsState extends Equatable { class GameSettingsState extends Equatable {
const SettingsState({ const GameSettingsState({
required this.settings, required this.settings,
}); });
......
import 'package:equatable/equatable.dart';
import 'package:flutter/material.dart';
import 'package:hydrated_bloc/hydrated_bloc.dart';
import 'package:jeweled/models/settings_global.dart';
part 'settings_global_state.dart';
class GlobalSettingsCubit extends HydratedCubit<GlobalSettingsState> {
GlobalSettingsCubit() : super(GlobalSettingsState(settings: GlobalSettings.createDefault()));
void setValues({
int? colorsTheme,
}) {
emit(
GlobalSettingsState(
settings: GlobalSettings(
colorsTheme: colorsTheme ?? state.settings.colorsTheme,
),
),
);
}
int getParameterValue(String code) {
switch (code) {
case 'colorsTheme':
return GlobalSettings.getColorsThemeValueFromUnsafe(state.settings.colorsTheme);
}
return 0;
}
void setParameterValue(String code, int value) {
print('GlobalSettingsCubit.setParameterValue');
print('code: ' + code + ' / value: ' + value.toString());
int colorsTheme = code == 'colorsTheme' ? value : getParameterValue('colorsTheme');
setValues(
colorsTheme: colorsTheme,
);
}
@override
GlobalSettingsState? fromJson(Map<String, dynamic> json) {
int colorsTheme = json['colorsTheme'] as int;
return GlobalSettingsState(
settings: GlobalSettings(
colorsTheme: colorsTheme,
),
);
}
@override
Map<String, dynamic>? toJson(GlobalSettingsState state) {
return <String, dynamic>{
'colorsTheme': state.settings.colorsTheme,
};
}
}
part of 'settings_global_cubit.dart';
@immutable
class GlobalSettingsState extends Equatable {
const GlobalSettingsState({
required this.settings,
});
final GlobalSettings settings;
@override
List<dynamic> get props => <dynamic>[
settings,
];
Map<String, dynamic> get values => <String, dynamic>{
'settings': settings,
};
}
...@@ -8,8 +8,9 @@ import 'package:hydrated_bloc/hydrated_bloc.dart'; ...@@ -8,8 +8,9 @@ import 'package:hydrated_bloc/hydrated_bloc.dart';
import 'package:path_provider/path_provider.dart'; import 'package:path_provider/path_provider.dart';
import 'package:jeweled/config/theme.dart'; import 'package:jeweled/config/theme.dart';
import 'package:jeweled/cubit/settings_cubit.dart';
import 'package:jeweled/cubit/game_cubit.dart'; import 'package:jeweled/cubit/game_cubit.dart';
import 'package:jeweled/cubit/settings_game_cubit.dart';
import 'package:jeweled/cubit/settings_global_cubit.dart';
import 'package:jeweled/ui/skeleton.dart'; import 'package:jeweled/ui/skeleton.dart';
void main() async { void main() async {
...@@ -44,7 +45,8 @@ class MyApp extends StatelessWidget { ...@@ -44,7 +45,8 @@ class MyApp extends StatelessWidget {
return MultiBlocProvider( return MultiBlocProvider(
providers: [ providers: [
BlocProvider<GameCubit>(create: (context) => GameCubit()), BlocProvider<GameCubit>(create: (context) => GameCubit()),
BlocProvider<SettingsCubit>(create: (context) => SettingsCubit()), BlocProvider<GlobalSettingsCubit>(create: (context) => GlobalSettingsCubit()),
BlocProvider<GameSettingsCubit>(create: (context) => GameSettingsCubit()),
], ],
child: MaterialApp( child: MaterialApp(
title: 'Jeweled', title: 'Jeweled',
......
import 'dart:math'; import 'dart:math';
import 'package:jeweled/config/default_game_settings.dart'; import 'package:jeweled/config/default_global_settings.dart';
import 'package:jeweled/models/game_board.dart'; import 'package:jeweled/models/game_board.dart';
import 'package:jeweled/models/game_cell.dart'; import 'package:jeweled/models/game_cell.dart';
import 'package:jeweled/models/cell_location.dart'; import 'package:jeweled/models/cell_location.dart';
import 'package:jeweled/models/game_settings.dart'; import 'package:jeweled/models/settings_game.dart';
import 'package:jeweled/models/settings_global.dart';
import 'package:jeweled/utils/color_theme.dart'; import 'package:jeweled/utils/color_theme.dart';
class Game { class Game {
final GameBoard board; final GameBoard board;
final GameSettings settings; final GameSettings gameSettings;
final GlobalSettings globalSettings;
List<int> shuffledColors = []; List<int> shuffledColors = [];
bool isRunning = false; bool isRunning = false;
bool isFinished = false; bool isFinished = false;
...@@ -19,7 +21,8 @@ class Game { ...@@ -19,7 +21,8 @@ class Game {
Game({ Game({
required this.board, required this.board,
required this.settings, required this.gameSettings,
required this.globalSettings,
required this.shuffledColors, required this.shuffledColors,
this.isRunning = false, this.isRunning = false,
this.isFinished = false, this.isFinished = false,
...@@ -31,18 +34,24 @@ class Game { ...@@ -31,18 +34,24 @@ class Game {
factory Game.createNull() { factory Game.createNull() {
return Game( return Game(
board: GameBoard.createNull(), board: GameBoard.createNull(),
settings: GameSettings.createDefault(), gameSettings: GameSettings.createDefault(),
shuffledColors: shuffleColors(DefaultGameSettings.defaultColorsThemeValue), globalSettings: GlobalSettings.createDefault(),
shuffledColors: shuffleColors(DefaultGlobalSettings.defaultColorsThemeValue),
); );
} }
factory Game.createNew({GameSettings? gameSettings}) { factory Game.createNew({
GameSettings settings = gameSettings ?? GameSettings.createDefault(); GameSettings? gameSettings,
GlobalSettings? globalSettings,
}) {
GameSettings newGameSettings = gameSettings ?? GameSettings.createDefault();
GlobalSettings newGlobalSettings = globalSettings ?? GlobalSettings.createDefault();
return Game( return Game(
board: GameBoard.createRandom(settings), board: GameBoard.createRandom(newGameSettings),
settings: settings, gameSettings: newGameSettings,
shuffledColors: shuffleColors(settings.colorsTheme), globalSettings: newGlobalSettings,
shuffledColors: shuffleColors(newGlobalSettings.colorsTheme),
isRunning: true, isRunning: true,
); );
} }
...@@ -100,8 +109,8 @@ class Game { ...@@ -100,8 +109,8 @@ class Game {
final CellLocation referenceCellLocation, final CellLocation referenceCellLocation,
List<CellLocation> siblingCells, List<CellLocation> siblingCells,
) { ) {
final int boardSizeHorizontal = this.settings.boardSize; final int boardSizeHorizontal = this.gameSettings.boardSize;
final int boardSizeVertical = this.settings.boardSize; final int boardSizeVertical = this.gameSettings.boardSize;
final int? referenceValue = this.getCellValue(referenceCellLocation); final int? referenceValue = this.getCellValue(referenceCellLocation);
...@@ -137,8 +146,8 @@ class Game { ...@@ -137,8 +146,8 @@ class Game {
} }
List<List<CellLocation>> getAvailableBlocks(final Game game) { List<List<CellLocation>> getAvailableBlocks(final Game game) {
final int boardSizeHorizontal = game.settings.boardSize; final int boardSizeHorizontal = game.gameSettings.boardSize;
final int boardSizeVertical = game.settings.boardSize; final int boardSizeVertical = game.gameSettings.boardSize;
final List<List<CellLocation>> blocks = []; final List<List<CellLocation>> blocks = [];
...@@ -170,8 +179,8 @@ class Game { ...@@ -170,8 +179,8 @@ class Game {
} }
bool hasAtLeastOneAvailableBlock() { bool hasAtLeastOneAvailableBlock() {
final int boardSizeHorizontal = this.settings.boardSize; final int boardSizeHorizontal = this.gameSettings.boardSize;
final int boardSizeVertical = this.settings.boardSize; final int boardSizeVertical = this.gameSettings.boardSize;
for (int row = 0; row < boardSizeVertical; row++) { for (int row = 0; row < boardSizeVertical; row++) {
for (int col = 0; col < boardSizeHorizontal; col++) { for (int col = 0; col < boardSizeHorizontal; col++) {
...@@ -192,9 +201,9 @@ class Game { ...@@ -192,9 +201,9 @@ class Game {
bool isInBoard(CellLocation cell) { bool isInBoard(CellLocation cell) {
if (cell.row > 0 && if (cell.row > 0 &&
cell.row < this.settings.boardSize && cell.row < this.gameSettings.boardSize &&
cell.col > 0 && cell.col > 0 &&
cell.col < this.settings.boardSize) { cell.col < this.gameSettings.boardSize) {
return true; return true;
} }
return false; return false;
...@@ -208,14 +217,14 @@ class Game { ...@@ -208,14 +217,14 @@ class Game {
final List<int> values = []; final List<int> values = [];
// All eligible values (twice) // All eligible values (twice)
final int maxValue = this.settings.colorsCount; final int maxValue = this.gameSettings.colorsCount;
for (int i = 1; i <= maxValue; i++) { for (int i = 1; i <= maxValue; i++) {
values.add(i); values.add(i);
values.add(i); values.add(i);
} }
// Add values of current col (twice) // Add values of current col (twice)
for (int r = 0; r <= this.settings.boardSize; r++) { for (int r = 0; r <= this.gameSettings.boardSize; r++) {
if (this.isInBoard(CellLocation.go(r, col))) { if (this.isInBoard(CellLocation.go(r, col))) {
final int? value = this.getCellValue(CellLocation.go(r, col)); final int? value = this.getCellValue(CellLocation.go(r, col));
if (value != null) { if (value != null) {
...@@ -228,12 +237,12 @@ class Game { ...@@ -228,12 +237,12 @@ class Game {
// Add values of sibling cols (twice for top rows) // Add values of sibling cols (twice for top rows)
for (int deltaCol = -1; deltaCol <= 1; deltaCol++) { for (int deltaCol = -1; deltaCol <= 1; deltaCol++) {
final int c = col + deltaCol; final int c = col + deltaCol;
for (int r = 0; r < this.settings.boardSize; r++) { for (int r = 0; r < this.gameSettings.boardSize; r++) {
if (this.isInBoard(CellLocation.go(r, c))) { if (this.isInBoard(CellLocation.go(r, c))) {
final int? value = this.getCellValue(CellLocation.go(r, c)); final int? value = this.getCellValue(CellLocation.go(r, c));
if (value != null) { if (value != null) {
values.add(value); values.add(value);
if (row < this.settings.boardSize / 3) { if (row < this.gameSettings.boardSize / 3) {
values.add(value); values.add(value);
} }
} }
...@@ -263,7 +272,8 @@ class Game { ...@@ -263,7 +272,8 @@ class Game {
print(''); print('');
print('## Current game dump:'); print('## Current game dump:');
print(''); print('');
this.settings.dump(); this.gameSettings.dump();
this.globalSettings.dump();
print(''); print('');
this.board.dump(); this.board.dump();
print(''); print('');
...@@ -284,7 +294,8 @@ class Game { ...@@ -284,7 +294,8 @@ class Game {
Map<String, dynamic>? toJson() { Map<String, dynamic>? toJson() {
return <String, dynamic>{ return <String, dynamic>{
'board': this.board.toJson(), 'board': this.board.toJson(),
'settings': this.settings.toJson(), 'gameSettings': this.gameSettings.toJson(),
'globalSettings': this.globalSettings.toJson(),
'shuffledColors': this.shuffledColors, 'shuffledColors': this.shuffledColors,
'isRunning': this.isRunning, 'isRunning': this.isRunning,
'isFinished': this.isFinished, 'isFinished': this.isFinished,
......
import 'dart:math'; import 'dart:math';
import 'package:jeweled/models/game_cell.dart'; import 'package:jeweled/models/game_cell.dart';
import 'package:jeweled/models/game_settings.dart'; import 'package:jeweled/models/settings_game.dart';
class GameBoard { class GameBoard {
final List<List<GameCell>> cells; final List<List<GameCell>> cells;
......
...@@ -3,12 +3,10 @@ import 'package:jeweled/config/default_game_settings.dart'; ...@@ -3,12 +3,10 @@ import 'package:jeweled/config/default_game_settings.dart';
class GameSettings { class GameSettings {
final int boardSize; final int boardSize;
final int colorsCount; final int colorsCount;
final int colorsTheme;
GameSettings({ GameSettings({
required this.boardSize, required this.boardSize,
required this.colorsCount, required this.colorsCount,
required this.colorsTheme,
}); });
static int getBoardSizeValueFromUnsafe(int size) { static int getBoardSizeValueFromUnsafe(int size) {
...@@ -27,19 +25,10 @@ class GameSettings { ...@@ -27,19 +25,10 @@ class GameSettings {
return DefaultGameSettings.defaultColorsCountValue; return DefaultGameSettings.defaultColorsCountValue;
} }
static int getColorsThemeValueFromUnsafe(int colorsTheme) {
if (DefaultGameSettings.allowedColorsThemeValues.contains(colorsTheme)) {
return colorsTheme;
}
return DefaultGameSettings.defaultColorsThemeValue;
}
factory GameSettings.createDefault() { factory GameSettings.createDefault() {
return GameSettings( return GameSettings(
boardSize: DefaultGameSettings.defaultBoardSizeValue, boardSize: DefaultGameSettings.defaultBoardSizeValue,
colorsCount: DefaultGameSettings.defaultColorsCountValue, colorsCount: DefaultGameSettings.defaultColorsCountValue,
colorsTheme: DefaultGameSettings.defaultColorsThemeValue,
); );
} }
...@@ -47,7 +36,6 @@ class GameSettings { ...@@ -47,7 +36,6 @@ class GameSettings {
print('Settings: '); print('Settings: ');
print(' boardSize: ' + boardSize.toString()); print(' boardSize: ' + boardSize.toString());
print(' colorsCount: ' + colorsCount.toString()); print(' colorsCount: ' + colorsCount.toString());
print(' colorsTheme: ' + colorsTheme.toString());
} }
String toString() { String toString() {
...@@ -58,7 +46,6 @@ class GameSettings { ...@@ -58,7 +46,6 @@ class GameSettings {
return <String, dynamic>{ return <String, dynamic>{
'boardSize': this.boardSize, 'boardSize': this.boardSize,
'colorsCount': this.colorsCount, 'colorsCount': this.colorsCount,
'colorsTheme': this.colorsTheme,
}; };
} }
} }
import 'package:jeweled/config/default_global_settings.dart';
class GlobalSettings {
final int colorsTheme;
GlobalSettings({
required this.colorsTheme,
});
static int getColorsThemeValueFromUnsafe(int colorsTheme) {
if (DefaultGlobalSettings.allowedColorsThemeValues.contains(colorsTheme)) {
return colorsTheme;
}
return DefaultGlobalSettings.defaultColorsThemeValue;
}
factory GlobalSettings.createDefault() {
return GlobalSettings(
colorsTheme: DefaultGlobalSettings.defaultColorsThemeValue,
);
}
void dump() {
print('Settings: ');
print(' colorsTheme: ' + colorsTheme.toString());
}
String toString() {
return 'GlobalSettings(' + this.toJson().toString() + ')';
}
Map<String, dynamic>? toJson() {
return <String, dynamic>{
'colorsTheme': this.colorsTheme,
};
}
}
...@@ -16,8 +16,8 @@ class GameBoardPainter extends CustomPainter { ...@@ -16,8 +16,8 @@ class GameBoardPainter extends CustomPainter {
void paint(Canvas canvas, Size size) { void paint(Canvas canvas, Size size) {
final double canvasSize = min(size.width, size.height); final double canvasSize = min(size.width, size.height);
final int cellsCountHorizontal = game.settings.boardSize; final int cellsCountHorizontal = game.gameSettings.boardSize;
final int cellsCountVertical = game.settings.boardSize; final int cellsCountVertical = game.gameSettings.boardSize;
final double cellSize = canvasSize / max(cellsCountHorizontal, cellsCountVertical); final double cellSize = canvasSize / max(cellsCountHorizontal, cellsCountVertical);
...@@ -33,7 +33,8 @@ class GameBoardPainter extends CustomPainter { ...@@ -33,7 +33,8 @@ class GameBoardPainter extends CustomPainter {
final CellLocation cellLocation = CellLocation.go(row, col); final CellLocation cellLocation = CellLocation.go(row, col);
final int? cellValue = game.getCellValueShuffled(cellLocation); final int? cellValue = game.getCellValueShuffled(cellLocation);
if (cellValue != null) { if (cellValue != null) {
final int colorCode = ColorTheme.getColorCode(cellValue, game.settings.colorsTheme); final int colorCode =
ColorTheme.getColorCode(cellValue, game.globalSettings.colorsTheme);
final Animation<double>? translation = this.animations[row][col]; final Animation<double>? translation = this.animations[row][col];
final double y = yOrigin + (translation?.value ?? 0) * cellSize; final double y = yOrigin + (translation?.value ?? 0) * cellSize;
......
...@@ -3,7 +3,8 @@ import 'dart:math'; ...@@ -3,7 +3,8 @@ import 'dart:math';
import 'package:flutter/material.dart'; import 'package:flutter/material.dart';
import 'package:jeweled/config/default_game_settings.dart'; import 'package:jeweled/config/default_game_settings.dart';
import 'package:jeweled/models/game_settings.dart'; import 'package:jeweled/models/settings_game.dart';
import 'package:jeweled/models/settings_global.dart';
import 'package:jeweled/utils/color_extensions.dart'; import 'package:jeweled/utils/color_extensions.dart';
import 'package:jeweled/utils/color_theme.dart'; import 'package:jeweled/utils/color_theme.dart';
...@@ -13,12 +14,14 @@ class ParameterPainter extends CustomPainter { ...@@ -13,12 +14,14 @@ class ParameterPainter extends CustomPainter {
required this.value, required this.value,
required this.isSelected, required this.isSelected,
required this.gameSettings, required this.gameSettings,
required this.globalSettings,
}); });
final String code; final String code;
final int value; final int value;
final bool isSelected; final bool isSelected;
final GameSettings gameSettings; final GameSettings gameSettings;
final GlobalSettings globalSettings;
@override @override
void paint(Canvas canvas, Size size) { void paint(Canvas canvas, Size size) {
...@@ -128,7 +131,7 @@ class ParameterPainter extends CustomPainter { ...@@ -128,7 +131,7 @@ class ParameterPainter extends CustomPainter {
final Offset bottomRight = topLeft + Offset(cellSize, cellSize); final Offset bottomRight = topLeft + Offset(cellSize, cellSize);
final squareColor = final squareColor =
Color(ColorTheme.getColorCode(col + row * gridWidth, gameSettings.colorsTheme)); Color(ColorTheme.getColorCode(col + row * gridWidth, globalSettings.colorsTheme));
paint.color = squareColor; paint.color = squareColor;
paint.style = PaintingStyle.fill; paint.style = PaintingStyle.fill;
...@@ -194,7 +197,8 @@ class ParameterPainter extends CustomPainter { ...@@ -194,7 +197,8 @@ class ParameterPainter extends CustomPainter {
final Offset bottomRight = topLeft + Offset(width, width); final Offset bottomRight = topLeft + Offset(width, width);
final squareColor = Color(ColorTheme.getColorCode(colorIndex, gameSettings.colorsTheme)); final squareColor =
Color(ColorTheme.getColorCode(colorIndex, globalSettings.colorsTheme));
paint.color = squareColor; paint.color = squareColor;
paint.style = PaintingStyle.fill; paint.style = PaintingStyle.fill;
canvas.drawRect(Rect.fromPoints(topLeft, bottomRight), paint); canvas.drawRect(Rect.fromPoints(topLeft, bottomRight), paint);
......
...@@ -57,7 +57,7 @@ class _GameBoard extends State<GameBoard> with TickerProviderStateMixin { ...@@ -57,7 +57,7 @@ class _GameBoard extends State<GameBoard> with TickerProviderStateMixin {
if (status == AnimationStatus.completed) { if (status == AnimationStatus.completed) {
gameCubit.postAnimate(); gameCubit.postAnimate();
resetAnimations(currentGame.settings.boardSize); resetAnimations(currentGame.gameSettings.boardSize);
setState(() {}); setState(() {});
controller.dispose(); controller.dispose();
...@@ -66,9 +66,9 @@ class _GameBoard extends State<GameBoard> with TickerProviderStateMixin { ...@@ -66,9 +66,9 @@ class _GameBoard extends State<GameBoard> with TickerProviderStateMixin {
// Count translation length for each cell to move // Count translation length for each cell to move
final List<List<int>> stepsDownCounts = List.generate( final List<List<int>> stepsDownCounts = List.generate(
currentGame.settings.boardSize, currentGame.gameSettings.boardSize,
(i) => List.generate( (i) => List.generate(
currentGame.settings.boardSize, currentGame.gameSettings.boardSize,
(i) => 0, (i) => 0,
), ),
); );
...@@ -105,7 +105,7 @@ class _GameBoard extends State<GameBoard> with TickerProviderStateMixin { ...@@ -105,7 +105,7 @@ class _GameBoard extends State<GameBoard> with TickerProviderStateMixin {
final Game currentGame = gameState.currentGame; final Game currentGame = gameState.currentGame;
if (this.animations.length == 0) { if (this.animations.length == 0) {
resetAnimations(currentGame.settings.boardSize); resetAnimations(currentGame.gameSettings.boardSize);
} }
return GestureDetector( return GestureDetector(
...@@ -122,8 +122,8 @@ class _GameBoard extends State<GameBoard> with TickerProviderStateMixin { ...@@ -122,8 +122,8 @@ class _GameBoard extends State<GameBoard> with TickerProviderStateMixin {
if (!animationInProgress) { if (!animationInProgress) {
final double xTap = details.localPosition.dx; final double xTap = details.localPosition.dx;
final double yTap = details.localPosition.dy; final double yTap = details.localPosition.dy;
final int col = xTap ~/ (displayWidth / currentGame.settings.boardSize); final int col = xTap ~/ (displayWidth / currentGame.gameSettings.boardSize);
final int row = yTap ~/ (displayWidth / currentGame.settings.boardSize); final int row = yTap ~/ (displayWidth / currentGame.gameSettings.boardSize);
final GameCubit gameCubit = BlocProvider.of<GameCubit>(context); final GameCubit gameCubit = BlocProvider.of<GameCubit>(context);
animateCells(gameCubit.tapOnCell(CellLocation.go(row, col))); animateCells(gameCubit.tapOnCell(CellLocation.go(row, col)));
......
...@@ -60,7 +60,7 @@ class GameTopIndicatorWidget extends StatelessWidget { ...@@ -60,7 +60,7 @@ class GameTopIndicatorWidget extends StatelessWidget {
child: Icon(UniconsSolid.refresh), child: Icon(UniconsSolid.refresh),
onPressed: () { onPressed: () {
final GameCubit gameCubit = BlocProvider.of<GameCubit>(context); final GameCubit gameCubit = BlocProvider.of<GameCubit>(context);
gameCubit.shuffleColors(currentGame.settings.colorsTheme); gameCubit.shuffleColors(currentGame.globalSettings.colorsTheme);
}, },
) )
], ],
......
...@@ -2,43 +2,47 @@ import 'package:flutter/material.dart'; ...@@ -2,43 +2,47 @@ import 'package:flutter/material.dart';
import 'package:flutter_bloc/flutter_bloc.dart'; import 'package:flutter_bloc/flutter_bloc.dart';
import 'package:jeweled/config/default_game_settings.dart'; import 'package:jeweled/config/default_game_settings.dart';
import 'package:jeweled/config/default_global_settings.dart';
import 'package:jeweled/cubit/game_cubit.dart'; import 'package:jeweled/cubit/game_cubit.dart';
import 'package:jeweled/cubit/settings_cubit.dart'; import 'package:jeweled/cubit/settings_game_cubit.dart';
import 'package:jeweled/models/game_settings.dart'; import 'package:jeweled/cubit/settings_global_cubit.dart';
import 'package:jeweled/ui/painters/parameter_painter.dart'; import 'package:jeweled/ui/painters/parameter_painter.dart';
class Parameters extends StatelessWidget { class Parameters extends StatelessWidget {
const Parameters({super.key}); const Parameters({super.key});
@override
Widget build(BuildContext context) {
final double displayWidth = MediaQuery.of(context).size.width;
final double separatorHeight = 8.0; final double separatorHeight = 8.0;
return BlocBuilder<SettingsCubit, SettingsState>( List<Widget> buildParametersLine({
builder: (BuildContext context, SettingsState settingsState) { required String code,
final GameCubit gameCubit = BlocProvider.of<GameCubit>(context); required bool isGlobal,
final SettingsCubit settingsCubit = BlocProvider.of<SettingsCubit>(context); }) {
final List<Widget> parameterButtons = [];
final List<Widget> lines = [ final List<int> availableValues = isGlobal
SizedBox(height: separatorHeight), ? DefaultGlobalSettings.getAvailableValues(code)
]; : DefaultGameSettings.getAvailableValues(code);
DefaultGameSettings.availableParameters.forEach((code) { availableValues.forEach((value) {
final List<int> availableValues = DefaultGameSettings.getAvailableValues(code); final Widget parameterButton = BlocBuilder<GameSettingsCubit, GameSettingsState>(
builder: (BuildContext context, GameSettingsState gameSettingsState) {
return BlocBuilder<GlobalSettingsCubit, GlobalSettingsState>(
builder: (BuildContext context, GlobalSettingsState globalSettingsState) {
final GameSettingsCubit gameSettingsCubit =
BlocProvider.of<GameSettingsCubit>(context);
final GlobalSettingsCubit globalSettingsCubit =
BlocProvider.of<GlobalSettingsCubit>(context);
final int currentValue = isGlobal
? globalSettingsCubit.getParameterValue(code)
: gameSettingsCubit.getParameterValue(code);
if (availableValues.length > 1) { final bool isActive = (value == currentValue);
final int currentValue = settingsCubit.getParameterValue(code);
final double displayWidth = MediaQuery.of(context).size.width;
final double itemWidth = displayWidth / availableValues.length - 25; final double itemWidth = displayWidth / availableValues.length - 25;
final List<Widget> parameterButtons = []; return TextButton(
availableValues.forEach((value) {
final bool isActive = (value == currentValue);
final Widget parameterButton = TextButton(
child: Container( child: Container(
margin: EdgeInsets.all(0), margin: EdgeInsets.all(0),
padding: EdgeInsets.all(0), padding: EdgeInsets.all(0),
...@@ -49,34 +53,63 @@ class Parameters extends StatelessWidget { ...@@ -49,34 +53,63 @@ class Parameters extends StatelessWidget {
code: code, code: code,
value: value, value: value,
isSelected: isActive, isSelected: isActive,
gameSettings: settingsState.settings, gameSettings: gameSettingsState.settings,
globalSettings: globalSettingsState.settings,
), ),
isComplex: true, isComplex: true,
), ),
), ),
onPressed: () => settingsCubit.setParameterValue(code, value), onPressed: () => isGlobal
? globalSettingsCubit.setParameterValue(code, value)
: gameSettingsCubit.setParameterValue(code, value),
);
},
);
},
); );
parameterButtons.add(parameterButton); parameterButtons.add(parameterButton);
}); });
return parameterButtons;
}
@override
Widget build(BuildContext context) {
final List<Widget> lines = [];
// Game settings
DefaultGameSettings.availableParameters.forEach((code) {
lines.add(Row(
mainAxisAlignment: MainAxisAlignment.spaceBetween,
children: buildParametersLine(
code: code,
isGlobal: false,
),
));
lines.add(SizedBox(height: separatorHeight));
});
// Global settings
DefaultGlobalSettings.availableParameters.forEach((code) {
lines.add(Row( lines.add(Row(
mainAxisAlignment: MainAxisAlignment.spaceBetween, mainAxisAlignment: MainAxisAlignment.spaceBetween,
children: parameterButtons, children: buildParametersLine(
code: code,
isGlobal: true,
),
)); ));
lines.add(SizedBox(height: separatorHeight)); lines.add(SizedBox(height: separatorHeight));
}
}); });
lines.add(SizedBox(height: separatorHeight)); lines.add(SizedBox(height: separatorHeight));
lines.add(buildStartNewGameButton(gameCubit, settingsState.settings)); lines.add(buildStartNewGameButton());
return Column( return Column(
children: lines, children: lines,
); );
},
);
} }
static Image buildImageWidget(String imageAssetCode) { static Image buildImageWidget(String imageAssetCode) {
...@@ -103,10 +136,16 @@ class Parameters extends StatelessWidget { ...@@ -103,10 +136,16 @@ class Parameters extends StatelessWidget {
); );
} }
static Container buildStartNewGameButton(GameCubit gameCubit, GameSettings settings) { static Widget buildStartNewGameButton() {
const double blockMargin = 3.0; const double blockMargin = 3.0;
const double blockPadding = 2.0; const double blockPadding = 2.0;
return BlocBuilder<GameSettingsCubit, GameSettingsState>(
builder: (BuildContext context, GameSettingsState gameSettingsState) {
return BlocBuilder<GlobalSettingsCubit, GlobalSettingsState>(
builder: (BuildContext context, GlobalSettingsState globalSettingsState) {
final GameCubit gameCubit = BlocProvider.of<GameCubit>(context);
return Container( return Container(
margin: EdgeInsets.all(blockMargin), margin: EdgeInsets.all(blockMargin),
padding: EdgeInsets.all(blockPadding), padding: EdgeInsets.all(blockPadding),
...@@ -120,7 +159,10 @@ class Parameters extends StatelessWidget { ...@@ -120,7 +159,10 @@ class Parameters extends StatelessWidget {
children: [ children: [
TextButton( TextButton(
child: buildImageContainerWidget('button_start'), child: buildImageContainerWidget('button_start'),
onPressed: () => gameCubit.startNewGame(settings), onPressed: () => gameCubit.startNewGame(
gameSettings: gameSettingsState.settings,
globalSettings: globalSettingsState.settings,
),
), ),
], ],
), ),
...@@ -130,5 +172,9 @@ class Parameters extends StatelessWidget { ...@@ -130,5 +172,9 @@ class Parameters extends StatelessWidget {
], ],
), ),
); );
},
);
},
);
} }
} }
0% Loading or .
You are about to add 0 people to the discussion. Proceed with caution.
Please register or to comment