[전동 Skateboard 만들기]#3 Wi-Fi 모듈 연결 및 Control 어플 구현
Hardware of Wi-Fi Receiver
Wi-Fi 수신기는 스마트폰에서 데이터를 수신하여 스케이트 보드의 속도를 조절하는 장치이며, 하드웨어 구성은 아래와 같다.
아래 사진은 완성된 하드웨어 사진이다. 배터리나 다른 보드들과의 circuit short를 방지하기 위해 절연 테이트를 부착하여 조금 부족해 보이지만 동작에는 문제가 없다.
오른쪽에 3핀, 2핀이 나와 있는데, 위에 3핀은 PWM,3.3V VCC,GND 핀이고, 아래 2핀은 배터리에서 받아 올 5V VCC, GND 핀이다.
Wi-Fi Receiver Firmware
Source Code
Wi-Fi Receiver firmware는 아래 그림과 같은 구조로 동작된다. 스마트폰에서 Speed Up 명령을 주면 Wi-Fi Receiver는 속도를 5% 올리고 Speed Down 명령을 주면 속도를 5% 내린다.
예외 상황에서는 아래 그림과 같이 Motor를 정지 한다. 단 Motor가 정지 되어도 가속도 때문에 스케이트 보드는 계속 움직일 수는 있다.
Wi-Fi 수신기에 대한 소스코드는 아래 경로에서 다운로드 할 수 있다.
https://developer.mbed.org/users/kaizen/code/Wifi_Electric_Skateboard/
#include "mbed.h"
#include "Servo.h"
#include "WizFi250Interface.h"
#define SECURE WizFi250::SEC_WPA2_MIXED
#define SSID "Kaizen_Skate"
#define PASS "qwertyuiop"
#define SERVER_PORT 5000
#define STOP_MOTOR 50
#if defined(TARGET_WIZwiki_W7500P)
WizFi250Interface wizfi250(PC_2,PC_3,PC_13,PC_14,PC_12,NC,115200);
Serial pc(USBTX, USBRX);
Servo motor_speed(PC_8);
DigitalOut green_led(LED2);
DigitalOut red_led(LED1);
DigitalOut blue_led(LED3);
#endif
#define START_MSG "START"
#define END_MSG "END\n"
#define CONTROL_UP "UPXX"
#define CONTROL_DOWN "DOWN"
#define CONTROL_CRUISER "CRUI"
#define CONTROL_STOP "STOP"
#define STATUS_CMD_OK "OKXX"
#define STATUS_CMD_FAIL "FAIL"
#define CONTROL_MSG_SIZE 19
struct control_pkt{
char start_msg[6];
char control_msg[5];
char speed_msg[4];
char end_msg[4];
};
void parse(char buffer[], int *j, char *string);
int main() {
int recv_cnt,j;
volatile float speed_value = 0.5;
char recv_control_msg[100];
char status_msg[100];
control_pkt control;
pc.baud(115200);
green_led = 1; red_led = 1; blue_led = 1;
wizfi250.init();
wizfi250.setAntMode(WizFi250::PCB);
wizfi250.setAddress("192.168.100.2","255.255.255.0","192.168.100.1");
if ( wizfi250.connect(SECURE, SSID, PASS, WizFi250::WM_AP))
{
red_led = 0;
return -1;
}
printf("IP Address is %s\r\n", wizfi250.getIPAddress());
green_led = 0; red_led = 0; blue_led = 0;
TCPSocketServer server;
TCPSocketConnection client;
while(true)
{
if( client.is_connected() == false )
{
green_led = 1; red_led = 1; blue_led = 0;
client.close();
server.close();
if(speed_value == 0.5)
{
server.bind(SERVER_PORT);
server.listen();
printf("\nWait for new connection...\r\n");
server.accept(client);
client.set_blocking(false, 1500);
}
else if(speed_value <= 0.4)
{
printf("Speed decrease +\r\n");
speed_value = 0.5;
motor_speed = speed_value;
}
else
{
printf("Speed decrease -\r\n");
speed_value = 0.5; motor_speed = speed_value;
}
}
else
{
motor_speed = speed_value;
green_led = 0; red_led = 1; blue_led = 1;
recv_cnt = client.receive_all((char*)recv_control_msg, sizeof(control));
j=0;
parse(recv_control_msg, &j, control.start_msg);
parse(recv_control_msg, &j, control.control_msg);
parse(recv_control_msg, &j, control.speed_msg);
parse(recv_control_msg, &j, control.end_msg);
if(recv_cnt > 0)
{
if( (strncmp(control.start_msg,START_MSG,sizeof(control.start_msg)) != 0) ||
(strncmp(control.end_msg,END_MSG,sizeof(control.end_msg)) != 0) )
{
printf("TEST Error\r\n");
sprintf(status_msg,"%s,%03d,%s,%s\n",START_MSG,int(speed_value*100),STATUS_CMD_FAIL,END_MSG);
client.send_all((char*)status_msg,strlen(status_msg));
continue;
}
if( strncmp(control.control_msg,CONTROL_UP,sizeof(control.control_msg)) == 0 )
{
speed_value += 0.05;
motor_speed = speed_value;
printf("TEST UP %f\r\n",speed_value);
}
else if( strncmp(control.control_msg,CONTROL_DOWN,sizeof(control.control_msg)) == 0)
{
speed_value -= 0.05;
motor_speed = speed_value;
printf("TEST DOWN %f\r\n",speed_value);
}
else if( strncmp(control.control_msg,CONTROL_CRUISER,sizeof(control.control_msg)) == 0)
{
printf("TEST CRUISER\r\n");
speed_value = (float)(atoi(control.speed_msg)) / 100;
motor_speed = speed_value;
}
else if( strncmp(control.control_msg,CONTROL_STOP,sizeof(control.control_msg)) == 0)
{
printf("TEST STOP\r\n");
speed_value = 0.5;
motor_speed = speed_value;
}
else
{
printf("TEST Error 1-2\r\n");
sprintf(status_msg,"%s,%03d,%s,%s\n",START_MSG,int(speed_value*100),STATUS_CMD_FAIL,END_MSG);
client.send_all((char*)status_msg,strlen(status_msg));
continue;
}
sprintf(status_msg,"%s,%03d,%s,%s\n",START_MSG,int(speed_value*100),STATUS_CMD_OK,END_MSG);
client.send_all((char*)status_msg,strlen(status_msg));
}
else
{
sprintf(status_msg,"%s,%03d,%s,%s\n",START_MSG,int(speed_value*100),STATUS_CMD_OK,END_MSG);
client.send_all((char*)status_msg,strlen(status_msg));
}
}
}
}
void parse(char buffer[], int *j, char *string) {
int i=0;
for (i=0; i<=strlen(buffer); i++) {
if ((buffer[*j+i] == ',')||(buffer[*j+i] == '\0' )) {
string[i]=0;
*j=*j+i+1;
break;
} else string[i]=buffer[*j+i];
}
}
스마트폰 어플
Source Code
https://github.com/kaizen8501/WiFi_Skateboard
Demo Video