PDA

Archiv verlassen und diese Seite im Standarddesign anzeigen : Asuro PollSwitch() für Anfänger



Doubleyou
16.02.2008, 14:20
Hallo Board Mitglieder,

ich beschäftige mich noch nicht lange mit Asuro und stehe sozusagen eigentlich noch ganz am Anfang der Programmierung von Asuro. Ich versuche gerade die verschiedenen Knöpfe mit an Asuro mit verschiedenen Funktionen zu belegen, ich hab mir dazu mal den Quellcode des Selftests angesehen und hab dann versucht einen Knopf mit einer Funktion zu belegen, ich häge hier mal den Code an:


#include "asuro.h"

unsigned char sw1, sw2;

int main(void){
Init();
StatusLED(OFF);
FrontLED(OFF);
BackLED(OFF,OFF);

sw1=PollSwitch();
sw2=PollSwitch();

if (sw1 || sw2 && 0x01){
StatusLED(RED);
Msleep(200);
StatusLED(GREEN);
Msleep(200);
StatusLED(YELLOW);
Msleep(200);
}
StatusLED(OFF);
BackLED(OFF,OFF);
FrontLED(OFF);

while(1);
return(0);
}


Nur passiert nichts, egal auf welchen Knopf ich drücke, was hab ich am Code falsch gemacht ?

Gruß DoubleU


PS: Ich muss auch sagen, dass ich noch nicht all zu viel Erfahrung in C# habe.

Sim Robot
16.02.2008, 14:44
Ich würde diesen part
if (sw1 || sw2 && 0x01){
mal umschreiben, so dass es so aussiht

if ((sw1==sw2)&&(sw1>0)){
dann müst es funktioniren

Doubleyou
16.02.2008, 15:14
Hmm, scheint irgendwie auch nicht zu gehen. Ist es nicht so, dass wen ich das so mache "(sw1>0)", dass dann alle Tasten die gleiche Funktion ausführen ?

radbruch
16.02.2008, 15:21
Der Code wird nur einmal ausgeführt und hängt dann am Ende in der while-Schleife.

if (sw1 || sw2 && 0x01){

prüft ob sw1 und sw2 einen Wert != 0 haben. Das && 0x01 bedeutet ein unnötiges && true Deshalb kann man auch schreiben:

if (sw1 || sw2){

was eben nur auf einen Wert != 0 prüft.

Gurß

mic

Doubleyou
16.02.2008, 15:31
Ok, dass die Funktion nur abläuft wenn der Knopf gedrückt ist muss ich die Abfrage immer wieder machen oder ? Oder geschieht das nun schon durch die while Schleife am Ende ?

Ok, ich hab gesehen, dass wenn ich gleich beim Anschalten einen Finger auf einem Knopf habe, dass es dann geht, also muss ich die Abfrage immer wieder machen. Und wie würde das dann aussehen ?

Werd mal kurz im Inet suchen wie das geht.

Doubleyou
16.02.2008, 16:10
So nun bin ich ein bisschen weiter, ich konnte mir mit dem Selftest Code soweit abhelfen, dass ich nun mit diesem Code ungefähr das ergebniss habe, welches ich wollte:


#include "asuro.h"

unsigned char sw;
unsigned int i;


void SwitchTest(void)
{
sw = PollSwitch();
BackLED(OFF,OFF);

if (sw & 0x01)
{
BackLED(OFF,ON);
}
}

int main(void){
Init();
StatusLED(OFF);
i=0;

for (i = 0; i < 0xFE00; i++)
SwitchTest();

BackLED(OFF,OFF);
while(1);
return(0);
}


Nur kann man jetzt nicht nur mit einem Taster die BackLED zum leuchten bringen sondern gleich mit vier ? Was muss ich machen, das z.B. nur durch den ersten Schalter die LED leuchtet ?

Und was bedeutet eigentlich das "0xFE00" ? Werd auch gleich im Inet danach schauen.

Gruß DoubleU

radbruch
16.02.2008, 16:11
#include "asuro.h"

unsigned char sw1, sw2;

int main(void){
Init();
StatusLED(OFF);
FrontLED(OFF);
BackLED(OFF,OFF);

while(1){
sw1=PollSwitch();
sw2=PollSwitch();
if (sw1 || sw2 && 0x01){
StatusLED(RED);
Msleep(200);
StatusLED(GREEN);
Msleep(200);
StatusLED(YELLOW);
Msleep(200);
}
}
return(0);
}

Doubleyou
16.02.2008, 17:06
Danke Radbruch,

ich hab das ganze nun noch ein bisschen erweitert:


#include "asuro.h"

unsigned char sw1, sw2;

int main(void){
Init();

while(1){
sw1=PollSwitch();
sw2=PollSwitch();
StatusLED(OFF);
BackLED(OFF,OFF);
FrontLED(OFF);
if (sw1 && sw2 & 0x01){
StatusLED(RED);
Msleep(200);
StatusLED(GREEN);
Msleep(200);
StatusLED(YELLOW);
Msleep(200);
}
if (sw1 && sw2 & 0x02){
BackLED(OFF,ON);
Msleep(200);
BackLED(ON,OFF);
Msleep(200);
}
if (sw1 && sw2 & 0x04){
FrontLED(ON);
Msleep(200);
FrontLED(OFF);
Msleep(200);
}
if (sw1 && sw2 & 0x08){
StatusLED(OFF);
BackLED(OFF,OFF);
FrontLED(OFF);
}
if (sw1 && sw2 & 0x16){
StatusLED(OFF);
BackLED(OFF,OFF);
FrontLED(OFF);
}
if (sw1 && sw2 & 0x32){
StatusLED(OFF);
BackLED(OFF,OFF);
FrontLED(OFF);
}
}
return(0);
}

Und nun sind drei Tasten mit einer extra Funktion belegt, nur die anderen drei, wo eigentlich nichts passieren sollte durchlaufen irgendwie alle drei verschiedenen Funktionen nacheinander.

radbruch
16.02.2008, 17:45
Hallo Doubleyou

Erstmal noch ein herzliches Willkommen im RN-Forum. Ich bin echt beeindruckt, was du alles findest, wenn du "Werd auch gleich im Inet danach schauen." machst.

Zu deinem Problem: Du hast zwar nun eine Überprüfung auf einzelne Werte, aber "doppelte" Tasten werden nicht abgefangen. Die Standartlösung sieht so aus:

if ((sw1 == sw2) && (sw1 == 0x01)) {

Gruß

mic

[Edit]
btw ist das natürlich Quatsch:

if (sw1 && sw2 & 0x01){

(sw2 & 0x01) ergibt true wenn in sw2 mindestens Bit0 gesetzt ist, auch wenn mehrere Bits gesetzt sind. Dieses true erklärst du dann für gültig wenn in sw1 irgendein Bit gesetzt ist.

Das hattest du vermutlich eh anders gedacht, oder hast du die Rangfolge der Funktionen beachten (quasi das punktvorstrich):

Bitweises & kommt vor logischem &&, d.h. deine Abfrage wird so ausgewertet:

if (sw1 && (sw2 & 0x01)){

du meintest aber vermutlich:

if ((sw1 && sw2) & 0x01){

Das macht dann die Abfrage auch nicht wesentlich besser. Wenn irgendwas in sw1 und irgendwas in sw2 steht, ist das Ergebniss true und du vergleichst dieses true (das der Compiler irgendwie speichert hat) dann bitweise mit 0b00000001...

Doubleyou
16.02.2008, 19:32
Danke für das Willkommen und danke auch für die gute und vorallem auch schnelle Hilfe.

Ich habs nun verstande und auch hinbekommen, mit
if ((sw1 == sw2) && (sw1 == 0x01)) { müssen die Pollswitches die gleiche Ausgabe haben und dürfen nur einen Bit enthalten und je nach Schalter, die verschieden viele Bits ausgeben, kann ich das dann korrekt anpassen.

Danke nochmal für die Hilfe, hätte vielleicht noch ein bisschen mehr nachdenken solle. Aber wie gesagt, ich steh noch am Anfang und bin auch dankbar, dass man so geduldig mirgegenüber ist.

Gruß DoubleU

radbruch
16.02.2008, 22:26
Hallo


je nach Schalter, die verschieden viele Bits ausgeben
Wenn die PollSwitch()-Funktion richtig kallibriert ist entspricht jeder Taster genau einem Bit im Wert, bzw. mehrere Taster gleichzeitig werden durch die entsprechenden Bits dargestellt. (Taster K6 ist dabei das Bit0)


und bin auch dankbar, dass man so geduldig mir gegenüber ist.
Immer gerne wenn ich merke, dass auch Eigeninitiative vorhanden ist. Weiterhin viel Spass mit deinem asuro.

Gruß

mic

damaltor
17.02.2008, 12:44
bewundernswert... wirklich. viele neue user fragen einfach irgendwas schreiben drei zeilen hin und kümmern sich nicht.
du nutzt die suchfunktion, bemühst dch selbst, kennst die deutsche rechtschreibung und interpunktion und hast sogar den code-button schnell gefunden =)


am ersten programm hat hauptäschlich eine while-schleife gefehlt, die das programm wiederholt... aber solche kleinigkeiten sind die, die sich am schwersten finden lassen ;)

zoerby
19.05.2008, 16:10
Hallo Leute,

ich bin nun auch einer von vielen ASURO- Besitzern und wie viele andere auch dachte ich nicht das C/C++ für Anfänger solche Probleme macht. :)

Zum Thema, ich hatte die gleiche Idee wie "Doubleyou" und möchte erst einmal die einzelen Sensoren genauer kennen lernen und verstehen.
Mit Hilfe des Forum und der Anleitung bin ich bisher zu follgenden Ergebnis gekommen:


#include "asuro.h"

unsigned char taste;

int main(void)
{

Init();

while(1){

taste = PollSwitch();

if ((taste>0) && (PollSwitch()>0) & 0x01) {StatusLED (GREEN);}
else if ((taste>0) && (PollSwitch()>0) & 0x02) {StatusLED (RED);}
else if ((taste>0) && (PollSwitch()>0) & 0x04) {FrontLED (ON);}
else if ((taste>0) && (PollSwitch()>0) & 0x08) {BackLED (OFF,ON);}
else if ((taste>0) && (PollSwitch()>0) & 0x16) {BackLED (ON,OFF);}
else if ((taste>0) && (PollSwitch()>0) & 0x32) {BackLED (ON,ON);}
else {StatusLED(OFF);BackLED(OFF,OFF);FrontLED(OFF);}
}
while(1);
return 0;
}


Zur Erklärung:
Als erstes habe ich mir eine Variable"taste" angelegt.
Die Variable erhält innerhalb der Schleife den Wert des Pollswitch.
Falls nun ein PollSwitch gedrückt wird und er den Byte 1 entspricht und dieses zusammen gleich der "taste" ist, dann soll die StatusLED grün leuchten.
anderenfalls, falls nun ein Pollswitch gedrückt wird und er den Byte2 entspricht und dieser gleich der "taste" ist, dann soll die StatusLED rot leuchten.
.
.
.
wenn nichts gedrückt wird sollen alle LED´s aus sein.
---------------------------------------------------------------------------------
Mein Problem ist nun, dass die grüne Status LED auf jeden Taster anspringt und nicht wie eigentlich gewollt nur an K6.
Könnt ihr mir bitte zu einen Erfolgserlebniss verhelfen?


EDIT//
Hhmm, ist es richtig das meine Variable nie den Wert2,4,8,16,32 erhält und da das Problem liegt???
EDIT2//
Nein, das ist falsch, oder? Ich frage ja nur ab ob "taste" & "PollSwitch" größer 0 ist. Liegt der Fehler in der Byte abfrage?
Gruß zoerby

hai1991
19.05.2008, 16:50
hallo

ich weiß zwar nicht ob es hilft, aber ich würde dein programm etwas anders schreiben:



#include "asuro.h"

unsigned char taste;

int main(void)
{

Init();

while(1){

do
{
taste = PollSwitch();
}while( taste != PollSwitch() ) // somit braucht man später nicht immer kontrollieren

switch(taste) // hier wird taste auf bestimmte werte geprüft
{
case 1:
StatusLED (GREEN);
break;
case 2:
StatusLED (RED);
break;
case 4:
FrontLED (ON);
break;
case 8:
BackLED (OFF,ON);
break;
case 16:
BackLED (ON,OFF);
break;
case 32:
BackLED (ON,ON);
break;
default:
StatusLED(OFF);
BackLED(OFF,OFF);
FrontLED(OFF);
break;
}
}
while(1);
return 0;
}

zoerby
19.05.2008, 17:30
Ein kleiner Fehler war drin, sonst funktioniert es wunderbar. Genau so wie ich es wollte.

Aber eigentlich würde ich gern mit meinem Programm weiter kommen wollen, sonst habe ich am Ende nichts verstanden.

Gruß zoerby

hai1991
19.05.2008, 17:45
mir ist gerade aufgefallen, dass bei deiner tasterabfrage ein kleiner (denk)fehler ist:

du hast 0x16 geschrieben, wobei dies aber 10110 als binärzahl ergibt.
richtiger wiese müsste es aber 10000, bzw. 16 als dezimalzahl sein

0x zeigt dem compiler an, dass die darauffolgende zahl in hexadezimaler schreibweise vorliegt

zoerby
19.05.2008, 17:52
Eine Frage noch, du benutzt follgende Schleife.


do {taste = PollSwitch();}
while( taste != PollSwitch() );


Hier wird geprüft ob "taste"=="PollSwitch" ist, ist das nicht der Fall so wird die Schleife durchlaufen.

Das bedeutet doch das eigentlich "taste"="PollSwitch" reichen müßte wenn ich diese Deklaration außerhalb der main()-Funktion setze, oder?

Was meinst du mit "somit braucht man später nicht immer kontrollieren"?
Nur um Code einzusparen?

bei dem "switch",


switch(taste) {case 1:}


kann ich dieses case (was immer es bedeutet) auch durch "int", "char"... ersetzen??

Gruß zoerby

zoerby
19.05.2008, 18:27
d.H. ich muss dort Binäre Zahlen eintragen?



if ((taste>0) && (PollSwitch()>0) & 0x000001) {StatusLED (GREEN);}
else if ((taste>0) && (PollSwitch()>0) & 0x000010) {StatusLED (RED);}
else if ((taste>0) && (PollSwitch()>0) & 0x000100) {FrontLED (ON);}
else if ((taste>0) && (PollSwitch()>0) & 0x001000) {BackLED (OFF,ON);}
else if ((taste>0) && (PollSwitch()>0) & 0x010000) {BackLED (ON,OFF);}
else if ((taste>0) && (PollSwitch()>0) & 0x100000) {BackLED (ON,ON);}
else {StatusLED(OFF);BackLED(OFF,OFF);FrontLED(OFF);}


hhmm leuchtet leider immer noch nur die grüne Status Leuchte (K1-K6).

EDIT//:

Ich habe es glaube ich. Mein Problem sind nur noch die Zahlen (0x01....).
Es funktioniert bei 0x01, 0x02, 0x04, 0x08 bei 0x16 und 0X32 nicht.

Kann mir jemand das erklären wie das mit den Zahlen da funktioniert?

hai1991
19.05.2008, 19:40
diese schleife:

1.


do {taste = PollSwitch();}
while( taste != PollSwitch() );

habe ich eingebaut, da PollSwitch() manchmal falsche werte liefert, jedoch nicht zwei mal hintereinander. wenn also der wert 2 mal gleich ist, kann man davon ausgehen, dass er richtig ist

2.
switch-case kann man verwenden, wenn man eine variable auf verschiedene werte überprüfen will (müsste eigentlich in der anleitung auch beschrieben sein, aber trotzdem eine kurze erklärung)

der aufbau ist folgendermaßen:



switch( zu_prüfende_variable )
{
case wert_1:
//... befehle, die ausgeführt werden sollen, wenn zu_prüfende_variable == wert_1
break; //um switch zu verlassen, wenn man es auslässt werden die nächsten befehle ebenfalls ausgeführt, auch wenn wert_1 != zu_prüfende_variable
case wert_2:
//...
....

default:
//... befehle, für den fall, dass sonst nichts zu trifft, muss nicht unbedingt vorhanden sein
}


3.
bei deiner abfrage:

if ((taste>0) && (PollSwitch()>0) & 0x000001) {StatusLED (GREEN);}

musst du wissen, dass sich der µC bei vergleichen (<,>,==,!=,...) immer nur das ergebnis, also TRUE und FALSE oder 1 und 0 merkt.

schauen wir nun was da bei deiner abfrage heraus kommt wenn ein taster gedrückt werd:
taste>0 ==> TRUE
PollSwitch()>0 ==> TRUE

(taste>0) && (PollSwitch()>0) entspricht also TRUE && TRUE ==> TRUE

TRUE & 0x000001 ist das selbe wie 1 & 1 ==> 1, also TRUE

das heißt, wenn du irgend einen taster drückst ist sofort das erste if() richtig. daher leuchtet die statusLED grün, und die ganzen else if werden übersprungen


wenn du es also mit if und else schaffen möchtest, musst du am besten so abfragen:



if(taste == 1){ //....}
else if(taste == 2){//....}
...



PS: ich habe auch erst nach einiger zeit gemerkt, was eigentlich in deinen if vor sich geht

zoerby
19.05.2008, 21:32
Wau Super! Vielen Dank für die Super Unterstützung!

Ich bin durch follgende Maßnahme zu einen Teilerfolg gekommen:

if ((taste>0) && (PollSwitch()>0) & 0x01) {StatusLED (GREEN);}

"(tast>0)" "(PollSwitch()>0)"
Das >0 ist ja eigentlich Schwachsinn wenn ich die "&&" durch "==" ersetze.
Nun habe ich einfach die gedrückte Taste nochmals mit den ausgegebenen Wert (Byte) verglichen:
...&& taste == 0x01) {StatusLED (GREEN);}

Das schaut dann so aus:


if (taste == PollSwitch() && taste == 0x01) {StatusLED (GREEN);}
else if (taste == PollSwitch() && taste == 0x02) {StatusLED (RED);}
else if (taste == PollSwitch() && taste == 0x04) {FrontLED (ON);}
else if (taste == PollSwitch() && taste == 0x08) {BackLED (OFF,ON);}


Bis hierhin funktioniert es nun einwandfrei.
Die letzten beiden Taster funktionieren ab leider nicht.
An den else if Anweisungen kann es also eigentlich nicht liegen, oder?
Vielmehr dann doch eher an den Zahlen gewurchtel wo ich noch nicht durch sehe, oder?

zoerby
20.05.2008, 09:25
Mein Programm funktioniert nun einwandfrei!

Nochmals vielen vielen Dank für deine Unterstützung! =D>

Das Problem lag wirklich an den Binären Zahlen. Für K2 und K1 habe ich nun Hexadezimalzahlen eingesetzt und siehe da, es funktioniert. Gott bin ich glücklich!!

Hier der gesammte code:



#include "asuro.h"

unsigned char taste;

int main(void)
{

Init();

while(1){

do {taste = PollSwitch();} while (taste != PollSwitch() );

if ((taste == PollSwitch()) & taste == 0x01) {StatusLED (GREEN);}
else if ((taste == PollSwitch()) & taste == 0x02) {StatusLED (RED);}
else if ((taste == PollSwitch()) & taste == 0x04) {FrontLED (ON);}
else if ((taste == PollSwitch()) & taste == 0x08) {BackLED (OFF,ON);}
else if ((taste == PollSwitch()) & taste == 0x10) {BackLED (ON,OFF);}
else if ((taste == PollSwitch()) & taste == 0x20) {BackLED (ON,ON);}
else {StatusLED(OFF);BackLED(OFF,OFF);FrontLED(OFF);}
}
while(1);
return 0;
}


Gruß zoerby

hai1991
20.05.2008, 14:04
nur noch eine frage:

warum fragst du jedes mal taste == PollSwitch() ab?

du hast doch oben schon die do-while schleife, daher wird es in diesem fall auch gleich sein.

zoerby
20.05.2008, 14:26
Jetzt wo du es sagst... Ist mir nicht aufgefallen bzw. habe ich gar nicht darüber nach gedacht.
Aber deshalb bin ich ja auch hier, um es zu lernen.