Skocz do zawartości

Sterowanie czujnikami w LF.


komabra

Pomocna odpowiedź

Cześć.

Niestety ale po wielu męczarniach nie mogę sam do tego dojść więć chciałbym prosić was o pomoc.

Mam problem z kodem który będzie sterował silnikiem w zależności od stanu pinu od czujników.

Czujniki podpięte są pod PC 0,1,2. Silnik pod PD 0,1.

Wiadomo, żeby sprawdzić czy silnik działa wystarczyło użyć :

if(!(PINC&(1<<PC0))) 	PORTD|=(1<<PD0);PORTD&=~(1<<PD1);

I tak samo dla PC1 oraz PC2. Wszystko śmiga.

Problem pojawia się gdy chciałbym, żeby silnik zaczął działać gdy na dwóch czujnikach będzie stan niski.

Nie jestem dobry z programowania. Pewnie jestem blisko odpowiedzi, bo trzeba się tu pobawił bramkami logicznymi ale nie wiem dokładnie jak.

Chcąc ruszyć silnik gdy piny PC0 , PC 1 będą w stanie niskim używam kodu:

if(!(PINC&(1<<PC0)&(PINC&(1<<PC1)))) 	PORTD|=(1<<PD0);PORTD&=~(1<<PD1);

Niestety silnik kręci olewając stan na pinach. Kombinowałem modyfikując kod w różny sposób ale nie mam pojęcia jak to ma być i mam już dość.

Może mi ktoś powiedzieć jak kod powinien wyglądać? To na pewno jest mega proste.

Link do komentarza
Share on other sites

Iloczyn logiczny powinieneś sprawdzać operatorem &&, po drugie w funkcji If ustawiasz jeden port i kończysz funkcje znakiem ";" następny rozkaz wykona się zawsze ponieważ nie jest on zależny od If. Lepiej ustawienie portów wykonać w nawiasach.

Link do komentarza
Share on other sites

if((!(PINC&(1<<PC0))&(!(PINC&(1<<PC1)))))     
{
   PORTD|=(1<<PD0);
   PORTD&=~(1<<PD1);
}

1. Brak nawiasów żeby oddzielić poszczególne PINC

2. Zapis if (x==0) a=1;b=2; spowoduje, że tylko a=1 będzie zależne od warunku, a b=2 będzie wywoływane za każdym razem, bo to już jest poza if'em. Dlatego potrzebujesz użyć nawiasów klamrowych { } do oddzielenia kawałka kodu.

Link do komentarza
Share on other sites

Przede wszystkim nie formatuj w ten sposób kodu, bo sam się oszukujesz. Kompilator C olewa Twoje pisanie, za to widzi średniki. Umieszczając w jednej linii kilka rzeczy wydaje Ci się, że dwie prawe instrukcje wykonują się po "if"? Nic bardziej mylnego. Jeżeli warunek jest spełniony wykonuje się tylko jedna, bo "if" tak działa niezależnie od tego jak to napiszesz.

Jeżeli chcesz umieścić parę rzeczy wykonywanych po "if", musisz użyć nawiasów grupujących w blok:

if (!(PINC&(1<<PC0)&(PINC&(1<<PC1))))
{
   PORTD |= (1<<PD0);
   PORTD &= ~(1<<PD1);
}

Jeżeli masz tylko 3 czujniki, to dają one 8 kombinacji stanów. Możesz użyć instrukcji "switch" która jest rozgałęzieniem programu na wiele ścieżek:

switch (stan_czujnikow)
{
   case 0b000:
       tu jest kod wykonywany dla stanu = 000;
       break;   // <- To ważne! Kończy wykonywanie przypadku 000
   case 0b001:
       tu jest kod wykonywany dla stanu = 001;
       break;
   case 0b010:
       tu jest kod wykonywany dla stanu = 010;
       break;
   case 0b011:
       tu jest kod wykonywany dla stanu = 011;
       break;
// i tak dalej aż do:
   case 0b111:
       tu jest kod wykonywany dla stanu = 111;
       break;
}

W odpowiednie miejsca wpisz swoje odpalanie silników lub.. nie 🙂

Mirek, Wikkan: Ale jesteście szybcy 🙂

Link do komentarza
Share on other sites

Zarejestruj się lub zaloguj, aby ukryć tę reklamę.
Zarejestruj się lub zaloguj, aby ukryć tę reklamę.

jlcpcb.jpg

jlcpcb.jpg

Produkcja i montaż PCB - wybierz sprawdzone PCBWay!
   • Darmowe płytki dla studentów i projektów non-profit
   • Tylko 5$ za 10 prototypów PCB w 24 godziny
   • Usługa projektowania PCB na zlecenie
   • Montaż PCB od 30$ + bezpłatna dostawa i szablony
   • Darmowe narzędzie do podglądu plików Gerber
Zobacz również » Film z fabryki PCBWay

Heh, mały nawias, a ile znaczy.

Dzięki wielkie 🙂

[ Dodano: 01-01-2015, 22:01 ]

marek1707 , Myślałem od początku nad takim właśnie rozwiązaniem z instrukcją switch ale nie mam wlaśnie pojęcia jak zdefiniować zmienną "stan_czujnikow".

Jak właśnie zrobić, żeby w zmiennej były tylko stany z 3 czujników a nie z całego PIN C ?

Po prostu przesunąć bitowo PINC ?

Link do komentarza
Share on other sites

Do tego właśnie używa sie operatora & (iloczyn), na wartość portu nakładasz maskę bitową np.

uint8_t zmienna = PORTC & 0x0000 0111

Spacja tak dla lepszego wyglądu 🙂

Link do komentarza
Share on other sites

No i jednak wciąż pojawia się problem.

Gdy kod jest zrobiony dla jednego czujnika, to po przyłożeniu do niego kartki silniki zaczynają chodzić .

Gdy kod jest taki jak napisaliście tzn.

if (!(PINC&(1<<PC0)&(PINC&(1<<PC1)))) 
{ 
   PORTD |= (1<<PD0); 
   PORTD &= ~(1<<PD1); 
}

silniki zaczynają pracować od razu po wgraniu kodu do atmegi, czyli jakby od razu widzą stan niski na czujnikach, pomimo, że nie są one ruszane. Co jest nie tak?

Link do komentarza
Share on other sites

Najpierw musisz zrozumieć co robią operacje logiczne i jak operuje się bitami. Zastanów się co daje zanegowany iloczyn, jaka to jest operacja ? Musisz wykonać iloczyn bitowy nie logiczny.

Link do komentarza
Share on other sites

Wlaśnie najgorsze chyba jest to, że wiem o co chodzi w operacjach logicznych. Ale jak widać teria to nie praktyka.

Po rozpisaniu na kartce wyszło mi tak :

if(!((PINC&(1<<PC0))&&((PINC&(1<<PC1)))))

Czyli gdy oba czujniki są w stanie niskim to :

PINC&(1<<PC0)=0x00
PINC&(1<<PC1)=0x00

Ich iloczn logiczny wyniesie 0 , a negacja na końcu da nam jedynkę co sprawi, że if będzie spełnione. Dobrze myślę?

[ Dodano: 01-01-2015, 22:58 ]

No pięknie. Już dawno bym to ogarnął. Dlaczego był taki problem? Kynar od zasilania czujników się pięknie urwał. Idę spać, tak czy siak pomogliście bo wcześniej z kablami było w porządku, tylko ja zapomniałem o roli nawiasów.

Link do komentarza
Share on other sites

Proponowałbym odejść od rozpisywania wszystkich stanów czujników jako "kejsy". Dodasz czwarty czujnik, to jeszcze sobie poradzisz, ale przy 8 będzie ciężko. Im szersza linijka czujników tym więcej nieprzewidywalnych stanów może się na niej pojawić. Po wielu próbach praktycznych i dziwnych przypadkach mogę śmiało powiedzieć, że należy tu przyjąć zasadę 2^N. Dla 8 czujników będziesz miał 256 możliwości.

Najlepiej każdemu czujnikowi przypisać wagę i pozycje określać jako średnią ważoną.

Link do komentarza
Share on other sites

Heh, to całkiem zabawne, bo właśnie dziś się dowiedziałem od kolegi o tym sposobie.

Póki co chciałem po prostu na spokojnie zrobić prostego LF'a żeby był gotowy.

To mi na pewno da motywację do dalszych działań.

Wiadomo, że dla czujników > 4 zabawa z i"if" nie ma sensu, ale wszystko przede mną ! 🙂

Link do komentarza
Share on other sites

Bądź aktywny - zaloguj się lub utwórz konto!

Tylko zarejestrowani użytkownicy mogą komentować zawartość tej strony

Utwórz konto w ~20 sekund!

Zarejestruj nowe konto, to proste!

Zarejestruj się »

Zaloguj się

Posiadasz własne konto? Użyj go!

Zaloguj się »
×
×
  • Utwórz nowe...

Ważne informacje

Ta strona używa ciasteczek (cookies), dzięki którym może działać lepiej. Więcej na ten temat znajdziesz w Polityce Prywatności.