ATmega32_LED_MENU

Čau lidi.

potřeboval bych udělat takové menší menu, které se bude projevovat na LED HD44780. Respektive při stisknutí TL1 se mi budou točit 2 možnosti. U těchto možností by mělo jít pomocí TL3 a TL4 zvyšovat nebo snižovat hodnotu. A TL2 by mělo toto nastavení uložit.

Nevíte někdo?

Má to být dělané na projekt Termostatu, kde již mám vytvořený kód na ukazování aktuální teploty na LCD.

Díky moc za rady

Mělo by to tedy být v jazyku C, pokud je to možné.

Ahoj.
Jednoduche menu si dokazes udelat sam.
Nicmene muzes dat tlacitko hledat a tam zadat menu, je tam dalsi priklad.
Komplexnejsi menu, ktere pouzivam ja je treba tady fourwalledcubicle.com/AVRCodeSamples.php
Nebo zadat do googlu avr menu.
Nicmene stejne si to budes muset dodelat aby to vyhovovalo tvemu pripadu.

No právě mi nejde udělat. Nenapadá mě vubec jak na to. No a když hledám tady další příklady tak taky tam nejsou nějak kompletní.

[code]void tlacidla (void)
{
if (!ok) clrdsp();
if (!c) clrdsp();
if (!up) clrdsp();
if (!down) clrdsp();

switch (mode)
	{
	case 254:{if (!ok) 	{menu1();}
			  if (!c) 	{off251();}
			  if (!up) 	{tplus249();}
			  if (!down){tminus248();}
			break;}

	case 253:{if (!ok) {hodn247();}
			  if (!c) 	{menu254();}
			  if (!up) 	{prog246();}
			  if (!down){prog246();}
			break;}

	case 249:{if (!c) 	{menu254();}
			break;}

	case 247:{if (!ok) 	{nden243();}
			  if (!c) 	{time253();}
			  if (!up) 	{minp244();}
			  if (!down){hodp245();}
			break;}

	case 246:{if (!ok) 	{nponpia242();}
			  if (!c) 	{menu254();}
			  if (!up) 	{time253();}
			  if (!down){time253();}
			break;}

	case 242:{if (!ok) 	{hk241();}
			  if (!c) 	{prog246();}
			  if (!up) 	{nsobned240();}
			  if (!down){nsobned240();}
			break;}

	case 241:{if (!ok) 	{tk239();}
			  if (!c) 	{ponsob();}		//;vyber ci ma ist na pon alebo sob
			  if (!up) 	{hkp237();}
			  if (!down){hkm238();}
			break;}

	case 240:{if (!ok) 	{hk241();}
			  if (!c) 	{prog246();}		
			  if (!up) 	{nponpia242();}
			  if (!down){nponpia242();}
			break;}

	case 239:{if (!ok) 	{onk236();}
			  if (!c) 	{hk241();}		
			  if (!up) 	{tkp234();}
			  if (!down){tkm235();}
			break;}

	case 236:{if (!ok) 	{save233();}
			  if (!c) 	{tk239();}		
			  if (!up) 	{onk231();}
			  if (!down){offk232();}
			break;}
	}
return;
}

void menu1 (void)
{
if (manualne)
{manualne=0;
nauto();
viewlcd();
__delay_ms(1000);
clrdsp();
tltest();}
else
{prog246();}
return;
}

void ponsob (void)
{
if (eram==1) nsobned240();//nponpia242();
else nponpia242();//nsobned240();
return;
}

void menu254 (void)
{
mode=254;
tltest();
return;
}

void time253 (void)
{
mode=253;
ntime();
tltest();
return;
}

void off251 (void)
{mode=254;
if(!nzv)
{nzv=1;
non();
__delay_ms(1000);
clrdsp();
}else
{
nzv=0;
dat3=0;
}
tltest();
return;
}

void tplus249 (void)
{
if (nzv)
{mode=254;
teplotaplus();
tnastavena();

	 nmanual();
	 manualne=1;
	 }
	 tltest();
return;
}

void tminus248 (void)
{
if (nzv)
{mode=254;
teplotaminus();
tnastavena();

	 nmanual();
	 manualne=1;
	 }
	 tltest();
return;
}

void hodn247 (void)
{mode=247;
ncasden();
return;
}
void ncasden (void)
{
// unsigned char denx;
eprom(0,0x71,16); //napis nastav cas a den
adresadna();
eprom(0,denx,6);
viewlcd();
tltest();
return;
}

[/code]

sand ti princip bude jasny.
Inak je t oasi najhorsia moznost ako to stvorit.

Urob si stromcek tj menu na papier kazdemu okienku prirad cislo. napr hlavne okno 1, nastavenie casu2, nastavenie budika 3. atd

To je hrozně zmatený. Moc se v tom nevyznám

A co třeba nějak takhle …

Definice typů a proměnných

[code]typedef struct // Položka menu
{
char *ItemText; // Text položky, pokud není definovaná programově generovaná položka.
void (*UserPaintLine)(void); // Programově generovaný text položky (třeba položka obsahující v textu nastavovanou hodnotu)
void *OnEnterKey; // Které menu se má zobrazit při krátkém stisku Enter.
void *OnLongEnterKey; // Které menu se má zobrazit při dlouhém stisku Enter.
void (*OnEnterCall)(void); // Funkce, která se zavolá při stisku Enter.
} MenuItemStruct;

typedef struct // Struktura menu
{
unsigned char ItemCount; // Počet položek
unsigned char ItemIndex; // Index vybrané položka
char *MenuLabel; // Záhlaví menu
void *OnEscapeKey; // Nadřazené menu (NULL = žádné)
void *OnLongEscapeKey; // Dlouhý stisk Escape (NULL = žádné)
MenuItemStruct MenuItem[4]; // Položky menu (počet položek odpovídá nejdelšímu menu
unsigned char TopIndex; // Index (0…x) první zobrazené položky (pro scrolování menu)
} MenuStruct;

MenuStruct *ActiveMenu; // Pointer na proměnnou aktuálně zobrazeného menu (NULL = žádné menu nezobrazeno)
[/code]

Zobrazovací rutina

[code]void UserMenu( void )
{
if (ActiveMenu!=NULL)
{
char Line = 0;

	if ( ActiveMenu->MenuLabel != NULL )
	{
		LCD_GotoXY(Line++, 0);
		LCD_Write_PM_String(ActiveMenu->MenuLabel);
	}

	volatile char PrintedMenuLine=ActiveMenu->TopIndex ;
	
	while((Line < 4)&&(PrintedMenuLine < ActiveMenu->ItemCount ))
	{
		if ( ActiveMenu->MenuItem[PrintedMenuLine].UserPaintLine != NULL )
		{
			LCD_GotoXY(Line++, 1);
			ActiveMenu->MenuItem[PrintedMenuLine].UserPaintLine();
		}
		else
		{
			if ( ActiveMenu->MenuItem[PrintedMenuLine].ItemText != NULL )
			{
				LCD_GotoXY(Line++, 1);
				LCD_Write_PM_String(ActiveMenu->MenuItem[PrintedMenuLine].ItemText);
			}
		}
		if ( PrintedMenuLine == ActiveMenu->ItemIndex )
		{
			LCD_GotoXY(Line-1, 0);
			LCD_Data = 0;
			LCD_Write_Data();
		}
		PrintedMenuLine++;
	}

}

}
[/code]

Hlavní program

// Deklarace textů položek menu.
const PROGMEM char MenuItemText][17] = {\
											"  Hlavni menu   ", "Polozka hl. 1  ", "Polozka hl. 2  ", "Polozka hl. 3  ", \
											"  Podmenu 1     ", "Polozka pm. 1-1", "Polozka pm. 1-2", "Polozka pm. 1-3", \
											"  Podmenu 2     ", "Polozka pm. 2-1", "Polozka pm. 2-2", "Polozka pm. 2-3", \
											"Polozka pm. 2-4", "Polozka pm. 3-1", "Polozka pm. 3-2", "Polozka pm. 3-3"  \
										};

MenuStruct HlavniMenu, Podmenu1, Podmenu2;	// Deklarace tří menu

int main(void)
{

// Nastavit hlavní menu	
	HlavniMenu.ItemIndex = 0;
	HlavniMenu.ItemCount = 2;
	HlavniMenu.MenuLabel = MenuItemText[0];
	HlavniMenu.MenuItem[0].ItemText = MenuItemText[1];
	HlavniMenu.MenuItem[1].ItemText = MenuItemText[2];
	HlavniMenu.MenuItem[2].ItemText = MenuItemText[3];
	HlavniMenu.MenuItem[0].OnEnterKey = &Podmenu1;
	HlavniMenu.MenuItem[1].OnEnterKey = &Podmenu2;
	
// Nastavit podmenu 1
	Podmenu1.ItemIndex = 0;
	Podmenu1.ItemCount = 2;
	Podmenu1.MenuLabel = MenuItemText[4];
	Podmenu1.MenuItem[0].ItemText = MenuItemText[5];
	Podmenu1.MenuItem[0].UserPaintLine = NapisTestovaciRadekMenu;
	Podmenu1.MenuItem[1].ItemText = MenuItemText[6];
	Podmenu1.MenuItem[2].ItemText = MenuItemText[7];
	Podmenu1.OnEscapeKey = &HlavniMenu;
	
// Nastavit podmenu 2
	Podmenu2.ItemIndex = 0;
	Podmenu2.ItemCount = 4;
	Podmenu2.MenuLabel = MenuItemText[8];
	Podmenu2.MenuItem[0].ItemText = MenuItemText[9];
	Podmenu2.MenuItem[1].ItemText = MenuItemText[10];
	Podmenu2.MenuItem[2].ItemText = MenuItemText[11];
	Podmenu2.MenuItem[3].ItemText = MenuItemText[12];
	Podmenu2.OnEscapeKey = &HlavniMenu;
	
// Zvolit hlavní menu
	ActiveMenu = &HlavniMenu;
	
// Zobrazit zvolené menu
	UserMenu();

.
.
.
.
.

Zobrazovací rutina i obsluha vstupů (tlačítka, rotační koder, dotykový panel atd.) je společná pro všechna menu. Přepínání jednotlvých menu se děje jenom přepnutím jednoho pointeru.

Psané je to v Atmel Studiu 7.

Daj vyvojovy diagram nieco zbucham.

To Vica :

  1. Původně jsi chtěl nasměrovat, abys měl představu, jak to napsat - to si myslím, že ukázka ve fóru splňuje.
  2. Přišel jsi na to, proč Ti to nejde vložit do Tvého projektu ? Skončil jsi na tom, že nevíš, kam máš napsat definici typů a proměnných nebo až na tom, že Ti chybí knihovna pro obsluhu LCD ?

Snaž se a my Ti tady poradíme, nasměrujeme a pomůžeme. Když Ti to někdo napíše, tak se toho moc nenaučíš.

Nojo, konec roku se blíží, školní práce hotové nejsou…

Ako su prisiel na to ze to je do skoly?

Zatím mám todle, ale nejde mi to přenést na LCD display

[code]#include <avr/io.h>
#include <util/delay.h>
#include <stdio.h>
#include <stdlib.h>

#include “dallas_one_wire.h”
#include “HD44780.h”
#include “crc8.h”

void scan_button(void);//
void switch_number(uint8_t show_number);

int button_state;
int prev_button_state;
int number;
int i;

int main ( void )
{

DDRB &= ~(1 << PINB0);
PORTB |= 1 << PINB0;
button_state = 1;

while(1)
{		
	scan_button();// funkce pro testování stisknutého tlačítka
	_delay_ms(10);//čekání 10ms;
}
return 0;

}

///////////////////////// OŠETŘENÍ ZÁKMITU TLAČÍTKA /////////////////////////////
void scan_button(void)
{
prev_button_state=button_state;
button_state=PINB;

button_state &= 0b00000001;

if (button_state == 0)
{
	if (prev_button_state == 1)
	{
	_delay_ms(150);	
	}
}	
else
{
	if (prev_button_state == 0)
	{
	_delay_ms(150);
	}
}

}

 void switch_number(uint8_t show_number)
 {	 
	 switch(show_number)
	 {
	 case 1:
	LCD_Clear(); 
	LCD_Initalize();
	LCD_GoTo(0,0);
	LCD_WriteText("  Zadana Hodnota  ");
	break;
	
	case 2:
	LCD_Clear(); 
	LCD_Initalize();
	LCD_GoTo(0,0);
	LCD_WriteText("  Hysterze  ");
	break;
	
	default:
	LCD_Clear();  
	LCD_Initalize();
	LCD_GoTo(0,0);
	LCD_WriteText("  ASD  ");
	break;
	 
	 }
 }[/code]

LCD_Initalize(); t osnad staci inicializovat raz na zaaciatku vecinou pred MAIN, tj while

Nikde nevidim nastavenie portu, input ouput???

V tom LCD H subore sa budu definovat piny na LCD

  1. Ať se koukám, jak chci, tak nikde nevidím volání funkce switch_number.
  2. Po zapnutí musíš nějakou dobu počkat, než začneš komunikovat s LCD displejem. Minimální čas, potřebný pro start kontroleru displeje, se dočteš v datasheetu.
  3. Jak psal Atlan - displej stačí inicializovat jednou na začátku.

Řekl bych, že je použití menu souvisí s tématem Prosba_Termostat. Tam je vidět, že ovládání displeje si porty nastaví podle konfigurace v HD44780.H souboru - a z použití kitu EvB 4.3 bych také (jako Radius) hádal na školní zadání. I když samozřejmě není vyloučeno, že by si kit někdo domů pořídil.

Mimochodem - u ovládání jakýchkoliv periferií je základem ČÍST DATASHEETY a ne stahovat knihovny po Internetu. Protože i když stahneš nejakou knihovnu, měl bys vědět, jak ta periferie fuguje pro případ, že bude něco špatně.

if(menu==0) {if (!tl1) {menu++;napiszadanahodnota();} Else napispracujem(); } if(menu==1) {if (!tl1) {menu++;napishystrezia();} if (!tl3) teplotaminus(); if (!tl4) teplotaplus(); if (!tl2) uloznastavenia(); } if(menu==2) {if (!tl1) {menu=0;} if (!tl3) hysterizaminus(); if (!tl4) hysterizaplus(); if (!tl2) uloznastavenia(); }