Autor Tema: Problema con Menu y Submenu  (Leído 4179 veces)

0 Usuarios y 1 Visitante están viendo este tema.

Desconectado ADY12

  • PIC10
  • *
  • Mensajes: 43
Problema con Menu y Submenu
« en: 07 de Julio de 2015, 06:25:25 »
Hola, tengo un pequeño con el menu y el submenu, el problema es el siguiente, hay un mensaje de bienvenida que te dice si quieres ir al menú o volcar los datos en el ordenador, si pulsas 1 vas al menú, ahí dentro hay 4 variables a medir, si seleccionamos la variable numero 4, dentro hay otro submenu donde hay la opción de obtener datos o volver al menú, pulsamos # para volver al menú, volvemos a estar donde las 4 variables, a partir de aquí surgen los problemas, porque intento seleccionar una de las 4 variables y no me deja, exceptuando si pulso uno obtiene los datos de la variable que hemos seleccionado anteriormente, no se que es lo que me falla, he ido probando cosas pero nada.

Código: [Seleccionar]

Cuelgo solo el menu de una variable, el resto serian igual pero cambiando los datos a obtener.

void MENU_NCOMB(){
   char k;
   kbd_init();
   lcd_putc('\f');
   lcd_gotoxy(1,1);
   printf(lcd_putc, "1.OBTENER DATOS");
   lcd_gotoxy(1,2);
   printf(lcd_putc, "#.VOLVER AL MENU");
      while (TRUE){
         k=kbd_getc();
         if (k!=0)
         switch(k){
            case '1':
               lcd_putc('\f');
               lcd_gotoxy(1,1);
               printf(lcd_putc,"OBTENIENDO");
               lcd_gotoxy(1,2);
               printf(lcd_putc,"DATOS...");
               delay_ms(100);
               NIVEL_COMBUSTIBLE();
//!               delay_ms(10000);
//!               lcd_putc('\f');
//!               GUARDAR_DATO();
               break;
            case '#':
               MENU();
               break;
         }
}
}

void SELECCIONAR(){
char z;
kbd_init();
WHILE(true){
z=kbd_getc();
            if (z!=0)
               switch(z){
                  case '1':
                     MENU_TEMP();
                     break; 
                  case '2':
                     MENU_NCOMB();
                     break;
                  case '3':
                     MENU_VEL();
                     break;
                  case '4':
                     MENU_RPM();
                     break;
               }           
}
}

void main(){
   char k;

   lcd_init();
   
   kbd_init();
   //RTC();
//!   delay_ms(1000);

   INICIO();

while(TRUE){  //Bucle infinito siempre consulta el teclado
   
      k=kbd_getc();
      if (k!=0){
      switch(k){
         case '1':
            MENU();
            SELECCIONAR();
            break;
                 
case '2':
TRANSMITIR_DATOS ();
break;
         }
      }
}
}


Desconectado KILLERJC

  • Colaborador
  • DsPIC33
  • *****
  • Mensajes: 8242
Re: Problema con Menu y Submenu
« Respuesta #1 en: 07 de Julio de 2015, 15:46:24 »
Algo asi?

Bienvenida()

1 - Menu
2 - Volcar datos PC


1-1 Variable1
1-2 Variable2
1-3 Variable3
1-4 Variable4


Cada variable tiene lo mismo

1-x-1 Obtener datos ( y luego vuelve al menu de las variables )
1-x-2 Menu




Código: C
  1. int j=0,nivel_menu=0,variable;
  2. Bienvenida();                                                           // O Mostrar_menu_inicial();
  3. while(1)
  4. {
  5.         k=kbd_getc();
  6.  
  7.         if (k!=0 & j!=k)                                                //Compruebo que se presiono algo Y no sea la misma tecla que la anterior ves,
  8.         {
  9.         switch(nivel_menu)
  10.         {
  11.         case 0:
  12.                 switch(k)                                               //Menu principal
  13.                 {
  14.                 case '1':
  15.                         Mostrar_menu_de_variables();
  16.                         nivel_menu=1;
  17.                         break;
  18.                 case '2':
  19.                         Enviar_datos();
  20.                         break:
  21.                 default:
  22.                         break;
  23.                 }
  24.                 break;
  25.         case 1:                                                         //Menu de variables, aca muesrto todas las variables para que seleccione una
  26.                 switch(k)
  27.                 {
  28.                 case '1':
  29.                         Mostrar_Menu_Var();
  30.                         variable=1;
  31.                         nivel_menu=2;
  32.                         break;
  33.                 case '2':
  34.                         Mostrar_Menu_Var();
  35.                         variable=2;
  36.                         nivel_menu=2;
  37.                         break;
  38.                 case '3':
  39.                         Mostrar_Menu_Var();
  40.                         variable=3;
  41.                         nivel_menu=2;
  42.                         break;
  43.                 case '4':
  44.                         Mostrar_Menu_Var();
  45.                         variable=4;
  46.                         nivel_menu=2;
  47.                         break;
  48.                 case '#':
  49.                         Mostrar_menu_inicial();
  50.                         nivel_menu=0;
  51.                         break;
  52.                 default:
  53.                         break;
  54.                 }
  55.                 break;
  56.         case 2:                                                         // Menu de cada variable, todas tienen 2 opciones, obtener datos y salir al menu anterior
  57.                 switch(k)
  58.                 {
  59.                 case '1':
  60.                         Obtener_datos(variable);                        // Segun sea el valor del argumento va a tomar un valor u otro
  61.                         nivel_menu=1;                                   // Indica que vuelva al menu anterior( los botones)
  62.                         Mostrar_menu_de_variables();
  63.                         break;
  64.                 case '#':
  65.                         Mostrar_menu_de_variables();                    // Se muestra el menu anterior y se vuelve a los botones del anterior tmb
  66.                         nivel_menu=1;
  67.                         break;
  68.                 default:
  69.                         break;
  70.                 }
  71.                 break;
  72.         default:                                                        // Caso unico que por algun problema se llegue este punto, poniendo a 0 y el nivel y mostrando el mnu inicial
  73.                 Mostrar_menu_inicial();
  74.                 nivel_menu=0;
  75.                 break;
  76.         }
  77.         }
  78.         j=k;                                    //Para que no entre de nuevo si se mantiene presionado la tecla
  79. }

Queda realizar las funciones que escriben en el LCD como
Mostrar_menu_inicial();      ( enviar datos y menu)
Mostrar_menu_de_variables();   ( var1 var2 var3 y var4)
Mostrar_Menu_Var();              ( obtener datos y menu )

Y la que obtiene los datos:
Obtener_datos(variable);

Segun "variable" va a actualizar una u otra, adentro de eso un switch...case con opciones de 1 a 4 y sale.

El codigo este se podria resumir aun mas, si es que esas opciones ya van a ser fijas y no pensas en agrandarla o modificarlas, como por ejemplo que cada variable tenga su propio menu.

No segui tu codigo por que esta incompleto, en tu afan de mostrar solo algunas partes por ejemplo no se que es MENU(), Pero por lo visto tenes problemas y que se encuentran en los while(true); lo que te encierra el programa ahi y no sale mas

Entonces la unica forma de salir de ahi es haciendo un break al while, pero el break del '#' es del switch..case , lo cual no estas saliendo apra nada, si MENU() es solamente mostrar las "opciones" y no tomar datos, esto quiere decir que vas a estar atrapado en ese while(true).

una forma "simple" de solucionarlo seria crear una variable para ese punto nomas e indicarle que debe salir de ahi

Código: C
  1. void MENU_NCOMB(){
  2.    char k,j=1;
  3.    lcd_putc('\f');
  4.    lcd_gotoxy(1,1);
  5.    printf(lcd_putc, "1.OBTENER DATOS");
  6.    lcd_gotoxy(1,2);
  7.    printf(lcd_putc, "#.VOLVER AL MENU");
  8.       while (j){
  9.          k=kbd_getc();
  10.          if (k!=0)
  11.          switch(k){
  12.             case '1':
  13.                lcd_putc('\f');
  14.                lcd_gotoxy(1,1);
  15.                printf(lcd_putc,"OBTENIENDO");
  16.                lcd_gotoxy(1,2);
  17.                printf(lcd_putc,"DATOS...");
  18.                delay_ms(100);
  19.                NIVEL_COMBUSTIBLE();
  20.                break;
  21.             case '#':
  22.                MENU();
  23.                j=0;
  24.                break;
  25.          }
  26. }
  27. }
  28.  
  29. void SELECCIONAR(){
  30. char z,j=1;
  31. WHILE(j){
  32. z=kbd_getc();
  33.             if (z!=0)
  34.                switch(z){
  35.                   case '1':
  36.                      MENU_TEMP();
  37.                      break;  
  38.                   case '2':
  39.                      MENU_NCOMB();
  40.                      break;
  41.                   case '3':
  42.                      MENU_VEL();
  43.                      break;
  44.                   case '4':
  45.                      MENU_RPM();
  46.                      break;
  47.                   case '#':
  48.                      MENU_INICIAL();
  49.                      j=0;
  50.                      break;
  51.                }            
  52. }
  53. }

Ahora si MENU() tambien toma opciones (es decir tiene un while tambien) estarias con un problema un poco mas grande todavia. Ya que si tiene un while(true) dentro va a ocurrir esto:

Menu_inicial -> menu variables -> menu_var -> menu vriables -> menu var -> etc etc etc

Como esta dentro de un while() C espera que el programa regrese y empieza a guardar las direcciones de retorno, llegando a un punto de saturar el stack de hardware.

----

Otra cosa mas que cambie fue sacarle los "kbd_init()" dentro de esas funciones, esa funcion solo debe ser llamada al comienzo del programa y nunca mas, ya que esa funcion es para setear los puertos del micro, una ves seteados no deberian tocarse.
« Última modificación: 07 de Julio de 2015, 15:58:51 por KILLERJC »

Desconectado ADY12

  • PIC10
  • *
  • Mensajes: 43
Re: Problema con Menu y Submenu
« Respuesta #2 en: 13 de Julio de 2015, 05:43:24 »
Gracias KILLERJC, el menú solo muestra esto:

Código: [Seleccionar]
void Mostrar_menu_inicial(){
lcd_putc('\f');
lcd_gotoxy(1,1);
printf(lcd_putc,"1. MENU");
lcd_gotoxy(1,2);
printf(lcd_putc,"2. ENVIAR DATOS");
}

En el caso de Obtener_Datos(variable);
He de crear una función que vayan pasando las diferentes variables a medir? (Según se seleccione en el dispositivo)

Algo asi?


Código: [Seleccionar]
void Obtener_datos(variable){
switch(variable){
case 1:
       NTC();
       break;
case 2:
       NIVEL_COMBUSTIBLE();
       break;
case 3:
       VELOCIDAD();
       break;
case 4:
       REVOLUCIONES();
       break;

}

Si lo hago asi, luego me saltan errores, en el MENU_TEMP y en los otros.

« Última modificación: 13 de Julio de 2015, 06:16:11 por ADY12 »

Desconectado ADY12

  • PIC10
  • *
  • Mensajes: 43
Re: Problema con Menu y Submenu
« Respuesta #3 en: 13 de Julio de 2015, 05:57:03 »
i
« Última modificación: 13 de Julio de 2015, 06:15:32 por ADY12 »

Desconectado KILLERJC

  • Colaborador
  • DsPIC33
  • *****
  • Mensajes: 8242
Re: Problema con Menu y Submenu
« Respuesta #4 en: 13 de Julio de 2015, 07:25:18 »
Si es posible pone todo el programa como quedo para saber como va el programa.
Asi como te lo pase yo, solo te quedaria hacer estas funciones:

Citar
Queda realizar las funciones que escriben en el LCD como
Mostrar_menu_inicial();      ( enviar datos y menu)
Mostrar_menu_de_variables();   ( var1 var2 var3 y var4)
Mostrar_Menu_Var();              ( obtener datos y menu )

Y la que obtiene los datos:
Obtener_datos(variable);

Las 3 primeras serian como lo pusiste vos, es decir solo escriben en el LCD, no esperan de ningun dato ni nada por el estilo.
Y la de obtener datos, como bien hiciste es ese switch.

Código: C
  1. void Mostrar_menu_inicial(){
  2.    lcd_putc('\f');
  3.    lcd_gotoxy(1,1);
  4.    printf(lcd_putc,"1. MENU");
  5.    lcd_gotoxy(1,2);
  6.    printf(lcd_putc,"2. ENVIAR DATOS");
  7. }
  8.  
  9. void Mostrar_menu_de_variables(){
  10.    lcd_putc('\f');
  11.    lcd_gotoxy(1,1);
  12.    printf(lcd_putc,"1 a 4 - Variables);
  13.   lcd_gotoxy(1,2);
  14.   printf(lcd_putc,"# - Volver");
  15. }
  16.  
  17. void Mostrar_Menu_Var(){
  18.    lcd_putc('\f');
  19.    lcd_gotoxy(1,1);
  20.    printf(lcd_putc,"1 - OBTENER DATOS");
  21.    lcd_gotoxy(1,2);
  22.    printf(lcd_putc,"# - MENU ANTERIOR");
  23. }

No se como son las funciones de NTC,NIVEL_COMBUSTIBLE,VELOCIDAD y REVOLUCIONES, pero estas deberian solo obtener los datos, actualizar las variables que se necesiten actualizar o mostrar y salir. Si estas funciones estan llamando a MENU_TEMP entonces estan mal

Yo no se por que te tiene que dar error MENU_TEMP, ya que no se utiliza para nada esa funcion en el codigo que pase y no creo que deberias usarla tampoco

Desconectado ADY12

  • PIC10
  • *
  • Mensajes: 43
Re: Problema con Menu y Submenu
« Respuesta #5 en: 15 de Julio de 2015, 06:15:28 »
No consigo, que cuando estas mostrando los datos por la pantalla del LCD, me aparezca una opción en la linea 2 del LCD en ese instante de que me diga si quiero SALIR(volver al menú de variables) o GUARDAR los datos, lo estado probando de hacer un case 3, pero no funciona.

Código: [Seleccionar]
while(TRUE){ 
k=kbd_getc();
if (k!=0 & j!=k){                     
switch(Nivelmenu){
   case 0:
          switch (k){                 
          case '1':
                  Mostrar_menu_de_variables();
                  Nivelmenu=1;
                  break;
          case '2':
                  EnviarDatos();
                  break;
          default:
                  break;
          }
          break;
   case 1:                         
          switch (k){
          case '1':
                  Mostrar_menu_var();
                  variable=1;
                  Nivelmenu=2;
                  break;
          case '2':
                  Mostrar_menu_var();
                  variable=2;
                  Nivelmenu=2;
                  break;
          case '3':
                  Mostrar_menu_var();
                  variable=3;
                  Nivelmenu=2;
                  break;
          case '4':
                  Mostrar_menu_var();
                  variable=4;
                  Nivelmenu=2;
                  break;   
          default:
                 break;
          }
          break;
    case 2:                                     
           switch (k){
           case '1':
                   Obtenerdatos (variable);                                         
                   Nivelmenu=1;                 
                   Mostrar_menu_de_variables();
                   break;
           case '#':                           
                   Mostrar_menu_de_variables();
                   Nivelmenu=1;                 
                   break;
           default:
                  break;
           }
           break;
//!    case 3:                               //Menu de salir o guardar
//!           switch(k){
//!           case 'A':
//!                   Mostrar_salir_o_guardar();
//!                   Nivelmenu=1;             
//!                   Mostrar_menu_de_variables();
//!                   break;
//!           case 'B':
//!                   Mostrar_salir_o_guardar();
//!                   break;
//!           default:
//!                   break;
//!           }
    default:                                 
            Mostrar_menu_inicial();
            Nivelmenu=0;
            break;
}
}
j=k;                                         
}
}

Desconectado KILLERJC

  • Colaborador
  • DsPIC33
  • *****
  • Mensajes: 8242
Re: Problema con Menu y Submenu
« Respuesta #6 en: 15 de Julio de 2015, 07:12:31 »
Con un poco de cambio, hago que el switch se este ejecutando constantemente.
Hay una funcion que le puse "Obtener_datos()" ahi lees todas las entradas calculas y guardas en su correspondientes variables. En esa funcion nada de loops while o for eternos

El if de j y k, hacen que si se mantiene presionada la misma tecla o no se presione nada, j sea igual a 0, lo que hace que caiga en los default break, cuando hay un switch(j), cambie en nivel_menu=2 el switch por un switch(variable) de esa forma como se ejecuta siempre toda la estructura se mantiene el valor ese y se esta continuamente actualizando el valor en el LCD, es decir, la variable se actualiza con Obtener_datos() y el LCD se actualiza con mostrar_variable_x()
Se pregunta si j es igual a # para volver al menu anterior.

Creo que esto es lo que querias hacer.

Código: C
  1. char k,j=0;
  2. int nivel_menu=0,variable;
  3. Bienvenida();                                                           // O Mostrar_menu_inicial();
  4. while(1)
  5. {
  6.         Obtener_datos();                                                //De todas las variables
  7.         k=kbd_getc();
  8.  
  9.         if (k!=0 & j!=k)                                                //Compruebo que se presiono algo Y no sea la misma tecla que la anterior ves,
  10.         {
  11.                 j=k;
  12.         }
  13.         else
  14.         {
  15.                 j=0;
  16.         }
  17.  
  18.         switch(nivel_menu)
  19.         {
  20.         case 0:
  21.                 switch(j)                                               //Menu principal
  22.                 {
  23.                 case '1':
  24.                         Mostrar_menu_de_variables();
  25.                         nivel_menu=1;
  26.                         break;
  27.                 case '2':
  28.                         Enviar_datos();
  29.                         break:
  30.                 default:
  31.                         break;
  32.                 }
  33.                 break;
  34.         case 1:                                                         //Menu de variables, aca muesrto todas las variables para que seleccione una
  35.                 switch(j)
  36.                 {
  37.                 case '1':
  38.                         Mostrar_Menu_Var();
  39.                         variable=1;
  40.                         nivel_menu=2;
  41.                         break;
  42.                 case '2':
  43.                         Mostrar_Menu_Var();
  44.                         variable=2;
  45.                         nivel_menu=2;
  46.                         break;
  47.                 case '3':
  48.                         Mostrar_Menu_Var();
  49.                         variable=3;
  50.                         nivel_menu=2;
  51.                         break;
  52.                 case '4':
  53.                         Mostrar_Menu_Var();
  54.                         variable=4;
  55.                         nivel_menu=2;
  56.                         break;
  57.                 case '#':
  58.                         Mostrar_menu_inicial();
  59.                         nivel_menu=0;
  60.                         break;
  61.                 default:
  62.                         break;
  63.                 }
  64.                 break;
  65.         case 2:                                                         // Muesta de cada variable
  66.                 switch(variable)
  67.                 {
  68.                 case 1:
  69.                         mostrar_variable_1();
  70.                         break;
  71.                 case 2:
  72.                         mostrar_variable_2();
  73.                         break;
  74.                 case 3:
  75.                         mostrar_variable_3();
  76.                         break;
  77.                 case 4:
  78.                         mostrar_variable_4();
  79.                         break;
  80.                 default:
  81.                         break;
  82.                 }
  83.                 if(j=='#')
  84.                 {
  85.                         Mostrar_menu_de_variables();                    // Se muestra el menu anterior y se vuelve a los botones del anterior tmb
  86.                         nivel_menu=1;
  87.                         break;
  88.                 }
  89.                 break;
  90.         default:                                                        // Caso unico que por algun problema se llegue este punto, poniendo a 0 y el nivel y mostrando el mnu inicial
  91.                 Mostrar_menu_inicial();
  92.                 nivel_menu=0;
  93.                 break;
  94.         }
  95. }

Sino algo un poco mas simplificado, al ser tan repetitivo el codigo de cada una de las variables

Código: C
  1. char k,j=0;
  2. int nivel_menu=0,variable;
  3. Bienvenida();                                                           // O Mostrar_menu_inicial();
  4. while(1)
  5. {
  6.         Obtener_datos();                                                //De todas las variables
  7.         k=kbd_getc();
  8.  
  9.         if (k!=0 & j!=k)                                                //Compruebo que se presiono algo Y no sea la misma tecla que la anterior ves,
  10.         {
  11.                 j=k;
  12.         }
  13.         else
  14.         {
  15.                 j=0;
  16.         }
  17.  
  18.         switch(nivel_menu)
  19.         {
  20.         case 0:
  21.                 switch(j)                                               //Menu principal
  22.                 {
  23.                 case '1':
  24.                         Mostrar_menu_de_variables();                    // las 4 variables
  25.                         nivel_menu=1;
  26.                         break;
  27.                 case '2':
  28.                         Enviar_datos();
  29.                         break:
  30.                 default:
  31.                         break;
  32.                 }
  33.                 break;
  34.         case 1:                                                         //Menu de variables, aca muesrto todas las variables para que seleccione una
  35.                 if(j=='#')
  36.                 {
  37.                         nivel_menu=0;                                   //En caso que se presiono # cambio menu y salgo
  38.                         break;
  39.                 }
  40.                 if(j<='4' && j>='0')
  41.                 {
  42.                         variable=j-'0';
  43.                         nivel_menu=2;
  44.                         mostrar_variable(variable);
  45.                 }
  46.                 break;
  47.         case 2:                                                         // Menu de cada variable, todas tienen 2 opciones, obtener datos y salir al menu anterior
  48.                 if(j=='#')
  49.                 {
  50.                         nivel_menu=1;
  51.                         Mostrar_menu_de_variables();                    // las 4 variables
  52.                         break;
  53.                 }
  54.                 mostrar_variable(variable);
  55.                 break;
  56.         default:                                                        // Caso unico que por algun problema se llegue este punto, poniendo a 0 y el nivel y mostrando el mnu inicial
  57.                 Mostrar_menu_inicial();
  58.                 nivel_menu=0;
  59.                 break;
  60.         }
  61. }

Luego haces una interrupcion para que te lo envie a esos datos cada X tiempo, mientras el micro sigue tomando muestras
« Última modificación: 15 de Julio de 2015, 07:15:55 por KILLERJC »

Desconectado ADY12

  • PIC10
  • *
  • Mensajes: 43
Re: Problema con Menu y Submenu
« Respuesta #7 en: 16 de Julio de 2015, 17:04:47 »
KillerJC, una pregunta, en lugar de realizar una interrupción para que envié los datos cada X tiempo, se podria utilizar el REAL TIME OPERATING SYSTEM? O es mas sencillo realizar-lo con la interrupción cada X tiempo.


Desconectado KILLERJC

  • Colaborador
  • DsPIC33
  • *****
  • Mensajes: 8242
Re: Problema con Menu y Submenu
« Respuesta #8 en: 16 de Julio de 2015, 18:09:32 »
Eso depende de tu gusto ADY12.

Hay gente que se acostumbra a manejarse con un RTOS y luego para todo lo utiliza. Un RTOS utiliza un timer para que por ejemplo cada 10ms o 1ms se produzca una interrupcion y asi el cambio de tareas (es decir codigos), tiene otra forma de programacion, es decir cada tarea deberia estar encerrada en un while, normalmente no se usan variables globales sino que son semaforos, queue, etc. Tambien requiere mas uso de memoria y tiempo del micro, debido a que deberia mover los stack que configura C para cada tarea. A no ser que los stack sean fijos y solo mueva la direccion de comienzo de los mismos.

Si vos deseas hacerlo con esto es completamente tu desicion, creo que CCS tiene un RTOS, yo jamas lo he usado. Solo use FreeRTOS en un ARM pero para aprender y luego pienso usarlo en un programa.

Ahora si decidis usar una interrupcion, no se que PIC tendras, pero si posee CCP se hace mucho mas facil ya que es configurar el CCP para que interrumpa y limpie solo el TMR, asi te ahorras de estar cargandolo etc. y el codigo de interrupcion seria algo asi:
(El codigo es solo de ejemplo, lo mas seguro que no funciona por que no use CCS y no se las directivas)
Supongo que tenes un cristal de 4Mhz, con eso podes hacer una interrupcion cada 0.5s, si tenes 8Mhz es cada 0.25s

Código: C
  1. #INT_CCP
  2. void isr(void){
  3.  if(j==10)
  4.  {
  5.    enviar_datos();
  6.    j==0;
  7.   }
  8.  else
  9.  {
  10.      j++;
  11.   }
  12. }

Y se agregarian unas 6/7 instrucciones de configuracion del CCP, y del TMR + interrupciones. (Esto es por unica vez apenas comienza el main() )
Si tenes un Timer nomas, entonces es exactamente lo mismo, nomas que ademas tenes que poner una instruccion de carga del timer. y con eso tendrias toda la interrupcion.

Lo que hagas Es decision pura y exclusivamente tuya. Si deseas aprender que es un RTOS entonces vas a tener que leer un poco mas sobre estos y comenza con ejemplos basicos, PD: en los RTOS tambien se usan interrupciones.

Desconectado ADY12

  • PIC10
  • *
  • Mensajes: 43
Re: Problema con Menu y Submenu
« Respuesta #9 en: 21 de Julio de 2015, 06:19:29 »
Hola KILLERJC, finalmente lo he hecho por ccp2 (tengo el pic18F4550 y el cristal de cuarzo que tengo es de 20MHz), lo he probado en un programa simple al principio y funciona correctamente. 

Por otro lado el menú según los cambios que me aconsejaste (para que las variables continuamente estuvieran funcionando)  para que tuviera la opción de salir cuando esta mostrando por LCD, se me queda pillado en el menu_principal, es decir, en el case, solo muestra 1.MENU 2.ENVIAR DATOS, pulsando cualquier tecla y no avanza. Estuve mirando si podian ser el if de k=j i tal, pero continuava igual. Prove el programa que tenia al principio que los datos no se actualizaban constantemente y funcionaba, pero este al seguir tus pasos no tiraba.

codigo Temperaturamotor
Código: [Seleccionar]
void TEMPERATURA_MOTOR(){
set_adc_channel(0);              //Habilita canal 0
delay_us(10);
do {
   q= Read_ADC(); //Valor que lee el ADC
   VT=5.0*q/1024.0;//Realiza conversion
   R1=10000;
   V=5.0;
   RT=VT*R1/(V-VT);
   B=4300;
   TO=25;
   TOK=TO+273.15;
   RO=10000;            //Resistencia 10 K a 25ºC
   TK=1/((1/B)*log(RT/RO)+(1/TOK));
   TC=TK-273.15;
 
   }
while(k=='\0');
}

codigo mostrar_variable_X:
Código: [Seleccionar]
void mostrar_variable_1(){
printf(lcd_putc, "TEMP = %04.1f ºC",TC);
}

codigo main:
Código: [Seleccionar]
while(TRUE){
Obtenerdatos(variable);
k=kbd_getc();

if (k!=0 & j!=k)
{
j=k;
}
else
{
j=0;
}
             
switch(Nivelmenu){
   case 0:
          switch (j){                 
          case '1':
                  Mostrar_menu_de_variables();
                  Nivelmenu=1;
                  break;
          case '2':
                  EnviarDatos();
                  break;
          default:
                  break;
          }
          break;
   case 1:                         
          switch (j){
          case '1':
                  Mostrar_menu_var();
                  variable=1;
                  Nivelmenu=2;
                  break;
          case '2':
                  Mostrar_menu_var();
                  variable=2;
                  Nivelmenu=2;
                  break;
          case '3':
                  Mostrar_menu_var();
                  variable=3;
                  Nivelmenu=2;
                  break;
          case '4':
                  Mostrar_menu_var();
                  variable=4;
                  Nivelmenu=2;
                  break;   
          default:
                 break;
          }
          break;
    case 2:                                     
           switch (variable){
           case '1':
                   mostrar_variable_1();                   
                   break;
           case '2':
                   mostrar_variable_2();                   
                   break;
           case '3':
                   mostrar_variable_3();                   
                   break;
//!           case '4':
//!                   mostrar_variable_1();                   
//!                   break;
           default:
                  break;
           }
           if (j=='#')
           {
                   Mostrar_menu_de_variables();
                   Nivelmenu=1;
                   break;
           }
           break;

    default:                               
            Mostrar_menu_inicial();
            Nivelmenu=0;
            break;
}
}
//j=k;                                       
}

Desconectado ADY12

  • PIC10
  • *
  • Mensajes: 43
Re: Problema con Menu y Submenu
« Respuesta #10 en: 21 de Julio de 2015, 06:54:01 »
Acabo de realizar una prueba, poniendo entre comentarios el Obtenerdatos(); puedo entrar en el menu de variables, y luego en el menu_de_var, sin poder ver las medidas por el LCD, porque picando en el 1 no hace, sin embargo puedo volver atras. Puede que sea que Obtenerdatos(); este mal planteado?
Quitee el int variable de dentro del Obtenerdatos, pero con el dentro tampoco funciona
Código: [Seleccionar]
void Obtenerdatos(){
switch(variable){
case 1:
       TEMPERATURA_MOTOR();
       break;
case 2:
       NIVEL_COMBUSTIBLE();
       break;
case 3:
       TACOMETRO();
       break;
case 4:
       TEMPERATURA_AMBIENTE();
       break;
}
}

Desconectado KILLERJC

  • Colaborador
  • DsPIC33
  • *****
  • Mensajes: 8242
Re: Problema con Menu y Submenu
« Respuesta #11 en: 21 de Julio de 2015, 07:38:20 »
Si, obtenerdatos() deberia actualizar TODOS, no solo esa variable, seria algo masomenos asi:

Código: C
  1. void Obtenerdatos(){
  2.        TEMPERATURA_MOTOR();
  3.        NIVEL_COMBUSTIBLE();
  4.        TACOMETRO();
  5.        TEMPERATURA_AMBIENTE();
  6. }

Obviamente ninguna de esas funciones de adentro puede tener un while(1)

Desconectado ADY12

  • PIC10
  • *
  • Mensajes: 43
Re: Problema con Menu y Submenu
« Respuesta #12 en: 21 de Julio de 2015, 12:12:54 »
Citar
Obviamente ninguna de esas funciones de adentro puede tener un while(1)

KILLERJC, pero en la funcion TEMPERATURA_MOTOR, me pide que haya un while, sino lo pongo da error.

Lo unico seria hacerlo con un for(;;) que no tiene while, pero tampoco funciona correctamente, se queda en el primer menu.
« Última modificación: 21 de Julio de 2015, 12:26:05 por ADY12 »

Desconectado KILLERJC

  • Colaborador
  • DsPIC33
  • *****
  • Mensajes: 8242
Re: Problema con Menu y Submenu
« Respuesta #13 en: 21 de Julio de 2015, 20:38:09 »
un for( ; ; ) es equivalente a un while().

Y no debes poner un while en esa funcion. el mismo while(1) del main lo va a estar actualizando.

Para que se entienda el programa quedo resumiendolo en:

Código: C
  1. main() {
  2. while(1)
  3. {
  4.    Tomo_datos()          // TODOS LOS DATOS 1 vez
  5.    Se_presiono_algo()   // me fijo si se presiono algo
  6.    Muestro_en_lcd()     // Aca muestra en el LCD si es que se presiono algo o se esta mostrando las variables
  7. }
  8. }

Entonces ese while(1) es el que va a hacer que constantemente se tome los datos de todos, motor,combustible,temperatura,tacometro,etc. Luego que se tomaron todos los datos se mostraran o no.Mientras que no se presione nada el LCD no se va a actualizar y queda casi igual que si fuera un while(1) { Tomo_datos() } , cuando se presione algo ademas de tomar los datos mostras en el LCD, Si estas mostrando una varaible, el LCD se va a actualizar siempre con los valores nuevos que se tomo al principio.

Desconectado ADY12

  • PIC10
  • *
  • Mensajes: 43
Re: Problema con Menu y Submenu
« Respuesta #14 en: 22 de Julio de 2015, 05:35:45 »
Pero haber porque no te estoy entendiendo, si yo en el temperatura motor no pongo un while el programa me da error, expect a while. Tu me estas hablando del main, que tiene el while, vale pero en la función TEMPERATURA_MOTOR ha de contener un while.

Código: [Seleccionar]
void TEMPERATURA_MOTOR(){
set_adc_channel(0);              //Habilita canal 0
delay_us(10);
do{
   q= Read_ADC(); //Valor que lee el ADC
   VT=5.0*q/1024.0;//Realiza conversion
   R1=10000;
   V=5.0;
   RT=VT*R1/(V-VT);
   B=4300;
   TO=25;
   TOK=TO+273.15;
   RO=10000;            //Resistencia 10 K a 25ºC
   TK=1/((1/B)*log(RT/RO)+(1/TOK));
   TC=TK-273.15;
   }
while(1);
}

Todo es problema de obtener datos para que pueda entrar en el menú.


 

anything