Схема не меняется.
Вот код, надо б получить похожие на рабочие значения: Частоту экструдера (в верхнем правом углу, в оборотах в минуту) Частоту шаговика (пока в герцах, в нижней строке под "St") 
Идеология такая: После включения символ "#" обозначает выбранную позицию. Кнопки влево и вправо позволяют выбирать другую.
Нажатие кнопки Select переключает выбранную позицию в режим редактирования. При этом кнопками вверх-вниз меняются единицы, а влево-вправо - десятые значения.
Повторное нажатие Select - возвращает к выбору.
Код:
/*
Управление шаговиком (драйвер степ-дир) переменным резистором 
теперь с кнопками! :)
А на этот раз - с экраном и резистивными кнопками.
Добавил измерение скорости вращения экструдера. Чуть подправил генерацию импульса на шаговик.
Управление преработано. Кнопка Select переключает режим "выбор" и "редактирование" Частота экструдера - в оборотах в минуту.
Добавлен коэффициент
v 0.6a */
/*
Вывод    Назначение
0        UART
1        UART
2        Внешнее прерывание от оптопары (не менять!)
3        
4        
5        Dir_pin
6        Step_pin     
7        LCD RS
8        LCD RW
9        LCD E
10       LCD DB4
11       LCD DB5
12       LCD DB6
13       LCD DB7
A0       Резистор
A1        Кнопки
A2
A3
A4        
A5        
A6
A7
 */
//#define Razr 1 //признак разработчика. Если пользователь - комментируем или удаляем.
#include <EEPROM.h> //подключаем библиотеку EEPROM
#include <LiquidCrystal.h> // Подключаем стандартную библиотеку LiquidCrystal
// Инициализируем объект-экран, передаём использованные 
// для подключения контакты на Arduino в порядке:
#define lcd_RS_pin 7
#define lcd_RW_pin 8
#define lcd_E_pin 9
#define lcd_DB4_pin 10
#define lcd_DB5_pin 11
#define lcd_DB6_pin 12
#define lcd_DB7_pin 13
//                    RS,         RW,        E,         DB4,           DB5,       DB6,          DB7
LiquidCrystal lcd(lcd_RS_pin, lcd_RW_pin, lcd_E_pin, lcd_DB4_pin, lcd_DB5_pin, lcd_DB6_pin, lcd_DB7_pin);
#define Step_pin 6 //вывод Arduino для ноги STEP контроллера (выход)
#define Dir_pin 5 //вывод Arduino для ноги DIR контроллера (выход)
#define Resistor_pin A0 //вывод Arduino резистора 0-5вольт (аналоговый вход)
//Оптодатчик:
#define OptoSensor_pin 2 //вывод Arduino для оптодатчика (вход)
#define ToothSumm 4 //сколько усреднять событий
#define ToothAll 140 // Событий на оборот
float ExtruderConst=(float)60/((float)(ToothAll/ToothSumm)*((float)1/250000)); // Коэффициент тиков :) Для оборотов в минуту делим его на измеренные
float DivK =1; //Коэффициент для соотношения скорости шаговика к скорости экструдера 
volatile unsigned long OptoSensorTicks=0;//Переменная для хранения тиков таймера на 1 вызов (время между зубьями)
volatile byte OptoToothCounter =0; //Указатель на текущтй зуб в массиве
volatile unsigned int OptoToothTimeArray [ToothSumm]; //массив с таймингами зубьев
//********** Кнопки:
#define btnRIGHT  1 //Определяем кнопки, это просто внутренние номера, НЕ ноги-выводы
#define btnUP     2
#define btnDOWN   3
#define btnLEFT   4
#define btnSELECT 5
#define btnNONE   0
//**********
#define btnDEFtime   30 //Значение для антидребезга - клавиша удерживаемая столько времени в миллисекундах считается нажатой.
#define btnPAUSEtime   400 //Значение в миллисекундах паузы между повторами
int lcd_key     = btnNONE;  //Для хранения полученного значеник кнопки
byte keyTemp = btnNONE; //Переменная для хранения временного состояния кнопок
byte keyCONTpress; //Переменная взводится после первого срабатывания клавиши и определяет автоповтор
unsigned long BtnTime; //Хранит время начала нажатия кнопок
byte btnCONTpress; //Переменная взводится после первого срабатывания клавиши и определяет автоповтор
byte btnTemp=btnNONE; //Для хранения номера ранее нажатой кнопки
#if defined(Razr)  //Мне для отладки
    #define ButtonPin A7 //Сюда подключены кнопки
#else
  #define ButtonPin A1 //Сюда подключены кнопки
#endif
//************
/*
//структура под меню
typedef struct
{
     char* nam; 
    byte posX;
    byte posY;
} menu;
//typedef struct menu menuEl;
menu menus[3] ={{"Mm1",0,0},
{"Mm2",1,1},
{"Mm3",3,3}};
*/
byte ControlPos = 0; //Переменная определяет элемент в строке управления. 1 - коэффициент. 0 - частота протяжки
byte ControlMode = 0; //Переменная определяет режим управления. 0 - выбор, 1 - редактирование
int ScreenPass =100; //Для пропуска циклов, чтоб экран не мерцал.
//Переменная для значения таймера
volatile unsigned char FullTimer0;
//Переменная для количества холостых 256циклов таймера
volatile unsigned int FullTimer256;//Переменная для количества холостых 256циклов таймера
volatile unsigned int FullTimer256Count; //внутренный счетчик таймера
//значение минимальной частоты
#define LowFreq 10
//значение МАКСИмальной частоты
#define HighFreq 1500
//Переменная для шага чаcтоты на едниницу изменения АЦП
// float FreqStep;
 float OutFreq = LowFreq; //Переменная для хранения установленной частоты
/*
//Переменная для текущего значения резистора
int sensorValue = 0;
//Переменная для Старого значения резистора
int OLDsensorValue = 0;
*/
void setup() {                
  pinMode(Step_pin,OUTPUT);  // Конфигурим вывод Step_pin как выход
  pinMode(Dir_pin,OUTPUT);  // Конфигурим вывод Dir_pin как выход
//  pinMode(Resistor_pin,INPUT);  // Конфигурим вывод Dir_pin как вход
  pinMode(OptoSensor_pin,INPUT);  // Конфигурим вывод OptoSensor_pin как вход
  attachInterrupt(0, OptoSensor, CHANGE); // привязываем 0-е прерывание к функции OptoSensor(). На изменение состояния. Да, из-за разницы между шириной самого зуба и межзубного расстояния - будут различия, усредним.
  
  lcd.begin(16,2); //Инициализируем экран
  
  
  //Установим на выходах 0
  digitalWrite(Step_pin, LOW);
  digitalWrite(Dir_pin, LOW);
  
//  // Посчитаем "шаг" изменения частоты на единицу изменения резистора
//  FreqStep=(float)(HighFreq-LowFreq)/1024;
  
  //Запускает последовательный порт
  Serial.begin(9600);
  
  //Сообщение о запуске программы
  Serial.println("Program started");  
 // Serial.print("FreqStep=");  
 // Serial.println(FreqStep);  
  
  //Запускает таймер и получает загружаемое значение таймера.
  //Параметр - желаемая частота в герцах.
  
   FullTimer0=SetupTimer2(OutFreq);
   
  //Установки Таймер2: Делитель частоты /64, режим 0
  //Частота = 16MHz/64 = 250000 герц или
  //Делитель /64 дает нам хороший рабочий диапазон в районе 1 кгц
  //так что сейчас мы просто жестко запрограммируем это.
  TCCR2A = 0;
  TCCR2B = 1<<CS22 | 0<<CS21 | 0<<CS20; //это на 64
  //Подключение прерывания по переполнению Timer2
  TIMSK2 = 1<<TOIE2;
  //Установки Таймер1: Делитель частоты /64, режим 0
  //Частота = 16MHz/64 = 250000 герц или
  //Делитель /64 дает нам хороший рабочий диапазон
  //так что сейчас мы просто жестко запрограммируем это.
  TCCR1A = 0;
  TCCR1B = 1<<CS22 | 0<<CS21 | 0<<CS20; //это на 64
  //Подключение прерывания по переполнению Timer0 (для обнуления скорости)
  TIMSK1 = 1<<TOIE1;
   
  
  //Выводит загружаемое значение таймера
  Serial.print("Timer2 Load:");
  Serial.println(FullTimer0,HEX);
  
  lcd.setCursor(0, 0); //устанавливаем курсор
  lcd.print("Stepper control"); //выводим на него  строку
  lcd.setCursor(0, 0); //устанавливаем курсор
  lcd.print("#St  Div  Ext"); //выводим на него  строку
  lcd.setCursor(0, 0); //устанавливаем курсор
//  lcd.cursor(); //Включим курсор
//  lcd.blink(); //Пусть мигает
  
  delay(10);
}
void loop() {
 OptoSensorTicks=0;
 //Один тик таймера - это 4 микросекунды (.000004) Зубъев у нас 70, причем реагируем на вход зуба а оптосенсор и на выход. Значит - 140 событий на оборот экструдера.
 //Складывая время
 for (int i=0; i<ToothSumm; i++)   {OptoSensorTicks+=OptoToothTimeArray[i];}
ScreenPass++; //Инкремент счетчика
if (ScreenPass>1000)
{
  ScreenPass=0; //Обнуляем счетчик
  
        lcd_key=read_LCD_buttons(); //прочитаем нажатую кнопку
      //0   4   8   12  |
      // St  Div  Ext
      //000  00000 00000 
        
        if (lcd_key) //Нажата какая-то кнопка
        {
           if (btnSELECT==lcd_key) //Если нажата кнопка Select
             {
               ControlMode=!ControlMode;
               if (ControlMode)
               {
                 if (ControlPos==0)
                     {
                       lcd.setCursor(0, 0);
                        lcd.print("*"); 
                        lcd.setCursor(4, 0);
                        lcd.print(" "); 
                     }
                 if (ControlPos==1)
                     {
                        lcd.setCursor(0, 0);
                        lcd.print(" "); 
                        lcd.setCursor(4, 0);
                        lcd.print("*"); 
                     }
                 }
                 else
                 {
                   lcd.setCursor(0, 0);
                   lcd.print(" "); 
                   lcd.setCursor(4, 0);
                   lcd.print(" "); 
                   if (ControlPos==1){lcd.setCursor(4, 0); lcd.print("#"); }
                   if (ControlPos==0){lcd.setCursor(0, 0); lcd.print("#"); }
                 }
              } //Меняем режим на другой :)
           if (ControlMode) //Если режим - "редактирование"
             {
               if (btnUP==lcd_key) //Если нажата кнопка "Больше"
                 {
                       if (ControlPos==0) //Меняем частоту протяжки шагами
                         {
                           OutFreq+=10;
                           SetupTimer2(OutFreq); //устанавливаем таймер
                          }
                       if (ControlPos==1) //Меняем коэффициент шагами
                         {DivK+=1;}
                  }
               if (btnDOWN==lcd_key) //Если нажата кнопка "Меньше"
                 {
                       if (ControlPos==0) //Меняем частоту протяжки шагами
                         {
                           OutFreq-=10;
                           SetupTimer2(OutFreq); //устанавливаем таймер
                          }
                       if (ControlPos==1) //Меняем коэффициент шагами
                         {DivK-=1;}
                  }
               if (btnRIGHT==lcd_key) //Если нажата кнопка "ВПРАВО"
                 {
                       if (ControlPos==0) //Меняем частоту протяжки единицами
                         {
                           OutFreq+=1;
                           SetupTimer2(OutFreq); //устанавливаем таймер
                          }
                       if (ControlPos==1) //Меняем коэффициент единицами
                         {DivK+=.01;}
                  }
               if (btnLEFT==lcd_key) //Если нажата кнопка "ВЛЕВО"
                 {
                       if (ControlPos==0) //Меняем частоту протяжки единицами
                         {
                           OutFreq-=1;
                           SetupTimer2(OutFreq); //устанавливаем таймер
                         }
                       if (ControlPos==1) //Меняем коэффициент единицами
                         {DivK-=.01;}
                  }
             }
            else //режим "выбор"
             {
                if (btnRIGHT==lcd_key) //нажата кнопка ВПРАВО
                  { 
                    lcd.setCursor(0, 0);
                    lcd.print(" "); 
                    lcd.setCursor(4, 0);
                    lcd.print("#"); 
                    ControlPos = 1;
                  }
                if (btnLEFT==lcd_key) //нажата кнопка ВЛЕВО    
                { 
                    lcd.setCursor(4, 0);
                    lcd.print(" "); 
                    lcd.setCursor(0, 0);
                    lcd.print("#"); 
                    ControlPos = 0;
                }
             }
        }
             
             
      //Теперь в зависимости от режима нужно...
      //Либо считать частоту шаговика от коэффициента при ControlMode==1 и ControlPos==1
      //Либо вычислять коэффициент при ControlMode==1 и ControlPos==0
      //Либо вычислять частоту шаговика от коэффициента при ControlMode==0 
      //Короче, только при ControlMode==1 и ControlPos==0 вычислять коэффициент. В остальных случаях - частоту.
       if ((ControlMode==1) && (ControlPos==0)) //Если режим - редактирование, изменение шаговика
        { 
         DivK= (float)OutFreq* ((float)100/OptoSensorTicks);  //Вычислим коэффициент 
         }
      else
        {
          OutFreq=(float)DivK/(float)(100/OptoSensorTicks);
          if (OutFreq>HighFreq){OutFreq=HighFreq;}
          if (OutFreq<LowFreq){OutFreq=LowFreq;}
          SetupTimer2(OutFreq); //устанавливаем таймер
        }
  
      //Выведем коэффициент
         lcd.setCursor(10, 1);
         lcd.print(DivK);
      
      //выведем скорость
          lcd.setCursor(10, 0);
          lcd.print("     ");
          lcd.setCursor(10, 0);
          lcd.print(ExtruderConst/OptoSensorTicks);
          
      //    lcd.setCursor(9, 1);
      //    lcd.print("     ");
      //    lcd.setCursor(9, 1);
      //    lcd.print(OptoSensorTicks);
      
          lcd.setCursor(0, 1);
          lcd.print(OutFreq); //выведем частоту
      
        
          /*
            Serial.print("sensor=");
            Serial.println(sensorValue,DEC);
            Serial.print("FullTimerCount");
            Serial.println(FullTimerCount);
            Serial.print("FullTimer");
            Serial.println(FullTimer,DEC);
            
            Serial.print("timer=");
            Serial.println(FullTimer0,DEC);
            
            Serial.print("ButtPressed=");
            Serial.println(ButtPressed,DEC);
            Serial.print("OutFreq=");
            Serial.println(OutFreq,DEC);
            Serial.println("***");
            Serial.println("");
         
          Serial.println("***");    
          Serial.println(OptoSensorTicks);
          delay (200);
              */
}
}
//Timer1 указатель вектора прерывания по переполнению
ISR(TIMER1_OVF_vect) 
{
    OptoToothTimeArray[OptoToothCounter]=0; //присваиваем элементу массива 0
    OptoToothCounter++; //инкрементим счетчик
    if (ToothSumm==OptoToothCounter) {OptoToothCounter=0;} //если счетчик равен количеству элементов массива (а индекс массива начинается с 0 - то обнуляем.
}
//Timer2 указатель вектора прерывания по переполнению
ISR(TIMER2_OVF_vect) 
{
  if (FullTimer256Count>1)
  {FullTimer256Count--;}
  else
  {if (FullTimer256Count==1) //предпоследний цикл
      {
       TCNT2+=FullTimer0;
       FullTimer256Count=0;
      }
   {if (FullTimer256Count==0) // Срабатывание
        {
         //Переключение IO-вывода в HIGH
          digitalWrite(Step_pin,HIGH);
         FullTimer256Count=FullTimer256;
         //Переключение IO-вывода в другое состояние.
        // digitalWrite(Step_pin,!digitalRead(Step_pin));
            //Перезагрузка таймера и коррекция по задержке
            if (FullTimer256)
                {TCNT2=0;} //Если холостые циклы есть  - максимальное значение
            else
                {TCNT2+=FullTimer0;}
          //Переключение IO-вывода в LOW
          digitalWrite(Step_pin,LOW);
        }
    }
  }
}
#define TIMER_CLOCK_FREQ 250000.0 
//15625 for /1024
//2MHz for /8 prescale from 16MHz
  //Установка Таймера2.
//Конфигурирует 8-битный Таймер2 ATMega168 для выработки прерывания
//с заданной частотой.
//Возвращает начальное значение таймера, которое должно быть загружено в TCNT2
//внутри вашей процедуры ISR.
//Смотри пример использования ниже.
unsigned char SetupTimer2(float timeoutFrequency){
  //Подсчет начального значения таймера
  //Слегка усложним, добавив холостые просчеты
  long ticks = TIMER_CLOCK_FREQ/timeoutFrequency; // тиков счетчика для получения заданной частоты
//          #if defined(Razr)
//             lcd.setCursor(9, 0);
//             lcd.print(ticks);
//          #endif
  FullTimer256=ticks/256; //Вычисляем количество ПОЛНЫХ 256 циклов таймера
  ticks-=FullTimer256*256;
  FullTimer0=(byte)(257.0-(ticks+0.5));  //Вычисляем количество доплнительных тиков таймера
  //257 на самом деле должно быть 256, но я получил лучшие результаты с 257.
  //загружает таймер для первого цикла
  if (FullTimer256)
    {TCNT2=0;} //Если холостые циклы есть  - максимальное значение
  else
      {TCNT2=FullTimer0;}
}
// *****************************
//Чтение кнопок с антидребезгом
// read the buttons
int read_LCD_buttons()
{
int adc_key_in = analogRead(ButtonPin);      // Получаем напряжение с АЦП
byte btnTempTemp = btnNONE; //Переменная для хранения свежесчитанного внутри функции
//digitalWrite (LED_pin,0); //debug
//lcd.setCursor(5, 0); //debug
//lcd.print(adc_key_in); //debug
//delay (400); //debug
 //Тут используем millis() для отслеживания нажатия кнопки
// Запоминиаем в переменной BtnTime ВРЕМЯ НАЧАЛА нажатия
// Запоминаем в переменной btnTemp нажатия 
// Дефиним время антидребезга #define 
 
 if (adc_key_in > 950) //Ничего не нажато
  {
   //BtnTime=0; //Скидываем время нажатия
   btnCONTpress=0;
   return btnNONE; // We make ths the 1st option for speed reasons since it will be the most likely result
  }
 else //что-то нажато
   {
      if (adc_key_in < 790) { btnTempTemp=btnSELECT; } //Определяем в переменную ТЕКУЩУЮ нажатую кнопку.
      if (adc_key_in < 555) { btnTempTemp=btnLEFT; }
      if (adc_key_in < 380) { btnTempTemp=btnDOWN; }
      if (adc_key_in < 195) { btnTempTemp=btnUP; }
      if (adc_key_in < 50)  { btnTempTemp=btnRIGHT; }
     //А тут проверим, совпадает ли с btnTemp (была ли нажата ранее)
/*     lcd.setCursor(0, 0); //debug
     lcd.print(btnTempTemp); //debug
     lcd.setCursor(2, 0); //debug
     lcd.print(btnTemp); //debug
     lcd.setCursor(1, 1); //debug
     lcd.print(millis()); //debug
     lcd.setCursor(12, 1); //debug
     digitalWrite (LED_pin,1); //debug
     delay (100);
     lcd.print("    "); //debug
     lcd.setCursor(12, 1); //debug
     lcd.print(adc_key_in); //debug
*/
     if (btnTempTemp==btnTemp) //Кнопка уже БЫЛА нажата
     {
        if (btnCONTpress) //Повторные установки клавиши
          {
            if ((millis()-BtnTime) > btnPAUSEtime)
            {
              BtnTime=millis(); // Ставим стартово время для автоповтора
              return btnTemp;
            }
          }  
        else //Первая установка клавиши
           {
              if ((millis()-BtnTime) > btnDEFtime)
              {
                btnCONTpress=1;
                BtnTime=millis(); // Ставим стартово время для автоповтора
                return btnTemp;
              }
           }
     }
     else //Раньше было другое состояние
     {
//       digitalWrite (LED_pin,1); //debug
//       delay (100);
       btnCONTpress=0;
       BtnTime=millis(); //Устанавливаем ТЕКУЩЕЕ время в переменную BtnTime
       btnTemp=btnTempTemp; //устанавливаем кнопку во временную переменную.
     }
   }
 return btnNONE;   // Если ничего не сработало, то ничего не возвращаем
}
//***********************************
void OptoSensor() // функция обработки прерывания. Меняет глобальные прееменные
{//Сработал - значит считаем тики. F njxytt - echtlyztv pf 
  OptoToothTimeArray[OptoToothCounter]=TCNT1; //присваиваем элементу массива текущее значение таймера
  TCNT1 = 0; //сбрасываем таймер
  OptoToothCounter++; //инкрементим счетчик
  if (ToothSumm==OptoToothCounter) {OptoToothCounter=0;} //если счетчик равен количеству элементов массива (а индекс массива начинается с 0 - то обнуляем.
}
Добавлено спустя 4 минуты 18 секунд:Хотя да, чего-то с частотой... Непропорционально меняется.
Добавлено спустя 25 минут 18 секунд:Ищу причину.