Компоненты · 11 мин чтения

Датчик отпечатков пальцев и Arduino: AS608, R307 и дверной замок

Как подключить датчик отпечатков пальцев к Arduino: цвета проводов и питание AS608/R307, регистрация и проверка с Adafruit Fingerprint, замок на реле, ESP32 и решение проблем.

Датчик отпечатков пальцев позволяет Arduino-проекту одним касанием спросить «кто ты?» и открыть дверь, ящик или сейф, когда палец узнан. Самые распространённые модели в любительской электронике — оптические модули на базе AS608 и R307: они сами обрабатывают изображение пальца, хранят отпечатки в собственной памяти и отправляют Arduino только короткий ответ вроде «совпадение с ID 3». Поэтому даже небольшая плата вроде Arduino Uno легко справится с замком по отпечатку на сотни человек.

В этом руководстве разберём, как работает датчик, как правильно его подключить, даже если цвета проводов у разных производителей отличаются, как регистрировать (enroll) и проверять отпечатки с библиотекой Adafruit Fingerprint и что означают ID и оценка достоверности. Затем соберём настоящий дверной замок с реле и соленоидом на 12 V, сделаем то же самое на ESP32 и Raspberry Pi Pico и пошагово устраним печально известную ошибку «Did not find fingerprint sensor».

Оптический датчик отпечатков пальцев AS608 с 6-проводным разъёмом
Оптический датчик отпечатков пальцев AS608: считывающее окно с призмой, DSP-чип, который обрабатывает изображение, и комплект разъёмов с тонкими проводами. Цвета проводов зависят от продавца.

Что такое датчик отпечатков пальцев и как он работает?

Модули вроде AS608 и R307 — это оптические датчики. Когда палец лежит на стекле, светодиод внутри подсвечивает призму под ним; гребни папиллярных линий касаются стекла и отражают свет иначе, чем бороздки, которые стекла не касаются. Крошечная камера снимает этот узор как изображение в оттенках серого с разрешением около 500 dpi. DSP-чип модуля находит точки, где линии обрываются или раздваиваются (минуции), и превращает их в файл признаков (character file) размером в несколько сотен байт. Два файла признаков одного пальца объединяются в шаблон (template), и этот шаблон сохраняется во встроенной флеш-памяти датчика под номером ID.

При проверке датчик снова превращает новое изображение в файл признаков и сравнивает его со всеми сохранёнными шаблонами. Такой поиск 1:N обычно занимает меньше секунды; в конце датчик возвращает ID совпавшей записи и оценку достоверности (confidence), которая показывает, насколько надёжно совпадение. Главное: изображение отпечатка вообще не попадает в Arduino, вся тяжёлая работа выполняется внутри датчика. Arduino лишь отправляет команды по последовательному порту (UART) и читает короткие ответы.

ХарактеристикаМодуль AS608R307FPM10A / ZFM-20
Питание3,3 V4,2–6 V (обычно 5 V)3,6–6 V
Число записейОбычно 300 (на некоторых платах 162)1000162
ИнтерфейсUART (TTL), по умолчанию 57600 бодUART (TTL), по умолчанию 57600 бодUART (TTL), по умолчанию 57600 бод
Пин обнаружения касанияЕсть (WAK + Vt)Есть (Touch + 3.3VT)У большинства нет
Уровень безопасности1–51–51–5
Вероятность ложного допуска (FAR)< 0,001%< 0,001%< 0,001%
Библиотека для ArduinoAdafruit FingerprintAdafruit FingerprintAdafruit Fingerprint

Значения в таблице могут зависеть от продавца и ревизии платы, особенно ёмкость памяти. Надёжнее всего запустить тестовый скетч ниже и прочитать ёмкость, которую сообщает датчик. Заодно определимся с тремя терминами: ID — номер ячейки шаблона в памяти (от 0 до ёмкости минус один); уровень безопасности задаёт порог совпадения от 1 (самый мягкий) до 5 (самый строгий); а оценка достоверности — это степень сходства, которую датчик возвращает при каждом совпадении.

Цвета проводов и питание: какой провод куда?

Самая частая ошибка с датчиками отпечатков — считать, что цвета проводов стандартные. Одна и та же модель у одного продавца приходит с красным, чёрным, жёлтым и белым проводами, а у другого — с красным, чёрным, зелёным и синим; даже Adafruit приводит разные схемы цветов для разных версий датчика. Поэтому не ориентируйся на цвет: смотри надписи у пинов на обороте датчика или рядом с разъёмом и схему продавца. У модулей AS608 обычно 6 пинов: V+ (Vi), TX, RX, GND, WAK (Touch) и Vt (3.3VT). Для базового использования хватит первых четырёх.

Пин датчикаНазначениеArduino UnoESP32Raspberry Pi Pico
V+ / Vi / VCCПитание3.3V (AS608) или 5V (R307)3V3 (5V/VIN для R307)3V3(OUT) (VBUS для R307)
GNDЗемляGNDGNDGND
TXВыход данных датчикаD2 (SoftwareSerial RX)GPIO 16 (RX2)GP1 (UART0 RX)
RXВход данных датчикаD3 (SoftwareSerial TX)GPIO 17 (TX2)GP0 (UART0 TX)
WAK / TouchСигнал обнаружения пальца (необязательно)D4GPIO 27GP2
Vt / 3.3VTПитание схемы обнаружения касания (необязательно)3.3V3V33V3(OUT)
Большинство плат AS608 работают от 3,3 V; 5 V на датчике с маркировкой 3.3V могут необратимо его повредить. R307, напротив, нужны 5 V, а от 3,3 V он часто вообще не отвечает. Пин 3.3V у Uno официально рассчитан всего на 50 mA, а оптический датчик при съёмке изображения потребляет больше (Adafruit указывает для своего оптического датчика рабочий ток до 120 mA). Если плата случайно перезагружается или датчик то и дело пропадает, запитай датчик от внешнего стабилизатора 3,3 V, например AMS1117, и соедини земли. Пин D3 у Uno выдаёт 5 V, поэтому для датчика на 3,3 V безопаснее всего поставить на линию RX делитель напряжения 1 kΩ + 2 kΩ (рассчитать его поможет утилита делителя напряжения).

Пин WAK (или Touch) подключён к маломощной схеме обнаружения касания внутри датчика. Если на пин Vt подано 3,3 V, уровень на WAK меняется в тот момент, когда палец касается стекла; на большинстве модулей он становится HIGH, на некоторых LOW, так что проверь это на своей плате. В замке на батарейках можно отключать основное питание MOSFET-ом, оставив запитанным только Vt, а сигналом WAK будить микроконтроллер из сна и только тогда включать датчик.

Установка библиотеки Adafruit Fingerprint

  1. В Arduino IDE открой Инструменты › Управлять библиотеками (Tools › Manage Libraries), найди Adafruit Fingerprint Sensor Library и установи её. Если библиотеки раньше не добавлялись, загляни в статью Как добавить библиотеку в Arduino.
  2. Библиотека работает со всеми датчиками с тем же набором команд — AS608, R307, R503, FPM10A и серией ZFM; менять код не нужно.
  3. В меню «Файл › Примеры» (File › Examples) есть примеры enroll (регистрация), fingerprint (проверка), delete (удаление одной записи) и emptyDatabase (удаление всех записей).
  4. На Uno и Nano датчик подключают к D2 и D3 через SoftwareSerial, чтобы не занимать пины 0 и 1, которые использует USB-соединение. На платах со вторым аппаратным последовательным портом, таких как Mega, Leonardo и ESP32, используется Serial1 или Serial2.

Первый тест: находится ли датчик?

Прежде чем регистрировать отпечатки, убедимся, что датчик общается с Arduino. Скетч ниже сначала ищет датчик на стандартной скорости 57600 бод, а если не находит, пробует другие распространённые скорости. Найдя датчик, он выводит в монитор порта скорость, на которой датчик ответил, заявленную ёмкость, уровень безопасности и число сохранённых отпечатков. Не забудь выставить в мониторе порта 9600 бод — это не зависит от скорости датчика.

C++ (Arduino IDE)
1#include <Adafruit_Fingerprint.h>
2#include <SoftwareSerial.h>
3
4SoftwareSerial fpSerial(2, 3);            // D2 = RX (sensör TX), D3 = TX (sensör RX) / D2 = RX (sensor TX), D3 = TX (sensor RX)
5Adafruit_Fingerprint finger(&fpSerial);
6
7const uint32_t rates[] = {57600, 9600, 19200, 38400, 115200};   // denenecek hızlar / baud rates to try
8
9void setup() {
10  Serial.begin(9600);
11  Serial.println(F("Sensor araniyor / searching for sensor..."));
12  bool found = false;
13  for (uint8_t i = 0; i < 5 && !found; i++) {
14    finger.begin(rates[i]);               // 1 sn bekler, portu açar / waits 1 s, opens the port
15    if (finger.verifyPassword()) {        // sensör cevap verdi mi? / did the sensor answer?
16      Serial.print(F("Bulundu / found @ "));
17      Serial.println(rates[i]);
18      found = true;
19    }
20  }
21  if (!found) {
22    Serial.println(F("Did not find fingerprint sensor :("));
23    while (1) delay(1);
24  }
25  finger.getParameters();                 // kapasite ve ayarları oku / read capacity and settings
26  Serial.print(F("Kapasite / capacity: "));
27  Serial.println(finger.capacity);
28  Serial.print(F("Guvenlik / security level: "));
29  Serial.println(finger.security_level);
30  finger.getTemplateCount();              // kayıtlı şablon sayısı / number of stored templates
31  Serial.print(F("Kayitli iz / templates: "));
32  Serial.println(finger.templateCount);
33}
34
35void loop() {
36}

Регистрация отпечатка (enroll) шаг за шагом

При регистрации датчик делает два отдельных снимка одного и того же пальца, сохраняет их как файлы признаков в двух буферах (CharBuffer1 и CharBuffer2), объединяет их в шаблон и записывает шаблон под выбранным ID. Готовый пример enroll от Adafruit запрашивает ID от 1 до 127 и хранит его в однобайтовой переменной. Упрощённая версия ниже хранит ID в 16 битах и берёт верхнюю границу из реальной ёмкости датчика, так что можно использовать все ячейки датчика на 300 или 1000 отпечатков. Шаги в библиотеке такие:

  1. getImage(): пытается получить изображение, пока палец не окажется на стекле; если пальца нет, возвращает FINGERPRINT_NOFINGER.
  2. image2Tz(1): превращает первое изображение в файл признаков и кладёт его в буфер 1.
  3. Палец убирают и снова прикладывают тот же палец; image2Tz(2) кладёт второе изображение в буфер 2.
  4. createModel(): сравнивает и объединяет два буфера; если они не совпадают, возвращает FINGERPRINT_ENROLLMISMATCH.
  5. storeModel(id): навсегда записывает шаблон во флеш-память датчика; при отключении питания он не стирается.
C++ (Arduino IDE)
1#include <Adafruit_Fingerprint.h>
2#include <SoftwareSerial.h>
3
4SoftwareSerial fpSerial(2, 3);            // D2 = RX, D3 = TX
5Adafruit_Fingerprint finger(&fpSerial);
6
7void setup() {
8  Serial.begin(9600);
9  finger.begin(57600);
10  if (!finger.verifyPassword()) {
11    Serial.println(F("Did not find fingerprint sensor :("));
12    while (1) delay(1);
13  }
14  finger.getParameters();                 // gerçek kapasiteyi öğren / learn the real capacity
15  Serial.println(F("Kayit modu / enroll mode"));
16}
17
18// Parmak gelene kadar bekle, görüntüyü tampona çevir / wait for a finger, convert the image into a buffer
19bool captureTo(uint8_t slot) {
20  while (finger.getImage() != FINGERPRINT_OK) delay(50);
21  uint8_t p = finger.image2Tz(slot);
22  if (p != FINGERPRINT_OK) {
23    Serial.print(F("Goruntu kotu / bad image, kod / code 0x"));
24    Serial.println(p, HEX);
25    return false;
26  }
27  return true;
28}
29
30void loop() {
31  Serial.print(F("ID gir / enter ID (1-"));
32  Serial.print(finger.capacity - 1);
33  Serial.println(F("):"));
34  while (!Serial.available()) delay(10);
35  uint16_t id = Serial.parseInt();
36  while (Serial.available()) Serial.read();   // satır sonunu temizle / clear the line ending
37  if (id == 0 || id >= finger.capacity) return;
38
39  Serial.println(F("Parmagini koy / place your finger"));
40  if (!captureTo(1)) return;
41  Serial.println(F("Kaldir / remove your finger"));
42  delay(1000);
43  while (finger.getImage() != FINGERPRINT_NOFINGER) delay(50);   // parmak kalkana kadar / until the finger is lifted
44
45  Serial.println(F("Ayni parmagi tekrar koy / place the same finger again"));
46  if (!captureTo(2)) return;
47
48  uint8_t p = finger.createModel();       // iki görüntüyü birleştir / merge the two images
49  if (p == FINGERPRINT_ENROLLMISMATCH) {
50    Serial.println(F("Fingerprints did not match"));
51    return;
52  }
53  if (p != FINGERPRINT_OK) return;
54
55  p = finger.storeModel(id);              // sensörün flash belleğine yaz / write to the sensor's flash
56  if (p == FINGERPRINT_OK) {
57    Serial.print(F("Kaydedildi / stored, ID #"));
58    Serial.println(id);
59  } else {
60    Serial.print(F("Kayit hatasi / store error 0x"));
61    Serial.println(p, HEX);
62  }
63}
Введи ID в мониторе порта, нажми Enter и следуй подсказкам. От качества регистрации зависят все последующие проверки: клади палец в центр стекла, не прижимая слишком сильно, а для второго снимка лишь слегка меняй угол. Для замка, которым пользуются каждый день, регистрация одного и того же пальца под двумя разными ID (один раз ровно, другой — с лёгким наклоном) заметно снижает число отказов. Записывай, какой ID кому принадлежит: датчик знает только номера, а не имена.

Проверка отпечатка: ID и оценка достоверности

Для проверки сначала получают изображение через getImage(), преобразуют его через image2Tz(), а затем ищут среди сохранённых шаблонов. В библиотеке две функции поиска: fingerFastSearch() работает быстро, но команда, которую отправляет библиотека, просматривает только первые 163 записи (ID 0–162); fingerSearch() ищет по всей ёмкости, прочитанной через getParameters(). Если нужны ID больше 162, используй fingerSearch() и обязательно вызывай getParameters() в setup(); иначе библиотека считает ёмкость равной 64 по умолчанию и ищет только среди первых 64 записей.

При успешном поиске finger.fingerID содержит номер совпавшей записи, а finger.confidence — оценку достоверности. Решение о совпадении датчик и так принимает по уровню безопасности; оценка лишь показывает, насколько совпадение надёжно. С хорошо зарегистрированным пальцем оценка обычно лежит в диапазоне от нескольких десятков до нескольких сотен. Для более строгого замка можно поднять порог через setSecurityLevel(4) или setSecurityLevel(5) либо добавить в коде свой нижний предел (например, отклонять всё, что ниже 50). Чем выше порог, тем меньше шанс впустить чужого, но тем больше шанс отказать своему; найди баланс, проверяя на своих пальцах.

Код возвратаСообщение в мониторе портаЗначение и решение
FINGERPRINT_OK (0x00)Image taken / Stored! (снимок получен / сохранено)Операция выполнена успешно.
FINGERPRINT_NOFINGER (0x02)No finger detected (палец не обнаружен)На стекле нет пальца; продолжай ждать в цикле.
FINGERPRINT_PACKETRECIEVEERR (0x01)Communication error (ошибка связи)Ответный пакет не получен; проверь подключение, скорость и питание.
FINGERPRINT_IMAGEFAIL (0x03)Imaging error (ошибка съёмки)Не удалось получить изображение; приложи палец ещё раз.
FINGERPRINT_IMAGEMESS (0x06)Image too messy (изображение слишком нечёткое)Размытое изображение; протри стекло, палец может быть слишком влажным или слишком сухим.
FINGERPRINT_FEATUREFAIL (0x07)Could not find fingerprint features (не найдены признаки отпечатка)Недостаточно деталей; приложи палец по центру и слегка прижми.
FINGERPRINT_NOTFOUND (0x09)Did not find a match (совпадение не найдено)Подходящей записи нет; палец не зарегистрирован или зарегистрирован плохо.
FINGERPRINT_ENROLLMISMATCH (0x0A)Fingerprints did not match (отпечатки не совпали)Два снимка при регистрации не совпали; повтори процедуру.
FINGERPRINT_BADLOCATION (0x0B)Could not store in that location (не удалось сохранить в эту ячейку)ID за пределами ёмкости; узнай предел через getParameters().
FINGERPRINT_FLASHERR (0x18)Error writing to flash (ошибка записи во флеш-память)Не удалось записать в память датчика; проверь питание и подключение.

Дверной замок по отпечатку пальца с реле и соленоидом

Теперь соберём всё вместе и сделаем дверной замок, который открывается на 3 секунды для разрешённого пальца, трижды пищит при неизвестном и блокирует систему на 30 секунд после 5 неудачных попыток подряд. В качестве замка используем соленоидный замок на 12 V. Соленоид потребляет 0,5–1 A, поэтому его ни в коем случае нельзя подключать напрямую к пину Arduino; между ними нужен модуль реле или MOSFET с логическим уровнем управления. Подключение: VCC и GND модуля реле — к 5V и GND Arduino, его пин IN — к D8, активный зуммер — к D9, плюс адаптера 12 V — к клемме COM реле, клемма NO реле — к плюсу соленоида, а минус соленоида — к минусу адаптера.

Соленоид — это катушка, и в момент отключения тока она выдаёт высокое обратное напряжение. Поэтому параллельно соленоиду в обратном направлении подключи диод 1N4007; конец диода с полоской идёт к плюсу. Если вместо реле используется MOSFET, выбери модель с логическим уровнем управления, например IRLZ44N, и соедини минус источника 12 V с GND Arduino. Подробности — в статье Управление большими токами с помощью MOSFET, а порядок выводов MOSFET можно посмотреть в утилите распиновки транзисторов.

C++ (Arduino IDE)
1#include <Adafruit_Fingerprint.h>
2#include <SoftwareSerial.h>
3
4SoftwareSerial fpSerial(2, 3);            // D2 = RX, D3 = TX
5Adafruit_Fingerprint finger(&fpSerial);
6
7const int RELAY_PIN = 8;                  // röle modülü IN / relay module IN
8const int BUZZER_PIN = 9;                 // aktif buzzer / active buzzer
9const uint8_t RELAY_ON = LOW;             // çoğu röle modülü LOW ile çeker / most relay modules switch on LOW
10const uint8_t RELAY_OFF = HIGH;
11const uint16_t MIN_CONFIDENCE = 50;       // ek güven eşiği / extra confidence threshold
12const unsigned long OPEN_MS = 3000;       // kilidin açık kalma süresi / unlock time
13
14uint8_t failCount = 0;
15
16void setup() {
17  digitalWrite(RELAY_PIN, RELAY_OFF);     // açılışta kilitli kalsın / stay locked at power-up
18  pinMode(RELAY_PIN, OUTPUT);
19  pinMode(BUZZER_PIN, OUTPUT);
20  Serial.begin(9600);
21  finger.begin(57600);
22  if (!finger.verifyPassword()) {
23    Serial.println(F("Did not find fingerprint sensor :("));
24    while (1) delay(1);
25  }
26  finger.getParameters();                 // fingerSearch için kapasite / capacity for fingerSearch
27}
28
29// Eşleşen ID; parmak yoksa -1, tanınmadıysa -2 / matching ID; -1 no finger, -2 not recognised
30int readFinger() {
31  if (finger.getImage() != FINGERPRINT_OK) return -1;
32  if (finger.image2Tz(1) != FINGERPRINT_OK) return -2;
33  if (finger.fingerSearch(1) != FINGERPRINT_OK) return -2;
34  if (finger.confidence < MIN_CONFIDENCE) return -2;
35  return finger.fingerID;
36}
37
38void beep(int count, int ms) {
39  for (int i = 0; i < count; i++) {
40    digitalWrite(BUZZER_PIN, HIGH);
41    delay(ms);
42    digitalWrite(BUZZER_PIN, LOW);
43    delay(ms);
44  }
45}
46
47void loop() {
48  int id = readFinger();
49  if (id >= 0) {
50    Serial.print(F("Hos geldin / welcome, ID #"));
51    Serial.print(id);
52    Serial.print(F(", guven / confidence "));
53    Serial.println(finger.confidence);
54    failCount = 0;
55    beep(1, 100);
56    digitalWrite(RELAY_PIN, RELAY_ON);    // kilidi aç / unlock
57    delay(OPEN_MS);
58    digitalWrite(RELAY_PIN, RELAY_OFF);   // yeniden kilitle / lock again
59  } else if (id == -2) {
60    failCount++;
61    Serial.println(F("Yetkisiz / not authorised"));
62    beep(3, 80);
63    if (failCount >= 5) {                 // 5 hatada 30 sn bekle / 30 s lockout after 5 failures
64      Serial.println(F("30 sn kilitli / locked for 30 s"));
65      delay(30000);
66      failCount = 0;
67    }
68    delay(1000);
69  }
70  delay(50);
71}
Этот проект отлично подходит для учёбы и хобби, но это ещё не полноценная система безопасности. Оптические датчики можно обмануть хорошо сделанным муляжом отпечатка, а любой, кто доберётся до проводов, может замкнуть реле напрямую. На настоящей двери держи электронику с внутренней стороны, оставь механический ключ или другой способ открыть дверь и продумай, что будет с замком при отключении электричества: коробчатые соленоидные замки без питания обычно остаются закрытыми, а электромагнитные открываются. Не держи соленоид под напряжением долго: катушка нагревается и может выйти из строя.

Датчик отпечатков пальцев с ESP32: подключение к Serial2

У ESP32 три аппаратных последовательных порта, поэтому SoftwareSerial не нужен: датчик подключается к UART2 (Serial2). ESP32 работает от 3,3 V, поэтому её уровни сигналов в точности совпадают с уровнями AS608, и делитель напряжения не нужен. Следить нужно только за пинами: в актуальном ядре Arduino-ESP32 (3.x) пины Serial2 по умолчанию уже не GPIO 16/17, как в старых руководствах, а GPIO 4 (RX) и GPIO 25 (TX). Поэтому пины нужно явно передать в Serial2.begin(); функция begin() библиотеки сохраняет заданные ранее пины. Карту пинов своей платы можно посмотреть в утилите распиновки.

C++ (Arduino IDE)
1#include <Adafruit_Fingerprint.h>
2
3#define FP_RX 16                          // ESP32 RX2 <- sensör TX / sensor TX
4#define FP_TX 17                          // ESP32 TX2 -> sensör RX / sensor RX
5const int RELAY_PIN = 23;                 // röle modülü IN / relay module IN
6
7Adafruit_Fingerprint finger(&Serial2);
8
9void setup() {
10  Serial.begin(115200);
11  pinMode(RELAY_PIN, OUTPUT);
12  digitalWrite(RELAY_PIN, HIGH);          // LOW tetiklemeli röle kapalı / active-LOW relay off
13  Serial2.begin(57600, SERIAL_8N1, FP_RX, FP_TX);   // pinleri açıkça ver / set the pins explicitly
14  finger.begin(57600);                    // önceki pinleri korur / keeps the pins set above
15  if (!finger.verifyPassword()) {
16    Serial.println("Did not find fingerprint sensor :(");
17    while (true) delay(10);
18  }
19  finger.getParameters();
20  finger.getTemplateCount();
21  Serial.printf("Kapasite / capacity: %u, kayitli / stored: %u\n", finger.capacity, finger.templateCount);
22}
23
24void loop() {
25  if (finger.getImage() == FINGERPRINT_OK && finger.image2Tz(1) == FINGERPRINT_OK) {
26    if (finger.fingerSearch(1) == FINGERPRINT_OK) {
27      Serial.printf("ID #%u, guven / confidence %u\n", finger.fingerID, finger.confidence);
28      digitalWrite(RELAY_PIN, LOW);       // kilidi aç / unlock
29      delay(3000);
30      digitalWrite(RELAY_PIN, HIGH);      // yeniden kilitle / lock again
31    } else {
32      Serial.println("Did not find a match");
33      delay(1000);
34    }
35  }
36  delay(50);
37}

На платах с модулем ESP32-WROVER пины GPIO 16 и 17 подключены к PSRAM; на такой плате замени FP_RX и FP_TX, например, на 25 и 26. У ESP32-C3 всего два UART, поэтому Serial2 нет; тот же код работает с Serial1 и любыми двумя удобными пинами. Благодаря Wi-Fi можно записывать каждый вход с отметкой времени на сервер или при неизвестном пальце отправлять уведомление на телефон через Telegram-бота.

Датчик отпечатков пальцев с Raspberry Pi Pico и MicroPython

Официальной версии библиотеки Adafruit для MicroPython нет, но протокол датчика настолько простой, что общаться с ним можно напрямую в несколько строк. Каждый пакет начинается со стартового кода EF 01, за ним идут 4-байтовый адрес (по умолчанию FF FF FF FF), тип пакета (01 — команда, 07 — ответ), 2-байтовая длина, команда с параметрами и в конце 2-байтовая контрольная сумма — сумма байтов типа, длины и данных. Первый байт данных в ответе — код подтверждения: 00 — успех, 02 — нет пальца, 09 — нет совпадения. Код ниже проверяет связь с датчиком, читает ёмкость и распознаёт приложенный палец, выдавая ID и оценку достоверности. Pico работает от 3,3 V, поэтому AS608 можно подключить прямо к пину 3V3(OUT); если Pico пока в новинку, хорошее начало — статья Что такое Raspberry Pi Pico?

MicroPython
1from machine import UART, Pin
2import time
3
4# GP0 = UART0 TX -> sensör RX, GP1 = UART0 RX <- sensör TX / sensor RX, sensor TX
5uart = UART(0, baudrate=57600, tx=Pin(0), rx=Pin(1), timeout=2000, timeout_char=100)
6HEADER = b'\xEF\x01\xFF\xFF\xFF\xFF'          # başlangıç kodu + adres / start code + address
7
8def command(*data):
9    while uart.any():                          # eski baytları at / drop stale bytes
10        uart.read()
11    length = len(data) + 2                     # veri + 2 bayt sağlama / data + 2-byte checksum
12    body = bytes([0x01, length >> 8, length & 0xFF]) + bytes(data)   # 0x01 = komut paketi / command packet
13    s = sum(body)
14    uart.write(HEADER + body + bytes([(s >> 8) & 0xFF, s & 0xFF]))
15    head = uart.read(9)                        # başlık + tip + uzunluk / header + type + length
16    if not head or len(head) < 9 or head[0] != 0xEF:
17        return None
18    n = (head[7] << 8) | head[8]
19    rest = uart.read(n)
20    if not rest or len(rest) < n:
21        return None
22    return rest[:-2]                           # sağlama hariç veri / data without checksum
23
24def ok(r):
25    return r is not None and r[0] == 0x00      # 0x00 = başarılı / success
26
27time.sleep(1)                                  # sensörün açılmasını bekle / let the sensor boot up
28if not ok(command(0x13, 0, 0, 0, 0)):          # VfyPwd: şifre 0 / password 0
29    print("Did not find fingerprint sensor")
30    while True:
31        time.sleep(1)
32
33p = command(0x0F)                              # ReadSysPara: sistem parametreleri / system parameters
34capacity = (p[5] << 8) | p[6] if ok(p) else 162
35print("Kapasite / capacity:", capacity)
36
37def identify():
38    if not ok(command(0x01)):                  # GenImg: parmak yoksa 0x02 / 0x02 = no finger
39        return None
40    if not ok(command(0x02, 1)):               # Img2Tz: CharBuffer1'e çevir / convert into CharBuffer1
41        return (-1, 0)
42    r = command(0x04, 1, 0, 0, capacity >> 8, capacity & 0xFF)   # Search: tüm kayıtlar / all records
43    if not ok(r):
44        return (-1, 0)                         # 0x09 = eşleşme yok / no match
45    return ((r[1] << 8) | r[2], (r[3] << 8) | r[4])   # (ID, güven / confidence)
46
47while True:
48    res = identify()
49    if res:
50        fid, score = res
51        if fid >= 0:
52            print("ID", fid, "guven / confidence", score)
53        else:
54            print("Eslesme yok / no match")
55        time.sleep(1)
56    time.sleep_ms(100)

Ошибка «Did not find fingerprint sensor» и другие частые проблемы

Это сообщение означает, что библиотека не получила от датчика корректного ответа на команду verifyPassword(); оно не значит, что датчик сломан. В подавляющем большинстве случаев дело в подключении, питании или неверной скорости. Пройди по таблице ниже сверху вниз:

СимптомВероятная причинаРешение
Did not find fingerprint sensor :( (датчик не найден)TX и RX соединены напрямую, а не крест-накрестTX датчика идёт на RX Arduino (D2), а RX — на TX (D3). Если поменять два провода данных местами, ничего не сгорит, так что попробуй.
Did not find fingerprint sensor :( (датчик не найден)Подключение по цветам проводовПереподключи по надписям пинов на плате или по схеме продавца; проверь GND мультиметром.
Did not find fingerprint sensor :( (датчик не найден)Неправильное или недостаточное питаниеПодай на AS608 3,3 V, а на R307 5 V; если пина 3.3V у Uno не хватает, используй внешний стабилизатор и соедини земли.
Did not find fingerprint sensor :( (датчик не найден)Датчик работает на другой скоростиЗапусти перебор скоростей из первого тестового скетча и подставь найденное значение в finger.begin().
Did not find fingerprint sensor :( (датчик не найден)Пароль датчика изменёнПередай пароль в конструктор: Adafruit_Fingerprint finger(&fpSerial, 0x12345678);
Датчик не находится на Mega или LeonardoSoftwareSerial может принимать данные не на всех пинахИспользуй Serial1: на Mega RX1 19, TX1 18; на Leonardo RX 0, TX 1.
Датчик не находится на ESP32Другие пины Serial2 по умолчанию или конфликт с PSRAMЗадай пины явно: Serial2.begin(57600, SERIAL_8N1, RX, TX); на WROVER не используй 16/17.
Частая ошибка «Communication error» (ошибка связи)Разболтанный разъём, длинные или тонкие проводаДелай провода короткими, вместо макетной платы используй пайку и добавь конденсатор 100 µF по питанию.
Зарегистрированный палец часто отклоняетсяГрязное стекло, сухой или влажный палец, регистрация только под одним угломПротри стекло мягкой тканью, зарегистрируй тот же палец под двумя ID и при необходимости снизь уровень безопасности до 2.
Датчик греется, светодиод не загораетсяПерепутана полярность питания или на AS608 подано 5 VНемедленно отключи питание и исправь подключение; датчик, возможно, уже повреждён.
Быстрый способ сузить круг поиска — подключить датчик к USB-TTL-преобразователю и проверить его тестовой программой для Windows, например SFGDemo: если датчик там виден, проблема в подключении или коде на стороне Arduino. И помни, что скорость монитора порта (9600) и скорость датчика (57600) — это разные вещи; не путай их.

Сканер отпечатков Waveshare с UART: короткая заметка

Модуль сканера отпечатков пальцев Waveshare с UART и плата контроллера
Waveshare UART Fingerprint Reader: оптический датчик подключается шлейфом к отдельной плате контроллера с процессором STM32F205; на плате есть пины VCC, GND, TXD, RXD, BL и RST.

Хотя внешне он похож, сканер отпечатков Waveshare с UART работает по другому протоколу, чем AS608 и R307: команды длиной 8 байт, начинаются и заканчиваются байтом 0xF5, а скорость по умолчанию — 19200 бод. Поэтому с библиотекой Adafruit Fingerprint он не работает; вместо неё используются таблица команд и примеры кода из руководства пользователя Waveshare. При регистрации палец сканируется три раза, каждому пользователю можно назначить уровень доступа от 1 до 3, а сравнение 1:N выполняется одной командой. Плату можно питать от 3,3 V или 5 V; TXD подключается к RX микроконтроллера, а RXD — к его TX. Если нужно много готовых библиотек и примеров, выбирай AS608 или R307; если написание своего кода протокола не пугает, Waveshare — хороший вариант.

Идеи проектов с датчиком отпечатков пальцев

  • Ящик или сейф по отпечатку: небольшой сейф, который открывается сервоприводом или соленоидом и поднимает тревогу при попытке чужого доступа. О фиксаторе на сервоприводе — в статье Что такое сервопривод?
  • Двухэтапная дверь: более защищённый вход, который сначала запрашивает отпечаток, а затем PIN-код на матричной клавиатуре.
  • Карта или палец: добавь к тому же замку считыватель RFID RC522, чтобы владельцы карт входили по карте, а остальные — по отпечатку.
  • Система учёта посещаемости: сопоставь каждый ID с именем для школы или кружка и записывай время входа.
  • Замок с дисплеем: выводи приветствие и имя человека на OLED-дисплей.
  • Вместе с домашней сигнализацией: сигнализация на Arduino, которая ставится на охрану и снимается с неё по отпечатку пальца.

Несколько проводов и подходящая библиотека — и датчик отпечатков пальцев добавляет в твой проект настоящий уровень проверки личности: сначала протестируй датчик, аккуратно зарегистрируй пальцы, а потом собери замок с реле и соленоидом. В приложении BlueGrays есть проекты по безопасности — «Умный электронный сейф», «RFID-аутентификация», «Дверной замок с RFID на ESP32» и «Кодовый замок с клавиатурой» — с пошаговыми схемами подключения и кодом; это готовая основа, к которой можно добавить датчик отпечатков.

Частые вопросы

Сколько отпечатков может хранить датчик отпечатков пальцев?

Зависит от модели: платы AS608 обычно хранят 300 (некоторые 162), R307 — 1000, а FPM10A и ZFM-20 — 162. Чтобы узнать ёмкость своего датчика, вызови getParameters() и выведи finger.capacity в монитор порта. Учти, что один палец, зарегистрированный под двумя ID, занимает две ячейки.

Датчик отпечатков пальцев работает от 5 V или от 3,3 V?

Большинству плат AS608 нужно 3,3 V, а R307 работает от 4,2–6 V, обычно от 5 V. Не подавай питание, пока не проверишь надпись на датчике и характеристики от продавца. Если TX-выход Arduino на 5 V подключается к RX датчика на 3,3 V, безопаснее всего использовать делитель напряжения.

Где хранятся отпечатки — в Arduino? И стираются ли они при отключении питания?

Нет, шаблоны хранятся во встроенной флеш-памяти датчика и при отключении питания не стираются. Даже если заменить Arduino или загрузить новый код, записи останутся в датчике. На стороне Arduino нужно только помнить, какой ID кому принадлежит; при желании это можно сохранить в EEPROM.

Как исправить ошибку «Did not find fingerprint sensor»?

Сначала убедись, что TX и RX соединены крест-накрест: TX датчика идёт на пин RX Arduino (D2 на Uno). Затем проверь, что питание нужного напряжения и с достаточным током, а земли общие. Если датчик всё равно не находится, возможно, он работает на другой скорости или с паролем; запусти тестовый скетч, который перебирает несколько скоростей.

Чем AS608 отличается от R307?

Оба — оптические датчики с одним и тем же набором команд, и с библиотекой Adafruit Fingerprint они работают на одном и том же коде. Главные отличия — питание и ёмкость: платы AS608 обычно работают от 3,3 V и хранят около 300 записей, а R307 работает от 5 V и вмещает 1000. Перед подключением сверь порядок пинов по маркировке своей модели.

Как удалить сохранённый отпечаток?

Для удаления одной записи используй finger.deleteModel(id), а для удаления всех — finger.emptyDatabase(). Примеры delete и emptyDatabase из библиотеки делают это через монитор порта. Позже под удалённым ID можно зарегистрировать новый отпечаток.

Все проекты
Умный электронный сейф
#92Продвинутый
Premium

Умный электронный сейф

Маленький сейф для ценных вещей, который открывается кодом. Ты вводишь на клавиатуре свой четырёхзначный код; если он верный, сервопривод открывает замок, загорается зелёный свет, а экран показывает с

4.7(42)
63
Дверной замок с RFID на ESP32 (RC522 + сервопривод + OLED + зуммер + светодиод)
#137Продвинутый
Premium

Дверной замок с RFID на ESP32 (RC522 + сервопривод + OLED + зуммер + светодиод)

Собираем умный дверной замок на ESP32, модуле RFID RC522, сервоприводе SG90, OLED-дисплее SSD1306, активном зуммере и 2 светодиодах. При поднесении карты её UID сравнивается со списком разрешённых карт в коде: если доступ разрешён, сервопривод поворачивается и открывает дверь (зелёный светодиод + 2 коротких сигнала), а через 5 секунд дверь снова запирается сама. При чужой карте загорается красный светодиод, звучат 3 быстрых сигнала, а прочитанный UID показывается на экране.

4.8(9)
15
Аутентификация по RFID
#54Средний
Premium

Аутентификация по RFID

Совсем как вход по карте у двери подъезда: ты подносишь карту к считывателю RFID, а Arduino сравнивает её номер с сохранённым. Правильная карта зажигает зелёный светодиод на три секунды, чужая — красн

4.8(64)
83
Чтение значения RFID
#53Новичок
Premium

Чтение значения RFID

В брелоке от подъезда или карте доступа спрятан секретный идентификационный номер, и этот проект его читает. Поднеси карту к считывателю RFID, и Arduino выведет номер карты на экран компьютера. Первый

4.7(47)
61
Кодовый замок с клавиатурой 4x4 и LCD
#64Продвинутый
Premium

Кодовый замок с клавиатурой 4x4 и LCD

Маленький электронный дверной замок, который не пускает тех, кто не знает кода. Ты нажимаешь клавишу решётки и вводишь код на клавиатуре; если он верный, экран сообщает, что доступ разрешён, загораетс

4.8(59)
75
Считыватель карт RFID RC522 на ESP32 (с LCD)
#123Средний

Считыватель карт RFID RC522 на ESP32 (с LCD)

В этом проекте модуль RFID RC522 на базе MFRC522 подключается к ESP32 по SPI и читает UID карты или метки. Это основа для дверных замков, клубных систем и контроля доступа. Прочитанный UID выводится на LCD-экран; эта версия не сравнивает его со списком разрешённых карт. ВНИМАНИЕ: RC522 работает только от 3.3V; подача 5V сожжёт модуль!

4.8(21)
39
Датчик двери на герконе
#38Новичок
Premium

Датчик двери на герконе

Узнай, открыта дверь или закрыта, просто взглянув на огонёк. Маленький магнит крепится на дверь, а чувствительный к магниту контакт — на раму; когда дверь закрыта, они рядом, и горит зелёный светодиод

4.7(34)
44
Сигнализация движения на ESP32 (PIR + зуммер + светодиод + Telegram)
#145Продвинутый
Premium

Сигнализация движения на ESP32 (PIR + зуммер + светодиод + Telegram)

Умная охранная сигнализация, которая при обнаружении движения PIR-датчиком включает зуммер и светодиод и одновременно сразу отправляет владельцу уведомление в Telegram. В ней есть 30-секундная пауза, ограничивающая частоту повторных тревог; этот механизм не проверяет срабатывания PIR и не устраняет ложные тревоги. Подходит для дома, гаража, склада или мастерской. С ESP32-CAM можно добавить уведомления с фото, а с обычной ESP32 DevKit V1 приходят текстовые.

0.0(0)
9