Энкодер

elisejkistanov
Offline
Зарегистрирован: 10.07.2021

пытаюсь повторить проект, но проблемы энкодером E6B2CWZ6C OMRON 1800 это открытый коллектор.
на Megа 2560 с этим кодом энкодер работает без резисторов
 

**************************************

 

b707
Offline
Зарегистрирован: 26.05.2017

Вы в своем уме? Вывали в конфу кучу мусора. Вставьте код правильно

elisejkistanov
Offline
Зарегистрирован: 10.07.2021

первый код где работает энкодер

#define encoder0PinA 2 //keep this on and interrupt pin
#define encoder0PinB 3 //keep this on and interrupt pin

volatile long encoder0Pos;

void setup () {
  Serial.begin(9600);

  // then the encoder inputs
  pinMode(encoder0PinA, INPUT);
  pinMode(encoder0PinB, INPUT);
  // enable pullup as we are using an open collector encoder
  digitalWrite(encoder0PinA, HIGH);
  digitalWrite(encoder0PinB, HIGH);

  // encoder pin on interrupt 0 (pin 2)
  attachInterrupt(0, encoderPinChangeA, CHANGE);
  // encoder pin on interrupt 1 (pin 3)
  attachInterrupt(1, encoderPinChangeB, CHANGE);
  encoder0Pos = 0; //reseet the encoder position to 0
}

void loop() {
  //do stuff dependent on encoder position here
  //such as move a stepper motor to match encoder position
  //if you want to make it 1:1 ensure the encoder res matches the motor res by dividing/multiplying
  Serial.println(encoder0Pos);
  delay(100);
}

void encoderPinChangeA() {
// look for a low-to-high on channel A
  if (digitalRead(encoder0PinA) == HIGH) {
    // check channel B to see which way encoder is turning
    if (digitalRead(encoder0PinB) == LOW) {
      encoder0Pos = encoder0Pos + 1;        // CW
    }
    else {
      encoder0Pos = encoder0Pos - 1;        // CCW
    }
  }
  else  // must be a high-to-low edge on channel A                                    
  {
    // check channel B to see which way encoder is turning
    if (digitalRead(encoder0PinB) == HIGH) {
      encoder0Pos = encoder0Pos + 1;          // CW
    }
    else {
      encoder0Pos = encoder0Pos - 1;          // CCW
    }
  }
}

void encoderPinChangeB() {
  // look for a low-to-high on channel B
  if (digitalRead(encoder0PinB) == HIGH) {
  // check channel A to see which way encoder is turning
    if (digitalRead(encoder0PinA) == HIGH) {
      encoder0Pos = encoder0Pos + 1;        // CW
    }
    else {
      encoder0Pos = encoder0Pos - 1;        // CCW
    }
  }
  // Look for a high-to-low on channel B
  else {
    // check channel B to see which way encoder is turning
    if (digitalRead(encoder0PinA) == LOW) {
      encoder0Pos = encoder0Pos + 1;          // CW
    }
    else {
      encoder0Pos = encoder0Pos - 1;          // CCW
    }
  }
}

 

elisejkistanov
Offline
Зарегистрирован: 10.07.2021

а вот код проекта нет) помогите хрен знает куда копать

перепробовал разные резисторы на выход от 500 ом до 3к не заводится земля Общая питание 5 вольт
первый код работает а нужный не могу завести
электроная гитара на токарный станок

 #include <avr / pgmspace.h>

// ***** ЖК-дисплей *****
#include <LiquidCrystal.h>
ЖК-дисплей LiquidCrystal (8, 9, 4, 5, 6, 7);
char LCD_Row_1 [17];
char LCD_Row_2 [17];

// ***** Шаговый двигатель *****
// # определить Motor_X_Step_Per_Revolution 2400
// # определить Motor_Y_Step_Per_Revolution 2400
#define MotorPort PORTL // под моторы выделен весь порт "L",
#define MotorInitialization() DDRL=B11111111 // сконфигурирован как выход
#define Motor_X_SetPulse () MotorPort & = ~ (1 << 0) // Pin49 1
#define Motor_X_RemovePulse () MotorPort | = (1 << 0) // Pin49 0
#define Motor_Y_SetPulse () MotorPort & = ~ (1 << 1) // Pin48 1
#define Motor_Y_RemovePulse () MotorPort | = (1 << 1) // Pin48 0
#define Motor_X_Forward () MotorPort & = ~ (1 << 2) // Pin47 0
#define Motor_X_Reverse () MotorPort | = (1 << 2) // Pin47 1
#define Motor_Y_Forward () MotorPort | = (1 << 3) // Pin46 0
#define Motor_Y_Reverse () MotorPort & = ~ (1 << 3) // Pin46 1
#define Motor_X_Enable () MotorPort | = (1 << 4) // Вывод 45 0
#define Motor_X_Disable () MotorPort & = ~ (1 << 4) // Pin45 1
#define Motor_Y_Enable () MotorPort | = (1 << 5) // Pin44 0
#define Motor_Y_Disable () MotorPort & = ~ (1 << 5) // Pin44 1
boolean Step_On_flag=false; // Флаг разрешаем/запрещаем счет до "шагать"
boolean Mode_On_flag=false; // Флаг On/Off режим

// ***** Тахо *****
#define TahoPort PortL
#define TahoSetPulse () TahoPort | = (1 << 6) // Pin43 1
#define TahoRemovePulse () TahoPort & = ~ (1 << 6) // Pin43 0

// ***** Кодировщик *****
#define Enc_Line_per_Revolution 1800 // Кол-во линий энкодера
#define Enc_Line Enc_Line_per_Revolution*2 // Рабочее кол-во тиков
#define EncoderPort PORTD
#define EncoderInitialization() DDRD=B00000000 // Под энкодер выделен весь порт "D", сконфигурирован на вход
#define Enc_Read () (PIND & B00000010)
volatile int Enc_Pos=0; // Счетчик положения энкодера
volatile byte Ks_Count=0; // Счетчик для "Подача", "Резьба" целая часть
volatile int Km_Count=0; // Счетчик для "Подача", "Резьба" дробная часть
byte Ks_Divisor=0; // Делитель для "Подача", "Резьба" целая часть
int Km_Divisor=0; // Делитель для "Подача", "Резьба" дробная часть
int Enc_Pos_tmp = 0;
long Spindle_Angle = 0;

// ***** Датчик *****
#define SensorPort PORTD
#define Датчик PIND
#define Sensor_Left_Mask B00001000
#define Sensor_Right_Mask B00000100
char Sensor_Mask = B00000000;

enum Pressed_Key
{
Key_None,
Key_Right,
Key_Up,
Key_Down,
Key_Left,
Key_Select
};
байт Pressed_Key = Key_None;
boolean key_flag=false; // флаг нажатой/отжатой кнопки

// ***** Режим *****
enum Mode
{
Mode_Thread_Left = 1,
Mode_Feed_Left,
Mode_Divider,
Mode_Feed_Right,
Mode_Thread_Right
};
байтовый режим = Mode_Divider;

// ***** Каналы *****
// Enc_Line / (Step_Per_Revolution / Feed_Screw * Feed_mm)
#define Total_Feeds 12 // Кол-во подач
typedef struct
{
byte s_Divisor; // Делитель для "Подача" целая часть
char Text [7];
}
FEED_INFO;
FEED_INFO Feed_Info [Total_Feeds] =
{
{180, "0,02мм"},
{90, "0,04мм"},
{60, "0,06мм"},
{45, "0,08мм"},
{36, "0,10 мм"},
{30, "0,12 мм"},
{26, "0,14мм"},
{23, "0,16мм"},
{20, "0,18мм"},
{18, "0,20 мм"},
{16, "0,22мм"},
{15, "0,24мм"},
};
byte Feed_Step = 3; // выборка из массива по умолчанию (0.08mm)

// ***** Потоки *****
// Enc_Line / (Step_Per_Revolution / Feed_Screw * Thread_mm)
#define Total_Threads 40 // Кол-во резьб
typedef struct
{
byte s_Divisor; // Делитель для "Резьба" целая часть
int m_Divisor; // Делитель для "Резьба" дробная часть
char Text [7];
}
THREAD_INFO;
THREAD_INFO Thread_Info [Total_Threads] =
{
{18, 0000, "0,20мм"},
{14, 4000, "0,25мм"},
{12, 0000, "0,30мм"},
{10, 2857, "0,35мм"},
{9, 0000, "0,40мм"},
{7, 2000, "0,50мм"},
{6, 0000, "0.60мм"},
{5, 1429, "0,70мм"},
{4,8000, "0,75мм"},
{4, 5000, "0,80мм"},
{3, 6000, "1,00мм"},
{2, 8800, "1,25мм"},
{2, 4000, "1,50мм"},
{2, 0571, "1,75мм"},
{1, 8000, "2,00мм"},
{1, 4400, "2,50мм"},
{1, 2000, "3,00мм"},
{11, 3386, "80tpi"},
{10, 2047, «72тпи»},
{9, 0707, "64tpi"},
{8, 5039, "60tpi"},
{7, 9370, "56tpi"},
{6, 8031, "48tpi"},
{6,2362, "44тпи"},
{5, 6693, "40tpi"},
{5, 1024, "36tpi"},
{4, 5354, "32tpi"},
{3,9685, «28tpi»},
{3,8268, "27тпи"},
{3, 6850, "26tpi"},
{3, 4016, "24tpi"},
{3, 1181, "22тпи"},
{2,8346, «20tpi»},
{2, 6929, "19тпи"},
{2, 5512, "18tpi"},
{2, 2677, "16tpi"},
{1, 9843, "14tpi"},
{1, 8425, "13tpi"},
{1, 7008, "12tpi"},
{1, 5591, "11tpi"},
};
byte Thread_Step = 12; // выборка из массива по умолчанию (1.0mm)

// ***** Прерывания *****
#define EnableINT0 () EIMSK | = (1 << INT0)
#define DisableINT0 () EIMSK & = ~ (1 << INT0)
#define Init_INT0_Any () EICRA = B00000001

//*********************************************************
установка void ()
{
TIMSK0=0; // !Отключаем таймер! (он что-то свое делает в фоновом режиме)

EncoderInitialization ();
PORTD=B00001111; // подтяжка PIN_21, 20, 19, 18

MotorInitialization ();
Init_INT0_Any ();
EnableINT0 ();

lcd.begin (16, 2);
}

//**********************************************************
пустой цикл ()
{
Enc_Pos_tmp = Enc_Pos; // в "void Divider" читаем повторно и сравниваем

if ((Mode == Mode_Divider) ||! Mode_On_flag)
{
Motor_X_Disable ();
// Motor_Y_Disable ();
}
еще
{
Motor_X_Enable ();
// Motor_Y_Enable ();
}

меню();
Датчики ();
}

// ********** Функция обработки событий в главном меню **********
пустое меню ()
{
int ADC_value = analogRead (A0);
если (ADC_value <65) Pressed_Key = Key_Right;
иначе, если (ADC_value <220) Pressed_Key = Key_Up;
иначе, если (ADC_value <390) Pressed_Key = Key_Down;
иначе, если (ADC_value <600) Pressed_Key = Key_Left;
иначе, если (ADC_value <870) Pressed_Key = Key_Select;
иначе Pressed_Key = Key_None;

если (! key_flag)
{
переключатель (Pressed_Key)
{
case Key_Left:
MenuKeyLeftPressed ();
перерыв;
case Key_Right:
MenuKeyRightPressed ();
перерыв;
case Key_Up:
MenuKeyUpPressed ();
перерыв;
case Key_Down:
MenuKeyDownPressed ();
перерыв;
case Key_Select:
MenuKeySelectPressed ();
перерыв;
}
}
если (Pressed_Key == Key_None) key_flag = false;

SelectWorkMode(); // вызов выбранного рабочего режима
}

// ********** Обработчик нажатия кнопки Select **********
void MenuKeySelectPressed ()
{
переключатель (режим)
{
case Mode_Thread_Left:
case Mode_Thread_Right:
case Mode_Feed_Left:
case Mode_Feed_Right:
Step_On_flag = false;
Mode_On_flag = !Mode_On_flag; // переворачиваем значение на противоположное
Ks_Count = 0;
Km_Count = 0;
перерыв;
case Mode_Divider:
Enc_Pos = 0;
перерыв;
}
key_flag = true;
}

// ********** Обработчик нажатия кнопки Up **********
void MenuKeyUpPressed ()
{
переключатель (режим)
{
case Mode_Thread_Left:
case Mode_Thread_Right:
if (Thread_Step <Total_Threads-1)
{
Mode_On_flag = false;
Step_On_flag = false;
Ks_Count = 0;
Km_Count = 0;
Thread_Step ++;
}
перерыв;
case Mode_Feed_Left:
case Mode_Feed_Right:
если (Feed_Step <Total_Feeds-1)
{
Ks_Count = 0;
Feed_Step ++;
}
перерыв;
}
key_flag = true;
}

// ********** Обработчик нажатия кнопки Down **********
void MenuKeyDownPressed ()
{
переключатель (режим)
{
case Mode_Thread_Left:
case Mode_Thread_Right:
если (Thread_Step> 0)
{
Mode_On_flag = false;
Step_On_flag = false;
Ks_Count = 0;
Km_Count = 0;
Thread_Step--;
}
перерыв;
case Mode_Feed_Left:
case Mode_Feed_Right:
если (Feed_Step> 0)
{
Ks_Count = 0;
Feed_Step--;
}
перерыв;
}
key_flag = true;
}

// ********** Обработчик нажатия кнопки Left **********
void MenuKeyLeftPressed ()
{
переключатель (режим)
{
case Mode_Feed_Left:
case Mode_Divider:
case Mode_Feed_Right:
case Mode_Thread_Right:
Mode_On_flag = false;
Step_On_flag = false;
Ks_Count = 0;
Km_Count = 0;
Режим--;
перерыв;
}

key_flag = true;
}

// ********** Обработчик нажатия кнопки Right **********
void MenuKeyRightPressed ()
{
переключатель (режим)
{
case Mode_Thread_Left:
case Mode_Feed_Left:
case Mode_Divider:
case Mode_Feed_Right:
Mode_On_flag = false;
Step_On_flag = false;
Ks_Count = 0;
Km_Count = 0;
Mode ++;
перерыв;
}

key_flag = true;
}

// ********** Выбор режима работы **********
void SelectWorkMode ()
{
переключатель (режим)
{
case Mode_Thread_Left:
Thread_Left ();
перерыв;
case Mode_Feed_Left:
Motor_X_Forward ();
Feed_Left ();
перерыв;
case Mode_Divider:
Разделитель ();
перерыв;
case Mode_Feed_Right:
Motor_X_Reverse ();
Feed_Right ();
перерыв;
case Mode_Thread_Right:
Thread_Right ();
}
}

//***************************************
void Thread_Left ()
{
Sensor_Mask = Sensor_Left_Mask;
Ks_Divisor = Thread_Info [Thread_Step] .s_Divisor;
Km_Divisor = Thread_Info [Thread_Step] .m_Divisor;
snprintf (LCD_Row_1, 17, (Mode_On_flag == true)? "Режим: ВКЛ": "Режим: ВЫКЛ");
snprintf (LCD_Row_2, 17, «Поток <=% s», Thread_Info [Thread_Step] .Text);
Распечатать();
}

void Feed_Left ()
{
Sensor_Mask = Sensor_Left_Mask;
Ks_Divisor = Feed_Info [Feed_Step] .s_Divisor;
snprintf (LCD_Row_1, 17, (Mode_On_flag == true)? "Режим: ВКЛ": "Режим: ВЫКЛ");
snprintf (LCD_Row_2, 17, "Feed <=% s", Feed_Info [Feed_Step] .Text);
Распечатать();
}

недействительный разделитель ()
{
если (Enc_Pos == Enc_Pos_tmp)
{
Spindle_Angle = (Enc_Pos * 360000 / (Enc_Line));
}
snprintf (LCD_Row_1, 17, «Режим: разделитель»);
snprintf (LCD_Row_2, 17, «Угол:% 3ld.% 03ld», Spindle_Angle / 1000, Spindle_Angle% 1000);
Распечатать();
}

void Feed_Right ()
{
Sensor_Mask = Sensor_Right_Mask;
Ks_Divisor = Feed_Info [Feed_Step] .s_Divisor;
snprintf (LCD_Row_1, 17, (Mode_On_flag == true)? "Режим: ВКЛ": "Режим: ВЫКЛ");
snprintf (LCD_Row_2, 17, "Feed =>% s", Feed_Info [Feed_Step] .Text);
Распечатать();
}

void Thread_Right ()
{
Sensor_Mask = Sensor_Right_Mask;
Ks_Divisor = Thread_Info [Thread_Step] .s_Divisor;
Km_Divisor = Thread_Info [Thread_Step] .m_Divisor;
snprintf (LCD_Row_1, 17, (Mode_On_flag == true)? "Режим: ВКЛ": "Режим: ВЫКЛ");
snprintf (LCD_Row_2, 17, «Thread =>% s», Thread_Info [Thread_Step] .Text);
Распечатать();
}

//******************************************************************
void Print ()
{
lcd.setCursor (0, 0);
lcd.print (LCD_Row_1);
lcd.setCursor (0, 1);
lcd.print (LCD_Row_2);
}

//******************************************************************
пустые датчики ()
{
if (! (Датчик и маска_сенсора))
{
Mode_On_flag = false;
}
}

//******************************************************************
ISR (INT0_vect)
{
TahoRemovePulse ();
Motor_X_RemovePulse ();

if (!Enc_Read()) // Вращение шпинделя вправо
{
Enc_Pos ++;
if (Enc_Pos == Enc_Line) // полный оборот
{
Enc_Pos = 0;
TahoSetPulse(); // при проходе 0 генерим сигнал Taho
Step_On_flag = (Mode_On_flag == true); // проверка режима на ON/OFF, только! после прохода 0 разрешаем счет до к.деления
}

если (Step_On_flag)
{
if (! (Датчик и маска_сенсора))
{
Step_On_flag = false;
возвращаться;
}

if (Mode == Mode_Feed_Left)
{
если (Ks_Count == Ks_Divisor)
{
Motor_X_SetPulse ();
Ks_Count = 0;
}
Ks_Count ++;
}

иначе, если (Mode == Mode_Feed_Right)
{
если (Ks_Count == Ks_Divisor)
{
Motor_X_SetPulse ();
Ks_Count = 0;
}
Ks_Count ++;
}

иначе, если (Mode == Mode_Thread_Left)
{
если (Ks_Count> Ks_Divisor)
{
Motor_X_Reverse ();
Motor_X_SetPulse ();
Km_Count = Km_Count + Km_Divisor;
если (Km_Count> Km_Divisor)
{
Km_Count = Km_Count - 10000;
Ks_Count = 0;
}
еще
{
Ks_Count = 1;
}
}
Ks_Count ++;
}

иначе, если (Mode == Mode_Thread_Right)
{
если (Ks_Count> Ks_Divisor)
{
Motor_X_Forward ();
Motor_X_SetPulse ();
Km_Count = Km_Count + Km_Divisor;
если (Km_Count> Km_Divisor)
{
Km_Count = Km_Count - 10000;
Ks_Count = 0;
}
еще
{
Ks_Count = 1;
}
}
Ks_Count ++;
}
}
}

еще
{ // Вращение шпинделя влево
Enc_Pos--;
если (Enc_Pos <0)
{
Enc_Pos = Enc_Line - 1;
TahoSetPulse ();
Step_On_flag = (Mode_On_flag == true); // проверка режима на ON/OFF, только! после прохода 0 разрешаем счет до к.деления
}

если (Step_On_flag)
{
if (! (Датчик и маска_сенсора))
{
Step_On_flag = false;
возвращаться;
}

if (Mode == Mode_Feed_Left)
{
если (Ks_Count == 0)
{
Motor_X_SetPulse ();
Ks_Count = Ks_Divisor;
}
Ks_Count--;
}

if (Mode == Mode_Feed_Right)
{
если (Ks_Count == 0)
{
Motor_X_SetPulse ();
Ks_Count = Ks_Divisor;
}
Ks_Count--;
}

if (Mode == Mode_Thread_Left)
{
если (Ks_Count == 0)
{
Motor_X_Forward ();
Motor_X_SetPulse ();
Km_Count = Km_Count - Km_Divisor;
если (Km_Count <1)
{
Km_Count = Km_Count + 10000;
Ks_Count = Ks_Divisor + 1;
}
еще
{
Ks_Count = Ks_Divisor;
}
}
Ks_Count--;
}

if (Mode == Mode_Thread_Right)
{
если (Ks_Count == 0)
{
Motor_X_Reverse ();
Motor_X_SetPulse ();
Km_Count = Km_Count - Km_Divisor;
если (Km_Count <1)
{
Km_Count = Km_Count + 10000;
Ks_Count = Ks_Divisor + 1;
}
еще
{
Ks_Count = Ks_Divisor;
}
}
Ks_Count--;
}
}
}
} 

 

inspiritus
Онлайн
Зарегистрирован: 17.12.2012

Вообщетто код надо еще и сворачивать.

код особо и неинтересен, интересно какой именно энкодер и как именно подключен

а код сворачивайте пожалуйста

интересно, как у вас компилируется строка с оператором «если»

rkit
Offline
Зарегистрирован: 23.11.2016

иначе, если (Mode == Mode_Thread_Right)

elisejkistanov
Offline
Зарегистрирован: 10.07.2021

не понял, я нуб . что нужно поменять?

rkit
Offline
Зарегистрирован: 23.11.2016

Для начала нужно перестать быть нубом.