Réorganisation du dossier

This commit is contained in:
2026-03-29 18:17:36 +02:00
parent 75650d7062
commit 8283bc0475
69 changed files with 1423 additions and 1035 deletions
+15 -1
View File
@@ -1 +1,15 @@
/build
*.iml
.gradle
/local.properties
/.idea/caches
/.idea/libraries
/.idea/modules.xml
/.idea/workspace.xml
/.idea/navEditor.xml
/.idea/assetWizardSettings.xml
.DS_Store
/build
/captures
.externalNativeBuild
.cxx
local.properties
+3
View File
@@ -0,0 +1,3 @@
# Default ignored files
/shelf/
/workspace.xml
Generated
+1
View File
@@ -0,0 +1 @@
Real Chuzzle
+6
View File
@@ -0,0 +1,6 @@
<?xml version="1.0" encoding="UTF-8"?>
<project version="4">
<component name="AndroidProjectSystem">
<option name="providerId" value="com.android.tools.idea.GradleProjectSystem" />
</component>
</project>
+6
View File
@@ -0,0 +1,6 @@
<?xml version="1.0" encoding="UTF-8"?>
<project version="4">
<component name="CompilerConfiguration">
<bytecodeTargetLevel target="21" />
</component>
</project>
+26
View File
@@ -0,0 +1,26 @@
<?xml version="1.0" encoding="UTF-8"?>
<project version="4">
<component name="deploymentTargetSelector">
<selectionStates>
<SelectionState runConfigName="app">
<option name="selectionMode" value="DROPDOWN" />
<DropdownSelection timestamp="2026-03-27T18:49:55.757608200Z">
<Target type="DEFAULT_BOOT">
<handle>
<DeviceId pluginId="LocalEmulator" identifier="path=C:\Users\tayzi\.android\avd\Medium_Phone.avd" />
</handle>
</Target>
</DropdownSelection>
<DialogSelection>
<targets>
<Target type="DEFAULT_BOOT">
<handle>
<DeviceId pluginId="LocalEmulator" identifier="path=C:\Users\tayzi\.android\avd\Medium_Phone.avd" />
</handle>
</Target>
</targets>
</DialogSelection>
</SelectionState>
</selectionStates>
</component>
</project>
+13
View File
@@ -0,0 +1,13 @@
<?xml version="1.0" encoding="UTF-8"?>
<project version="4">
<component name="DeviceTable">
<option name="columnSorters">
<list>
<ColumnSorterState>
<option name="column" value="Name" />
<option name="order" value="ASCENDING" />
</ColumnSorterState>
</list>
</option>
</component>
</project>
+19
View File
@@ -0,0 +1,19 @@
<?xml version="1.0" encoding="UTF-8"?>
<project version="4">
<component name="GradleMigrationSettings" migrationVersion="1" />
<component name="GradleSettings">
<option name="linkedExternalProjectsSettings">
<GradleProjectSettings>
<option name="testRunner" value="CHOOSE_PER_TEST" />
<option name="externalProjectPath" value="$PROJECT_DIR$" />
<option name="gradleJvm" value="#GRADLE_LOCAL_JAVA_HOME" />
<option name="modules">
<set>
<option value="$PROJECT_DIR$" />
<option value="$PROJECT_DIR$/app" />
</set>
</option>
</GradleProjectSettings>
</option>
</component>
</project>
+10
View File
@@ -0,0 +1,10 @@
<?xml version="1.0" encoding="UTF-8"?>
<project version="4">
<component name="ProjectMigrations">
<option name="MigrateToGradleLocalJavaHome">
<set>
<option value="$PROJECT_DIR$" />
</set>
</option>
</component>
</project>
+9
View File
@@ -0,0 +1,9 @@
<project version="4">
<component name="ExternalStorageConfigurationManager" enabled="true" />
<component name="ProjectRootManager" version="2" languageLevel="JDK_21" default="true" project-jdk-name="jbr-21" project-jdk-type="JavaSDK">
<output url="file://$PROJECT_DIR$/build/classes" />
</component>
<component name="ProjectType">
<option name="id" value="Android" />
</component>
</project>
+17
View File
@@ -0,0 +1,17 @@
<?xml version="1.0" encoding="UTF-8"?>
<project version="4">
<component name="RunConfigurationProducerService">
<option name="ignoredProducers">
<set>
<option value="com.intellij.execution.junit.AbstractAllInDirectoryConfigurationProducer" />
<option value="com.intellij.execution.junit.AllInPackageConfigurationProducer" />
<option value="com.intellij.execution.junit.PatternConfigurationProducer" />
<option value="com.intellij.execution.junit.TestInClassConfigurationProducer" />
<option value="com.intellij.execution.junit.UniqueIdConfigurationProducer" />
<option value="com.intellij.execution.junit.testDiscovery.JUnitTestDiscoveryConfigurationProducer" />
<option value="org.jetbrains.kotlin.idea.junit.KotlinJUnitRunConfigurationProducer" />
<option value="org.jetbrains.kotlin.idea.junit.KotlinPatternConfigurationProducer" />
</set>
</option>
</component>
</project>
+1
View File
@@ -0,0 +1 @@
/build
+42
View File
@@ -0,0 +1,42 @@
plugins {
alias(libs.plugins.android.application)
}
android {
namespace = "sae.chuzzle"
compileSdk {
version = release(36)
}
defaultConfig {
applicationId = "sae.chuzzle"
minSdk = 24
targetSdk = 36
versionCode = 1
versionName = "1.0"
testInstrumentationRunner = "androidx.test.runner.AndroidJUnitRunner"
}
buildTypes {
release {
isMinifyEnabled = false
proguardFiles(
getDefaultProguardFile("proguard-android-optimize.txt"),
"proguard-rules.pro"
)
}
}
compileOptions {
sourceCompatibility = JavaVersion.VERSION_11
targetCompatibility = JavaVersion.VERSION_11
}
}
dependencies {
implementation(libs.activity)
testImplementation(libs.junit)
androidTestImplementation(libs.ext.junit)
androidTestImplementation(libs.espresso.core)
}
View File
@@ -1,41 +1,41 @@
<?xml version="1.0" encoding="utf-8"?>
<manifest xmlns:android="http://schemas.android.com/apk/res/android"
package="sae.chuzzle">
<application
android:allowBackup="true"
android:label="Chuzzle"
android:theme="@android:style/Theme.Light.NoTitleBar">
<!-- Point d'entrée : le menu principal -->
<activity android:name=".MenuActivity"
android:exported="true">
<intent-filter>
<action android:name="android.intent.action.MAIN"/>
<category android:name="android.intent.category.LAUNCHER"/>
</intent-filter>
</activity>
<!-- Partie avec graine : retour arrière = MenuActivity -->
<activity
android:name=".SeedActivity"
android:parentActivityName=".MenuActivity"/>
<!-- Options : retour arrière = MenuActivity -->
<activity
android:name=".OptionsActivity"
android:parentActivityName=".MenuActivity"/>
<!-- Jeu : retour arrière = MenuActivity -->
<activity
android:name=".MainActivity"
android:parentActivityName=".MenuActivity"/>
<!-- Fin de partie : retour arrière = MenuActivity -->
<activity
android:name=".FinPartieActivity"
android:parentActivityName=".MenuActivity"/>
</application>
<?xml version="1.0" encoding="utf-8"?>
<manifest xmlns:android="http://schemas.android.com/apk/res/android"
package="sae.chuzzle">
<application
android:allowBackup="true"
android:label="Chuzzle"
android:theme="@android:style/Theme.Light.NoTitleBar">
<!-- Point d'entrée : le menu principal -->
<activity android:name=".MenuActivity"
android:exported="true">
<intent-filter>
<action android:name="android.intent.action.MAIN"/>
<category android:name="android.intent.category.LAUNCHER"/>
</intent-filter>
</activity>
<!-- Partie avec graine : retour arrière = MenuActivity -->
<activity
android:name=".SeedActivity"
android:parentActivityName=".MenuActivity"/>
<!-- Options : retour arrière = MenuActivity -->
<activity
android:name=".OptionsActivity"
android:parentActivityName=".MenuActivity"/>
<!-- Jeu : retour arrière = MenuActivity -->
<activity
android:name=".MainActivity"
android:parentActivityName=".MenuActivity"/>
<!-- Fin de partie : retour arrière = MenuActivity -->
<activity
android:name=".FinPartieActivity"
android:parentActivityName=".MenuActivity"/>
</application>
</manifest>
@@ -1,209 +1,209 @@
package sae.chuzzle;
import android.app.Activity;
import android.os.Bundle;
import android.view.View;
import android.widget.Button;
import android.widget.TextView;
import android.widget.Toast;
public class Controleur {
private final Activity activite;
private final EtatJeu etatJeu;
private final VueGrille vueGrille;
private final long graine;
private final TextView tvScore;
private final TextView tvCoups;
// Hard Mode logic
private final boolean hardMode;
private GestionnaireObjectifs gestionnaireObjectifs;
private Objectif objectifActuel;
private TextView tvObjectif;
private TextView tvNbObjectifs;
private TextView tvCles;
private Button btnReinitialisationObjectif;
private View layoutCles;
public Controleur(Activity activite, EtatJeu etatJeu, VueGrille vueGrille,
long graine, TextView tvScore, TextView tvCoups,
boolean hardMode) {
this.activite = activite;
this.etatJeu = etatJeu;
this.vueGrille = vueGrille;
this.graine = graine;
this.tvScore = tvScore;
this.tvCoups = tvCoups;
this.hardMode = hardMode;
if (hardMode) {
this.gestionnaireObjectifs = new GestionnaireObjectifs(graine);
this.tvObjectif = activite.findViewById(R.id.tvObjectif);
this.tvNbObjectifs = activite.findViewById(R.id.tvNbObjectifs);
this.tvCles = activite.findViewById(R.id.tvCles);
this.layoutCles = activite.findViewById(R.id.layoutCles);
this.btnReinitialisationObjectif = activite.findViewById(R.id.btnReinitialisationObjectif);
if (tvObjectif != null) tvObjectif.setVisibility(View.VISIBLE);
if (tvNbObjectifs != null) tvNbObjectifs.setVisibility(View.VISIBLE);
if (layoutCles != null) layoutCles.setVisibility(View.VISIBLE);
if (btnReinitialisationObjectif != null) {
btnReinitialisationObjectif.setOnClickListener(v -> reinitialiserObjectif());
}
}
rafraichirAffichage();
}
/**
* Initialise l'objectif au début de la partie ou lors de la restauration.
*/
public void initialiserObjectif(Bundle savedState) {
if (!hardMode) return;
gestionnaireObjectifs.restaurer(savedState);
objectifActuel = Objectif.restaurer(savedState);
if (objectifActuel == null) {
objectifActuel = gestionnaireObjectifs.genererObjectif();
}
rafraichirAffichage();
}
/**
* Gère la validation d'un coup réussi (mise à jour objectif, score, affichage).
* Centralise la logique pour être appelé par le bouton ET par le tactile.
*/
public void gererFinDeCoup() {
// 1 clé tous les 5 coups
if (hardMode && etatJeu.obtenirNbCoups() % 5 == 0) {
gestionnaireObjectifs.ajouterCle();
}
// --- Logique Hard Mode
if (hardMode && objectifActuel != null) {
// 1. Décrémenter les coups de l'objectif
objectifActuel.decrementerCoups();
// 2. Compter les séries de la couleur cible
int[] series = etatJeu.getSeriesParCouleurDernierCoup();
objectifActuel.ajouterSeries(series[objectifActuel.getCouleur()]);
// 3. Vérifier réussite ou échec
if (objectifActuel.estReussi()) {
gestionnaireObjectifs.incrementerReussites();
objectifActuel = gestionnaireObjectifs.genererObjectif();
} else if (objectifActuel.estEchoue()) {
// Plus de coups disponibles et objectif non réussi -> fin de partie immédiate
Toast.makeText(activite, "Objectif échoué !",
Toast.LENGTH_SHORT
).show();
etatJeu.forcerFinDePartie();
}
}
rafraichirAffichage();
verifierFinDePartie();
}
/**
* Tente de réinitialiser l'objectif en cours en consommant 3 clés.
* Affiche un Toast si le joueur n'a pas assez de clés.
*/
public void reinitialiserObjectif() {
if (!hardMode || gestionnaireObjectifs == null) return;
if (gestionnaireObjectifs.consommerCles()) {
objectifActuel = gestionnaireObjectifs.genererObjectif();
rafraichirAffichage();
} else {
Toast.makeText(activite, "Pas assez de clés !", Toast.LENGTH_SHORT).show();
}
}
/**
* Lancer l'écran de fin.
*/
public void verifierFinDePartie() {
int nbARetenir;
if (hardMode) {
nbARetenir = gestionnaireObjectifs.getNbObjectifsRealises();
} else {
nbARetenir = 0;
}
String description;
if (hardMode == true && objectifActuel != null) {
description = objectifActuel.getDescription();
} else {
description = null;
}
if (etatJeu.estTerminee()) {
FinPartieActivity.demarrer(
activite,
etatJeu.obtenirScore(),
etatJeu.obtenirNbCoups(),
graine,
nbARetenir,
description,
etatJeu.obtenirGrille(),
etatJeu.obtenirVerrous()
);
}
}
public void rafraichirAffichage() {
tvScore.setText("Score : " + etatJeu.obtenirScore());
tvCoups.setText("Coups : " + etatJeu.obtenirNbCoups());
vueGrille.definirGrille(etatJeu.obtenirGrille());
vueGrille.definirVerrous(etatJeu.obtenirVerrous());
if (hardMode && objectifActuel != null) {
if (tvObjectif != null){
tvObjectif.setText(objectifActuel.getDescription());
}
if (tvNbObjectifs != null){
tvNbObjectifs.setText("Objectifs réussis : " + gestionnaireObjectifs.getNbObjectifsRealises());
}
int nbCles = gestionnaireObjectifs.getNbCles();
if (tvCles != null) {
tvCles.setText("🗝️ Clés : " + nbCles + " (Max 1)");
}
if (btnReinitialisationObjectif != null) {
// Grisé si 0 clé
float alpha;
if (nbCles >= 1) {
alpha = 1f; // visible
} else {
alpha = 0.4f; // grisé
}
btnReinitialisationObjectif.setAlpha(alpha);
}
}
}
public void sauvegarderEtat(Bundle out) {
if (hardMode) {
gestionnaireObjectifs.sauvegarder(out);
if (objectifActuel != null) {
objectifActuel.sauvegarder(out);
}
}
}
package sae.chuzzle;
import android.app.Activity;
import android.os.Bundle;
import android.view.View;
import android.widget.Button;
import android.widget.TextView;
import android.widget.Toast;
public class Controleur {
private final Activity activite;
private final EtatJeu etatJeu;
private final VueGrille vueGrille;
private final long graine;
private final TextView tvScore;
private final TextView tvCoups;
// Hard Mode logic
private final boolean hardMode;
private GestionnaireObjectifs gestionnaireObjectifs;
private Objectif objectifActuel;
private TextView tvObjectif;
private TextView tvNbObjectifs;
private TextView tvCles;
private Button btnReinitialisationObjectif;
private View layoutCles;
public Controleur(Activity activite, EtatJeu etatJeu, VueGrille vueGrille,
long graine, TextView tvScore, TextView tvCoups,
boolean hardMode) {
this.activite = activite;
this.etatJeu = etatJeu;
this.vueGrille = vueGrille;
this.graine = graine;
this.tvScore = tvScore;
this.tvCoups = tvCoups;
this.hardMode = hardMode;
if (hardMode) {
this.gestionnaireObjectifs = new GestionnaireObjectifs(graine);
this.tvObjectif = activite.findViewById(R.id.tvObjectif);
this.tvNbObjectifs = activite.findViewById(R.id.tvNbObjectifs);
this.tvCles = activite.findViewById(R.id.tvCles);
this.layoutCles = activite.findViewById(R.id.layoutCles);
this.btnReinitialisationObjectif = activite.findViewById(R.id.btnReinitialisationObjectif);
if (tvObjectif != null) tvObjectif.setVisibility(View.VISIBLE);
if (tvNbObjectifs != null) tvNbObjectifs.setVisibility(View.VISIBLE);
if (layoutCles != null) layoutCles.setVisibility(View.VISIBLE);
if (btnReinitialisationObjectif != null) {
btnReinitialisationObjectif.setOnClickListener(v -> reinitialiserObjectif());
}
}
rafraichirAffichage();
}
/**
* Initialise l'objectif au début de la partie ou lors de la restauration.
*/
public void initialiserObjectif(Bundle savedState) {
if (!hardMode) return;
gestionnaireObjectifs.restaurer(savedState);
objectifActuel = Objectif.restaurer(savedState);
if (objectifActuel == null) {
objectifActuel = gestionnaireObjectifs.genererObjectif();
}
rafraichirAffichage();
}
/**
* Gère la validation d'un coup réussi (mise à jour objectif, score, affichage).
* Centralise la logique pour être appelé par le bouton ET par le tactile.
*/
public void gererFinDeCoup() {
// 1 clé tous les 5 coups
if (hardMode && etatJeu.obtenirNbCoups() % 5 == 0) {
gestionnaireObjectifs.ajouterCle();
}
// --- Logique Hard Mode
if (hardMode && objectifActuel != null) {
// 1. Décrémenter les coups de l'objectif
objectifActuel.decrementerCoups();
// 2. Compter les séries de la couleur cible
int[] series = etatJeu.getSeriesParCouleurDernierCoup();
objectifActuel.ajouterSeries(series[objectifActuel.getCouleur()]);
// 3. Vérifier réussite ou échec
if (objectifActuel.estReussi()) {
gestionnaireObjectifs.incrementerReussites();
objectifActuel = gestionnaireObjectifs.genererObjectif();
} else if (objectifActuel.estEchoue()) {
// Plus de coups disponibles et objectif non réussi -> fin de partie immédiate
Toast.makeText(activite, "Objectif échoué !",
Toast.LENGTH_SHORT
).show();
etatJeu.forcerFinDePartie();
}
}
rafraichirAffichage();
verifierFinDePartie();
}
/**
* Tente de réinitialiser l'objectif en cours en consommant 3 clés.
* Affiche un Toast si le joueur n'a pas assez de clés.
*/
public void reinitialiserObjectif() {
if (!hardMode || gestionnaireObjectifs == null) return;
if (gestionnaireObjectifs.consommerCles()) {
objectifActuel = gestionnaireObjectifs.genererObjectif();
rafraichirAffichage();
} else {
Toast.makeText(activite, "Pas assez de clés !", Toast.LENGTH_SHORT).show();
}
}
/**
* Lancer l'écran de fin.
*/
public void verifierFinDePartie() {
int nbARetenir;
if (hardMode) {
nbARetenir = gestionnaireObjectifs.getNbObjectifsRealises();
} else {
nbARetenir = 0;
}
String description;
if (hardMode == true && objectifActuel != null) {
description = objectifActuel.getDescription();
} else {
description = null;
}
if (etatJeu.estTerminee()) {
FinPartieActivity.demarrer(
activite,
etatJeu.obtenirScore(),
etatJeu.obtenirNbCoups(),
graine,
nbARetenir,
description,
etatJeu.obtenirGrille(),
etatJeu.obtenirVerrous()
);
}
}
public void rafraichirAffichage() {
tvScore.setText("Score : " + etatJeu.obtenirScore());
tvCoups.setText("Coups : " + etatJeu.obtenirNbCoups());
vueGrille.definirGrille(etatJeu.obtenirGrille());
vueGrille.definirVerrous(etatJeu.obtenirVerrous());
if (hardMode && objectifActuel != null) {
if (tvObjectif != null){
tvObjectif.setText(objectifActuel.getDescription());
}
if (tvNbObjectifs != null){
tvNbObjectifs.setText("Objectifs réussis : " + gestionnaireObjectifs.getNbObjectifsRealises());
}
int nbCles = gestionnaireObjectifs.getNbCles();
if (tvCles != null) {
tvCles.setText("🗝️ Clés : " + nbCles + " (Max 1)");
}
if (btnReinitialisationObjectif != null) {
// Grisé si 0 clé
float alpha;
if (nbCles >= 1) {
alpha = 1f; // visible
} else {
alpha = 0.4f; // grisé
}
btnReinitialisationObjectif.setAlpha(alpha);
}
}
}
public void sauvegarderEtat(Bundle out) {
if (hardMode) {
gestionnaireObjectifs.sauvegarder(out);
if (objectifActuel != null) {
objectifActuel.sauvegarder(out);
}
}
}
}
File diff suppressed because it is too large Load Diff
@@ -1,102 +1,102 @@
package sae.chuzzle;
import android.os.Bundle;
import java.util.ArrayList;
import java.util.List;
import java.util.Random;
/**
* Gère la génération aléatoire et le comptage des objectifs.
*/
public class GestionnaireObjectifs {
private final Random random;
private int nbObjectifsRealises = 0;
private int nbCles = 0;
public GestionnaireObjectifs(long graine) {
this.random = new Random(graine);
}
/**
* Génère un nouvel objectif en respectant les probabilités de difficulté.
*/
public Objectif genererObjectif() {
List<Objectif> pool = new ArrayList<>();
int totalPoids = 0;
// M (nbCoupsMax) entre 2 et 5.
// N (nbSeriesCible) tel que M - N >= 1 et N <= 3.
for (int m = 2; m <= 5; m++) {
for (int n = 1; n <= m - 1 && n <= 3; n++) {
// Probabilité inversement proportionnelle à la facilité (M-N).
// Plus (M-N) est petit, plus c'est dur.
int diff = m - n;
int poids = diff * diff; // On utilise le carré pour accentuer la différence de probabilité
for (int color = 0; color < 7; color++) {
pool.add(new Objectif(color, n, m, poids));
totalPoids += poids;
}
}
}
if (totalPoids == 0) return null;
int tirage = random.nextInt(totalPoids);
int cumul = 0;
for (Objectif obj : pool) {
cumul += obj.getPoids();
if (tirage < cumul) {
return new Objectif(obj.getCouleur(), obj.getNbSeriesCible(), obj.getNbCoupsMax(), obj.getPoids());
}
}
return pool.get(0);
}
public void incrementerReussites() {
nbObjectifsRealises++;
// 1 clé gagnée tous les 2 objectifs réussis, maximum 1 clés en stock
if (nbObjectifsRealises % 2 == 0) {
ajouterCle();
}
}
public int getNbCles() {
return nbCles;
}
public void ajouterCle() {
// Ajoute une clé maximum 1 en stock
nbCles = Math.min(nbCles + 1, 1);
}
/**
* Consomme 1 clé pour réinitialiser l'objectif.
*/
public boolean consommerCles() {
if (nbCles >= 1) {
nbCles -= 1;
return true;
}
return false;
}
public int getNbObjectifsRealises() {
return nbObjectifsRealises;
}
public void sauvegarder(Bundle out) {
out.putInt("nb_objectifs_total", nbObjectifsRealises);
out.putInt("nb_cles", nbCles);
}
public void restaurer(Bundle in) {
if (in != null) {
nbObjectifsRealises = in.getInt("nb_objectifs_total", 0);
nbCles = in.getInt("nb_cles", 0);
}
}
}
package sae.chuzzle;
import android.os.Bundle;
import java.util.ArrayList;
import java.util.List;
import java.util.Random;
/**
* Gère la génération aléatoire et le comptage des objectifs.
*/
public class GestionnaireObjectifs {
private final Random random;
private int nbObjectifsRealises = 0;
private int nbCles = 0;
public GestionnaireObjectifs(long graine) {
this.random = new Random(graine);
}
/**
* Génère un nouvel objectif en respectant les probabilités de difficulté.
*/
public Objectif genererObjectif() {
List<Objectif> pool = new ArrayList<>();
int totalPoids = 0;
// M (nbCoupsMax) entre 2 et 5.
// N (nbSeriesCible) tel que M - N >= 1 et N <= 3.
for (int m = 2; m <= 5; m++) {
for (int n = 1; n <= m - 1 && n <= 3; n++) {
// Probabilité inversement proportionnelle à la facilité (M-N).
// Plus (M-N) est petit, plus c'est dur.
int diff = m - n;
int poids = diff * diff; // On utilise le carré pour accentuer la différence de probabilité
for (int color = 0; color < 7; color++) {
pool.add(new Objectif(color, n, m, poids));
totalPoids += poids;
}
}
}
if (totalPoids == 0) return null;
int tirage = random.nextInt(totalPoids);
int cumul = 0;
for (Objectif obj : pool) {
cumul += obj.getPoids();
if (tirage < cumul) {
return new Objectif(obj.getCouleur(), obj.getNbSeriesCible(), obj.getNbCoupsMax(), obj.getPoids());
}
}
return pool.get(0);
}
public void incrementerReussites() {
nbObjectifsRealises++;
// 1 clé gagnée tous les 2 objectifs réussis, maximum 1 clés en stock
if (nbObjectifsRealises % 2 == 0) {
ajouterCle();
}
}
public int getNbCles() {
return nbCles;
}
public void ajouterCle() {
// Ajoute une clé maximum 1 en stock
nbCles = Math.min(nbCles + 1, 1);
}
/**
* Consomme 1 clé pour réinitialiser l'objectif.
*/
public boolean consommerCles() {
if (nbCles >= 1) {
nbCles -= 1;
return true;
}
return false;
}
public int getNbObjectifsRealises() {
return nbObjectifsRealises;
}
public void sauvegarder(Bundle out) {
out.putInt("nb_objectifs_total", nbObjectifsRealises);
out.putInt("nb_cles", nbCles);
}
public void restaurer(Bundle in) {
if (in != null) {
nbObjectifsRealises = in.getInt("nb_objectifs_total", 0);
nbCles = in.getInt("nb_cles", 0);
}
}
}
@@ -1,108 +1,108 @@
package sae.chuzzle;
import android.os.Bundle;
/**
* Représente un objectif dynamique pour le mode Hard.
*/
public class Objectif {
private final int couleur; // Index de la couleur cible (0-6)
private final int nbSeriesCible; // Nombre de séries à réaliser
private final int nbCoupsMax; // Limite de coups à faire
private final int poids; // Probabilité d'apparition (poids pour le tirage)
private int seriesRealisees = 0;
private int coupsRestants;
public Objectif(int couleur, int nbSeries, int nbCoupsMax, int poids) {
this.couleur = couleur;
this.nbSeriesCible = nbSeries;
this.nbCoupsMax = nbCoupsMax;
this.coupsRestants = nbCoupsMax;
this.poids = poids;
}
// Getters
public int getCouleur() {
return couleur;
}
public int getNbSeriesCible() {
return nbSeriesCible;
}
public int getNbCoupsMax() {
return nbCoupsMax;
}
public int getCoupsRestants() {
return coupsRestants;
}
public int getPoids() {
return poids;
}
public void decrementerCoups() {
if (coupsRestants > 0) coupsRestants--;
}
public void ajouterSeries(int n) {
this.seriesRealisees += n;
}
public boolean estReussi() {
return seriesRealisees >= nbSeriesCible;
}
public boolean estEchoue() {
return coupsRestants <= 0 && !estReussi();
}
public String getDescription() {
String nomCouleur = obtenirNomCouleur(couleur);
return "Éclatez " + nbSeriesCible + " fois des Chuzzle " + nomCouleur +
" en moins de " + nbCoupsMax + " coups (" + seriesRealisees + "/" + nbSeriesCible +
").\nCoups restants : " + coupsRestants;
}
private String obtenirNomCouleur(int c) {
switch (c) {
case 0: return "Gris";
case 1: return "Rose";
case 2: return "Vert";
case 3: return "Bleu";
case 4: return "Jaune";
case 5: return "Orange";
case 6: return "Rouge";
default: return "Inconnue";
}
}
// Persistance pour la rotation d'écran
public void sauvegarder(Bundle out) {
out.putInt("obj_couleur", couleur);
out.putInt("obj_cible", nbSeriesCible);
out.putInt("obj_max", nbCoupsMax);
out.putInt("obj_restants", coupsRestants);
out.putInt("obj_realise", seriesRealisees);
out.putInt("obj_poids", poids);
}
public static Objectif restaurer(Bundle in) {
if (in == null || !in.containsKey("obj_couleur")) return null;
Objectif obj = new Objectif(
in.getInt("obj_couleur"),
in.getInt("obj_cible"),
in.getInt("obj_max"),
in.getInt("obj_poids")
);
obj.coupsRestants = in.getInt("obj_restants");
obj.seriesRealisees = in.getInt("obj_realise");
return obj;
}
}
package sae.chuzzle;
import android.os.Bundle;
/**
* Représente un objectif dynamique pour le mode Hard.
*/
public class Objectif {
private final int couleur; // Index de la couleur cible (0-6)
private final int nbSeriesCible; // Nombre de séries à réaliser
private final int nbCoupsMax; // Limite de coups à faire
private final int poids; // Probabilité d'apparition (poids pour le tirage)
private int seriesRealisees = 0;
private int coupsRestants;
public Objectif(int couleur, int nbSeries, int nbCoupsMax, int poids) {
this.couleur = couleur;
this.nbSeriesCible = nbSeries;
this.nbCoupsMax = nbCoupsMax;
this.coupsRestants = nbCoupsMax;
this.poids = poids;
}
// Getters
public int getCouleur() {
return couleur;
}
public int getNbSeriesCible() {
return nbSeriesCible;
}
public int getNbCoupsMax() {
return nbCoupsMax;
}
public int getCoupsRestants() {
return coupsRestants;
}
public int getPoids() {
return poids;
}
public void decrementerCoups() {
if (coupsRestants > 0) coupsRestants--;
}
public void ajouterSeries(int n) {
this.seriesRealisees += n;
}
public boolean estReussi() {
return seriesRealisees >= nbSeriesCible;
}
public boolean estEchoue() {
return coupsRestants <= 0 && !estReussi();
}
public String getDescription() {
String nomCouleur = obtenirNomCouleur(couleur);
return "Éclatez " + nbSeriesCible + " fois des Chuzzle " + nomCouleur +
" en moins de " + nbCoupsMax + " coups (" + seriesRealisees + "/" + nbSeriesCible +
").\nCoups restants : " + coupsRestants;
}
private String obtenirNomCouleur(int c) {
switch (c) {
case 0: return "Gris";
case 1: return "Rose";
case 2: return "Vert";
case 3: return "Bleu";
case 4: return "Jaune";
case 5: return "Orange";
case 6: return "Rouge";
default: return "Inconnue";
}
}
// Persistance pour la rotation d'écran
public void sauvegarder(Bundle out) {
out.putInt("obj_couleur", couleur);
out.putInt("obj_cible", nbSeriesCible);
out.putInt("obj_max", nbCoupsMax);
out.putInt("obj_restants", coupsRestants);
out.putInt("obj_realise", seriesRealisees);
out.putInt("obj_poids", poids);
}
public static Objectif restaurer(Bundle in) {
if (in == null || !in.containsKey("obj_couleur")) return null;
Objectif obj = new Objectif(
in.getInt("obj_couleur"),
in.getInt("obj_cible"),
in.getInt("obj_max"),
in.getInt("obj_poids")
);
obj.coupsRestants = in.getInt("obj_restants");
obj.seriesRealisees = in.getInt("obj_realise");
return obj;
}
}
@@ -1,31 +1,31 @@
package sae.chuzzle;
import android.app.Activity;
import android.content.SharedPreferences;
import android.os.Bundle;
import android.widget.Button;
import android.widget.CheckBox;
public class OptionsActivity extends Activity {
private SharedPreferences prefs;
private CheckBox checkHard;
private Button btnRetour;
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_options);
prefs = getSharedPreferences("chuzzle_prefs", MODE_PRIVATE);
checkHard = findViewById(R.id.checkHard);
btnRetour = findViewById(R.id.btnBack);
checkHard.setChecked(prefs.getBoolean("hard_mode", false));
OptionsController controller = new OptionsController(this, prefs);
checkHard.setOnCheckedChangeListener(controller);
btnRetour.setOnClickListener(controller);
}
}
package sae.chuzzle;
import android.app.Activity;
import android.content.SharedPreferences;
import android.os.Bundle;
import android.widget.Button;
import android.widget.CheckBox;
public class OptionsActivity extends Activity {
private SharedPreferences prefs;
private CheckBox checkHard;
private Button btnRetour;
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_options);
prefs = getSharedPreferences("chuzzle_prefs", MODE_PRIVATE);
checkHard = findViewById(R.id.checkHard);
btnRetour = findViewById(R.id.btnBack);
checkHard.setChecked(prefs.getBoolean("hard_mode", false));
OptionsController controller = new OptionsController(this, prefs);
checkHard.setOnCheckedChangeListener(controller);
btnRetour.setOnClickListener(controller);
}
}
@@ -1,65 +1,65 @@
package sae.chuzzle;
import android.app.Activity;
import android.content.Intent;
import android.os.Bundle;
import android.view.View;
import android.widget.Button;
import android.widget.EditText;
import android.widget.Toast;
public class SeedActivity extends Activity implements View.OnClickListener {
private EditText etGraine;
private Button btnJouer;
private Button btnRetour;
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_seed);
etGraine = findViewById(R.id.etGraine);
btnJouer = findViewById(R.id.btnJouer);
btnRetour = findViewById(R.id.btnBack);
btnRetour.setOnClickListener(this);
btnJouer.setOnClickListener(this);
}
@Override
public void onClick(View v) {
if (v == btnJouer) {
lancerPartieAvecGraine();
}
if (v == btnRetour) {
Intent intent = new Intent(this, MenuActivity.class);
startActivity(intent);
}
}
private void lancerPartieAvecGraine() {
String texte = etGraine.getText().toString().trim();
if (texte.isEmpty()) {
Toast.makeText(this, "Veuillez entrer une graine.",
Toast.LENGTH_SHORT
).show();
return;
}
long graine;
try {
graine = Long.parseLong(texte);
} catch (NumberFormatException e) {
graine = texte.hashCode();
}
Intent intent = new Intent(this, MainActivity.class);
intent.putExtra("graine", graine);
startActivity(intent);
}
package sae.chuzzle;
import android.app.Activity;
import android.content.Intent;
import android.os.Bundle;
import android.view.View;
import android.widget.Button;
import android.widget.EditText;
import android.widget.Toast;
public class SeedActivity extends Activity implements View.OnClickListener {
private EditText etGraine;
private Button btnJouer;
private Button btnRetour;
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_seed);
etGraine = findViewById(R.id.etGraine);
btnJouer = findViewById(R.id.btnJouer);
btnRetour = findViewById(R.id.btnBack);
btnRetour.setOnClickListener(this);
btnJouer.setOnClickListener(this);
}
@Override
public void onClick(View v) {
if (v == btnJouer) {
lancerPartieAvecGraine();
}
if (v == btnRetour) {
Intent intent = new Intent(this, MenuActivity.class);
startActivity(intent);
}
}
private void lancerPartieAvecGraine() {
String texte = etGraine.getText().toString().trim();
if (texte.isEmpty()) {
Toast.makeText(this, "Veuillez entrer une graine.",
Toast.LENGTH_SHORT
).show();
return;
}
long graine;
try {
graine = Long.parseLong(texte);
} catch (NumberFormatException e) {
graine = texte.hashCode();
}
Intent intent = new Intent(this, MainActivity.class);
intent.putExtra("graine", graine);
startActivity(intent);
}
}

Before

Width:  |  Height:  |  Size: 30 KiB

After

Width:  |  Height:  |  Size: 30 KiB

Before

Width:  |  Height:  |  Size: 1.4 KiB

After

Width:  |  Height:  |  Size: 1.4 KiB

Before

Width:  |  Height:  |  Size: 2.8 KiB

After

Width:  |  Height:  |  Size: 2.8 KiB

Before

Width:  |  Height:  |  Size: 982 B

After

Width:  |  Height:  |  Size: 982 B

Before

Width:  |  Height:  |  Size: 1.7 KiB

After

Width:  |  Height:  |  Size: 1.7 KiB

Before

Width:  |  Height:  |  Size: 1.9 KiB

After

Width:  |  Height:  |  Size: 1.9 KiB

Before

Width:  |  Height:  |  Size: 3.8 KiB

After

Width:  |  Height:  |  Size: 3.8 KiB

Before

Width:  |  Height:  |  Size: 2.8 KiB

After

Width:  |  Height:  |  Size: 2.8 KiB

Before

Width:  |  Height:  |  Size: 5.8 KiB

After

Width:  |  Height:  |  Size: 5.8 KiB

Before

Width:  |  Height:  |  Size: 3.8 KiB

After

Width:  |  Height:  |  Size: 3.8 KiB

Some files were not shown because too many files have changed in this diff Show More