用户工具

站点工具


导航菜单

首页

Home


锤蚁出品

By TREEE


培训活动

Workshop


知识技术

Tech & Skills


里程碑

Milestone


加入我们

Opening

m:sk:mcu:arduino:serial

这是本文档旧的修订版!


Arduino 串口通信 - UART通信

例子:


//版权声明什么的最无聊了,大家随便用,随便复制,随便改.
//Copyright is nothing, feel free to use it in anyway.
//v151206 加入了从串口修改时间的功能
 
#include <avr/pgmspace.h>
#include "font.h"
#include <stdio.h>
 
#define LCD_SCK 13      //LCD SPI时钟
#define LCD_SI 11       //LCD SPI数据端口
#define LCD_CS 10       //LCD SPI片选
#define LCD_CD 9        //LCD SPI命令/数据
#define LCD_RST 8       //LCD SPI复位
 
//对arduino端口操作方式的重新定义
#define Set(x) digitalWrite(x,1)
#define Clr(x) digitalWrite(x,0)
#define Out(x) pinMode(x, 1)
#define In(x) pinMode(x, 0)
 
//SPI写入
void SPI_write(unsigned char dat)
{
  for(unsigned char i = 0; i < 8; i++)
  {
    Clr(LCD_SCK);
    if (dat & 0x80)
      Set(LCD_SI);
    else
      Clr(LCD_SI);
    dat <<= 1;
    Set(LCD_SCK);
  }
  Clr(LCD_SCK);
}
 
//向LCD写入命令
void write_cmd(unsigned char dat)
{
  Clr(LCD_CD);  //Wrtie CMD
  SPI_write(dat);
}
 
//向LCD写入数据
void write_dat(unsigned char dat)
{
  Set(LCD_CD);  //Wrtie Data
  SPI_write(dat);
}
 
//LCD初始化
void LCD_init(){
  Clr(LCD_CS);
  Clr(LCD_RST);  delay(20);
  Set(LCD_RST);     //Reset the LCD
  write_cmd(0xe2);  /*软复位*/     delay(5);
  write_cmd(0x2c);  /*升压步聚1*/  delay(5); 
  write_cmd(0x2e);  /*升压步聚2*/  delay(5);
  write_cmd(0x2f);  /*升压步聚3*/  delay(5);
  write_cmd(0x23);  /*粗调对比度,可设置范围0x20~0x27*/
  write_cmd(0x81);  /*微调对比度*/
  write_cmd(0x2f);  /*0x28,微调对比度的值,可设置范围0x00~0x3f*/
  write_cmd(0xa2);  /*1/9偏压比(bias)*/
  write_cmd(0xc8);  /*行扫描顺序:从上到下*/
  write_cmd(0xa0);  /*列扫描顺序:从左到右*/
  write_cmd(0x40);  /*起始行:第一行开始*/
  write_cmd(0xaf);  /*开显示*/
  Set(LCD_CS);
}
 
//LCD 光标地址设定
void LCD_add(unsigned page, unsigned column)
{
  write_cmd(0xb0 + page);
  write_cmd(0x10 + ((column>>4) & 0x0f));
  write_cmd(column & 0x0f);
}
 
//LCD 屏幕内容清除
void Clr_LCD()
{
  unsigned char i,j;
  Clr(LCD_CS);
  for(i=0;i<9;i++)
  {
    write_cmd(0xb0 + i);
    write_cmd(0x10);
    write_cmd(0x00);
    for(j=0;j<132;j++)
    {
        write_dat(0x00);
    }
  }
  Set(LCD_CS);
}
 
//在某一个位置上显示一个字符
void Dis_char(unsigned char line, unsigned char column, char *chr)
{
  unsigned char page = line * 2;
  Clr(LCD_CS);
  for (unsigned char i = 0; i < 2; i++)
  {
    LCD_add(page + i, column);
    for (unsigned j = 0; j < 8; j++)
    {
      int loc = (*chr - 32) * 16 + j + i * 8;
      write_dat(pgm_read_byte_near(ascii+loc));
    }
  }
  Set(LCD_CS);
}
 
//在某一个位置上显示一个字符串
void Dis_str(unsigned char line, unsigned char column, char *str)
{
  while(*str)
  {
    Dis_char(line, column, str);
    column += 8;
    str++;
  }
}
 
unsigned long os_time;
String inputString = "";         // a string to hold incoming data
boolean stringComplete = false;  // whether the string is complete
 
void setup() {
  // put your setup code here, to run once:
  Out(LCD_SCK);
  Out(LCD_SI);
  Out(LCD_CS);
  Out(LCD_CD);
  LCD_init();
  Clr_LCD();
  Serial.begin(9600);
  os_time = millis();
}
unsigned hour=0, mi=0, sec=0;
char dispstr[16] = "";
void loop() {
  // put your main code here, to run repeatedly:
  sprintf(dispstr, "%02d:%02d:%02d",hour,mi,sec); //这里的%02d是可以让时分秒补零,满足两位,显示出来更加好看
  sec++;
  if (sec >= 60)
  {
    sec = 0;
    mi++;
  }
  if (mi>=60)
  {
    mi = 0;
    hour++;
  }
  Dis_str(1,4,"-----TIMER-----");
  Dis_str(2,31, dispstr);
  while(millis() - os_time <= 1000)
  {
    if (stringComplete) {
    Serial.println(inputString);
    sscanf(inputString.c_str(), "h%dm%ds%d",&hour,&mi,&sec);  //改时间的语句
    // clear the string:
    inputString = "";
    stringComplete = false;
  }
 
  }
    //这种计时方式比用delay准确
  os_time = millis();
}
 
void serialEvent() {
  while (Serial.available()) {
    // get the new byte:
    char inChar = (char)Serial.read();
    // add it to the inputString:
    inputString += inChar;
    // if the incoming character is a newline, set a flag
    // so the main loop can do something about it:
    if (inChar == '\n') {
      stringComplete = true;
    }
  }
}

另一个例子

· 最后更改: 2015/12/06 19:45