# **串口双向调用 (握手连接)**
> 本例向你展示使用握手连接在Arduino和Genuino板和电脑之间建立多字节的通信(multi-byte communication)。
> 代码最开始在**setup()**中不断输出字母A到串口监视器(用ASCII方式,对应byte值65),直到收到电脑的“回复”(收到一个byte)才进入loop。第一次进入**loop()**后代码将发送三个传感器的值到电脑一次。而后在loop循环中,程序一直等待电脑的信息(不会再发送字母A的等待信息),直到下次再收到一个byte再返回三个传感器值一次,不断重复。
>
> 译者注:为了帮助大家理解,我在**译者解析程序逻辑**板块绘制了流程图,不懂的可以看看。
你可以使用Arduino IDE 串口监视器来查看数据,或者也可用Processing(下附代码),Flash, PD, Max/MSP(下附补丁)等代替。
### **所需硬件**
* Arduino板或Genuino板
* 2个模拟信号传感器 (电位器, 光电管, 压力传感器等等均可)
* 按键
* 3 个10kΩ电阻
* 跳线
* 面包板
* 连接线
### **所需软件**
Processing 或 Max/MSP version 5.x
### **电路连接**
![图片来自官网](http://img.blog.csdn.net/20160518172332529)
将模拟信号传感器连接到A0口、A1口(还要用10kΩ电阻进行分压)。然后用一个10kΩ电阻连接按键或者开关到A2口。
### **原理图**
![图片来自官网](http://img.blog.csdn.net/20160518172351138)
### **程序逻辑**
#### **Arduino程序流程图**
(此处为流程图,如果看不见可能是浏览器问题)
进入setup()函数establishContact() {Arduino不断发送握手连接请求信号}是否收到电脑请求字节?进入loop()函数yesno
进入loop()函数串口是否有数据?返回三个传感器值yes
大家可以这样理解
1. Arduino第一次收到输入之前处于“**空闲状态**”,因此不断广播信息:“**我已经准备好,如果要传感器信息就来吧**”。【**Arduino尝试找电脑握手**】
2. 电脑说:“**Arduino,我日后要串口数据,我和你握手**”,这时Arduino就知道电脑要数据了。因此就不再发送“**我已经准备好……**”的信息。默默等待电脑需要数据的时刻。Arduino目前出于“**等待状态**”,等待给电脑发送传感器信息。【**电脑和Arduino握手成功**】
3. 电脑说:”**现在给我数据**“。Arduino返回三个传感器值,然后继续等待电脑的下一个请求。【**握手成功后的通信**】
这就是握手连接,大家也可以网上搜搜握手连接的含义和作用。
### **例程代码**
~~~
/*
串口双向调用
语言: Arduino
代码不断输出字母A到串口监视器(用ASCII方式,对应byte值65),直到收到电脑的“回复”才
停止。收到电脑的“回复”后(收到一个byte),代码将发送三个传感器的值到电脑。
感谢Greg Shakar和Scott Fitzgerald 改善代码
电路搭建:
* 两个电位器分别连接到A0、A1
* 按键连接到2号引脚
代码是公开的。
*/
int firstSensor = 0; // 第一个模拟信号传感器
int secondSensor = 0; // 第二个模拟信号传感器
int thirdSensor = 0; // 数字信号传感器
int inByte = 0; // 收到的串口数据
void setup() {
// 用9600波特率打开串口:
Serial.begin(9600);
while (!Serial) {
// 等待串口建立完成,只有当使用本地USB口时有用
}
pinMode(2, INPUT); // 2号引脚为数字传感器
establishContact(); // 发送A字符到电脑,直到电脑发送回来数据才返回
}
void loop() {
// 如果串口有一个byte的数据,就读取传感器值:
if (Serial.available() > 0) {
// 获取发送来的byte:
inByte = Serial.read();
// 读取第一个模拟信号传感器,然后除以4,以保证值域在0-255:
firstSensor = analogRead(A0) / 4;
// 等待10ms,让ADC数模转换电路完成处理工作:
delay(10);
//读取第一个模拟信号传感器,然后除以4,以保证值域在0-255:
secondSensor = analogRead(1) / 4;
//读取开关,将值映射到0-255
thirdSensor = map(digitalRead(2), 0, 1, 0, 255);
// 发送传感器值:
Serial.write(firstSensor);
Serial.write(secondSensor);
Serial.write(thirdSensor);
}
}
void establishContact() {
while (Serial.available() <= 0) {
Serial.print('A'); // 发送A字符
delay(300);
}
}
~~~
#### **Processing代码**
将下列代码拷贝到Processing工程,当你改变模拟信号传感器时,你会看到屏幕上有一个小球跳动。只有当你按下按钮时才会看到小球
![图片来自官网](http://img.blog.csdn.net/20160518172147698)
~~~
// 代码公开.
import processing.serial.*;
int bgcolor; // 背景色
int fgcolor; // 填充色
Serial myPort; // 串口
int[] serialInArray = new int[3]; // 串口接收数据存储
int serialCount = 0; // 串口数据数量
int xpos, ypos; // 小球初始位置
boolean firstContact = false; // 是否从板子收到了数据
void setup() {
size(256, 256); // 设置舞台(窗口)大小
noStroke(); // 设置下一个绘制的东西无边框
// 设置小球初始位置在舞台(窗口)中间
xpos = width/2;
ypos = height/2;
// 为了调试方便,将串口枚举并且输出
// 如果使用Processing 2.1或更早版本,使用Serial.printArray()
println(Serial.list());
// 在我的mac上第一个总归是Arduino的FTDI串口适配器,因此我直接打开了Serial.list()[0]。
// Windows系统上一般都是COM1。
// 下列代码根据你使用的串口进行调整。
String portName = Serial.list()[0];
myPort = new Serial(this, portName, 9600);
}
void draw() {
background(bgcolor);
fill(fgcolor);
// 画球
ellipse(xpos, ypos, 20, 20);
}
void serialEvent(Serial myPort) {
// 从串口读取一个值:
int inByte = myPort.read();
// 如果是第一次获取到数据,说明Arduino上的程序第一次运行,将串口数据清空。如果不是第一次,则说明是传感器数据收到了。:
if (firstContact == false) {
if (inByte == 'A') {
myPort.clear(); // 清除数组存储
firstContact = true; // 这是第一次连接,收到了Arduino的握手请求
myPort.write('A'); // 电脑发送一个字节到Arduino,以此获取更多组传感器数据。
}
}
else {
// 将最新数据放入数组:
serialInArray[serialCount] = inByte;
serialCount++;
//如果有三个字节:
if (serialCount > 2 ) {
xpos = serialInArray[0];
ypos = serialInArray[1];
fgcolor = serialInArray[2];
// 打印值(调试用):
println(xpos + "\t" + ypos + "\t" + fgcolor);
// 发送大写字母A,请求Arduino反馈更多的数据:
myPort.write('A');
serialCount = 0;
}
}
}
~~~
#### **Max补丁**
![图片来自官网](http://img.blog.csdn.net/20160518172120088)
~~~
----------begin_max5_patcher----------
3908.3oc6ckziiaiE9b0+J3XjCIXpp.WzZNMURv.jCInQ5fYNjNngrDssRKK
4nkp6JA4+973hrkrsjncKu0SRiXasQ83G+dKj7QV+4qtaxzrOxKlf9Zzuft6
t+7U2cm7ThSbm936lrL3igIAExaaRJ+CYS+sI2qtTI+ikxSuBMKNojm+N3D4
Aua5KkPwpuoUAkgKhSm+tbdXo5cQXVOhuGwrohuHD4WT7iXzupen3HY4BuqG
rH0kzrrzxzfkb4kdJONHo9JoUKiSS3kRgjt4jYUk0mkznPJh+CYgHewpSqty
xWVwUh3jIqkEYEfmqQEMr.ETbB+YddQbVZix+tIAqV03z203QDX4ukIKHm6W
ep3T0ovqOUN+435m2Rcx+5U0E+FTzVBh9xOsHXIh5YuADg1x4IYgumG0r3mj
shmFmtJmWvSKCJ0um0WNhOKnJo7c6GmZe8YAg7Ne381Rc2j44wQYoBgn0SJN
c8qCHH1RhQqJi7NRCVsmGt.pGUESCxE31zDdCV.PRyxRZeo0MU.WOHMdYPIu
LVIrT75BMd4p73zxVuHdZ.TFKJByyRRZUTpq77dtRDzZFx+PbT4BYY0DJgaO
dUcSvj0XTT7bdQY6yUFLun8YZo71jl0TIt042RYNLa4RfCTWfsznKWDWfJpl
tJHrbgV6t.AZInfzWP.4INpJHA8za91u+6QN1nk7hh.PpQwonxEbTAWzpilV
MimilkmsDtPbo3TPiUdY0pGa9ZShS4gYUJz1pwE1iwCpxbAgJI9DGGwWNzFT
ksLf3z7M0MybG6Hj1WngsD7VEXS8j5q7Wu5U0+39ir8QJJS5GMHdtRimL4m1
0e1EVX0YsE2YssINriYRoFRyWVMoRRUGQvnkmms3pnXDYHbBKMPpIOL5i1s8
3rMPwFcRCsGRyPH780.8HBnpWz.vlEQBWJ+0CSunehJSmJxiIZRtNGhhDYrU
jt3ZQyA2fHJhZDifXIQHUHH8oGYgOREI5nqHIzhFWUndPyBdB3VzHJGwUhkV
rgvRl2UCVNMHcd234lf1DN16HFEIdHt99A5hrp7v5WWMSBQZgMP.Tkwoqig8
W1.Sn1f3h3nn1wLpBypPDzlJ7XinEGkLiMPloWOhrgR7dpZWJQV1faDy35Qj
MThMFkWFGsJChQPqrQp8iorV6Q28HBVF4nMVDJj7f1xyYACFScisg.ruLHOW
uMUS4Am4pI4PTnHi.6bi02HNzSYnDBe4cgAgKzRk1jc8PJLoH3Ydz6.Q.7K8
tfxx73oUkJq1MGuCy5TpAi.POWZ3AenidLOOIaZPhdjZVW3sdk6LXEGzHb7p
Mfr7SEy3SXHyBSxJ3J2ncNNYVJsXG6Me10nj4cfCRFdTFjLo7q3SiCpjjEDM
.nvra.GN39.E2CDTHWXPo8.xzfqrHCHKnf5QUYUVdoZPUjCSC7LU8.XtTUXl
X8vr51GjwFGLC2AlMdLkU4RiaRrnmJuiudnDk0ZW+9p6TuKBe433JUCzp6fU
iOF0SUk2UQYUPNTEkiZubvKa1tsmgL5SCTXGHnnG0CceLpkpR9Rs28IUESWl
EwWNKfHlg.zj6Ee7S+nE8A+m9F7Cu40u9gMm+aRp3kYYkKd3GDOz5y+c7b96
K9gfvuIK68uNO6g2vUUL80WxihCVFD9vlB30e2SOrmxUb527RZ3nZNrljGrR
70vs1J9suWuZ3zaHVdG3RIJLgGj2Gfn6TcGcstEfvtH.hpFLlnBndjOLGQAI
z98BXc6yQxghmOn6gZqj0ShPOXhynLOjzCESt+XwE8TxrCvrdXo16rqnLgvb
HaFmbh29QD+K0DyNdjDwvzQL.NXpoMvoOBxkger0HwMRQbpbCh91fjjG9Idw
prTH9SzaSea5a.GQEPnnh43WNefMlsOgx18n.vgUNO.tKl7tDyI3iHzafJHZ
VVNedVEbGgYIY42i93prB0i7B7KT1LnnCiyAiinpBnsPV7OG.tYKfBsrJOkG
UG5aq26iJw6GyJ4eM5mEgEKaNQPMEBUp.t8.krplOVTlZdJAW27bjvGK7p2p
HQPgLOSJDYv4E9gQBYBjMUselRxDy+4WplIzm9JQAWOEmfb.E364B43CAwp5
uRRDEv8hWXprjADMUOYpOg9.bVQpEfhKgGCnAnk.rghBJCdTVICA3sDvAhE5
oU4hf67ea5zWPuILqrD8uiK+i477fjHIt9y.V88yy3uMsZUj7wnxGKNAdPx5
fAZMErDZOcJU4M01WFQokix.pKa+JE1WacmnKFeYd7b.0PeIzB8Kk+5WIZpB
Ejt34KJeHgOCh4HK8Y3QiAkAfs8TRhhOkG7AAGQf0qxyfmQxa+PLb8Ex.2PS
4BdO5GB9Hvg+cfJCMofAIMu9Qz+UPCjckqVJlEmyA8Bf.rC6.3hAEuG8TdTU
bZljQ0nr1ayIqmTwQYfyRGafZhur5vfuyMSqYNWmtAPwWHalDSuUgT0Bosh.
JpAR89Y6Ez5QEfPTQO4J0DHLInIliz8BZV2JfV3Bd36qsQwAVVXbr1BGXp6s
Sd5sSDruo74wofx.HxUgxQwTnMLqTXvRmiGh2PUZr5pBynKChjl6feNUjSRn
hEUfRPT1GfG9Ik4TQBm.hEZZ.bc38HjAMKGzDRijEm1ifx1dbgzQyKh6FZc3
wOCkRJH+KUh0daWs6wzltWx1puXxlWW6NZWY2JiTBzzILRIANku02NourySM
VI1VJTvQZff32AJr+dS9e34QAoA6EGXlGFH9yk7yyQAlVd3SR94g+TxOu1sU
Flgd6ICI96LzazyPu1cgqsZ8r74SgF.65+efbMf4pGHT7lgHh30Sha3N5Ia.
oqjMf7nsuMwycf7iYDybiAAVr3eC.oTMjpzEr8GDRc9bFRGHYXDrzg.Tlx+q
NW8TY1IkzCfZ2IftkQstbB08HUezoDS+oFyI.cWIhWBaDiUo7qIrDO7f.L6n
AXqCmyNT9act.z+Iv.GR0uES0ZXfjdz.IczAxQOUR+zvRsUTigRxmyPYeNlj
yXv8Peef2ZFzuLzWPPeAE8ELzWXYlhe8WzAcUg+b1UkIoCLzIH60zwASGXau
a1Dq2nUY.sox4vng+m0nACePngC9lEMLZMBPodOxf+yx5d4uMCTHm3kJvIIG
jcLMedEQldkjpoBkQyjY1Hk.hmSY95Iwos8NDb9VSlIWOIntqgxryUjL6bCJ
y1lli5tWWxrQ7YmqGYlc6shK1iY2dr0wtNjYxgHyzaq0OznY235awCr8zSz6
EGd1QNUKf.74dADTBbTbeotjpW95IolY0WpKYONY8M83Rx2MChx3fL+iG5Mm
tXpdmvXj8uTvaAL1WjbbarQD4Z6kXBpnm6a69oKV2PY9WY174IbC3CaRQ9iK
Q4sYGQpwdtZ5wFrc7n569.M83OOR5ydSB1ZcAWCxdbKuavz9LILxfD.wWO.W
Nq+Zu4Es+AP6s5p9jDWH8ET+c85+XbW0.N1nDCTD7U4DGc6ohnU019fS7kQ0
o43luuOGjv5agHp0DT.CysOfgLR3xXlXTUKm16RivRsn3z0O6cl3YScAvtrb
hwekGB7BZuqESUzBJWmCvK7t9HF8Ts6cUAPoFWso3aP8ApWyJ3wqOPo2pJDC
BQ0NI0Pj8QCQ2r1L5vKaU5lDRYX7yRur1UYYZmJQ9iDHwN9dndB5n5ejflmm
UsBwLHnDkKXWRuAkb3NeuzqRstiQGP.fCQFdHNzaE.8u58Nz9svFE9SGIE1X
kv9Iwfl1BdNWjA7xcThsWCS847loyFD8pZq2E2F04lYULzBTDYhrFSDDJdjo
fisN2NUN26e4xRu51zD5ZseJ4HC63WyIX6jRqsp0jangBnK.Qlo58PCpWevt
ahzqK7fbKsdX6R64aao8LmWhBPh9jKVAPMzb5a2cV6opdWHneMmqMEmAGsPh
ieigIjV+4gF1GgbMNXg+NH44YaRYyd..S1ThHzKhFwwGRaWVITqyj9FvPqMT
d0pDuSqDrOGF.Uogf.juCFi9WAUkYR+rFPanDcPG8SbrtjyG03ZQ8m3AqC5H
NcUUoXSwVrqXKVcZu.5ZnkwIfIVdXVZTwAuTTUiYuxwjZDK6ZgnRtYV8tJmP
hEcuXgz2Goxyaiw35UkaWbpqtfzD02oUkkYqi.YQbZqIIWrIljFolsdmMKFR
wCJ2+DTn.9QlkOld+d9Qy9IJdpLfy05Ik2b8GsG9h8rdm1ZFx1FrmmlA2snw
qI9Mcdi2nr6q3Gc87nLawurbw1dda+tMyGJ9HaQmlkGwy6davisMgrkM65oz
eulfYCzG46am8tSDK144xV4cEvVMTRXq9CIX8+ALNWb6sttKNkiZetnbz+lx
cQnb1Nds2C0tvLNe14hwQtxYbxhqc17qHfamUcZZ3NYSWqjJuiDoizZ+ud2j
naRK4k3346IIVdR1kKiQjM39adMamvc6n+Xp36Yf3SIGh3uKbquqs1JksTII
kuJ7RrZSFb2Cn9j5a6DT8cMo0iczU+lsYaU8YNVh5k5uzJLU26ZcfuJE6XLY
0mcRp9NTCp+L+Ap+in7Xf3b9jFQBLtIY06PbrGhcrU6N00Qlaf9N0+QPo9nS
P6qsI7aYNLSNOHpsAxis0ggnZLjYqyyFkdSqinVsPaqSDZaYBZ6c93uLCjGm
iCroJVLzU45iNE.pIUfs3TWb.0FejHp9uANr0GcJPTroFDNOHpkIweLnI1QT
dHl3P7LhOF3Ahd9rnvLwAMy5JSdNezGlsIsW9mW44r26js+alhxjlkdhN0YE
YqiH5MTeWo6D4Qm.ieLS7OynmuVGSbmbFUlnWWhiQlhOeN+Yl35bq.tGo9JR
cj8AVqdz7nSgVB9zNj.FTOU68o5d9KO5TUOGxVMw+jTO8T6wqD0hEiHsOJO5
TTOMoS.zlqN0SpZjz6GcH05ylVM0jwuidlkmAif374ih5M5QPfccr8Hqifff
otN8pt3hUcaWu8nosBhwmD0Epw5KmoF.poxy4YHbnjqfPJqcM3Y2vun7nS.i
f3eETiqcRX2LR.4QmhZrkoCSGwzZrqKHrVR8caari+55d2caPqmq5n.ywe8Q
WrZL9fpwVXeaogMByE6y1SMdjk+gbavbN7fYvVtt1C2XwHJSzpk+tidUO25H
UB9onw9mlFQ10fhpZBaDatcMTTEGcJpwzqg92qqiVtM6Cu0IRQ0ndEdfCAqV
l0qYAUmPrctbxO4XCuPMa1asYzKDks1D52ZCne6Mednz9qW8+.vfqkDA
-----------end_max5_patcher-----------
~~~
### **相关资料**
[serial.begin()](http://www.arduino.cc/en/Serial/Begin)
[serial.available()](http://www.arduino.cc/en/Serial/Available)
[serial.print()](http://www.arduino.cc/en/Serial/Print)
[analogRead()](http://www.arduino.cc/en/Reference/AnalogRead)
- 说明
- 系统示例文件目录结构及说明
- 01.Basics
- AnalogReadSerial
- BareMinimum
- Blink
- DigitalReadSerial
- Fade
- ReadAnalogVoltage
- 02.Digital
- BlinkWithoutDelay
- Button
- Debounce
- DigitalInputPullup
- StateChangeDetection
- toneKeyboard
- toneMelody
- toneMultiple
- tonePitchFollower
- 03.Analog
- AnalogInOutSerial
- AnalogInput
- AnalogWriteMega
- Calibration
- Fading
- Smoothing
- 04.Communication
- ASCIITable
- Dimmer
- Graph
- Midi
- MultiSerial
- PhysicalPixel
- ReadASCIIString
- SerialCallResponse
- SerialCallResponseASCII
- SerialEvent
- SerialPassthrough
- VirtualColorMixer
- 05.Control
- Arrays
- ForLoopIteration
- IfStatementConditional
- switchCase
- switchCase2
- WhileStatementConditional
- 06.Sensors
- ADXL3xx
- Knock
- Memsic2125
- Ping
- 07.Display
- barGraph
- RowColumnScanning
- 08.Strings
- CharacterAnalysis
- StringAdditionOperator
- StringAppendOperator
- StringCaseChanges
- StringCharacters
- StringComparisonOperators
- StringConstructors
- StringIndexOf
- StringLength
- StringLengthTrim
- StringReplace
- StringStartsWithEndsWith
- StringSubstring
- StringToInt
- 09.USB
- Keyboard
- KeyboardLogout
- KeyboardMessage
- KeyboardReprogram
- KeyboardSerial
- KeyboardAndMouseControl
- Mouse
- ButtonMouseControl
- JoystickMouseControl
- 10.StarterKit_BasicKit (与特定硬件相关,暂无)
- p02_SpaceshipInterface
- p03_LoveOMeter
- p04_ColorMixingLamp
- p05_ServoMoodIndicator
- p06_LightTheremin
- p07_Keyboard
- p08_DigitalHourglass
- p09_MotorizedPinwheel
- p10_Zoetrope
- p11_CrystalBall
- p12_KnockLock
- p13_TouchSensorLamp
- p14_TweakTheArduinoLogo
- p15_HackingButtons
- 11.ArduinoISP(暂无)
- ArduinoISP