Arduino - Problema de resultados estáticos en cálculos en subrutinas

   
Vista:

Problema de resultados estáticos en cálculos en subrutinas

Publicado por Julio Cesar julio_cesar_53@hotmail.com (1 intervención) el 24/11/2017 02:36:02
Hola foro.
Soy nuevo en este foro, y también en el mundo de arduino.
Estoy tratando de perfeccionar un software para un analizador de antenas en banda HF.
Estoy trabajando con un arduino UNO.
La frecuencia la genero con sintetizador de frecuencias AD9850 y un encoder rotativo con pulsador en el eje.
Los resultados los visualizo en un display lcd de 20x4 conectado mediante un adaptador I2C.
En un puente de impedancias tomo 4 tensiones que las rectifico y las introduzco a las entradas analógicas del arduino.
Luego aplicando fórmulas matemáticas voy calculando los distintos parámetros.
Escribi una subrutina llamada void resultados(), para ir cambiando la presentación de los resultados en el display, en la tercera y cuarta fila del display, mediante un pulsador que se va presionando.
El problema que presenta, es que los cálculos los hace bien, pero los resultados quedan fijos, no cambian de acuerdo a la variación de las tensiones de entrada.
El único parámetro que cambia de valor con cada delay de 500 ms es el ROE que está dentro del void loop() principal.
Alguna idea que me permita solucionar este conflicto.
Gracias.

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
212
213
214
215
216
217
218
219
220
221
222
223
224
225
226
227
228
229
230
231
232
233
234
235
236
237
238
239
240
241
242
243
244
245
246
247
248
249
250
251
252
253
254
255
256
257
258
259
260
261
262
263
264
265
266
267
268
269
270
271
272
273
274
275
276
277
278
279
280
281
282
283
284
285
286
287
288
289
290
291
292
293
294
295
296
297
298
299
300
301
302
303
304
305
306
307
308
309
310
311
312
313
314
315
316
317
318
319
320
321
322
323
324
325
326
327
328
329
330
331
332
333
334
335
336
337
338
339
340
341
342
// Inclusion de librerias
#include <LiquidCrystal_I2C.h>·     //Libreria I2C para display LCD.
#include <Wire.h>                   //Libreria utilizada para comunicar el arduino con el dispositivo I2C.
LiquidCrystal_I2C lcd(0x3F, 20, 4); //Dirección del dispositivo_Número de columnas_Número de filas.
#include <rotary.h>                 //Librería del Encoder Rotativo.
 
int VFd;  //Tensión incidente en valor digital.
float VF; //Tensión incidente en valor analógico.
 
int VRd;  //Tensión reflejada en valor digital.
float VR; //Tensión reflejada en valor analógico.
 
int VZd;  //Tensión en la carga en valor digital.
float VZ; //Tensión en la carga en valor analógico.
 
int VAd;  //Tensión en una rama en valor digital.
float VA; //Tensión en una rama en valor analógico.
 
float ROE; //Relación de Onda Estacionaria.
float CR;  //Coeficiente de Reflexión.
float Z;   //Módulo de Impedancia.
float fi;  //Fase de la impedancia.
float R;   //Parte resistiva de la impedancia.
float X;   //Parte reactiva en valor absoluto de la impedancia.
float L;   //Inductancia.
float C;   //Capacidad.
float PR;  //Pérdida de Retorno.
float PC;  //Pérdida de Cable.
 
//definicion de algunos items
#define W_CLK 8   // Pin 8 - (CLK)AD9850
#define FQ_UD 9   // Pin 9 - (FQ)AD9850
#define DATA 10   // Pin 10 - (DATA)AD9850
#define RESET 11  // Pin 11 -(RESET) AD9850
#define pulseHigh(pin) {digitalWrite(pin, HIGH); digitalWrite(pin, LOW); }
Rotary r = Rotary(2, 3); // pins del rotary encoder
int_fast32_t rx = 15000000; // Frecuencia de inicio VFO
int_fast32_t rx2 = 1; // Variable auxiliar para retener la nueva frecuencia
int_fast32_t increment = 1000000; // paso de sintonia inicial.
int_fast32_t iffreq = 0000000; //FRECUENCIA INTERMEDIA
int buttonstate = 0;// var boton pasos de sintonia
int Modo = 0; // Lee pulsador de cambio de resultados
int Resultado = 0; // Varia presentacion de resultados
int GoIF = 1;//var suma o resta FI
String hertz = "x1MHz";
int  hertzPosition = 10;
byte ones, tens, hundreds, thousands, tenthousands, hundredthousands, millions ; //Ubicacion lugares
String freq; // string para retener la frecuencia
int_fast32_t timepassed = millis(); //
 
void setup() {
 
  lcd.init(); // Inicializar el LCD
  lcd.backlight();  //Encender la luz de fondo.
  pinMode(4, INPUT); // STEP (Boton a GND que cambia los pasos de sintonia)
  pinMode(7, INPUT); // Pulsador de modo de funciones
 
  pinMode(A0, INPUT); // Entrada tensión VFd de onda incidente.
  pinMode(A1, INPUT); // Entrada tensión VRd de onda reflejada.
  pinMode(A2, INPUT); // Entrada tensión VZd de la carga.
  pinMode(A3, INPUT); // Entrada tensión VAd de la rama.
 
  digitalWrite(4, HIGH);
  digitalWrite(7, HIGH);
 
  PCICR |= (1 << PCIE2);
  PCMSK2 |= (1 << PCINT18) | (1 << PCINT19);
  sei();
  pinMode(FQ_UD, OUTPUT);
  pinMode(W_CLK, OUTPUT);
  pinMode(DATA, OUTPUT);
  pinMode(RESET, OUTPUT);
  pulseHigh(RESET);
  pulseHigh(W_CLK);
  pulseHigh(FQ_UD);  // este pulso habilita el modo serie del AD9850
  lcd.setCursor(13, 0);
  lcd.print(hertz);
  lcd.setCursor(0, 1);
  lcd.print("ROE=    ");
  lcd.setCursor(0,2);
  lcd.print(" ANALIZADOR BANDA HF");
  lcd.setCursor(0,3);
  lcd.print("  PRESIONE PULSADOR ");
}
 
void loop() {
 
   VFd = analogRead(A0);
   VF = VFd*0.004882812; //Convierte el valor digital de tensión a valor analógico.
 
   VRd = analogRead(A1);
   VR = VRd*0.004882812; //Convierte el valor digital de tensión a valor analógico.
 
   VZd = analogRead(A2);
   VZ = VZd*0.004882812; //Convierte el valor digital de tensión a valor analógico.
 
   VAd = analogRead(A3);
   VA = VAd*0.004882812; //Convierte el valor digital de tensión a valor analógico.
 
   lcd.setCursor(4,1);
   ROE = (VF+VR)/(VF-VR); //Calcula el valor de Relación de Onda Estacionaria.
   delay(500);            //Demora 500 milisegundos en imprimir el resultado después de cada cálculo.
   lcd.print(ROE);        //Imprime en pantalla el valor de Relación de Onda Estacionaria.
 
 
 
 
   // Lee pulsador cambio de resultados
   Modo = digitalRead(7);
  if (Modo == LOW) {
    resultados();
  }
 
  // Actualiza la frecuencia del display cuando la frecuencia nueva es distinta a al actual
  if (rx != rx2) {
    showFreq();
    sendFrequency(rx);
    rx2 = rx;
  }
 
  // Lee el boton STEP y cambia los pasos de sintonia (1, 10, 100, 1k , 10k, 100k, 1M)
  buttonstate = digitalRead(4);
  if (buttonstate == LOW) {
    setincrement();
  };
 
  sendFrequency(rx);
 
}
 
// rutina de interrupcion del rotary encoder
ISR(PCINT2_vect) {
  unsigned char result = r.process();
  if (result) {
    if (result == DIR_CW) {
      rx = rx + increment;
    }
    else {
      rx = rx - increment;
    };
    if (rx >= 40000000) {
      rx = rx2;
    }; // LIMITE SUPERIOR DEL VFO
    if (rx <= 00000001) {
      rx = rx2;
    }; // LIMITE INFERIOR DEL VFO
  }
}
 
// CALCULO DE FRECUENCIA DDS= <sys clock> * <frequency tuning word>/2^32
void sendFrequency(double frequency) {
  if (GoIF == 1) {
    frequency = frequency + iffreq;
  }; //Si el pin esta en alto SUMA la FI
  if (GoIF == 0) {
    frequency = frequency - iffreq  ;
  }; // Si el pin esta en bajo RESTA la FI
  int32_t freq = frequency * 4294967295 / 125000000; // 125 MHz clock del AD9850. Se puede realizar un ajuste fino de frecuencia cambiando este valor.
  for (int b = 0; b < 4; b++, freq >>= 8) {
    tfr_byte(freq & 0xFF);
  }
  tfr_byte(0x000);// byte de control final
  pulseHigh(FQ_UD);  // Listo !!!
}
// transfiere los datos al AD9850
void tfr_byte(byte data)
{
  for (int i = 0; i < 8; i++, data >>= 1) {
    digitalWrite(DATA, data & 0x01);
    pulseHigh(W_CLK);
  }
}
//pasos de sintonia
void setincrement() {
  if (increment == 1000000) {
    increment = 100000;
    hertz = "x100KHz";
    hertzPosition = 10;
    lcd.setCursor(13, 0);
    lcd.print(hertz);
    delay(500);
  }
  else if (increment == 100000) {
    increment = 10000;
    hertz = "x10KHz";
    hertzPosition = 10;
    lcd.setCursor(14, 0);
    lcd.print(hertz);
    delay(500);
  }
  else if (increment == 10000) {
    increment = 1000;
    hertz = "x1KHz";
    hertzPosition = 10;
    lcd.setCursor(15, 0);
    lcd.print(hertz);
    delay(500);
  }
  else if (increment == 1000) {
    increment = 100;
    hertz = "x100Hz";
    hertzPosition = 10;
    lcd.setCursor(14, 0);
    lcd.print(hertz);
    delay(500);
  }
  else if (increment == 100) {
    increment = 10;
    hertz = "x10Hz";
    hertzPosition = 10;
    lcd.setCursor(15, 0);
    lcd.print(hertz);
    delay(500);
  }
  else if (increment == 10) {
    increment = 1;
    hertz = "x1Hz";
    hertzPosition = 10;
    lcd.setCursor(16, 0);
    lcd.print(hertz);
    delay(500);
  }
  else {
    increment = 1000000;
    hertz = "x1MHz";
    hertzPosition = 10;
    lcd.setCursor(15, 0);
    lcd.print(hertz);
    delay(500);
  };
};
// muestra  la frecuencia en el display
void showFreq() {
  millions = int(rx / 1000000);            //Millones (1 MHz)
  hundredthousands = ((rx / 100000) % 10); //Cientos de Miles (100 KHz)
  tenthousands = ((rx / 10000) % 10);      //Diez Mil (10 KHz)
  thousands = ((rx / 1000) % 10);          // Miles (1 KHz)
  hundreds = ((rx / 100) % 10);            //Centenares (100 Hz)
  tens = ((rx / 10) % 10);                 //Decenas (10 Hz)
  ones = ((rx / 1) % 10);                  // Unos (1Hz)
  lcd.setCursor(0, 0);
  lcd.print("F=        ");
  lcd.setCursor(10, 0);
  lcd.print("Hz");
  lcd.setCursor(2, 0);
  lcd.print(millions);         //Millones (1 MHz)
  lcd.print(hundredthousands); //Cientos de Miles (100 KHz)
  lcd.print(tenthousands);     //Diez Mil (10 KHz)
  lcd.print(thousands);        // Miles (1 KHz)
  lcd.print(hundreds);         //Centenares (100 Hz)
  lcd.print(tens);             //Decenas (10 Hz)
  lcd.print(ones);             // Unos (1Hz)
  timepassed = millis();
 
};
 
  void resultados() {
 
     if (Resultado == 0) {
           Resultado = 1;
           lcd.setCursor(0, 2);
           lcd.print("Z=                  ");
           lcd.setCursor(2,2);
           Z = 50*(VZ/VA);                      //Se calcula el módulo de la impedancia en ohmios.
           lcd.print(Z);                        //Se imprime en pantalla el módulo de la impedancia en ohmios.
 
           lcd.setCursor(0, 3);
           lcd.print("Fase=               ");
           lcd.setCursor(5,3);
           R = (2500+VZ*VZ)*ROE/(50*ROE*ROE+1); //Se calcula la resistencia en ohmios.
           X = sqrt((Z*Z)-(R*R));               //Se calcula el módulo de la reactancia en ohmios.
           fi= atan(X/R)*(180/PI);              //Se calcula la fase de la impedancia en grados.
           lcd.print(fi);             //Se imprime en pantalla la fase de la impedancia en grados.
 
                        }
 
         else if (Resultado == 1) {
         Resultado = 2;
           lcd.setCursor(0, 2);
           lcd.print("R=                  ");
           lcd.setCursor(2,2);
           R = (2500+VZ*VZ)*ROE/(50*ROE*ROE+1); //Se calcula la resistencia en ohmios.
           lcd.print(R);                        //Se imprime en pantalla la resistencia en ohmios.
 
           lcd.setCursor(0, 3);
           lcd.print("X=                  ");
           lcd.setCursor(2,3);
           Z = 50*(VZ/VA);                      //Se calcula el módulo de la impedancia en ohmios.
           X = sqrt((Z*Z)-(R*R));               //Se calcula el módulo de la reactancia en ohmios.
           lcd.print(X);                        //Se imprime en pantalla el módulo de la reactancia en ohmios.
 
         }
         else if (Resultado == 2) {
           Resultado = 3;
           lcd.setCursor(0,2);
           lcd.print("L(uHy)=             ");
           lcd.setCursor(7,2);
           L = (X/rx)*159154.9431;           //Se calcula la inductancia en microHenry.
           lcd.print(L);                     //Se imprime en pantalla la inductancia en microHenry.
 
           lcd.setCursor(0, 3);
           lcd.print("C(pF)=              ");
           lcd.setCursor(6,3);
           C = 159154943100*(1/(rx*X));      //Se calcula la capacidad en picoFaradios.
           lcd.print(C);                     //Se imprime en pantalla la capacidad en picoFaradios.
 
           }
           else if (Resultado == 3) {
             Resultado = 4;
           lcd.setCursor(0, 2);
           lcd.print("Coef Reflex=        ");
           lcd.setCursor(12,2);
           CR = (ROE-1)/(ROE+1);             //Se calcula el coeficiente de reflexión.
           lcd.print(CR);                    //Se imprime en pantalla el coeficiente de reflexión.
 
           lcd.setCursor(0, 3);
           lcd.print("Per. Ret.(dB)=      ");
           lcd.setCursor(14,3);
           PR = (-20*log(CR))/log(10);       //Se calcula la pérdida de retorno en dB.
           lcd.print(PR);                    //Se imprime en pantalla la pérdida de retorno en dB.
           }
              else if (Resultado == 4) {
             Resultado = 5;
           lcd.setCursor(0, 2);
           lcd.print(" Perd. de Cable (dB)");
           lcd.setCursor(0,3);
           lcd.print("                    ");
           lcd.setCursor(1,3);
           CR = (ROE-1)/(ROE+1);             //Se calcula el coeficiente de reflexión.
           PC = (-10*log(CR))/log(10);       //Se calcula la pérdida en el cable en dB.
           lcd.print(PC);                    //Se imprime en pantalla la pérdida en el cable en dB.
          }
 
          else {
            Resultado = 0;
            //Escribimos en las 2 últimas filas el mismo texto que en el void setup()
           lcd.setCursor(0,2);
           lcd.print(" ANALIZADOR BANDA HF");
           lcd.setCursor(0,3);
           lcd.print("  PRESIONE PULSADOR ");
};
  };
Valora esta pregunta
Me gusta: Está pregunta es útil y esta claraNo me gusta: Está pregunta no esta clara o no es útil
0
Responder
Revisar política de publicidad