Hallo zusammen, ich bin zwar kein Anfänger in der Mikrocontroller Programmierung, doch die Projekte die ich bisher für mich privat realisiert habe, hatten einen geringeren Umfang als mein jetziges. Dementsprechend habe ich einige Fragen. Ich Arbeite mit VSCode und der der PlatformIO IDE und schrieb bisher kleinere Programme für den ESP32. Mein aktuellsten Projekt soll, grob gesagt, ein Menü haben wo man auswählen kann, welches "Sub-Programm" man nutzen möchte. Folgendes Beispiel möchte ich nicht umsetzen, verbildlicht aber mein anliegen: Ich habe eine Menü wo ich zwischen verschiedene Spielen aussuchen kann. Soweit so gut. Ich frage mich grade nur wie ich das umsetze. Die einzelnen Programme sind mehr oder weniger fertig geschrieben und funktionieren auch, wenn man Sie als einzelnes Programm auf den Controller lädt. Dies ist aber nur die halbe miete. Ich habe mir überlegt das Menü so zu schreiben, dass ich mit Switch Case die einzelnen Programm aufrufen kann. Die Überlegung dass man vom Menü Programm, in ein anderes Programm "springt" scheint mir nicht möglich zu sein. Macht man sowas am besten etwa mit Headerdatein? Ich weiß es nicht. Daher die frage an euch. Wie setze ich sowas um. So das die einzelnen Programm wirklich getrennt von einander sind. Ist für die Übersicht, Fehlersuche und Erweiterbarkeit am sinnvollsten. Viele Grüße
:
Verschoben durch Moderator
Hercules schrieb: > Daher die frage an euch. Wie setze ich sowas um. So das die einzelnen > Programm wirklich getrennt von einander sind. ...mit einem Betriebssystem auf dem ESP! Der zweite Absatz des dt. Wikipedia-Artikels fasst es schön zusammen: https://de.wikipedia.org/wiki/Betriebssystem
In der Theorie kann man es so etwa machen: Host Partition -> Startet nach Reset und hostet das Menu. -> Steuert ein Reset Safe Struct bei um die "Cluster"(Spiele Partitionen) zu verwalten ( wenn ein direkt Sprung von Spiel A nach Spiel B zB gewünscht ist). -> Schreibt in das Struct das gewünschte Spiel und springt direkt oder per Reset, falls nötig, an die Startadresse des gewählten Cluster. Cluster Partitionen: -> Stellen ein Interface zur Verfügung, was zum Host oder mit einem Reset wieder zum Host springt. Das ist jetzt nur ganz grundsätzlich ein Vorgehen, wie man die Spiele gleich lassen kann. Evtl kann man auch direkt die Startadresse vor dem Reset manipulieren, das weiß ich aber nicht). Mit dem Reset stellt man zB uninitialisierte Peripherie für das jeweilige Spiel sicher. Grundsätzlich ist das kein großes Hexenwerk, man wird nur einiges selber am Memory Layout rumbasteln müssen.
:
Bearbeitet durch User
Hercules schrieb: > Ich Arbeite mit VSCode und der der PlatformIO IDE Arduino-Framework? Schmeiß den Quellcode der einzelnen Spiele zusammen, lass alles gemeinsam kompilieren, aber benenn die "setup()" und "loop()" jeweils um. Dabei sind sicher viele gemeinsam benutzte Funktionen dabei, die dann auch nur einmal im Flash landen. Und dann in etwa:
1 | void setup() { |
2 | aktives_programm=MENU; |
3 | setup_menu(); |
4 | }
|
5 | |
6 | void loop() { |
7 | switch (aktives_programm) { |
8 | case MENU: loop_menu(); break; |
9 | case SPIEL1: loop_spiel1(); break; |
10 | case SPIEL2: loop_spiel2(); break; |
11 | }
|
12 | }
|
usw. Beim Wechsel des Aktiven Programms einmal das zugehörige "setup_spielX()" laufen lassen. Wenn darin Sachen initialisiert werden, die wieder aufgeräumt gehören, z.B. Interrupts, große Speicher-Allokationen: für jedes noch eine "cleanup_spielX()"-Funktion schreiben, die beim Programmwechsel vor dem setup des nächsten läuft.
1 | void switch_task(task_enum_t new_task) { |
2 | switch (aktives_programm) { |
3 | case MENU: cleanup_menu(); break; |
4 | case SPIEL1: cleanup_spiel1(); break; |
5 | case SPIEL2: cleanup_spiel2(); break; |
6 | }
|
7 | aktives_programm=new_task; |
8 | switch (aktives_programm) { |
9 | case MENU: setup_menu(); break; |
10 | case SPIEL1: setup_spiel1(); break; |
11 | case SPIEL2: setup_spiel2(); break; |
12 | }
|
13 | }
|
Und wenn dir die ganzen switch-case-Teile auf die Nerven gehen: bastel dir ein Array-von-Struct-mit-Funktionspointern. Oder, mehr OOP, Objekte. Und wenn dir für die Fehlersuche das Starten des jeweils zu debuggenden Programms über das Menu zu aufwändig ist: änder setup(), so dass gleich das richtige loslegt.
:
Bearbeitet durch User
Hi,
1 | Hi, |
2 | so könnte es prinzipiell aussehen. |
3 | |
4 | Lösung 1 - einfach |
5 | -------------------
|
6 | menu setup |
7 | menu loop |
8 | game1 setup |
9 | game1 loop |
10 | game2 setup |
11 | game2 loop |
12 | ...
|
13 | reset button in every game --> ESP.restart(); |
14 | |
15 | |
16 | |
17 | Lösung 2 - das letzte Game beim Einschalten wieder starten |
18 | -----------------------------------------------------------
|
19 | // Read menuIndex on startup or reset
|
20 | void preferencesRead(void) |
21 | {
|
22 | // read menu index, stored permanently
|
23 | // 0 or undefined = menu, 1 = game1, 2 = game2 ...
|
24 | preferences.begin("menuIndex", true); |
25 | menuIndex= preferences.getInt("menuIndex", 0); |
26 | preferences.end(); |
27 | }
|
28 | |
29 | -
|
30 | if menuIndex == 0 // perform menu |
31 | preferencesWrite() // write menuIndex 1 for game1 / 2 for game2 ... |
32 | ESP.restart(); |
33 | -
|
34 | |
35 | -
|
36 | if menuIndex == 1 // perform game1 setup & loop |
37 | preferencesWrite() // write menuIndex 0 for menu (Reset/Exit Button) |
38 | ESP.restart(); |
39 | -
|
40 | |
41 | -
|
42 | if menuIndex == 2 |
43 | game2 // perform game2 setup & loop |
44 | preferencesWrite() // write menuIndex 0 for menu (Reset/Exit Button) |
45 | ESP.restart(); |
46 | -
|
47 | |
48 | |
49 | |
50 | // Write menuIndex selected
|
51 | void preferencesWrite() |
52 | {
|
53 | // write menu index, stored permanently
|
54 | preferences.begin("menuIndex", false); |
55 | preferences.clear(); |
56 | preferences.putInt("menuIndex", menuIndex); |
57 | preferences.end(); |
58 | }
|
Bitte melde dich an um einen Beitrag zu schreiben. Anmeldung ist kostenlos und dauert nur eine Minute.
Bestehender Account
Schon ein Account bei Google/GoogleMail? Keine Anmeldung erforderlich!
Mit Google-Account einloggen
Mit Google-Account einloggen
Noch kein Account? Hier anmelden.