单片机
返回首页

MSP430F149 反应速度测试仪 oled 显示

2022-09-15 来源:csdn

/***********************************

利用MSP430设计一款“反应速度测试仪”

 在P2.3口接有一高亮度LED(低电平点亮)

P2.3口接有一按键(低电平表示按下)。

要求受试者在看到红灯亮后立即按键。

测量从亮灯到按键之间的时间并显示出来,就是受试者的反应时间

***********************************/

#include 'msp430x14x.h'

#include 'iic.h'

//使用系统自带延时

#define CPU_F ((double)1000000)

#define delay_ms(x)  __delay_cycles((long)(CPU_F*(double)x/1000.0))

#define delay_us(x)  __delay_cycles((long)(CPU_F*(double)x/1000000.0))


unsigned int TA_OverflowCnt;        //TA溢出次数存放变量  

unsigned long int ResponseTime;     //执行时间存放变量  


void display()     //显示

{


     //OLED_ShowString(0, 2, 'haha:',16);

    // OLED_ShowString(0, 0, '20',16);

     //OLED_ShowChar(33, 0, '-',16);

     //OLED_ShowChar(57, 0, '-',16);

   //  OLED_ShowChar(78, 2,':',16);

    // OLED_ShowChar(102, 2,':',16);

     OLED_ShowCHinese(0,0,0);      //显示汉字 反

     OLED_ShowCHinese( 16,0,1);   //显示汉字 应

     OLED_ShowCHinese(32,0,2);   //显示汉字 时

     OLED_ShowCHinese(48,0,3);   //显示汉字 间

     OLED_ShowChar(64, 0,':',16);  

     //OLED_ShowString(0, 6, 'new money:',16);

     OLED_ShowNum(0,6,ResponseTime,5,16);

     OLED_ShowString(0, 2, 'TAR:',16);

     OLED_ShowNum(32,2,TAR,6,16);

     OLED_ShowNum(0,4,TA_OverflowCnt,2,16);

}


void main( void )

{

  

  WDTCTL = WDTPW + WDTHOLD;     //关闭看门狗

  //BCSCTL1 = 0;        //BTCTL上电不初始化,需要人为清零

  Initial_LY096BG30();        //oled 初始化

  OLED_Clear();

  _EINT();

  P2DIR |= BIT3 + BIT7;    //红灯所在IO设为输出

  _EINT();          //总中断允许

  while(1)

  {

    TA_OverflowCnt = 0;   //长执行时间函数TA会溢出,用一变量计数溢出次数

    P2OUT &= ~BIT3;        //灯亮

    TACTL = TASSEL_1 + MC_2 + TAIE +TACLR;    //TA清零并开始计时,ACLK,开中断

    while(P1IN & BIT0);   //等待P1.5按键被按下

    TACTL = TASSEL_1 + MC_0;    //TA停止计时

    P2OUT |= BIT3;             //灯灭

    ResponseTime = TA_OverflowCnt*65536 + TAR;    //读取TA计数值及溢出次数计算总周期

    OLED_ShowNum(82,0,ResponseTime,5,16);

    ResponseTime = (TA_OverflowCnt*1000000)/32768;     //将ACLK周期数换算成毫秒时间值

    display();    //显示反应时间测量结果,精确到毫秒

    __delay_cycles(3000000);     //延迟约3s,重新开始

  }

   

  

}


#pragma vector = TIMERA1_VECTOR

__interrupt void TA_ISR(void)

{

  switch(TAIV)

  {

  case 2: break;

  case 4: break;

  case 10:

          {

            P2OUT ^= BIT7;

            TA_OverflowCnt++;   //TA每次溢出,溢出次数变量+1

          }

          break;

  }

}


#ifdef  iic_c

      #define iic_ext

#else

      #define  iic_ext extern

#endif


#define uchar unsigned char

#define uint  unsigned int

#define SET_SCL         P2OUT|=BIT0;

#define CLR_SCL         P2OUT&=~BIT0;

#define SET_SDA         P2OUT|=BIT1;

#define CLR_SDA         P2OUT&=~BIT1;

#define SDA_IN          P2DIR&=~BIT1;

#define SDA_OUT         P2DIR|=BIT1;     //SDA P2.1

#define SCL_OUT         P2DIR|=BIT0;    //SCL P2.0

#define SDA_Read        P2IN&BIT1

#define OLED_CMD        0 //写命令

#define OLED_DATA       1 //写数据

iic_ext void delay();

iic_ext void Initial_LY096BG30();

iic_ext void Delay_1ms(unsigned int Del_1ms);

iic_ext void Delay_50ms(unsigned int Del_50ms);

iic_ext void picture_1();

iic_ext void fill_picture(unsigned char fill_Data);

iic_ext uchar IIC_Addresing(uchar addr);

iic_ext void OLED_Clear();

iic_ext void OLED_ShowCHinese(uchar x,uchar y,uchar n);

iic_ext void OLED_ShowString(uchar x,uchar y,uchar *ptr,uchar size);

iic_ext void OLED_ShowChar(uchar x,uchar y,uchar ptr,uchar size);

iic_ext void OLED_DrawBMP(unsigned char x0, unsigned char y0,unsigned char x1, unsigned char y1,unsigned char BMP[]);

iic_ext void OLED_ShowNum(uchar x,uchar y,uint num,uchar len,uchar size);

iic_ext void OLED_DrawPoint(uint x,uchar y,uchar t);

iic_ext void OLED_Refreash_Gram();

iic_ext void OLED_Fill(uchar x1,uchar y1,uchar x2,uchar y2,uchar dot);

iic_ext void Oled_RunShow(uchar y,uchar num,uchar len,uchar betw);

iic_ext void OLED_ShowOneHZ(uint x,uchar y,uchar chr,uchar size,uchar mode);

iic_ext void OLED_Clear_kuai(uchar x,uchar y,uchar dat);

iic_ext void OLED_ShowHz(uchar x,uchar y,uchar len,uchar size);

iic_ext void OLED_ShowBattery(uchar x,uchar y,uchar no);

iic_ext void OLED_ShowBatCharge(uchar x,uchar y,uchar len,uchar size);

iic_ext void OLED_DS1302_Num(uchar x,uchar y,uint num,uchar size);

//iic_ext void  OLED_Show_DS1302(uchar x,uchar y,uchar no);


```c

#define iic_c

#include

#include'iic.h'

#include'oled.h'

//uchar OLED_GRAM0[128][8];

//uchar OLED_GRAM1[128][8];

void delay()

{

unsigned char q0;

for(q0=0;q0<3;q0++)

{

_NOP();

}

}

void IIC_Start()

{

    SDA_OUT;

    SCL_OUT;      //设置为输出模式

    SET_SDA;

    SET_SCL;

    delay();

    CLR_SDA;

    delay();

    CLR_SCL;

    delay();

}

void IIC_Stop()

{

    SDA_OUT;

    SCL_OUT;

    CLR_SCL;

    CLR_SDA;

    delay();

    SET_SCL;

    delay();

    SET_SDA;

    delay();


}

uchar Write_IIC_Byte(uchar dat)

{

      uchar ack=0;

      uchar mask;

      SDA_OUT;

      delay();

      for(mask=0x80;mask!=0;mask>>=1)

      {

            if((mask&dat)==0)

            {

                CLR_SDA;

            }

            else

            {

                SET_SDA;

            }

            delay();

            SET_SCL;

            delay();

            CLR_SCL;

            delay();

      }

      SET_SDA;

      delay();

      SDA_IN;

      SET_SCL;

      delay();

      ack=SDA_Read;   //接收应答位

      CLR_SCL;


      delay();

      return ack;

}

/*

uchar IIC_Addresing(uchar addr)

{

      uchar ack=0;

      IIC_Start();

      ack= Write_IIC_Byte(addr);

      IIC_Stop();

      return ack;

}

*/

 /**********************************************

// IIC Write Command

**********************************************/

void Write_IIC_Command(unsigned char IIC_Command) //写命令

{

   IIC_Start();

   Write_IIC_Byte(0x78);            //Slave address,SA0=0

   Write_IIC_Byte(0x00); //write command

   Write_IIC_Byte(IIC_Command);

   IIC_Stop();

}

/**********************************************

// IIC Write Data

**********************************************/

void Write_IIC_Data(unsigned char IIC_Data)        //写数据

{

   IIC_Start();

   Write_IIC_Byte(0x78);

   Write_IIC_Byte(0x40); //write data

   Write_IIC_Byte(IIC_Data);

   IIC_Stop();

}


void  OLED_WR_Byte(uchar dat,uchar cmd)

{

      if(cmd)

      {

          Write_IIC_Data(dat);  //写数据

      }

      else

      {

          Write_IIC_Command(dat);   //写指令

      }

}

/********************************************

// fill_Picture

********************************************/

void fill_picture(unsigned char fill_Data)

{

unsigned char m,n;

for(m=0;m<8;m++)

{

OLED_WR_Byte(0xb0+m,OLED_CMD);

            OLED_WR_Byte(0x00,OLED_CMD);

            OLED_WR_Byte(0x10,OLED_CMD);

           // Write_IIC_Command(0xb0+m); //page0-page1

//Write_IIC_Command(0x00); //low column start address

//Write_IIC_Command(0x10); //high column start address

for(n=0;n<128;n++)

{

OLED_WR_Byte(fill_Data,OLED_DATA);

}

}

}

#if(0)

/******************************************

// picture

******************************************/

void picture_1()            //显示图片

{

  unsigned char x,y;

  unsigned int i=0;

  for(y=0;y<8;y++)

    {

      Write_IIC_Command(0xb0+y);    //页地址

      Write_IIC_Command(0x00);      //低位

      Write_IIC_Command(0x10);      //高位

      for(x=0;x<128;x++)

        {

          Write_IIC_Data(show1[i++]);

        }

    }

}

#endif

/***********************Delay****************************************/

void Delay_50ms(unsigned int Del_50ms) //

{

unsigned int m;

for(;Del_50ms>0;Del_50ms--)

for(m=6245;m>0;m--);

}


void Delay_1ms(unsigned int Del_1ms) //

{

unsigned char j;

while(Del_1ms--)

{

for(j=0;j<123;j++);

}

}

坐标位置/

void OLED_Set_Pos(uchar x,uchar y)

{

      OLED_WR_Byte(0xb0+y,OLED_CMD);

      OLED_WR_Byte((x&0x0f),OLED_CMD);

      OLED_WR_Byte(((x&0xf0)>>4)|0x10,OLED_CMD);

}

void OLED_Clear_kuai(uchar x,uchar y,uchar dat)

{

     // uchar pos,bx,temp=0;

     // pos=7-y/8;

      OLED_Set_Pos(x,y);


      OLED_WR_Byte(dat,OLED_DATA);

}

void OLED_Fill(uchar x1,uchar y1,uchar x2,uchar y2,uchar dot)

{

     uchar x,y;

      for(x=x1;x      {

            for(y=y1;y            OLED_Clear_kuai(x,y,dot);

      }

    //  OLED_Refresh_Gram();//更新显示

}

/*

//更新显存

void OLED_Refresh_Gram()

{

     uint i,n;

     for(i=0;i<8;i++)

     {

            OLED_WR_Byte(0xb0+i,OLED_CMD);

            //OLED_WR_Byte(0xb0,OLED_CMD);

            OLED_WR_Byte(0x00,OLED_CMD);

            OLED_WR_Byte(0x10,OLED_CMD);

            for(n=0;n<128;n++)

            {

            OLED_WR_Byte(OLED_GRAM0[n][i],OLED_DATA);

            }


     }


}

滚屏清零

void OLEDRun_Clear()

{

      uint i,n;

      for(i=0;i<8;i++)

      {

            for(n=0;n<128;n++)

            {

                  OLED_GRAM0[n][i]=0;

            }

      }

      OLED_Refresh_Gram(); //更新显示

}

//点亮点

void OLED_DrawPoint(uint x,uchar y,uchar t)

{

      uchar pos,bx,temp=0;

      if(x>255||y>63) return;

      pos=7-y/8;        //第几页

      bx=y%8;           //页的第几行

temp=1<<(7-bx);   //y方向上对应的点 0-7

if(t)OLED_GRAM0[x][pos]|=temp;

else OLED_GRAM0[x][pos]&=~temp;

      OLED_Refresh_Gram();

}


区域填充  0 灭 1亮/

void OLED_Fill(uchar x1,uchar y1,uchar x2,uchar y2,uchar dot)

{

      uchar x,y;

      for(x=x1;x      {

            for(y=y1;y            OLED_DrawPoint(x,y,dot);

      }

      OLED_Refresh_Gram();//更新显示

}

*/

void OLED_Clear()     //清零

{

    uchar i,n;

    for(i=0;i<8;i++)

    {

        OLED_WR_Byte(0xb0+i,OLED_CMD);

        OLED_WR_Byte(0x00,OLED_CMD);

        OLED_WR_Byte(0x10,OLED_CMD);

        for(n=0;n<128;n++)  OLED_WR_Byte(0,OLED_DATA);

    }

}

/指定位置显示ASCLL字符

void OLED_ShowChar(uchar x,uchar y,uchar ptr,uchar size)

{

     uchar c=0,i=0;

     c=ptr-' ';

    // if(x>127) {x=0;y=y+2;}

     if(size==16)

     {

         OLED_Set_Pos(x,y);

         for(i=0;i<8;i++)

         {

    OLED_WR_Byte(F8X16[c*16+i],OLED_DATA);

         }

OLED_Set_Pos(x,y+1);

for(i=0;i<8;i++)

         {

    OLED_WR_Byte(F8X16[c*16+i+8],OLED_DATA);

         }

     }


}

///显示字符串

void OLED_ShowString(uchar x,uchar y,uchar *ptr,uchar size)

{

   uchar j=0;

   while(ptr[j]!='')    //通过循环的方式扫描显示任意字符

   {

        OLED_ShowChar(x,y,ptr[j],size);

        x+=8;

        if(x>120){x=0;y+=2;}

        j++;

   }



}

//显示汉字 2个字节//

void  OLED_ShowCHinese(uchar x,uchar y,uchar no)     //显示温度

{

      uchar i;

      OLED_Set_Pos(x,y);

      for(i=0;i<16;i++)    //8*16=128

      {

            OLED_WR_Byte(Hzk[2*no][i],OLED_DATA);

      }

      OLED_Set_Pos(x,y+1);

      for(i=0;i<16;i++)    //8*16=128

     {

            OLED_WR_Byte(Hzk[2*no+1][i],OLED_DATA);

      }


}

/*

void  OLED_Show_DS1302(uchar x,uchar y,uchar no)     //显示时间设置

{

      uchar i;

      OLED_Set_Pos(x,y);

      for(i=0;i<16;i++)    //8*16=128

      {

            OLED_WR_Byte(ds1302[2*no][i],OLED_DATA);

      }

      OLED_Set_Pos(x,y+1);

      for(i=0;i<16;i++)    //8*16=128

     {

            OLED_WR_Byte(ds1302[2*no+1][i],OLED_DATA);

      }


}

*/

void  OLED_ShowBattery(uchar x,uchar y,uchar no)

{

      uchar i;

      OLED_Set_Pos(x,y);

      for(i=0;i<16;i++)    //8*16=128

      {

            OLED_WR_Byte(baterry[no][i],OLED_DATA);

      }


}

void OLED_ShowBatCharge(uchar x,uchar y,uchar len,uchar size)

{

      uchar i;


      for(i=0;i      {

           OLED_ShowBattery(x,y,i);

          // x+=size;

      }

}

/显示多个汉字/


void OLED_ShowHz(uchar x,uchar y,uchar len,uchar size)

{

      uchar  i;

      for(i=0;i      {

           OLED_ShowCHinese(x,y,i);

           x+=size;


      }


}


//****汉字滚屏*****/

///y 0-6 区域显示

///num   数组中的对应汉字

///len   数组长度  num失效

///betw  单个汉字滚屏与汉字数字滚屏

/*

void Oled_RunShow(uchar y,uchar num,uchar len,uchar betw)

{

      static uchar n=0;

      if(betw)

      {

           // for(t=0;t            OLED_ShowCHinese(n,y,num);

            OLED_Clear_kuai(n,y,0);

        //    OLED_Fill()

           n++;

         // betw++;

           if(n>128) {n=0;}

      }

      else

      {

           OLED_ShowHz(n,y,len,16);

            n++;

            if(n>128) {n=0;}

      }





}

*/

//显示数字///

uint oled_pow(uchar m,uchar n)

{

      uint result=1;

      while(n--) result*=m;

      return result;

}

void  OLED_ShowNum(uchar x,uchar y,uint num,uchar len,uchar size)

{

      uchar t,temp;

      uchar enshow=0;

      for(t=0;t      {

            temp=(num/oled_pow(10,len-t-1))%10;

            if(enshow==0&&t<(len-1))  //为零时消隐

            {

                  if(temp==0)

                  {

                      OLED_ShowChar(x+(size/2)*t,y,'0',size);

                      continue;

                  }

                  else enshow=1;

            }

            OLED_ShowChar(x+(size/2)*t,y,temp+'0',size);

      }

}

void  OLED_DS1302_Num(uchar x,uchar y,uint num,uchar size)

{

      uchar dat[3];

      dat[0]=(num>>4)+0x30;

      dat[1]=(num&0x0f)+0x30;

      dat[2]='';

      OLED_ShowString(x,y,dat,size);

}

//显示图片///

//#if(0)

void  OLED_DrawBMP(unsigned char x0, unsigned char y0,unsigned char x1, unsigned char y1,unsigned char BMP[])

{

      uint j=0;

      uchar x,y;

      if(y1%8==0) y=y1/8;

      else   y=y1/8+1;

      for(y=y0;y      {

           OLED_Set_Pos(x0,y);

           for(x=x0;x           {

               OLED_WR_Byte(BMP[j++],OLED_DATA);

           }

      }

}

//#endif

/***********************Initial code*********************/

void Initial_LY096BG30()

{

OLED_WR_Byte(0xAE,OLED_CMD);//--display off

OLED_WR_Byte(0x00,OLED_CMD);//---set low column address

OLED_WR_Byte(0x10,OLED_CMD);//---set high column address

OLED_WR_Byte(0x40,OLED_CMD);//--set start line address

OLED_WR_Byte(0xB0,OLED_CMD);//--set page address

OLED_WR_Byte(0x81,OLED_CMD); // contract control

OLED_WR_Byte(0xFF,OLED_CMD);//--128

OLED_WR_Byte(0xA1,OLED_CMD);//set segment remap

OLED_WR_Byte(0xA6,OLED_CMD);//--normal / reverse

OLED_WR_Byte(0xA8,OLED_CMD);//--set multiplex ratio(1 to 64)

OLED_WR_Byte(0x3F,OLED_CMD);//--1/32 duty

OLED_WR_Byte(0xC8,OLED_CMD);//Com scan direction

OLED_WR_Byte(0xD3,OLED_CMD);//-set display offset

OLED_WR_Byte(0x00,OLED_CMD);//

OLED_WR_Byte(0xD5,OLED_CMD);//set osc division

OLED_WR_Byte(0x80,OLED_CMD);//

OLED_WR_Byte(0xD8,OLED_CMD);//set area color mode off

OLED_WR_Byte(0x05,OLED_CMD);//

OLED_WR_Byte(0xD9,OLED_CMD);//Set Pre-Charge Period

OLED_WR_Byte(0xF1,OLED_CMD);//

OLED_WR_Byte(0xDA,OLED_CMD);//set com pin configuartion

OLED_WR_Byte(0x12,OLED_CMD);//

OLED_WR_Byte(0xDB,OLED_CMD);//set Vcomh

OLED_WR_Byte(0x30,OLED_CMD);//

OLED_WR_Byte(0x8D,OLED_CMD);//set charge pump enable

OLED_WR_Byte(0x14,OLED_CMD);//

OLED_WR_Byte(0xAF,OLED_CMD);//--turn on oled panel

}

进入单片机查看更多内容>>
相关视频
  • RISC-V嵌入式系统开发

  • SOC系统级芯片设计实验

  • 云龙51单片机实训视频教程(王云,字幕版)

  • 2022 Digi-Key KOL 系列: 你见过1GHz主频的单片机吗?Teensy 4.1开发板介绍

  • TI 新一代 C2000™ 微控制器:全方位助力伺服及马达驱动应用

  • MSP430电容触摸技术 - 防水Demo演示

精选电路图
  • PIC单片机控制的遥控防盗报警器电路

  • 红外线探测报警器

  • 使用ESP8266从NTP服务器获取时间并在OLED显示器上显示

  • 用NE555制作定时器

  • RS-485基础知识:处理空闲总线条件的两种常见方法

  • 基于ICL296的大电流开关稳压器电源电路

    相关电子头条文章