Загрузка данных


#include <Stepper.h>

// Пины фоторезисторов
#define NORTH_PIN A5
#define WEST_PIN  A4
#define EAST_PIN  A3
#define SOUTH_PIN A2

// Настройки двигателя
const int stepsPerRevolution = 520;
Stepper stepper(stepsPerRevolution, 8, 10, 9, 11);

const int threshold = 100;

// Переменные для позиционирования
int currentStepPosition = 0;  // Текущая позиция в шагах (0 = Север)
bool isCalibrated = false;

struct Direction {
  int stepTarget;  // Целевая позиция в шагах
  String name;
};

void setup() {
  Serial.begin(9600);
  stepper.setSpeed(15);
  
  Serial.println("Поверните двигатель в положение СЕВЕР и нажмите любую клавишу в мониторе порта...");
  
  // Ждём калибровки через Serial Monitor
  while (!isCalibrated) {
    if (Serial.available()) {
      Serial.read();
      currentStepPosition = 0;
      isCalibrated = true;
      Serial.println("Калибровка завершена! Север задан.");
      delay(1000);
    }
  }
}

void loop() {
  // Считываем фоторезисторы
  int northValue = analogRead(NORTH_PIN);
  int westValue  = analogRead(WEST_PIN);
  int eastValue  = analogRead(EAST_PIN);
  int southValue = analogRead(SOUTH_PIN);
  
  // Вывод для отладки
  Serial.print("N:");
  Serial.print(northValue);
  Serial.print(" E:");
  Serial.print(eastValue);
  Serial.print(" S:");
  Serial.print(southValue);
  Serial.print(" W:");
  Serial.println(westValue);
  
  // Определяем активные стороны (исправлено: юг и север поменяны местами в логике)
  bool northActive = northValue > threshold;
  bool eastActive  = eastValue  > threshold;
  bool southActive = southValue > threshold;
  bool westActive  = westValue  > threshold;
  
  Direction target = getTargetDirection(northActive, eastActive, southActive, westActive);
  
  if (target.stepTarget != -1) {
    Serial.print("Целевое направление: ");
    Serial.println(target.name);
    rotateToPosition(target.stepTarget);
  }
  
  delay(200);
}

Direction getTargetDirection(bool north, bool east, bool south, bool west) {
  // Исправлено: север и юг поменяны местами
  if (south && !east && !north && !west) return {0, "Север"};
  if (south && east && !north && !west)  return {45, "Северо-Восток"};
  if (!south && east && !north && !west) return {90, "Восток"};
  if (!south && east && north && !west)  return {135, "Юго-Восток"};
  if (!south && !east && north && !west) return {180, "Юг"};
  if (!south && !east && north && west)  return {225, "Юго-Запад"};
  if (!south && !east && !north && west) return {270, "Запад"};
  if (south && !east && !north && west)  return {315, "Северо-Запад"};
  
  return {-1, "Нет сигнала"};
}

void rotateToPosition(int targetStep) {
  // Вычисляем кратчайший путь
  int delta = targetStep - currentStepPosition;
  
  // Нормализуем дельту в диапазон -stepsPerRevolution/2 .. stepsPerRevolution/2
  if (delta > stepsPerRevolution / 2) delta -= stepsPerRevolution;
  if (delta < -stepsPerRevolution / 2) delta += stepsPerRevolution;
  
  if (delta == 0) {
    Serial.println("Уже на месте");
    return;
  }
  
  Serial.print("Поворот на ");
  Serial.print(delta);
  Serial.print(" шагов (");
  Serial.print((delta * 360) / stepsPerRevolution);
  Serial.println(" градусов)");
  
  // Поворачиваем
  stepper.step(delta);
  
  // Обновляем текущую позицию с учётом полного оборота
  currentStepPosition = (currentStepPosition + delta) % stepsPerRevolution;
  if (currentStepPosition < 0) currentStepPosition += stepsPerRevolution;
  
  Serial.print("Новая позиция: ");
  Serial.print(currentStepPosition);
  Serial.print(" шагов (");
  Serial.print((currentStepPosition * 360) / stepsPerRevolution);
  Serial.println(" градусов)");
  
  delay(300);
}