2x6x6 Umschalter - Hilfe beim "merken" eines Status

War mir eben auch aufgefallen. Den Beitrag habe ich bereits editiert. In meinem Gerät sind die Relais in Ruhestellung offen.
Danke für den Hinweis.

wenn man den Code ändert dann kanns funktionieren aber mit der Logik "einen Einschalten und gleichzeitig alle anderen Aus" kann man keine 2 anschalten.
Grüße Uwe

Es wäre einfach, zu erklären ob beim Routing von GIOx auchCIOx geroutet werden soll, oder bei GIOx dann GIOy.
Auf diese Frage hast Du noch immer keine Antwort gegeben...

@my_xy_projekt
Entschuldige, das habe ich nicht verstanden.
Es soll jeder Eingang auf jeden Ausgang geroutet werden können. So wie das im Skatch im ersten Post auch funktioniert. Aber es funktioniert immer nur ein Eingang auf einen Ausgang. Es sollen aber zwei Eingänge auf zwei Ausgänge geroutet werden können.

Ich kann heute Abend noch ein kurzes Video vom breadboard mit angeschlossenen Relaisplatinen machen. Dann wir es deutlicher.

Ich habe leider nicht verstanden was du mit der isSet Variabelen versucht hast. Habe gestern Abend damit noch "rumgespielt" bin aber zu keinem Ergebniss gekommen da ich das einfach nicht verstanden habe.

Hallo threewood

Wofür ist der Input "sperrPin" gedacht?

Die Variable ist erstmal egal.
Die Frage ist, ob bei:
GIO0 -> CIO0
GIO1 -> CIO1
GIO2 -> CIO2
usw.
oder z.B. sowas hier
GIO0 -> CIO4
GIO1 -> CIO1
GIO2 -> CIO3
rauskommen soll?
Der Plan ist ganz einfach - man müsste nur wissen, was Du als Ergebnis haben willst.
(Die Frage hab ich schon in #3 gestellt - und wenn Du Dich weiter einer Antwort verweigerst, bin ich raus. Ich habe keine Lust mich ständig zu wiederholen)

Ich gebe mir größte Mühe euch die nötigen Informationen zu geben um mir zu helfen. Ich bin leider Anfänger. Bitte seid etwas nachsichtig. :wink:

Alle Relais sind LOW switching und in Ruhestellung sind die Ausgänge vom Arduino HIGH

InputSwitchG1[x] setzt outputG1[x] auf LOW und outputGIO[x] auf HIGH
InputSwitchG2[x] setzt outputG1[x] auf LOW und outputGIO[x] auf LOW

InputSwitchC1[x] setzt outputC1[x] auf LOW und outputCIO[x] auf HIGH
InputSwitchC2[x] setzt outputC1[x] auf LOW und outputCIO[x] auf LOW

@paulpaulson
sperrpin[x] setzt outputC1[x] auf HIGH. Das ist nur eine zusätzliche Sicherung. Nicht wirklich nötig im ersten Schritt.

Soweit funktioniert der Skatch auch wirklich gut. (Viod loop)
Ich denke mein Problem liegt in den 4 Void Schalte[x].

Der Schaltplan zeigt nur die 24 Ausgänge (4x6) der schalte[x] voids.

Beispiel G1:
Über InputSwichG1[x] soll jeweils ein output G1[x] gesetzt werden und gleichzeitig kann über InputSwitchG2[x] auch ein output G1[x] UND outputGIO[x] gesetzt werden.

Ich hoffe, ich habe deine Frage nun richtig verstanden und beantwortet.

Das wäre dann richtig. Alle sollen auf alles schaltbar sein.

Ich werd nicht schlau daraus.
Oben nimmst Du noch die Variante der Eingang zum gleichnumerierten Ausgang, jetzt unten wird es gemischt.

Es ist eine 6-2-6 Matrix.
Dann wird das auch irgendwie gehen...
Mal sehen, was mir dazu einfällt.

was macht das?!?
soll outputCIO[x] nun HIGH oder LOW gehen?!?

Tippfehler. Ist editiert.

@my_xy_projekt
Danke für deine Geduld. :slight_smile:

heißt das der InputSwitchC2 löscht immer beide Ausgänge?

Es wäre einfacher, alle 12 Eingänge fortlaufend durchzunumerieren. Dann reichen zwei Variablen für die beiden Ausgänge und mit welchem Eingang sie verbunden sind. Die Relais können mit diesen beiden Angaben geschaltet werden.

die Pin-Zuordnung kann frei gewählt werden,
der Code wäre meiner Meinung schon lange fertig, wenn @anon26300737 endlich vollständige Angaben machen würde ...

aber solange ich die Logik nicht von ihm lesen kann, zeige ich die Klasse nicht.

Da mache ich mal mit und hier ist mein Ausschnit, beim dem die I/Os noch nicht endgültig ausformuliert sind. In dem Ausschnitt fehlen die Datenstrukturen mit Membervariablen und Memberfunktioen.

Ausschnitt:

//https://forum.arduino.cc/t/2x6x6-umschalter-hilfe-beim-merken-eines-status/1219241
//https://europe1.discourse-cdn.com/arduino/original/4X/7/e/0/7e0ee1e51f1df32e30893550c85f0dd33244fb0e.jpeg
#define ProjectName "2x6x6 Umschalter - Hilfe beim  merken eines Status"
#define NotesOnRelease "Arduino DUE NANO UNO MEGA tested"
// make names
enum TimerEvent {NotExpired, Expired};
enum TimerControl {Halt, Run};
enum ButtonStates {Released, Pressed};
enum Names {One, Two, Three, Four, Five, Six};
enum Branches {G1, G2, C1, C2};
// make variables
constexpr  uint8_t inputSwitchG1 [] {A5, A4, A3, A2, A1, A0};
constexpr  uint8_t inputSwitchG2 []  {A13, A12, A11, A10, A9, A8};
constexpr  uint8_t inputSwitchC1 []  {8, 9, 10, 11, 12, 13};
constexpr  uint8_t inputSwitchC2 []  {2, 3, 4, 5, 6, 7};
constexpr  uint8_t outputG1 []  {27, 26, 25, 24, 23, 22};
constexpr  uint8_t outputC1 []  {43, 42, 41, 40, 39, 38};
constexpr  uint8_t outputGIO []  {32, 33, 34, 35, 36, 37};
constexpr  uint8_t outputCIO []  {48, 49, 50, 51, 52, 53};
constexpr  uint8_t sperrPin []  {19, 18, 17, 16, 15, 14};

// make structures
------ Schnipp Schnapp -------
struct TIMER
{
  uint32_t interval;
  uint8_t control;
  uint32_t now;
  uint8_t expired(uint32_t currentMillis)
  {
    uint8_t timerEvent = currentMillis - now >= interval and control;
    if (timerEvent == Expired) now = currentMillis;
    return timerEvent;
  }
};
BANK banks[]
{
  { 20, Run, 0,
    A0, 9, LOW, A1, 10, LOW,
    A2, 11, LOW, A3, 12, LOW,
  },
};
// make support
void heartBeat(const uint8_t LedPin, uint32_t currentMillis)
{
  static bool setUp = false;
  if (setUp == false) pinMode (LedPin, OUTPUT), setUp = true;
  digitalWrite(LedPin, (currentMillis / 500) % 2);
}
// make application
void setup()
{
  Serial.begin(115200);
  Serial.print("Source: "), Serial.println(__FILE__);
  Serial.print(ProjectName), Serial.print(" - "), Serial.println(NotesOnRelease);
  for (auto &bank : banks) bank.make();
  Serial.println(" =-> and off we go\n");
}
void loop()
{
  uint32_t currentMillis = millis();
  heartBeat(LED_BUILTIN, currentMillis);
  for (auto &bank : banks) bank.run(currentMillis);
}

Sketch uses 3756 bytes (1%) of program storage space. Maximum is 253952 bytes.
Global variables use 523 bytes (6%) of dynamic memory, leaving 7669 bytes for local variables. Maximum is 8192 bytes.

Danke, werde ich mir gleich genauer anschauen.

Hier das Video. Hoffentlich wir es dann klarer.
Leider mit Corona-Heiserkeit.

Am liebsten wäre es mir, wenn man das in den bestehenden code einbauen kann. Ich habe da ja auch noch ein paar andere Abhängigkeiten drin.

das sind nur 6!

Der hat 6 Eingänge, die auf 2 Sammelschienen gemappt werden und 6 Ausgänge, die sich das Signal von den Sammelschienen holen.

Ein Audiomixer funktioniert nach dem selben Prinzip.
Wenn er Subchannels hat, werden die Inputs auf die Sub's gemappt und die Subs dann z.B. nach den Effekten auf die Master-Out.

Darum schrieb ich oben schon:

Ich werd noch immer nicht schlau.
Das ist jetzt mein letzter Versuch.

Ausgehend von deiner Zeichnung hab ich das mal als ASCII-Grafik gemacht und beschriftet.

  1      2      3      4      5      6
  *      *      *      *      *      *
  |      |      |      |      |      |
  \      \      \      \      \      \
   \11    \21    \31    \41    \51    \61
  |      |      |      |      |      |
  |      |      |      |      |      |
  \      \      \      \      \      \
   \12    \22    \32    \42    \52    \62
  | |    | |    | |    | |    | |    | |
  | |    | |    | |    | |    | |    | |
 1a 1b  2a 2b  3a 3b  4a 4b  5a 5b  6a 6b  

Das ist jetzt die Ausgangsstellung.
Die Abgänge (x)a und (x)b sind Deine Sammelschienen.

Löst Du jetzt 11 aus, matcht 1 auf 1b
Löst Du danach 22 aus, geht 11 wieder in Ruhestellung und 2 matcht mit 21 auf 2a

Du möchtest jetzt:
11 löst aus -> match auf 1b
22 löst aus -> 11 bleibt erhalten, 21 und 22 matchen auf 2a

Soweit alles klar.

Wir haben jetzt

  1      2      3      4      5      6
  *      *      *      *      *      *
  |      |      |      |      |      |
  |      |      \      \      \      \
  | 11   | 21    \31    \41    \51    \61
  |      |      |      |      |      |
  |      |      |      |      |      |
  \      |      \      \      \      \
   \12   | 22    \32    \42    \52    \62
  | |    | |    | |    | |    | |    | |
  | |    | |    | |    | |    | |    | |
 1a 1b  2a 2b  3a 3b  4a 4b  5a 5b  6a 6b  

Was passiert, wenn Du aus diesem Zustand
a) 31 auslöst?
b) 42 auslöst?

zusätzlich gehe ich davon aus, dass aus diesem Zustand bei
c) 11 ausgelöst
die Verbindung 1 -> 1b aufgehoben wird.

d) 21 ausgelöst
die Verbindung 2 -> 2a aufgehoben wird aber 22 in Stellung 2a bleibt 2b zurück geht.
[edit]
Ich glaub, jetzt verstanden zu haben, was Deine Tasten da auslösen.

Ich hab mal was.

const byte A = 0;                                   // 
const byte B = 1;
const byte bankSize = 2;                            // Anzahl Sammelschienen

const byte channelSize = 6;                         // 

const bool gedrueckt = HIGH;                        // Taste....
const bool ein = LOW;                               // Relais ...
const bool aus = !ein;

const byte inputPin[bankSize][channelSize] =
{
  {A5, A4, A3, A2, A1, A0},                      // Tasten Bank A
  {A13, A12, A11, A10, A9, A8}                   // Bank B
};

const byte inputChannel[bankSize][channelSize] =
{
  {27, 26, 25, 24, 23, 22},                      // Relais Bank A
  {32, 33, 34, 35, 36, 37}                       // Bank B 
};


void checkInputChannelB()
{
  for (byte b = 0; b < channelSize; b++)                // frage alle Kanäle ab
  {
    if (digitalRead(inputPin[B][b]) == gedrueckt)       // Channel ausgelöst
    {
      for (byte c = 0; c < channelSize; c++)            // Frage alle Channel ab
      {
        if (c != b)                                     // aktueller Channel ist nicht der ausgelöste
        {
          if (digitalRead(inputChannel[B][b]) == ein)   // aber der Channel ist aktiv
          {
            digitalWrite(inputChannel[A][b], aus);      // Channel deaktivieren
            digitalWrite(inputChannel[B][b], aus);
          }
        }
        else                                            // der aktuelle ist der ausgelöste
        {
          digitalWrite(inputChannel[A][b], ein);        // Channel aktivieren
          digitalWrite(inputChannel[B][b], ein);
        }
      }
    }
  }
}

void checkInputChannelA()
{
  for (byte b = 0; b < channelSize; b++)
  {
    if (digitalRead(inputPin[A][b]) == gedrueckt)          // Channel ausgelöst ...
    {
      for (byte c = 0; c < channelSize; c++)               // ... durchlaufe alle A/B ....
      {
        if (c == b)                                        // Channel soll aktiv werden ...
        {
          digitalWrite(inputChannel[A][b], ein);           // ... A aktiv setzen
          digitalWrite(inputChannel[B][b], aus);           // ... sicherstellen das B inaktiv
        }
        else if (digitalRead(inputChannel[B][b]) == aus)   // nur wenn channel B inaktiv ...
        {
          digitalWrite(inputChannel[A][b], aus);           // ... channel A inaktiv setzen
        }
      }
    }
  }
}

void setup()
{
  for (byte a = 0; a < bankSize; a++)
  {
    for (byte b = 0; b < channelSize; b++)
    {
      pinMode(inputPin[a][b], INPUT);
      pinMode(inputChannel[a][b], OUTPUT);
      digitalWrite(inputChannel[a][b], aus);
    }
  }
}

void loop()
{
  checkInputChannelA();
  checkInputChannelB();
}

ungetestet - kompiliert.
Schieb den mal rauf, ob der Deine Tasten / Relaiskombi richtig verarbeitet.
Wenn Fragen sind, frag.

a) Wenn ich 31 auslöse, dann soll Relais 11 auf machen.
b) 42 wird nur in Kombination mit 41 ausgelöst. Dann soll 21 auf machen. (22 muss nicht zurück gehen. Ist ja durch 21 bereits unterbrochen)
C) und D) sollten damit beantwortet sein, wenn ich das richtig verstanden habe.

Danke für deinen Code. Leider macht er nicht das, was ich benötige.

Ich habe einen Lösungsansatz, weiß aber nicht ob der umsetzbar ist.

z.B. im Void schalteG2 aus dem code von Post#1.
Wenn outputG1[x] = LOW und outputGIO[x] = HIGH, dann digitalWrite(outputG1[x], LOW)

Im Void schalteG1 könnte es dann heißen:
Wenn outputG2[x] = LOW und outputGIO[x] = LOW, dann digitalWrite(outputG2[x], LOW) ; digitalWrite(outputGIO[x], LOW)

Wir merken uns den Status nicht sondern setzen den einfach neu!?