情報処理演習II
本日の講義内容
• Processingのダウンロード • 前回の復習 • アナログ出力とPWM制御 • 演習1: アナログ出力によりLEDの輝度を調整し点灯させよ • 出力装置概要 • ディスプレイの紹介 • 演習2: アナログ出力によりフルカラーLEDを点灯させよ • 演習3: シリアル入力によりフルカラーLEDの色を変化させて点灯させよ • ProcessingとArduinoの連携 • 演習4: PCのウィンドウ上をマウスクリック時にLEDを点灯させよ • 演習5: 加速度センサのX軸の値でPC上に円を描画せよ • 課題 –加速度センサのX,Y,Z軸の値を用いてPC上に図形を描画せよ • X,Yの値で位置を指定,Zの値で図形のサイズを変更 マウスクリックでLEDを点灯させよProcessingのダウンロード
• Processingをダウンロード
–http://processing.org/
復習:プルアップ・プルダウン抵抗の使用
const int SW = 7; const int LED = 13; int state = 0; void setup() { pinMode(LED, OUTPUT); pinMode(SW , INPUT); } void loop() { state = digitalRead(SW); if (state == HIGH) { digitalWrite(LED, HIGH); } else { digitalWrite(LED, LOW); } }
復習:内部プルアップ抵抗の使用
const int SW = 7; const int LED = 13; int state = 0; void setup() { pinMode(LED, OUTPUT); pinMode(SW, INPUT); digitalWrite(SW, INPUT_PULLUP); } void loop() { state = digitalRead(SW); if (state == HIGH) { digitalWrite(LED, HIGH); } else { digitalWrite(LED, LOW); } }
復習:演習1: シリアル通信で学籍と名前を送信
char ID[] = "b1013000¥n"; //自分の学籍番号に変更 char NAME[] = "Sato Ikuma¥n"; //自分の氏名に変更 void setup() { Serial.begin(9600); } void loop() { Serial.print(ID); Serial.print(NAME); delay(1000); }
復習:演習2: シリアル通信による氏名の送信と受信
• @b103000 IkumaSato.? をシリアルモニタから送信し, b103000 IkumaSato¥n¥0がarduinoから送信されシリアルモニタに表示 char NAME[256]; int rx,i = 0; void setup() { Serial.begin(9600); } void loop() { rx = Serial.read(); if(rx != -1){ //受信データが有の場合 if(rx == '?'){ //送信指令を受信した場合 Serial.print(NAME); //配列(氏名)を送信 } else{ if(rx == '@'){ //スタートマークを受信した場合 i = 0; } else if(rx == '.'){ NAME[i++] = '¥n'; NAME[i++] = '¥0'; } else{ NAME[i++] = rx; } } } }復習:演習3: シリアル通信による氏名の送信と記録
• @b103000 IkumaSato.をシリアルモニタから送信し, b103000 IkumaSato¥n¥0がarduinoに記録 #include <EEPROM.h> char NAME[256]; int rx,i = 0; void setup() { Serial.begin(9600); } void loop() { rx = Serial.read(); if(rx != -1){ //受信データが有の場合 if(rx == '@'){ //スタートマークを受信した場合 i = 0; } else if(rx == '.'){ EEPROM.write(i++, '¥n'); EEPROM.write(i++, '¥0'); } else{ EEPROM.write(i++, rx); } } }復習:演習4: シリアル通信による記録した氏名の表示
• Arduinoに記録したb103000 IkumaSato¥n¥0をシリアルモニタで表示 #include <EEPROM.h> char NAME[256]; int rx,i = 0; void setup() { Serial.begin(9600); } void loop() { NAME[i] = EEPROM.read(i); if(NAME[i] == '¥0'){ Serial.print(NAME); i = 0; } i++; delay(100); }復習: センサ紹介(抜粋)
• 単純なアナログ/デジタル入力で扱える
センサの事例を紹介
復習: ArduinoのA/D変換
• 分解能
–Arduino のA/D変換は10bit (0~1023): 10ビット変換機
• 0~5Vの範囲を0~1023の数値で表現 • 5 / 1023 ≒ 0.005 → 5mV単位の変化を検出
• サンプリング周波数
– ArduinoのA/D変換は標準で約9.6kHz • 高速化もできるが,精度が低下 1023 512 2.5V 5.0V 0V 0復習: 演習5:サーミスタの値を抵抗値と摂氏への変換し、PCへ表示
• 片側をGND
• もう片側をアナログ
入力(A0)
• A0と5V間に抵抗
(10KΩ)を配置
–テスターでチェックすること黒
10kΩ
5V
A0
GND
復習: 高精度サーミスタ (AT Thermistor)
• 温度によって抵抗値が変化
–今回配布するのは「石塚電子 103AT-2」 –25度時に約10KΩ • 温めると抵抗値が減少 – 仕様書を確認復習: サーミスタの仕様
y = -0.63x + 25.83 y = -0.6296x + 25.831 0 5 10 15 20 25 30 0 5 10 15 20 25 30 温度(℃) 抵 抗 値 ( kΩ )復習: サーミスタの回路
A/D変換値が520のとき
520:(1023-520) =
y
:10
kΩ
503
y
= 5200
kΩ
y
= 5200/503 = 10.33
kΩ
10.33 = -0.63
x
+25.83
0.63
x
= 15.50
x
= 24.60
℃
復習: ソースコード(アナログ入力→シリアル通信)
void loop() { value = analogRead(SENSOR); y = 10.0* value /(1023.0-value); x = (25.83-y)/0.63; Serial.print("sensor = " ); Serial.println(value); Serial.print("Resistor = " ); Serial.println(y); Serial.print("Temperature = " ); Serial.println(x); delay(1000); }復習:演習6:加速度センサの値を加速度への変換し、PCへ表示
• 以下の通りに設置せよ
–ピンアサインと向きに注意すること –間違えるとセンサが壊れるので注意すること 加速度センサの ピン番号 機能 マイコンボードの ピン番号 1 電源 5V 2 パワーシャットダウン 5V 3 GND GND 4 パリティ N.C. 5 セルフテスト GND 6 X軸出力 A2 7 Y軸出力 A1 8 Z軸出力 A0 1 4 5 8復習: 3軸加速度センサモジュール
•
振動,慣性力,重力加速度
(地軸に対する傾き)などを検出
–配ったものは秋月電子 KXM52-1050 • 測定レンジ: ±2G • 電源が5V時は 2.5Vが0G+X
+Y
+Z
+X
+Y
+Z
復習: 加速度センサの仕様
x = y - 2.5
復習: 3軸加速度を表示
const int ACCX = A2; const int ACCY = A1; const int ACCZ = A0; int value = 0; float ACC = 0.0; float offset= 2.5; void setup() { Serial.begin(9600); } void loop() { value = analogRead(ACCX);
ACC = value * 0.005 - offset;
Serial.print(ACC); Serial.print(",");
value = analogRead(ACCY);
ACC = value * 0.005 - offset;
Serial.print(ACC); Serial.print(",");
value = analogRead(ACCZ);
ACC = value * 0.005 - offset;
Serial.println(ACC); delay(100);}
デジタル出力とアナログ出力
• デジタル出力
–0V or 5Vの電圧を出力 • digitalWrite(LED, HIGH) -> 5V • digitalWrite(LED, LOW) -> 0V• アナログ出力
–0~5Vの電圧変化を疑似的に再現• パルス幅変調(Pulse Width Modulation,PWM)を利用
5 0 時間 (t) 電圧 (V) 電圧 (V)
PWMによる疑似的なアナログ出力
• 出力を高速な周期で切り替えること(PWM)で,
疑似的に電圧変化を表現
PWM
• パルス幅のデューティ比を変化させ変調
–デューティ比:パルス幅をパルス周期で割ったもの
パルス周期
PWM
• パルス幅のデューティ比を変化させ変調
–デューティ比:パルス幅をパルス周期で割ったもの • 一定の周期(T)内のHigh/Lowの比率 –アナログ出力: 出力電圧(High)×デューティ比 パルス周期 (T) Low Low パルス幅 パルス幅 High High デューティ比: 25% デューティ比: 50% 実質電圧2.5V 実質電圧1.25Vアナログ(PWM)出力ポート
3,5,6,9,10,11
~
演習1: アナログ出力によりLEDの輝度を調整し点灯させよ
• LED(A)
–「~9」に接続
• LED(K)
ソースコード
const int LED = 9; void setup() { } void loop() { for(int i = 0 ; i <= 255; i+=5) { analogWrite(LED, i); delay(10); } for(int i = 255 ; i >= 0; i-=5) { analogWrite(LED, i); delay(10); } }
デューティ比
100% = 255
関数リファレンス
• analogWrite(pin, value)
–指定したピンからアナログ値を出力、 PWM信号の周波数は約490Hz • [パラメータ] – pin: 出力に使うピンの番号 – value: デューティ比(0から255) • [戻り値] – なし出力装置
視覚: ディスプレイ
聴覚: スピーカー
ディスプレイ
• LED (Light Emitting Diode)
–発光ダイオード
• LCD (Liquid Crystal Display)
–液晶ディスプレイ
• OELD (Organic Electro-Luminescence Display)
LED (Light Emitting Diode)
• 多種多様な種類が存在
–色 –明るさ • 通常/高輝度/ハイパワー(照明用) –サイズ • 5㎜/3mm/チップフルカラーLED
• R/G/Bを独立制御
7セグメントLED
• 数値表示に最適化したLED
7セグメントLED
• 数値表示に最適化したLED
LEDマトリクス
• LEDを縦横に敷き詰めたもの
–少ないピン数で利用できるような工夫 –フルカラーLEDマトリクス存在
LCD
• コンピュータの液晶ディスプレイの小型版
–モノクロとカラーが存在
• カラーは1画素をRBGの3つの素子で構成
LCD
• コンピュータの液晶ディスプレイの小型版
–モノクロとカラーが存在 • カラーは1画素をRBGの3つの素子で構成 –バックライト(LED or 冷陰極管)が必要 • 輝度を調整 –電極への信号により液晶層を制御 • 3種類のピクセルデータの信号(+,-) • ピクセルクロック(+,-)液晶モニタ (PC用)
• LCDの制御部への入力方式
–アナログ入力 • D-Sub 15ピン –デジタル入力 • HDMI • DisplayPort • DVI アナログ・デジタル信号制御部
LCD
• 制御信号 – ピクセルデータ – ピクセルクロックテキストLCD (Liquid Crystal Display)
• 文字出力専用の液晶ディスプレイ
–部分的に自由描画できるものもある
OELD(有機ELディスプレイ)
• 薄い/柔軟な自己発光型ディスプレイ
• 鮮やかで発色がよく,視野角が広い
演習2:アナログ出力によりフルカラーLEDを点灯させよ
• フルカラーLED
–R(1kΩ) • ~ 11 –GND –B(1kΩ) • ~ 10 –G(1kΩ) • ~ 9• 可変抵抗
–5V –アナログ入力 • A0 –GNDソースコード(可変抵抗でLEDが変化)
int ledPins[3] = {9, 10, 11};
const int SENSOR = A0;
int val;
void setup() {
}
void loop() {
val = analogRead(SENSOR);
val = map(val, 0, 1023, 0, 255);
analogWrite(ledPins[0],val);
analogWrite(ledPins[1],val);
analogWrite(ledPins[2],val);
delay(10);
}
演習3: シリアル入力によりフルカラーLEDの色を変化させて点灯させよ
• フルカラーLED
–R(1kΩ) • ~ 11 –GND –B(1kΩ) • ~ 10 –G(1kΩ) • ~ 9• 可変抵抗
–5V –アナログ入力 • A0 –GNDシリアルから対象の色を選択
else if(color == 1) { analogWrite(ledPins[0],0); analogWrite(ledPins[1],val); analogWrite(ledPins[2],0); } else if(color == 0) { analogWrite(ledPins[0],0); analogWrite(ledPins[1],0); analogWrite(ledPins[2],val); } else{ analogWrite(ledPins[0],val); analogWrite(ledPins[1],val); analogWrite(ledPins[2],val); } delay(10); } int ledPins[3] = {9, 10, 11};const int SENSOR = A0; int val; int color = 0; void selectColor(); void setup() { Serial.begin(9600); } void loop() { selectColor(); val = analogRead(SENSOR); val = map(val, 0, 1023, 0, 255); if(color == 2){ analogWrite(ledPins[0],val); analogWrite(ledPins[1],0); analogWrite(ledPins[2],0); }
シリアルから対象の色を選択
void selectColor(){ if(Serial.available() > 0){ switch(Serial.read()){ case 'g': color = 2; break; case ‘b’: color = 1; break; case ‘r’: color = 0; break; default: color = 4; break; } } }Processingの特徴(1)
• Arduinoの開発環境のベース
• 見た目も似てる
• MITを中心に開発
• 2002~開発開始
• 2005~ベータ版公開
• 2008~正式版公開
• Javaをベースに遥かに
単純化
• 非プログラマでもOK
Processingの特徴(2)
• インタラクティブなグラフィックス/アニメーションを簡単に実現
Processingのソースコード
void setup(){
size (480, 240);
}
void draw(){
if(mousePressed){
fill(0);
}
else{
fill(255);
}
ellipse(mouseX, mouseY,80, 80);
}
ProcessingとArduinoを連携
• シリアル通信を利用
–PCアプリ→Arduino • マウスクリックでLED点灯 –Aruduino→PCアプリ • センサで画面に描画⇒
⇒
演習4: PCのウィンドウ上をマウスクリック時にLEDを点灯させよ
• ウィンドウ上でマウスをクリックするとLEDが点灯
–マウスのX座標によってLEDの明るさが変化
ソースコード(
Arduino
)
const int LED = 9;
int value = 0;
void setup() {
Serial.begin(9600);
}
void loop() {
if(Serial.available()>0){
value = Serial.read();
analogWrite(LED, value );
}
}
ソースコード(
Processing
)
import processing.serial.*;
Serial myPort;
void setup(){
size(256,256);
myPort=new Serial(this, “
COM1
”,9600);
}
void draw(){
background(255);
}
void mousePressed(){
myPort.write(mouseX);
}
void mouseReleased(){
myPort.write(0);
}
変 Arduino->Tool->Port演習5: 加速度センサのX軸の値でPC上に描画せよ
• 以下の通りに設置せよ
–ピンアサインと向きに注意すること –間違えるとセンサが壊れるので注意すること 加速度センサの ピン番号 機能 マイコンボードの ピン番号 1 電源 5V 2 パワーシャットダウン 5V 3 GND GND 4 パリティ N.C. 5 セルフテスト GND 6 X軸出力 A2 7 Y軸出力 A1 8 Z軸出力 A0 1 4 5 8ソースコード(
Arduino
)
const int ACCX = A2; int value = 0; void setup() { Serial.begin(9600); } void loop() { value = analogRead(ACCX); value = map(value, 0, 1023, 0, 255 ); Serial.write(value ); delay(100); }
ソースコード(
Processing
)
import processing.serial.*; Serial myPort; int x = 0; void setup(){ size(256,256);myPort=new Serial(this, “COM11”,9600);
} void draw(){ background(255); ellipse(x,100,50,50); } void serialEvent(Serial p){ x = myPort.read(); }
ソースコード(
Arduino
)
通信同期機能実装(ウインドウをクリックで開始)
const int ACCX = A2; int value = 0; void setup() { Serial.begin(9600); } void loop() { value = analogRead(ACCX); value = map(value, 0, 1023, 0, 255 ); if(Serial.available()>0) { Serial.read(); Serial.write(value ); } delay(100); }
ソースコード(
Processing
)
通信同期機能実装(ウインドウをクリックで開始)
import processing.serial.*; Serial myPort; int x = 0; void setup(){ size(256,256); myPort=new Serial(this, “COM11”,9600);
} void draw(){ background(255); ellipse(x,100,50,50); } void serialEvent(Serial p){ if(myPort.available()>0) { x = myPort.read(); myPort.write(255); } } void mousePressed(){ myPort.write(mouseX); }
関数リファレンス(1)
• map(value, fromLow, fromHigh, toLow, toHigh)
–数値をある範囲から別の範囲に変換 • [パラメータ] – value: 変換したい数値 – fromLow:現在の範囲の下限 – fromHigh:現在の範囲の上限 – toLow: 変換後の範囲の下限 – toHigh: 変換後の範囲の上限 • [戻り値] – 変換後の数値