## **讀取ASCII字符串**
> 本例使用Serial.parseInt()函數來**解析**一列用**非字母字符**分割的值。一般來所,人們使用逗號來分隔一段數據的不同的部分(這種格式的數據一般被稱作?**comma-separated-values**?簡稱?**CSV**)。不過這里用空格或者其他字符分割也可以。解析出來的數據將被來給RGB LED調光。你可以使用Arduino?
> IDE的串口監視器來發送類似“5,220,70”這樣的顏色數據到板子來改變LED顏色。
### **所需硬件設備**
* Arduino板或Genuino板
* 共陽RGB
* LED
* 3個220Ω電阻
* 跳線
* 面包板
* 連接線
### **電路**

### **原理圖**
?
你需要四根線來搭建電路。第一根線從5V連接到RGB LED的長腳。你應該將LED引腳稍微轉一下,以保證長腳是左數第二個引腳。
然后將RGB LED插到面包板上,注意,長腳應在從上往下第二個。檢查數據手冊來確定引腳的意義,一般的RGB LED應該有?**R**,**V+**,**G**和**B**四個引腳,從上往下第二個引腳應該接5V。請參照原理圖。
用三個電阻分別連接R引腳到3號引腳、G引腳到5號引腳、B引腳到6號引腳。
**共陽**?RGB LED中共陽的意思是共享陽極。因此如果要讓其亮起來,你要將R/G/B 引腳置LOW,以此在發光二級管兩端創造一個電壓差,讓它亮起來。因此?**analogWrite()**?中傳入255會將LED關閉,而0代表LED將會常開。在下列代碼中,你會看到我們進行了一些數學運算來解決問題,主要是使用了**analogWrite(pin, 255-brightness)**來代替原來的**analogWrite(pin, brightness)**。
### **RGB LED原理**

> 白光LED 與 RGB LED 兩者殊途同歸,都是希望達到白光的效果, 只不過一個是直接以白光呈現,另一個則是以紅綠藍三色混光而成。RGB燈是以三原色共同交集成像,此外,也有藍光LED配合黃色熒光粉,以及紫外LED配合RGB熒光粉,整體來說,這兩種都有其成像原理。某些LED背光板出現的顏色特別清楚而鮮艷,甚至有高畫質電視的程度,這種情形,正是RGB的特色,標榜紅就是紅、綠就是綠、藍就是藍的特性,在光的混色上,具備更多元的特性。([來自百度百科](http://baike.baidu.com/subview/2017681/2017681.htm))
簡單來說RGB LED中有三個小LED,分別是紅色LED、綠色小LED和藍色小LED。通過PWM控制三個小燈的亮度(使用PWM其實是**等效亮度**。依靠人的視覺暫留來實現,并非是直接調整輸出的電壓。)
### **代碼**
首先,你要為RGB LED的各引腳定義全局常量。這將讓你能夠在后面更好的區分哪個引腳是紅色(red),哪個引腳是綠色(green),哪個引腳是藍色(blue):
~~~
const int redPin = 3;
const int greenPin = 5;
const int bluePin = 6;
~~~
在setup()函數中,用下列代碼打開電腦和板子之間的串口連接(波特率9600):
~~~
Serial.begin(9600);
~~~
在setup()函數中, 用下列代碼將引腳定義為OUTPUT:
~~~
pinMode(redPin, OUTPUT);
pinMode(greenPin, OUTPUT);
pinMode(bluePin, OUTPUT);
~~~
在loop()中,檢查是否串口有任何內容。while循環保證后面代碼執行時一定串口有數據:
~~~
while (Serial.available() > 0) {
~~~
然后,聲明一些局部變量來存儲串口獲取的數據。這些數據就是LED的紅色亮度、綠色亮度、藍色亮度信息。用Serial.parseInt()來根據逗號分隔數據,并且存入對應變量:
~~~
int red = Serial.parseInt();
int green = Serial.parseInt();
int blue = Serial.parseInt();
~~~
一旦你將數據存儲到了變量,你還要進行數據校驗,如果收到換行符就說明串口監視器發送的顏色數據全部接收到了:
~~~
if (Serial.read() == '\n') {
~~~
用constrain()函數,你可以將值**約束**為PWM操作的合理數值。通過這種方式,就算是發來的值超過了PWM的允許值,也能夠正常執行。 這些值還要用255減一下,以適配共陽RGB LED,作差后才是在0時LED關閉,在255時LED打開。在約束和數學運算完成后,RGB LED內的三個小LED就能夠工作了。
~~~
red = 255 - constrain(red, 0, 255);
green = 255 - constrain(green, 0, 255);
blue = 255 - constrain(blue, 0, 255);
~~~
已經將RGB值處理完畢, 使用analogWrite()來改變LED的顏色:
~~~
analogWrite(redPin, red);
analogWrite(greenPin, green);
analogWrite(bluePin, blue);
~~~
用十六進制的形式將顏色發回串口監視器:
~~~
Serial.print(red, HEX);
Serial.print(green, HEX);
Serial.println(blue, HEX);
~~~
在你給板子編程完畢后,打開Arduino IDE 串口監視器。按照下列格式輸入:**紅色**+逗號+**綠色**+逗號+**藍色**?(例如?**255**,**255**,**255**)。注意,串口數據的最后一定要有**換行符**(**\n**),不過Arduino IDE的串口監視器默認在發送的每條數據后都加上了換行符,因此這里不用多加。完成這一切后,你會看到LED會根據你提供的數據改變它的顏色。
~~~
/*
讀取ASCII字符串
本代碼展示了Serial庫中parseInt()函數的使用。
parseInt()函數尋找數據中的用逗號分隔的值,然后將他們解析為整型。我們用parseInt()返回的值來給RGB LED設置顏色。
電路搭建: 共陽RGB LED如下連接:(原文錯誤,已經修正)
* 紅色陰極: 3號引腳
* 綠色陰極: 5號引腳
* 藍色陰極: 6號引腳
* 陽極 : +5V
代碼是公開的。
*/
// LED引腳:
const int redPin = 3;
const int greenPin = 5;
const int bluePin = 6;
void setup() {
// 初始化串口:
Serial.begin(9600);
// 將串口設置為OUTPUT模式:
pinMode(redPin, OUTPUT);
pinMode(greenPin, OUTPUT);
pinMode(bluePin, OUTPUT);
}
void loop() {
// 如果串口有數據就繼續:
while (Serial.available() > 0) {
// 獲取下一個整數:
int red = Serial.parseInt();
// 獲取下一個整數:
int green = Serial.parseInt();
// 獲取下一個整數:
int blue = Serial.parseInt();
// 如果是換行符則表示獲取完畢:
if (Serial.read() == '\n') {
// 將rgb值約束到0到255并且進行數學運算
// 如果你用的是共陰LED,只需要寫成"constrain(color, 0, 255);"即可
red = 255 - constrain(red, 0, 255);
green = 255 - constrain(green, 0, 255);
blue = 255 - constrain(blue, 0, 255);
// 給RGB LED調光:
analogWrite(redPin, red);
analogWrite(greenPin, green);
analogWrite(bluePin, blue);
// 以十六進制值輸出顏色數值:
Serial.print(red, HEX);
Serial.print(green, HEX);
Serial.println(blue, HEX);
}
}
}
~~~
### **相關資料**
[if()](https://www.arduino.cc/en/Reference/If)?
[while()](https://www.arduino.cc/en/Reference/While)?
[Serial](https://www.arduino.cc/en/Reference/Serial)?
- 說明
- 系統示例文件目錄結構及說明
- 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