2016年7月29日 星期五

使用Python透過Bluetooth與Arduino連結


        這篇文章示範如何使用Python透過Bluetooth跟Arduino連結.並使用Python建立出來的圖形介面來控制Arduino上LED 的ON/OFF.
 底下實驗概念接線圖

   Python 因為是跨平台的程式語言所以也執行在windows或是Linux,底下範例是直接使用一般電腦及windows 10去做示範.Python原始程式碼只要稍微修改一下也可以改成使用在安裝Linux的系統上,如樹梅派.


底下是之前USB2Serial範例的介紹連結:
http://arbu00.blogspot.tw/2016/07/pythonarduinoled.html




    底下所建立出來的圖形介面如下圖所示,
當按下按鈕<check>去跟Arduino確認是否已經連線成功.
按下按鈕<ButtonA>則會傳送字元'a' 到arduino當指令去啟動LED跑馬燈1
按下按鈕<ButtonB>則會傳送字元'b' 到arduino當指令去啟動LED跑馬燈2
按下按鈕<ButtonC>則會傳送字元'c' 到arduino當指令去啟動LED閃燈的動作.
按下按鈕<Exit>則會傳送'ESC' 鍵字元到arduino當指令去結束視窗跟所有動作.
當成是執行時必須先按下<Check>Button 再reset Arduino才能順執行以確保連線成功.
 


底下圖示當按下Button A 時會傳字元'a' 到Arduino,即可進行跑馬燈動作.
 








有關這個範例的實際示範及詳細的說明可以觀看底下的影片教學.






底下是本範例的Python &Arduino程式碼.

<Python source code>


# -*- coding:utf-8 -*-
from time import sleep
import serial
import tkinter
Ready_flag=0
##==============================================================================
ser =serial.Serial("COM9", 9600, timeout=2) # Establish the connection on a specific port
##==============================================================================
##===============For Linux=========================================================
#ser =serial.Serial("/dev/ttyACM0", baudrate=9600, timeout=2) # Establish the connection on a specific port
##==============================================================================
def SerialWrite(command):
 ser.write(command)
 rv=ser.readline()
 #print (rv) # Read the newest output from the Arduino
 print (rv.decode("utf-8")) 
 sleep(1) # Delay for one tenth of a second
 ser.flushInput()

##===When button A be pressed then Send 'a' to arduino============
def SendCmdA():
 global Ready_flag
 if Ready_flag==1:
  Arduino_cmd='a'
  cmd=Arduino_cmd.encode("utf-8") 
  SerialWrite(cmd)
  #Show to LabelA----------------
  LabelA.config(text="Send the command 'a' to Arduino")
  LabelA.update_idletasks()
  Tkwindow.update()
 else:
  LabelA.config(fg='red',)
  LabelA.config(text="Arduino not ready!Please check it again")
  LabelA.update_idletasks()
  Tkwindow.update()
##===When button A be pressed then Send 'a' to arduino============
def SendCmdB():
 global Ready_flag
 if Ready_flag==1:
  Arduino_cmd='b'
  cmd=Arduino_cmd.encode("utf-8") 
  SerialWrite(cmd)
  #Show to LabelA----------------
  LabelA.config(text="Send the command 'b' to Arduino")
  LabelA.update_idletasks()
  Tkwindow.update()
 else:
  LabelA.config(fg='red',)
  LabelA.config(text="Arduino not ready!Please check it again")
  LabelA.update_idletasks()
  Tkwindow.update()
##===When button A be pressed then Send 'a' to arduino============
def SendCmdC():
 global Ready_flag
 if Ready_flag==1:
  Arduino_cmd='c'
  cmd=Arduino_cmd.encode("utf-8") 
  SerialWrite(cmd)
  #Show to LabelA----------------
  LabelA.config(text="Send the command 'c' to Arduino")
  LabelA.update_idletasks()
  Tkwindow.update()
 else:
  LabelA.config(fg='red',)
  LabelA.config(text="Arduino not ready!Please check it again")
  LabelA.update_idletasks()
  Tkwindow.update()
 
##==Serial connect and Get arduino  Ready================
def Serial_Connect():
 global Ready_flag
 for i in range (1,10):
  print("Checking...")
  #Show to LabelA----------------
  Str_index=""
  str_check="th Checking...\n"
  Str_index=str(i)
  Label_msg="The " +Str_index +str_check
  LabelA.config(fg='green',)
  LabelA.config(text=Label_msg)
  LabelA.update_idletasks()
  buttonStart.config(state="disabled")
  Tkwindow.update()
  
  rv=ser.readline()
  #Debug print (rv) # Read the newest output from the Arduino
  print (rv.decode("utf-8")) 
  ser.flushInput()
  sleep(0.5) # Delay 
  Str_Message=rv.decode("utf-8")
  #Debug print(Str[0:5])
  if Str_Message[0:5]=="Ready": 
   Ready_flag=1
   print("Get Arduino Ready !")
   #Show to LabelA----------------
   LabelA.config(text="Get Arduino connecting Ready !")
   LabelA.update_idletasks()
   Tkwindow.update()
   break
  elif  i==9: 
   Ready_flag=0
   LabelA.config(fg='red',)
   LabelA.config(text="Can't connnect to Arduino successfully!\
                               \nPlease press 'check' button then reset Arduino to try again!")
   buttonStart.config(state="active")
   LabelA.update_idletasks()
   Tkwindow.update()
   sleep(1) # Delay 
 
##------------------------------------------------------
##==Serial connect Exit================
def All_Exit():
 print("Exit.....")
 #Show to LabelA----------------
 LabelA.config(text="Exit.....")
 LabelA.update_idletasks()
 Tkwindow.update()
 sleep(1)
 chr_num = 27  ##ESC
 cmd=(chr(chr_num).encode('utf-8'))
 SerialWrite(cmd)
 ser.close()
 Tkwindow.destroy() # Kill the root window! 

##------------------------------------------------------
Tkwindow=tkinter.Tk()
Tkwindow.title("Using Python to Control Arduino LED ON/OFF")
Tkwindow.minsize(600,400)
LabelA=tkinter.Label(Tkwindow,
        bg='white',
        fg='blue',
        text="Press 'Check' Button then reset Arduino to connect!",
        width=80,
        height=10,
        justify=tkinter.LEFT
        )
LabelA.pack(side=tkinter.TOP)
buttonA=tkinter.Button(Tkwindow,
         anchor=tkinter.S,
         text="Button A",
         width=10,
         height=1,
         command=SendCmdA)
buttonA.pack(side=tkinter.LEFT)
buttonB=tkinter.Button(Tkwindow,
         anchor=tkinter.S,
         text="Button B",
         width=10,
         height=1,
         command=SendCmdB)
buttonB.pack(side=tkinter.LEFT)
buttonC=tkinter.Button(Tkwindow,
         anchor=tkinter.S,
         text="Button C",
         width=10,
         height=1,
         command=SendCmdC)
buttonC.pack(side=tkinter.LEFT)
buttonStart=tkinter.Button(Tkwindow,
         anchor=tkinter.S,
         text="Check",
         width=10,
         height=1,
         command=Serial_Connect)
buttonStart.pack(side=tkinter.RIGHT)

buttonEnd=tkinter.Button(Tkwindow,
         anchor=tkinter.S,
         text="Exit",
         width=10,
         height=1,
         command=All_Exit)
buttonEnd.pack(side=tkinter.RIGHT)

Tkwindow.mainloop() 



<Arduino source code>


//*****************************************************************************
//*****************************************************************************
//ArbuluckyChat  V1.0
//阿布拉機的3D列印與機器人
//http://arbu00.blogspot.tw/
//
//2016/07/ˇ0 Writen By Ashing Tsai
//
//******************************************************************************
#include 
const int LedPin12=12;
const int LedPin11=11;
const int LedPin10=10;
//USB-Serial String Str01="";
SoftwareSerial BT(2,3);    //RX,TX
String ReadBTString="";       
  
void setup() {
    BT.begin(9600);  
    BT.println("Ready"); // print "Ready" once
 //USB-Serial Serial.begin(115200); // set the baud rate
 //USB-Serial Serial.println("Ready"); // print "Ready" once

   pinMode(LedPin12,OUTPUT);
   pinMode(LedPin11,OUTPUT);
   pinMode(LedPin10,OUTPUT);
   digitalWrite(LedPin12,LOW);
   digitalWrite(LedPin11,LOW);
   digitalWrite(LedPin10,LOW);
}
void loop() {
 /*USB-Serial+
  if (Serial.available())
{  
   Str01="";
   delay(1);
   while(Serial.available())
    {
      Str01+=(char)Serial.read(); 
    }
    Serial.println(Str01); // send the data back in a new line so that it is not all one long line
}
 USB-Serial-*/

//BT+========================
  if(BT.available()) {  
        ReadBTString="";
        while(BT.available()) {  
                ReadBTString+=(char)BT.read();
                delay(1);   
        }
      BT.println(ReadBTString);
  }
//BT-========================

if (ReadBTString[0]=='a')
{
   digitalWrite(LedPin12,HIGH);
   digitalWrite(LedPin11,LOW);
   digitalWrite(LedPin10,LOW);
   delay(500);
   digitalWrite(LedPin12,LOW);
   digitalWrite(LedPin11,HIGH);
   digitalWrite(LedPin10,LOW);
   delay(500);
   digitalWrite(LedPin12,LOW);
   digitalWrite(LedPin11,LOW);
   digitalWrite(LedPin10,HIGH);
   delay(500);
}

if (ReadBTString[0]=='b')
{
   digitalWrite(LedPin12,HIGH);
   digitalWrite(LedPin11,LOW);
   digitalWrite(LedPin10,LOW);
   delay(100);
   digitalWrite(LedPin12,LOW);
   digitalWrite(LedPin11,HIGH);
   digitalWrite(LedPin10,LOW);
   delay(100);
   digitalWrite(LedPin12,LOW);
   digitalWrite(LedPin11,LOW);
   digitalWrite(LedPin10,HIGH);
   delay(100);
}
if (ReadBTString[0]=='c')
{
   digitalWrite(LedPin12,HIGH);
   digitalWrite(LedPin11,HIGH);
   digitalWrite(LedPin10,HIGH);
   delay(300);
   digitalWrite(LedPin12,LOW);
   digitalWrite(LedPin11,LOW);
   digitalWrite(LedPin10,LOW);
   delay(300);
}
}
  

加入阿布拉機的3D列印與機器人的FB粉絲團
https://www.facebook.com/arbu00/

Scan QRcode to join FB Fans.