اطلاعیه

Collapse
No announcement yet.

راهنمایی برای خطا در کد اسکن کیپد

Collapse
X
 
  • فیلتر
  • زمان
  • Show
Clear All
new posts

    راهنمایی برای خطا در کد اسکن کیپد

    سلام بر همه..
    بنده نمونه کدی در کدویژن برای اسکن کیپد نوشتم اما در عملکرد دچار اختلال شد و با تغییر یک سطر این مشکل برطرف شد اما علتش رو نمیدونم و میخوام از دوستان بپرسم:
    این نمونه کد برنامه هست که بصورت خلاصه نوشتم و بقیه برنامه رو پاک کردم..در اینجا متغیر عمومی A یک عدد رو از خوندن صفحه کلید میگیره...
    کد:
    #include <mega16a.h>
    #include <delay.h>
    #define c1 PINA.4 
    #define c2 PINA.5 
    #define c3 PINA.6 
    #define c4 PINA.7 
    
    flash unsigned char row[]={0b11111110,0b11111101,0b11111011,0b11110111};
    unsigned char A ;
    
    void main(){ 
        
     unsigned char A1=0b10111111 , A2=0b10111111 , A3=0b10111111 ; 
     unsigned char r,ac;
     DDRA=0x0f;  <<<<<<<<<<<<<<<<<<<
     
     while(1)
     {
     A=20; 
     for(r=0;r<4;r++){
    ac=4;
    PORTA=row[r];
    DDRA=0x0f;   <<<<<<<<<<<<<<<<<<<<
    if(c1==0) ac=0;
    if(c2==0) ac=1;
    if(c3==0) ac=2;
    if(c4==0) ac=3;
    if(!(ac==4)){
    A=(r*4)+ac;
    while(c1==0);
    while(c2==0);
    while(c3==0);
    while(c4==0);}
    }

    اضافه شده در تاریخ :
    حالا مشکل اینجاست که اگه عبارت DDRA=0x0f رو که با فلش مشخص شده نیارم این مشکل ایجاد میشه..درواقع با اینکه در ابتدای برنامه و قبل از حلقه while چهار پین اول پورت A رو خروجی کردم اما بعد از خلقه هم لازمه که اینکارو بکنم تا برنامه بدرستی اجرا بشه.درحالی که این کار قبلا و در ابتدای برنامه انجام شده...چرا؟

    #2
    پاسخ : راهنمایی برای خطا در کد اسکن کیپد

    من فهمیدم که هروقت عبارت PORTA=row[r رو بعد از DDRA=0x0f; که هردو داخل حلقه for هستند بیارم برنامه بدرستی اجرا نمیشه و اول باید سطح منطقی پین های پورت A رو مشخص کنم و بعد از اون جهتشون رو تعریف کنم...
    در حالی که در برنامه های دیگه مشاهده کردم که اگر اول جهت رومشخص کنیم و بعد از اون سطح منطقی رو هیچ مشکلی بوجود نمیاد...
    علت چیه؟

    دیدگاه


      #3
      پاسخ : راهنمایی برای خطا در کد اسکن کیپد

      بدون اطلاعات کافی از هیج کس انتظار کمک نداشته باشید
      هیج توضیحی از مدار - کیپد - یا دست کم از پیکربندی پایه های متصل به کیپد ندادید که برای خطایابی نیاز است
      اگر از روش کیپد ماتریسی استفاده میکنید الگوریتم به صورت زیر است

      برای کیپد چهار در چهار
      چهار پایه ی اول را ورودی و چهار پایه ی دوم را خروجی و همه را یک میکنیم
      چهار پایه ی اول را اسکن میکنیم (همه را یکجا) و جهت همه پایه ها را وارون میکنیم و همین کار را تکرار می کنیم
      اکنون می توانیم به روش جدول ماتریسی کلید فشرده شده را مشخص کنیم
      If the wind will not serve, take to the oars

      دیدگاه


        #4
        پاسخ : راهنمایی برای خطا در کد اسکن کیپد

        خب این تنها روش نیست...کدی که من نوشتم هم درسته...
        میخواستم تمام کد رو بزارم اما گفتم ساده ترش کنم قابل فهم تر میشه و راحتتره...درصورت دسترسی حتما کاملش رو میزارم...
        البته اگه این چند خط رو بخونید شاید متوجه بشید....
        در کل حطایابی و مشکل برنامه من حل شده و این مشکل ناشی از این بود که اگر DDRA رو قبل از PORTA مشحص کنم خطا در برنامه ایجاد میشه و من دنبال این هستم که چرا حطا ایجاد میشه؟
        وظیفه اسکن صفجه کلید بر عهده پورت A هست و من برنامه رو تا جایی نوشتم که یک عدد رو از صفحه کلید بخونه و در متغیر A ذخیره کنه...حالا چطوری A نمایش داده بشه مهم نیست...

        دیدگاه


          #5
          پاسخ : راهنمایی برای خطا در کد اسکن کیپد

          نوشته اصلی توسط amin tal
          خب این تنها روش نیست...کدی که من نوشتم هم درسته...
          میخواستم تمام کد رو بزارم اما گفتم ساده ترش کنم قابل فهم تر میشه و راحتتره...درصورت دسترسی حتما کاملش رو میزارم...
          البته اگه این چند خط رو بخونید شاید متوجه بشید....
          در کل حطایابی و مشکل برنامه من حل شده و این مشکل ناشی از این بود که اگر DDRA رو قبل از PORTA مشحص کنم خطا در برنامه ایجاد میشه و من دنبال این هستم که چرا حطا ایجاد میشه؟
          وظیفه اسکن صفجه کلید بر عهده پورت A هست و من برنامه رو تا جایی نوشتم که یک عدد رو از صفحه کلید بخونه و در متغیر A ذخیره کنه...حالا چطوری A نمایش داده بشه مهم نیست...
          همیشه باید از الگوریتم بهینه تر استفاده کنید.
          گاهی هم بهتر است که کدها مستقل از یک مدل میکرو خاص باشند تا براحتی و با کمترین تغییرات در پروژه ها یا میکروی دیگر قابل پیاده سازی باشند

          [code=c]

          // keypad.h

          #ifndef _KEYPAD_LIB_INCLUDED_
          #define _KEYPAD_LIB_INCLUDED_

          #include <mega16a.h>
          #include <delay.h>

          // Column config
          #define COL1 PORTC.1
          #define COL2 PORTC.2
          #define COL3 PORTC.3
          #define COL4 PORTC.4

          #define DIRC1 DDRC.1
          #define DIRC2 DDRC.2
          #define DIRC3 DDRC.3
          #define DIRC4 DDRC.4

          // Row Config
          #define ROW1 PORTA.1
          #define ROW2 PORTA.2
          #define ROW3 PORTA.3
          #define ROW4 PORTA.4

          #define DIRR1 DDRA.1
          #define DIRR2 DDRA.2
          #define DIRR3 DDRA.3
          #define DIRR4 DDRA.4

          // Place holders
          #define REG1 0x01
          #define REG2 0x02
          #define REG3 0x04
          #define REG4 0x08
          // #define REG5 0x10
          // #define REG6 0x20
          // #define REG7 0x40
          // #define REG8 0x80

          void keypad_dir(unsigned char col, unsigned char row){
          DDRC1 = col & REG1;
          DDRC2 = col & REG2;
          DDRC3 = col & REG3;
          DDRC4 = col & REG4;

          DDRR1 = row & REG1;
          DDRR2 = row & REG2;
          DDRR3 = row & REG3;
          DDRR4 = row & REG4;
          }

          void keypad_set(unsigned char col, unsigned char row){
          COL1 = col & REG1;
          COL2 = col & REG2;
          COL3 = col & REG3;
          COL4 = col & REG4;

          ROW1 = row & REG1;
          ROW2 = row & REG2;
          ROW3 = row & REG3;
          ROW4 = row & REG4;
          }

          unsigned char keypad_column(){
          return (COL4 << 3) | (COL3 << 2) | (COL2 << 1) | (COL1);
          }

          unsigned char keypad_row(){
          return (ROW4 << 3) | (ROW3 << 2) | (ROW2 << 1) | (ROW1);
          }

          unsigned char keypad_read(void){

          unsigned char col, row;

          keypad_set(0x00, 0x00);
          delay_us(5);
          keypad_dir(0x0f, 0x00);
          delay_us(5);
          keypad_set(0x0f, 0x00);
          delay_us(5);
          row = keypad_row();

          keypad_set(0x00, 0x00);
          delay_us(5);
          keypad_dir(0x00, 0x0f);
          delay_us(5);
          keypad_set(0x00, 0x0f);
          delay_us(5);
          col = keypad_col();

          // now we have row and column data

          if(row == REG1) row = 0;
          else if(row == REG2) row = 1;
          else if(row == REG3) row = 2;
          else if(row == REG4) row = 3;
          else return 0; // invalid data

          if(col == REG1) col = 0;
          else if(col == REG2) col = 1;
          else if(col == REG3) col = 2;
          else if(col == REG4) col = 3;
          else return 0; // invalid data

          return row * 4 + col;
          }

          #endif
          [/code]

          [code=c]
          //main.c

          #include <mega16a.h>
          #include "keypad.h"

          int main(){
          unsigned char key;
          // device_init()

          while(1){
          key = keypad_read();
          if(key > 0){
          // a valid keypress detected ...
          // ranging from 1 to 16
          }
          }
          }
          [/code]

          توی برنامه فقط تابع
          keypad_read()
          فراخوانی خواهد شد. بقیه ی تابع ها کمکی هستند
          If the wind will not serve, take to the oars

          دیدگاه

          لطفا صبر کنید...
          X