Спойлер
Код: Выделить всё
while(1){ ......
//*************************AUTOTUNE RID*********************
if(bitRead(myFlags, flag_TUNE)){
target_temperature = 100;
if(value_temperature > target_temperature) \
{sevseg.setChars("ERR 4"); sevseg.refreshDisplay();} else{
LedEvent=t.oscillate(ledPin, 70, HIGH);
sevseg.setChars("TUNE");
// target_temperature = 120;
//pidCycle = t.every(windowSize, pidCompute, (void*)0);
byte i = 0; // Cycle counter
byte cycles = 3;
uint16_t outputValue = ICR1;
bool output = true;
OCR1B = 0;
START_PWM;
//TCCR1B |= (1<<WGM13)|(1 << WGM12)|(1<<CS12)|(1<<CS10);
long t1, t2, tHigh, tLow;
float pAverage, iAverage, dAverage;
float ku = (4.0 * ((ICR1) / 2.0));
tHigh = tLow = 0; // More time variables
byte max = 0; // Max input
byte min = 255; // Min input
pAverage = iAverage = dAverage = 0;
t1 = t2 = millis(); // Times used for calculating period
//**********************************************************************************************************
while (i <= cycles) {
OCR1B = outputValue;
// display(value_temperature, index[T]);
sevseg.refreshDisplay();
t.update(); // Updates the timer
if ((ADCSRA & (1 << ADIF))) value_temperature = get_temperature(); else;
max = (max > value_temperature) ? max : value_temperature; // Calculate max and min
min = (min < value_temperature) ? min : value_temperature;
if (output && value_temperature > target_temperature) { // Output is on and value_temperature signal has risen to target
output = false; // Turn output off, record current time as t1, calculate tHigh, and reset maximum
outputValue = 0;
t1 = millis();
tHigh = t1 - t2;
}
if (!output && value_temperature < target_temperature) { // Output is off and value_temperature signal has dropped to target
output = true; // Turn output on, record current time as t2, calculate tLow
outputValue = ICR1;
t2 = millis();
tLow = t2 - t1;
// Calculate Ku (ultimate gain)
// Formula given is Ku = 4d / πa
// d is the amplitude of the output signal
// a is the amplitude of the value_temperature signal
/*ku = ku / (M_PI * (max - min) / 2.0);
uint32_t tu = tLow + tHigh; // Calculate Tu (period of output oscillations)
// Calculate gains
Kp = 0.2 * ku;
Ki = (Kp / (0.5 * tu)) * windowSize;
Kd = (0.33 * Kp * tu) / windowSize;
if (i <= 8) { // Average all gains after the first two cycles
pAverage += Kp;
iAverage += Ki;
dAverage += Kd;
} */
++i;// Increment cycle count
display(i, index[3]);
max = min = target_temperature; // Reset minimum, maximum
}
}
//output = false;
//t.stop(pidCycle);
STOP_PWM; // PWM Stop
RELAY_OFF;
TCNT1 = outputValue = OCR1B = 0;
TCCR1A &=~(1<<COM1B1); TRELAY_OFF;
Kp = pAverage / (i - 1);
EEPROM_float_write(addr_Kp, Kp);
Ki = iAverage / (i - 1);
EEPROM_float_write(addr_Ki, Ki);
Kd = dAverage / (i - 1);
EEPROM_float_write(addr_Kd, Kd);
bitClear(myFlags, flag_TUNE);
sevseg.setChars("-END-");
t.oscillate(buzzerPin, 1000, HIGH,10);
t.stop(LedEvent);
bitClear(myFlags, flag_TUNE);
target_temperature = EEPROM.read(addr_TEMPR);
}
}
}Тема закрыта, всем, давшим реально дельные советы -- большое спасибо

