Отговори на тема  [ 33 мнения ]  Отиди на страница 1, 2, 3  Следваща
PIC16f628A програма 
Автор Съобщение
Ранг: Минаващ
Ранг: Минаващ
Аватар

Регистриран на: Пон Май 06, 2013 11:58 pm
Мнения: 15
Мнение PIC16f628A програма
Здравейте, сега навлизам в програмирането на PIC-ове и все още не знам доста...

Тръгнах да си играя с горепосочения пик...
Та пиша на C и се чудя как ще стане, че когато на RA1,2,3,4 имам светодиоди и на RB1,2,3,4 съответните им бутони и когато натисна бутон 1 да се изгаси ra1, натисна бутон 2 да се изгаси RA2, и съответни RB4->RA4, RB3->RA3...

RA0 ми е входящ старт на програмата...

Код:

#include <htc.h> //CALL PIC CONFIGS
#include <stdio.h> //CALL LIBRARY
#include <stdlib.h> //CALL LIBRARY
#define _XTAL_FREQ 4000000 //SET XTAL FREQ on 4MHZ

__CONFIG(FOSC_INTOSCIO & WDTE_OFF & PWRTE_OFF & MCLRE_ON & BOREN_ON & LVP_OFF & CPD_OFF & CP_OFF);

void delayS(int s){
    for(int i=0; i<s; i++){
        __delay_ms(800);
    }
}

/*void closePin(int b1, int b2, int b3, int b4){
    if(b1==1){
        RA1=0;
    }else if(b2==1){
        RA2=0;
    }else if(b3==1){
        RA3=0;
    }else if(b4==1){
        RA4=0;
    }

}*/

int main(int argc, char** argv) {
    TRISA = 0b01100001;
    TRISB = 0b00011110;
    PORTB = 0x00;
    OSCF = 1;
    while(1){
        if(RA0==1){
            while(RB1==0 || RB2==0 || RB3==0 || RB4==0){
                RA1=1;RA2=1;RA3=1;RA4=1;
                   //Тука вече не знам как да изгасям съответния светодиод независимо, кой бутон съм натиснал да изгасне точно неговия светодиод ;(
            }
        }else if(RA6=1){
            delayS(8);
            RA7=1;
            delayS(1);
        }
    }

    return (EXIT_SUCCESS);
}




Изображение


Пон Фев 10, 2014 6:50 pm
Профил
Ранг: Почетен член
Ранг: Почетен член
Аватар

Регистриран на: Съб Сеп 17, 2005 5:07 pm
Мнения: 813
Местоположение: Сливен
Мнение Re: PIC16f628A програма
Не знам на колко си годинки но е похвално ,че си почнал от някъде и се блъскаш Браво !
Сега по темата ... не пиша точно на този компилатор и може да греша синтаксиса но образно мисля ще ме разбереш.
1.На практика запомни ВИНАГИ когато имаш механичен бутон ей така за късмет слагай по един delayms(50) че и повече за да избегнеш "претреперването" на пластинките :)
2.Ако искаш РА0 да ти стартира програмата тогава дефинирай едно флагче (да речем start) и го вдигай/сваляй при натиснат РА0;

while(1)
{
if(RA0==1) // ако има натиснат РА0
{
delay_ms(50);
start=!start;//тук вдигаш или сваляш флагчето
}
while(start) {//циклиш докато ти е вдигнато флагчето т.е. стартирал си си програмката :)
if(RB1){
delay_ms(50);
RA1=!RA1; //не помня можеше ли по този начин да четеш регистъра едновременно за вход и изход ... но образно казано това е "трика" , ако не можеш по този начин просто си дефинирай по едно флагче за всеки пин и си го манипулирай .
}
......... /// за четирите бутона еднакво
}
}

има и много по оптимални начини но за насока и ориентир се надявам да съм помогнал :)

_________________
Код:
while(true);


Пон Фев 10, 2014 11:32 pm
Профил ICQ
Ранг: Минаващ
Ранг: Минаващ
Аватар

Регистриран на: Пон Май 06, 2013 11:58 pm
Мнения: 15
Мнение Re: PIC16f628A програма
valioman написа:
Не знам на ... за насока и ориентир се надявам да съм помогнал :)


Здравей,
на 18 съм и те първа почвам да му го уча електрониката. Все още съм в гимназия, но специалността, която съм си избрал за ВУЗ-а ми се налага да уча и електроника та си и падам по програмирането и реших поне да имам някакви знания за PIC-овете и как се управляват.

С 2 изречения това, което се стремя да направя. Двете програми да работят разделено и в зависимост от настиснатото копче /RA6, RA0/, да се изпълнява съответната програма. След изпълняване на програмата при повторно натискане да се изпълнява отново.
- Добре това има по-лесен начин да го направя, след като се изпълнят програмите да ресетвам PIC-а и отново да гледам, кое копче ще бъде натиснато, но не искам така...

Опитах по твоя начин и никакъв напредък :(

Код:

void prog1(){
    if(RA6==1){
        delayS(1);
        while(RA6==1){
            if(RA6==1){
                RA7=1;

            }else{
                RA7=0;
            }
        }
    }
}

void prog2(){
    RA1=1;RA2=1;RA3=1;RA4=1;
    while(RB1==0 || RB2==0 || RB3==0 || RB4==0){
        if(RB1==1 && RA1==1){
            __delay_ms(50);
            RA1=0;
        }
        if(RB2==1 && RA2==1){
            __delay_ms(50);
            RA2=0;
        }
        if(RB3==1 && RA3==1){
            __delay_ms(50);
            RA3=0;
        }
        if(RB4==1 && RA4==1){
            __delay_ms(50);
            RA4=0;
        }
    }
}

int main(int argc, char** argv) {
    TRISA = 0b01100001;
    TRISB = 0b00011110;
    PORTA = 0x00;
    PORTB = 0x00;
    OSCF = 1; //OSC FREQUENSY AT 4MHZ

    int startL=0, startW=0;
    while(1){
        if(RA6==1){
            __delay_ms(50);
            startL=!startL;
        }
        while(startL){
            prog1();
        }
        if(RA0==1){
            __delay_ms(50);
            startW=!startW;
        }
        while(startW){
            prog2();
        }
    }
   

    return (EXIT_SUCCESS); //RETURN TO BUILDER SUCCESS
}



Изображение


Вто Фев 11, 2014 12:28 am
Профил
Ранг: Почетен член
Ранг: Почетен член
Аватар

Регистриран на: Съб Сеп 17, 2005 5:07 pm
Мнения: 813
Местоположение: Сливен
Мнение Re: PIC16f628A програма
Обатачил си се повече :) .. сега дай да подкараме едната па после мисли за втора "подпрограма"
та по първата .
Дефинирай 4 променливи от тип boolean
да речем b1,b2,b3,b4 ı edna startW

в основния while нищо не пипай само махни
if(RA6==1){
__delay_ms(50);
startL=!startL;
}
while(startL){
prog1();
}

засега ... пък после щ еги включваш но по малко по елегантен начин .

сега да помислим за prog2()

няма смисъл вътре да въртиш цикъл защото while(startW)..... ти го прави
сега да помислим .... като натиснем бутон РБ1 искаме да светнем или угаснем РА1. Приемаме ,че променливата "флаг" b1 ти е състоянието на изхода РА1 т.е. когато направиш РА1=b1; това значи че каквото е състоянието на b1 (1 или 0) това щ ее и на изхода.
накратко

if(RB1==1){ //натиснат бутон
delayms(50); //трепкането
b1=!b1; //смяна на нсъстоянието на флагчето т.е. това е еквивалентно на израза if(b1==1)b1=0;else b1=1;
RA1=b1; //присвояване стойността на флагчето на пин-а
} // и така за 4 те пина

_________________
Код:
while(true);


Вто Фев 11, 2014 12:43 am
Профил ICQ
Ранг: Популярен
Ранг: Популярен

Регистриран на: Пон Мар 22, 2010 8:52 pm
Мнения: 328
Мнение Re: PIC16f628A програма
RA1 = !RA1;
Не работи ли?


Вто Фев 11, 2014 6:58 am
Профил
Ранг: Форумен бог
Ранг: Форумен бог
Аватар

Регистриран на: Сря Апр 27, 2005 12:48 pm
Мнения: 6094
Мнение Re: PIC16f628A програма
порта(GPIO вход) го ползвай за четене, а LAT-а за запис (GPIO изход)

_________________
main[-1u]={1};


Вто Фев 11, 2014 8:44 am
Профил ICQ
Ранг: Форумен бог
Ранг: Форумен бог

Регистриран на: Нед Дек 19, 2004 6:26 pm
Мнения: 1628
Местоположение: Сливен
Мнение Re: PIC16f628A програма
Не съм пикльофен, но си мисля, че това ще ти е от полза
http://www.mikroe.com/products/view/285 ... ming-in-c/


Вто Фев 11, 2014 10:23 am
Профил ICQ
Ранг: Минаващ
Ранг: Минаващ
Аватар

Регистриран на: Пон Май 06, 2013 11:58 pm
Мнения: 15
Мнение Re: PIC16f628A програма
valioman написа:
Обатачил си се повече :) .. сега дай да подкараме едната па после мисли за втора "подпрограма"
та по първата .
Дефинирай 4 променливи от тип boolean
да речем b1,b2,b3,b4 ı edna startW

в основния while нищо не пипай само махни
if(RA6==1){
__delay_ms(50);
startL=!startL;
}
while(startL){
prog1();
}

засега ... пък после щ еги включваш но по малко по елегантен начин .

сега да помислим за prog2()

няма смисъл вътре да въртиш цикъл защото while(startW)..... ти го прави
сега да помислим .... като натиснем бутон РБ1 искаме да светнем или угаснем РА1. Приемаме ,че променливата "флаг" b1 ти е състоянието на изхода РА1 т.е. когато направиш РА1=b1; това значи че каквото е състоянието на b1 (1 или 0) това щ ее и на изхода.
накратко

if(RB1==1){ //натиснат бутон
delayms(50); //трепкането
b1=!b1; //смяна на нсъстоянието на флагчето т.е. това е еквивалентно на израза if(b1==1)b1=0;else b1=1;
RA1=b1; //присвояване стойността на флагчето на пин-а
} // и така за 4 те пина



При натискане на RA0 светват RA1,RA2,RA3,RA4 и чак когато се натисне RB1,RB2,RB3,RB4 се изгася съответния светодиод. При натискане на RA0 програмата се повтаря, а не когато натисна RB1-4 да светват и изгасят диодите. Целта е винаги да изгасят ако са светнати..


Вто Фев 11, 2014 10:50 am
Профил
Ранг: Почетен член
Ранг: Почетен член
Аватар

Регистриран на: Съб Сеп 17, 2005 5:07 pm
Мнения: 813
Местоположение: Сливен
Мнение Re: PIC16f628A програма
Е това е друга бира тогава :) но принципа е същия .
while(1){
if(RA0==1){
delayms(50);
startW=!startW;
RA1=RA2=RA3=RA4=startW;//swetwame/izgasiame wsichki
}
if(startW){
if(RB1){delayms(50);RA1=0;}//pri natiskane gasim syotwetnia
........//// i taka za wsichki
}
}

Дано захапа идеята на променливите и логиката на работа .
Протеуса има едно много хубаво нещо а именно ,че можеш да дебъгваш т.е. задай вместо .hex -> .cof файла и после с brekpoints i F10 можеш да си се движиш по кода и да си гледаш стойности на променливите и регистрите и да видиш постъпково как се изпълнява програмата ти и какво се случва на всеки един ред ;)

_________________
Код:
while(true);


Вто Фев 11, 2014 11:21 am
Профил ICQ
Ранг: Популярен
Ранг: Популярен

Регистриран на: Пон Мар 22, 2010 8:52 pm
Мнения: 328
Мнение Re: PIC16f628A програма
valioman написа:
Е това е друга бира тогава :) но принципа е същия .
while(1){
if(RA0==1){
delayms(50);
startW=!startW;
RA1=RA2=RA3=RA4=startW;//swetwame/izgasiame wsichki
}
if(startW){
if(RB1){delayms(50);RA1=0;}//pri natiskane gasim syotwetnia
........//// i taka za wsichki
}
}

Дано захапа идеята на променливите и логиката на работа .
Протеуса има едно много хубаво нещо а именно ,че можеш да дебъгваш т.е. задай вместо .hex -> .cof файла и после с brekpoints i F10 можеш да си се движиш по кода и да си гледаш стойности на променливите и регистрите и да видиш постъпково как се изпълнява програмата ти и какво се случва на всеки един ред ;)

Така написана програмата докато е натиснат бутона на РА0 StartW, ше прави тогъл през 50mS. И при отпускане, ще е гадаене в какаво състояние ще е. И също така ако целта е просто при натискане на RBx съответният диод да изгасне закъснението от 50мС е излишно. Може би нещо подобно:

x = RB1;
while(1)
{
delayms(20);
x1 = RB1;
if(x!= x1)
{
x = x1;
start = !start;
}
if(start)
{
if(RB1)
RA1 = 0; // led off
}
else
RA1=RA2=RA3=RA4=1; // all off
}


Вто Фев 11, 2014 11:37 am
Профил
Ранг: Почетен член
Ранг: Почетен член
Аватар

Регистриран на: Съб Сеп 17, 2005 5:07 pm
Мнения: 813
Местоположение: Сливен
Мнение Re: PIC16f628A програма
Начини и мераци много ... :) разбира се че на практика ще трябва да се сложат подходящите закъснения и полирания но за виртуални тестове на рпотеус не са критични . Аи доколкото виждам детето не може да оправи битовете а ние искаме времена да смята ;) . Едно по едно ... най лесно е да му се напише наготово ама не е това целта .

_________________
Код:
while(true);


Вто Фев 11, 2014 12:04 pm
Профил ICQ
Ранг: Минаващ
Ранг: Минаващ
Аватар

Регистриран на: Пон Май 06, 2013 11:58 pm
Мнения: 15
Мнение Re: PIC16f628A програма
valioman написа:
Начини и мераци много ... :) разбира се че на практика ще трябва да се сложат подходящите закъснения и полирания но за виртуални тестове на рпотеус не са критични . Аи доколкото виждам детето не може да оправи битовете а ние искаме времена да смята ;) . Едно по едно ... най лесно е да му се напише наготово ама не е това целта .


Здравей, не искам да се хваля но съм се занимавал с програмиране, мога да чета код всякакъв и да го разбирам. Отделно от това се занимавам и с правенето на сайтове и мога да разсъждавам логично, кое как преди кое трябва да стане, но като почнах пиковете, явно моят начин на логическо мислене не съвпада с техния :D. Така че, за мен няма никакво значение дали ще бъде цял код или отделни сегменти подсказани. Аз още от началото разбрах, че не сте ме разбрали какво се мъча да направя, но ще дойде сетния старт на програмата, че когато натисна START в протеуса да няма бъг ;d Все още не съм го направил. Ще видя довечера или утре, ще се помъча още малко. Все пак Ви благодаря много :)


Вто Фев 11, 2014 6:54 pm
Профил
Ранг: Минаващ
Ранг: Минаващ
Аватар

Регистриран на: Пон Май 06, 2013 11:58 pm
Мнения: 15
Мнение Re: PIC16f628A програма
Изведнъж музата ми дойде и седнах да го оправя кода, ся всичко бачка ;) Реших да го направя по най-елементарния начин за мен. Благодаря на всички Ви за времето, което оделихте за мен (:

Код:
void delayS(int s){
    for(int i=0; i<s; i++){
        //RA0 = 1;
        __delay_ms(400);
       // RA0 = 0;
        __delay_ms(400);
    }
}

void prog1(){
   delayS(1);
   int chek=0;
   while(chek==0){
      if(RA6==1){
         RA7=1;
      }else{
         RA7=0;
         chek=1;
      }
   }
}

void prog2(){
    RA1=1;RA2=1;RA3=1;RB0=1;
    int chek=0;
    while(chek==0){
        if(RB1==1 && RA1==1){
            RA1=0;
        }else if(RB2==1 && RA2==1){
            RA2=0;
        }else if(RB3==1 && RA3==1){
            RA3=0;
        }else if(RB4==1 && RB0==1){
            RB0=0;
        }else if(RA1==0 && RA2==0 && RA3==0 && RB0==0){
            chek=1;
        }
    }
}

int main(int argc, char** argv) {
    TRISA = 0b01100001;
    TRISB = 0b00011110;
    PORTA = 0x00;
    PORTB = 0x00;
    OSCF = 1; //OSC FREQUENSY AT 4MHZ

    while(1){     
        if(RA0 == 1){
            prog2();
        }
        if(RA6==1){
            prog1();
        }   
    }
    return (EXIT_SUCCESS); //RETURN TO BUILDER SUCCESS
}


Изображение


Пет Мар 07, 2014 8:12 pm
Профил
Ранг: Форумен бог
Ранг: Форумен бог

Регистриран на: Нед Сеп 26, 2004 9:21 pm
Мнения: 30686
Местоположение: София
Мнение Re: PIC16f628A програма
Без да се засягаш, но каквото и да си писал явно е било далеч от истината ..
while(chek==0) избягвай такива цикли, както казаха колегите варианти има много, един от най-удобните е прекъсване, но дори и с полиране да е пак е по добре от този безкраен while който ако забелязваш може да те държи вътре безкрайно дълго време. От друга страна ако WDT като му изтече времето ще те рестартне .. и от там насетне нкой не зна екакво ще стане.


Съб Мар 08, 2014 7:37 pm
Профил
Ранг: Минаващ
Ранг: Минаващ

Регистриран на: Пон Авг 15, 2011 5:37 pm
Мнения: 12
Мнение Re: PIC16f628A програма
ToHu, без да се засягаш ама аргументите са ти "майко мила". Какво значи while може да го държи вечно? Естествено че може, докато е изпълнено условието check == 0. По този начин maguss4o остава в цикъла на prog1, prog2. Но maguss4o много хитро е направил и условие за излизане от така наречения от теб "вечен цикъл", и това условие е:
Код:
else if(RA1==0 && RA2==0 && RA3==0 && RB0==0){
            chek=1;
        }

А това за WDT e направо ъпсурд. След като се рестартне процесора е абсолютно ясно къде ще отиде. Има едно нещо наречено reset vektor, ако погледнеш datasheet ще видиш че при рестарт няма "кой знае какво ще стане". Има точно определен адрес от програмната памет "който ще стане :D"

maguss4o много добре за начало! Като за образувателна цел програмката е супер!


Нед Мар 09, 2014 4:03 pm
Профил
Покажи мненията от миналия:  Сортирай по  
Отговори на тема   [ 33 мнения ]  Отиди на страница 1, 2, 3  Следваща

Кой е на линия

Потребители разглеждащи този форум: 0 регистрирани и 1 госта


Вие не можете да пускате нови теми
Вие не можете да отговаряте на теми
Вие не можете да променяте собственото си мнение
Вие не можете да изтривате собствените си мнения
Вие не можете да прикачвате файл

Търсене:
Иди на:  
Powered by phpBB © 2000, 2002, 2005, 2007 phpBB Group.
Designed by ST Software for PTF.
Хостинг и Домейни