Forum: Mikrocontroller und Digitale Elektronik Atmega8 C Relais ansteuern


von Dominik (Gast)


Angehängte Dateien:

Lesenswert?

Hallo Leute,

habe mir vor kurzer Zeit das MK2 board von myAVR zugelegt. Etwa zur 
gleichen Zeit, habe ich auch angefangen mich mit der Programmiersprache 
C zu befassen. Desshalb begann ich auch damit, den µC mit C zu benutzen.

Jetzt habe ich mir 2 Platinen gelötet, 1ne mit den Tastern S1 - S4, die 
andere mit 2 bistabilen Relais.
Taster S1 = Position 1 des Relais 1
Taster S2 = Position 2 des Relais 1
Taster S3 = Position 1 des Relais 2
Taster S4 = Position 2 des Relais 2

Nun zu meinem Problem:

Wenn ich eine einfach if-Abfrage der Eingänge mache , also:

if ( ! (PINC & (1<<PINC0) ))
  PORTB = (1<<0);

... bis PINC3

ist logischerweise immer nur die Stellung des zuletzt betätigten Tasters 
Aktiv.

Am ende soll jedoch z.b. Relais 1 auf Pos1 stehen. Dann betätige ich 
Taster 4. Relais 1 soll Pos 1 behalten, bzw an B0 sollen die +5V 
weiterhin anliegen, und zusätzlich sollen die +5V auf B3 anliegen und 
Relais 2 auf Pos 2 fallen ...

Ich hoffe ich habe mich nicht zu verwirrend ausgedrückt :D

Hätte jemand einen Tipp / Vorschlag wie ich dies möglichst (da beginner) 
einfach, aber trotzdem recht elegant lösen könnte?

(die angefügte Zeichnung stimmt nicht zu 100%. In Wirklichkeit sind noch 
Transistoren und 1ne LED vor dem Relais. Desshalb wird auch die 
andauernde +5V versorgung benötigt)

Ich bedanke mich schonmal für jeden Gedankenanstoß ^^.

Grüße,
Dominik

von Dominik (Gast)


Lesenswert?

P.S

Alle Eingänge sind Pull-Up , also auf Masse gelegt

von Karl H. (kbuchegg)


Lesenswert?

> Ich hoffe ich habe mich nicht zu verwirrend ausgedrückt :D

So ganz kenne ich mich ehrlich gesagt nicht aus, was du willst bzw. was 
das Problem ist.


Ich glaube allerdings zu erkennen, dass du auf der Suche nach den 
Einzelbitoperationen bist, mit denen man einen Ausgangsportpin 
unabhängig von den anderen Portpins auf wahlweise 0 oder 1 schalten 
kann. Denn so etwas
1
   PORTB = (1<<0);
artet ganz schnell in einen Albtraum aus, wenn man ständig über alle 
möglichen Schaltzustände an diesem Port Buch führen muss.

Bit auf 1 setzen
1
    PORTB |= ( 1 << PB0 );

Bit auf 0 setzen
1
    PORTB &= ( 1 << PB0 );

Durch Kombinationen dieser Techniken gelingt es nun, an einem Port 
beliebige Bits aus 0 bzw. 1 zu setzen, ohne sich um die restlichen Bits 
kümmern zu müssen.

Um dein bistabiles Relais also in einen Zustand zu setzen genügt es, 
wenn du den zugehörigen Pin, und nur diesen auf 1 (bzw. den jeweils 
anderen für dieses Relais zuständigen Pin auf 0) zu setzen. (oder anders 
rum, je nachdem wie jetzt deine Treibertransistoren verschaltet sind)
1
....
2
3
  if ( ! (PINC & (1<<PINC1) ))
4
  {
5
    PORTB |= ( 1 << PB1 );
6
    PORTB &= ~( 1 << PB2 );
7
  }
8
9
  if ( ! (PINC & (1<<PINC2) ))
10
  {
11
    PORTB &= ~( 1 << PB1 );
12
    PORTB |= ( 1 << PB2 );
13
  }
14
15
  if ( ! (PINC & (1<<PINC3) ))
16
  {
17
    PORTB |= ( 1 << PB3 );
18
    PORTB &= ~( 1 << PB4 );
19
  }
20
21
  if ( ! (PINC & (1<<PINC4) ))
22
  {
23
    PORTB &= ~( 1 << PB3 );
24
    PORTB |= ( 1 << PB4 );
25
  }

Das du hier die eigenschaft der bistabilen Relais nicht ausnutzt, auch 
ohne Spannung den Zustand beizubehalten ist dir klar?

Im Grunde könnte man auch zum Stromsparen jeden Pin nachdem das Relais 
geschaltet hat, wieder auf 0 zurück fallen lassen. Und bräuchte sich 
dann bei der Behandlung des jeweils anderen tasters nicht mehr darum 
kümmern.
In diesem Sinne bringen dir die bistabilen Relais im Moment eigentlich 
gar nichts. Ganz im Gegenteil.

Allerdings: das kann man programmtechnisch ebenfalls lösen :-)
Wenn keine Taste gedrückt ist, wird auch keine Spule bestromt
1
....
2
3
  if ( ! (PINC & (1<<PINC1) ))
4
  {
5
    PORTB |= ( 1 << PB1 );
6
  }
7
8
  else if ( ! (PINC & (1<<PINC2) ))
9
  {
10
    PORTB |= ( 1 << PB2 );
11
  }
12
13
  else if ( ! (PINC & (1<<PINC3) ))
14
  {
15
    PORTB |= ( 1 << PB3 );
16
  }
17
18
  else if ( ! (PINC & (1<<PINC4) ))
19
  {
20
    PORTB |= ( 1 << PB4 );
21
  }
22
23
  else  // keine Taste? dann werden alle Spulen abgeschaltet
24
        // die Relais halten ganz von alleine den letzten Zustand
25
  {
26
    PORTB &= ~( 1 << PB1 );
27
    PORTB &= ~( 1 << PB2 );
28
    PORTB &= ~( 1 << PB3 );
29
    PORTB &= ~( 1 << PB4 );
30
  }

von Dominik (Gast)


Lesenswert?

Ich kann mich garnicht oft genug bei dir bedanken ! :D

Genau nach soetwas wie den Einzelbitoperationen habe ich gesucht. Aus 
diesem kleinen "Lehrheftchen" welches bei meinem Board dabei war wird 
man nicht schlau.Da ist alles so schwammig, bzw. zu C garnicht erklärt 
... lediglich ein paar Code schnipsel wo man sich zurechtsuchen darf auf 
10 Seiten..

Das ich Momentan noch nicht die funktion der Relais benutze ist mir aber 
kla :) Zur Zeit muss ich mit normalen Relais arbeiten, welche später 
jedoch durch bistabile HF Relais ersetz werden. Desshalb die 
Dauerspannung und die LED zur Anzeige und solche spielereien.

Aber vielen herzlichen Dank für deine Hilfe und für den Hinweis mit den 
Einzelbitoperationen ^^.

Grüße,
Dominik

von Harry L. (mysth)


Lesenswert?

Karl Heinz Buchegger schrieb:
> Bit auf 0 setzen    PORTB &= ( 1 << PB0 );

Muß heissen:
Bit auf 0 setzen PORTB &= ~( 1 << PB0 );

von Amateur (Gast)


Lesenswert?

@Dominik

>man nicht schlau.Da ist alles so schwammig, bzw. zu C garnicht erklärt

>Aber vielen herzlichen Dank für deine Hilfe und für den Hinweis mit den
>Einzelbitoperationen ^^.

Solltest Du aber noch ein bisschen weiter machen wollen, kommst Du um 
das Erlenen von C nicht herum. Dabei geht’s dann aber nicht mehr um 
dünne Heftchen und einzelne (einfache) Operationen.

von Moritz A. (moritz_a)


Lesenswert?

Dominik schrieb:
> Genau nach soetwas wie den Einzelbitoperationen habe ich gesucht. Aus
> diesem kleinen "Lehrheftchen" welches bei meinem Board dabei war wird
> man nicht schlau.Da ist alles so schwammig, bzw. zu C garnicht erklärt
> ... lediglich ein paar Code schnipsel wo man sich zurechtsuchen darf auf
> 10 Seiten..

Dann lies hier doch mal AVR-Tutorial und AVR-GCC-Tutorial

von Karl H. (kbuchegg)


Lesenswert?

Harry L. schrieb:
> Karl Heinz Buchegger schrieb:
>> Bit auf 0 setzen    PORTB &= ( 1 << PB0 );
>
> Muß heissen:
> Bit auf 0 setzen PORTB &= ~( 1 << PB0 );

Huch. Danke für den Catch.
In den Codebeispielen hab ich es dann richtig geschrieben.

von Harry L. (mysth)


Lesenswert?

Karl Heinz Buchegger schrieb:
> Huch. Danke für den Catch.

immer gern! ;)

von Dominik (Gast)


Lesenswert?

Amateur schrieb:
> Solltest Du aber noch ein bisschen weiter machen wollen, kommst Du um
> das Erlenen von C nicht herum. Dabei geht’s dann aber nicht mehr um
> dünne Heftchen und einzelne (einfache) Operationen.

Das ist mir bewusst ;) Ich finde es halt nur am Anfang recht schwer, 
wenn man bei diesem Einsteigersett in C "reingeworfen" wird, ohne 
Erklärung und mit 1nem Beispiel für UART, dem anschalten 1ner LED bei 
Tastendruck und Interupts.

Hatte in der FOS leider nur Pascal und nichts zeitgemäßes. Jetzt, wo ich 
in der Ausbildung bin, werd ich mich mit den etwas höheren Dingen 
beschäftigen und mich ranarbeiten :)

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
Noch kein Account? Hier anmelden.