본문 바로가기

프로그래밍/Python

[프로그래밍/Python] 아두이노 HC-06 와 라즈베리파이 블루투스 RFCOMM 통신

참고 https://webnautes.tistory.com/979

 

bluetooth.ino

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
#include <SoftwareSerial.h>
 
SoftwareSerial BTSerial(23);   //bluetooth module Tx:Digital 2 Rx:Digital 3
 
void setup() {
  pinMode(8, OUTPUT);    //HC-05
  digitalWrite(8,HIGH);
  
  Serial.begin(9600);
  BTSerial.begin(9600);
  Serial.println("ATcommand");  //ATcommand Start
}
 
void loop() {
  if (BTSerial.available())
    Serial.write(BTSerial.read());
  if (Serial.available())
    BTSerial.write(Serial.read());
}

 

Arduino.py

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
import serial
 
class arduino():
    def __init__(self,Port,Baud=9600,connState=0):
        self.parent=self
        self.port=Port
        self.baud=Baud
        self.connState=connState
        self.ser=None
        self.connect()
    def connect(self):
        try:
            self.ser=serial.Serial(self.port,self.baud,timeout=0.001)
            self.connState=1
        except:
            print('cannot connect')
    def loadData(self):
        while(1):
            ret = self.ser.readline()
            if(ret!=b''): 
                return ret
        
 

 

 

chat.py

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
import Arduino
import serial.tools.list_ports
import re
import time
import threading
 
class receiveThread(threading.Thread):
    def __init__(self,arduino):
        super().__init__()
        self._kill = threading.Event()
        self.ard = arduino
        self.start()
    def run(self):
        while True:
            msg = self.ard.loadData()
            print(self.ard.port, msg.decode(),end='')
            is_killed = self._kill.wait(0.5)
            if is_killed:
                break
        print(ard.port, "thread killed")
    def kill(self):
        self._kill.set()
 
def receiveMsg(stop,ard):
    print(ard.ser.port,": started receiving messages...")
    while True:
        if stop():
            print("stopped {} receiving...".format(ard.port))
            break;
        msg = ard.loadData()
        print(ard.ser.port,msg.decode(),end='')
        
def killThread():
    id = input("Enter thread id :")
    return int(id)
 
def sendMessage(arduino):
    arduino = arduino[:]
    msg = input("Enter message to send : ")+'\n'
    for a in arduino:
        a.ser.write(msg.encode());
    
def main():
    ports = [c.device for c in serial.tools.list_ports.comports() if re.search("rfcomm",c.device)!=None]
 
    for a in ports:
        print(a)
 
    arduino = [Arduino.arduino(port) for port in ports]
    arduino = [a for a in arduino if a.connState==1]
 
    #thread = [receiveThread(a) for a in arduino]
    stop_thread = [False]*len(arduino)
    i=0
    threads = []
    for a in arduino:
        t = threading.Thread(target=receiveMsg,args=(lambda: stop_thread[i],a))
        threads.append(t)
        t.start()
        ++i
 
 
    while(1):
        option = input("(1: broadcast message, 2: send message to certain device ,3: kill thread) ")
        if option == "1":
            sendMessage(arduino)
        elif option == "2":
            sendMessage(arduino)
        elif option == "3":
            stop_thread[killThread()] = True
 
if __name__ == '__main__':
    main()