ArduinoでCdS光センサーを使う方法|配線・コード・しきい値設定を徹底解説
CdSセル(光センサー、CdSフォトレジスタ)は、周囲の明るさに応じて抵抗値が変化する部品です。Arduinoと組み合わせれば、「明るい・暗い」をコードの中で判定できます。本記事では、配線の基本からanalogReadでの値の取得までを解説します。さらに、しきい値を使ったLED連動まで、初心者の方に向けて順を追って紹介します。
01CdSセル(光センサー)とは

明るいほど抵抗が下がる部品
CdSセルは、光の強さによって内部の抵抗値が変化する部品です。「CdS」は素材である硫化カドミウムの略称です。フォトレジスタや光依存抵抗(LDR)とも呼ばれます。明るい光が当たると抵抗値は下がります。逆に、暗くなると抵抗値は上がります。この性質を利用して、周囲の明るさをArduinoに伝えることができます。
可変抵抗と似た考え方で扱える
CdSセルの働きは、つまみを回すと抵抗値が変わる可変抵抗とよく似ています。違うのは、指ではなく光の量が抵抗値を変える点です。そのため、電気的な扱い方も可変抵抗と共通する部分が多くあります。可変抵抗をすでに学んだ方は、本記事の内容もスムーズに理解できるはずです。
可変抵抗の記事で分圧回路の考え方を学んだUさんは、次にCdSセルに挑戦した。回路の組み方が可変抵抗とほとんど同じだったため、迷うことなく配線できた。「抵抗値が変化する部品」という共通点に気づいたのだ。この気づきが、新しい部品を学ぶスピードを上げてくれます。
02なぜ分圧回路が必要か
Arduinoは抵抗値を直接読み取れない
ここで注意したい点があります。ArduinoのanalogRead()が読み取れるのは「電圧」です。「抵抗値」ではありません。CdSセルの抵抗値がどれだけ変化しても、それだけではArduinoに伝わりません。そこで必要になるのが「分圧回路」という仕組みです。
分圧回路の考え方
分圧回路とは、2つの抵抗を直列につなぐ仕組みです。その中間点の電圧を取り出します。CdSセルと固定抵抗を直列につなぐとどうなるでしょうか。CdSセルの抵抗値の変化に応じて、中間点の電圧も変化します。この電圧の変化を、Arduinoのアナログ入力ピンで読み取るのです。可変抵抗の記事で紹介した仕組みと、基本的な考え方は同じです。
「センサーの値を電圧の変化に変換してから読み取る」という考え方があります。これは、CdSセルに限らず多くのアナログセンサーに共通しています。この分圧回路の仕組みを一度理解しておきましょう。今後さまざまなセンサーを扱う際の土台になります。
03配線方法:Arduino・CdSセル・抵抗

分圧回路の組み方
もっとも一般的な配線を紹介します。CdSセルの片側をArduinoの5Vにつなぎます。もう片側はArduinoのアナログピン(例:A0)につなぎます。同じA0のラインから、10kΩ程度の抵抗をもう1本つなぎます。その抵抗の反対側はGNDにつなぎます。これで分圧回路が完成します。
明るさと値の対応関係
この配線の場合、対応関係はシンプルです。明るいほどCdSセルの抵抗値は下がります。すると、A0側の電圧が上がります。その結果、analogRead()の値は大きくなります。逆に、暗いほど値は小さくなります。CdSセルには極性(+-の向き)がありません。2本のリード線はどちらを5V側につないでも動作します。
編集部の見解として、抵抗値は10kΩ程度から試すのがおすすめです。一般的なCdSセルであれば、室内の明るさで良好な変化幅が得られます。値の変化が小さすぎる場合もあるでしょう。あるいは片方に張り付いてしまう場合もあります。そうしたときは、抵抗値を1kΩ〜100kΩの範囲で変えて試してみてください。
04基本のコード|analogReadで明るさを読み取る
最小構成のコード
配線ができたら、コードで値を読み取ってみましょう。Arduino公式のanalogRead()リファレンスを確認しましょう。ピン番号を渡すだけで、0〜1023の値を取得できます。
// CdSセルの値をシリアルモニタに表示するコード
const int cdsPin = A0;
void setup() {
Serial.begin(9600);
}
void loop() {
int value = analogRead(cdsPin);
Serial.println(value);
delay(200);
}
シリアルモニタで傾向をつかむ
このコードを書き込んだら、シリアルモニタを開いてみましょう。手でCdSセルを覆うと、値がどう変化するか確認できます。部屋の照明を消してみるのもよい方法です。まずは、自分の環境での明暗のおおよその値の範囲をつかんでおきましょう。次の章のしきい値設定に役立ちます。
05しきい値を設定してLEDを連動させる

if文でしきい値判定
明るさの値が取得できたら、次のステップに進みましょう。「ある値より暗くなったらLEDを点灯する」という処理を書いてみます。if文を使って、値がしきい値を下回ったかどうかを判定します。
// 暗くなったらLEDを点灯させる基本コード
const int cdsPin = A0;
const int ledPin = 8;
const int threshold = 400; // このしきい値は環境に合わせて調整する
void setup() {
pinMode(ledPin, OUTPUT);
Serial.begin(9600);
}
void loop() {
int value = analogRead(cdsPin);
if (value < threshold) {
digitalWrite(ledPin, HIGH); // 暗いのでLEDを点灯
} else {
digitalWrite(ledPin, LOW); // 明るいのでLEDを消灯
}
Serial.println(value);
delay(100);
}
チカチカが起きる理由
しきい値ちょうどの明るさでは、困った現象が起きることがあります。わずかな値の変動だけで、LEDのON/OFFが何度も切り替わるのです。ちらついてしまいます。これは、タクトスイッチのチャタリングと似た症状です。
ヒステリシスで対策する
対策として、ON用とOFF用に異なる2つのしきい値を用意する方法があります。この考え方を「ヒステリシス」と呼びます。
// ヒステリシスを使ってチカチカを防ぐコード
const int cdsPin = A0;
const int ledPin = 8;
const int thresholdOn = 350; // これより暗くなったら点灯
const int thresholdOff = 450; // これより明るくなったら消灯
bool ledState = false;
void setup() {
pinMode(ledPin, OUTPUT);
Serial.begin(9600);
}
void loop() {
int value = analogRead(cdsPin);
if (!ledState && value < thresholdOn) {
ledState = true; // 暗くなったので点灯状態にする
} else if (ledState && value > thresholdOff) {
ledState = false; // 明るくなったので消灯状態にする
}
digitalWrite(ledPin, ledState);
Serial.println(value);
delay(100);
}
2つのしきい値の間に幅を持たせます。これにより、境界付近での細かい変動を無視できます。チャタリング対策の考え方について、詳しくは下記の記事も参考にしてください。
06実践例:暗くなったら自動点灯するライト
PWMで自然な明るさの変化を再現する
ON/OFFの切り替えだけではありません。明るさに応じてLEDの輝度をなめらかに変化させることもできます。map()関数を使って、CdSセルの値をLEDの明るさに変換してみましょう。値の変換方法については、可変抵抗の記事でも詳しく解説しています。
実装コード
// 暗いほどLEDが明るくなる自動ライトのコード
const int cdsPin = A0;
const int ledPin = 9; // PWM対応ピン(~マーク付き)を使用
void setup() {
pinMode(ledPin, OUTPUT);
Serial.begin(9600);
}
void loop() {
int value = analogRead(cdsPin);
// 暗いほど値が小さい配線なので、明るさは反転させて変換する
int brightness = map(value, 0, 1023, 255, 0);
analogWrite(ledPin, brightness);
Serial.println(value);
delay(100);
}
この例では、map()の変換先を255から0という順番で指定しています。値が小さい(暗い)ほど明るさが大きくなるように反転させているのです。LEDの配線や抵抗値の考え方については、下記の記事も参考にしてください。
07よくあるトラブルと対処法

症状別の対処早見表
| 症状 | 主な原因 | 対処法 |
|---|---|---|
| 値がまったく変化しない | 分圧回路が組めていない(CdSセルか抵抗だけがピンに接続) | CdSセルと抵抗を直列にし、中間点をアナログ入力につなぎ直す(3章参照) |
| 値が常に0または1023付近で固定 | 抵抗値がCdSセルの特性と合っていない | 抵抗値を1kΩ〜100kΩの範囲で変えて試す(3章参照) |
| LEDがしきい値付近でちらつく | ヒステリシスのない単純なしきい値判定 | ON用・OFF用の2つのしきい値を設定する(5章参照) |
| 明るさとLEDの動きが逆になる | 配線の向き、またはmap()の変換方向の解釈違い | 実機で値を確認し、しきい値やmap()の引数順を調整する |
| コードを書き込んでも一切反応しない | 配線ミス、またはピン番号の指定違い | CdSセル・抵抗の配線とコード内のピン番号を再確認する |
原因を素早く切り分けるコツ
Hさんは自動点灯ライトを作ったが、部屋を暗くしてもLEDが点灯しなかった。そこで、いったんしきい値判定を外してみた。シリアルモニタで生の値だけを確認したのだ。すると、明るい部屋で値が20程度しかないことに気づいた。暗くしても10程度までしか下がらなかった。配線を見直すと、CdSセルと抵抗の位置が逆になっていた。正しくつなぎ直すと、明るい部屋で900前後、暗い部屋で50前後と、大きく変化するようになった。
08よくある質問
基本のQ&A
応用のQ&A
関連記事・参考資料
基礎を学べる記事
- YOFUKASI LAB「Arduinoで可変抵抗を読む|配線と値の取得」2026年, https://yofukasi-lab-wp.com/2026/08/27/arduino-potentiometer-analogread/
- YOFUKASI LAB「analogRead・analogWriteの使い方」2026年, https://yofukasi-lab-wp.com/2026/07/30/analog-read-analogwrite/
- YOFUKASI LAB「Arduinoに必要な工具・部品リスト」2026年, https://yofukasi-lab-wp.com/2026/08/22/arduino-tools-parts/
応用・トラブルシューティング記事
- YOFUKASI LAB「Arduinoでタクトスイッチ入力|配線とコード」2026年, https://yofukasi-lab-wp.com/2026/08/27/arduino-tact-switch-input/
- YOFUKASI LAB「Arduinoのシリアルモニタ活用術」2026年, https://yofukasi-lab-wp.com/2026/08/22/arduino-serial-monitor-debugging/
- YOFUKASI LAB「Arduinoのコンパイルエラー一覧」2026年, https://yofukasi-lab-wp.com/2026/07/30/error/
参考資料(外部・一次情報)
- Arduino Documentation「analogRead()」, https://docs.arduino.cc/language-reference/en/functions/analog-io/analogRead/
- Adafruit Learning System「Photocells」, https://learn.adafruit.com/photocells
※本記事は個人の学習・電子工作用途を対象にしています。実際の製品や医療機器へ組み込む場合は、電気安全・製品規格の専門家に別途ご相談ください。
コメント