[C] Zobrazování nesmyslných hodnot na LCD – Mikrokontroléry – Fórum – Programujte.com
 x   TIP: Přetáhni ikonu na hlavní panel pro připnutí webu

[C] Zobrazování nesmyslných hodnot na LCD – Mikrokontroléry – Fórum – Programujte.com[C] Zobrazování nesmyslných hodnot na LCD – Mikrokontroléry – Fórum – Programujte.com

 

jirkaj40
Newbie
21. 4. 2013   #1
-
0
-

Ahojte.

Chtěl bych se zeptat. Napsal jsem si jednoduchý prográmek (časovač). Ale mám problém, že pouze ve funkci nastaveni_casu() se mi zobrazují nesmyslné znaky na LCD. Však video je za víc než ticíc slov.

http://www.youtube.com/watch?v=tob1o02Rk2M&feature=youtu.be

No funkce vypadá takto:

/****************************************************
***************fce pro nastaveni casu osvitu*********
****************************************************/
void nastaveni_casu(void)
{
		//hodiny
		if (flag==2){
			lcd_gotoxy(0,0);
			lcd_puts("nastaveni hodin ");
				//nastaveni sekund probiha v preruseni
			lcd_gotoxy(0,1);
			sprintf(buffer,"    %02d:%02d.%02d    ",hodiny,minuty,sekundy);
			lcd_puts(buffer);
		}
		//minuty
		if (flag==3){
			lcd_gotoxy(0,0);
			lcd_puts("nastaveni minut ");
				//nastaveni sekund probiha v preruseni
			lcd_gotoxy(0,1);
			sprintf(buffer,"    %02d:%02d.%02d    ",hodiny,minuty,sekundy);
			lcd_puts(buffer);
		}
		//sekundy
		if (flag==4){
			lcd_gotoxy(0,0);
			lcd_puts("nastaveni sekund");
				//nastaveni sekund probiha v preruseni
			lcd_gotoxy(0,1);
			sprintf(buffer,"    %02d:%02d.%02d    ",hodiny,minuty,sekundy);
			lcd_puts(buffer);

			//ulozani hodnoty hodiny,minuty, sekundy pro pozdejsi praci
				pom_h=hodiny;
				pom_m=minuty;
				pom_s=sekundy;
			//ulozani hodnoty hodiny,minuty, sekundy pro pozdejsi praci	
				hod=hodiny;
				min=minuty;
				sek=sekundy;

			cas=( 3600 * (long)hodiny) + ( 60 * (long)minuty) + (long)sekundy;	//prevod hodnot hod, min, sek na CAS
		}
}

prvně jsem zde měl i nastavování těchto hodnot. Ale přenusul jsem je do přerušení. Ale ani toto nepomohlo.

Tato funkce je stále dokola volaná z nekonečné funkce ještě s ostatníma funkcema, které fungují správně.

hodnota flag je měněná při stlačení tlačítka. Takt MCU mám 16MHz.

Nahlásit jako SPAM
IP: 89.102.184.–
KIIV
~ Moderátor
+43
God of flame
21. 4. 2013   #2
-
0
-

jak ti psali na avr freaks.. vypada ze se ti do toho cpe spis neco jako nejaky tlacitko (mozna to, ktery pouzivas na prepinani rezimu), pricitani casu vypada ze nic takovyho nedela.. . bych se zameril na to... taky co vse mas v preruseni ... jestli neco jeste nevypisujes i tam a pak se to popere... + se muze smatat do bufferu, kdo vi kde... nejakej buffer overrun nekde jinde a tak dale.. funkce jako takova vypada v pohode... jak uz bylo receno...

Nahlásit jako SPAM
IP: 94.113.92.–
Program vždy dělá to co naprogramujete, ne to co chcete...
jirkaj40
Newbie
21. 4. 2013   #3
-
0
-

V přerušení je toto. A nic tam nevypisuju.

ISR(TIMER0_COMP_vect){ 		//přerušení od čítače časovače 0
	//ošetření tlačítka a jeho zákmitů
	  if((PIND & (1 << tlacitko))){
	        if(tlac_prodleva<20) tlac_prodleva++;
	        if(tlac_prodleva==19) tlac_present=1;  
      }
      else{	
	        if(tlac_prodleva==20){		//sem se dostane pouze pri stisku tlacitka
		    
				if (flag==0){rozmer_dps=encoder;encoder=0;}	//ulozeni rozmeru DPS
				if (flag==1){oboustr=encoder;encoder=hodiny;}	//ulozeni oboustrane DPS		
				if (flag==2){encoder=minuty;}					//resetuje hodnotu v enkoderu
				if (flag==3){encoder=sekundy;}
				if (flag==4){encoder=0;}

				flag++;		//zvyseni pri stisku tlacitka
	            }       
	        tlac_prodleva=0;
				
        }
			
			//nastaveni casu
		if (flag==2){	//nastaveni hodin
			hodiny=encoder;
			if (hodiny>=24){hodiny=0;encoder=0;}
		}
		if (flag==3){	//nastaveni minut
			minuty=encoder;
			if (minuty>=60){minuty=0;encoder=0;}
		}
		if (flag==4){	//nastaveni sekund
			sekundy=encoder;
			if (sekundy>=60){sekundy=0;encoder=0;}
		}
}
Nahlásit jako SPAM
IP: 89.102.184.–
KIIV
~ Moderátor
+43
God of flame
21. 4. 2013   #4
-
0
-

kazdopadne chyba muze byt nekde jinde v kodu...

(prepisovani promennych a tak)

Nahlásit jako SPAM
IP: 94.113.92.–
Program vždy dělá to co naprogramujete, ne to co chcete...
jirkaj40
Newbie
21. 4. 2013   #5
-
0
-

   

Ne jednou jsem ten kód kontroloval.    Ale jak to tak u mě typuju, tak to bude nějaká blbost.

Teď už jenom zjistit, kde ta chyba je.

Nahlásit jako SPAM
IP: 89.102.184.–
jirkaj40
Newbie
21. 4. 2013   #6
-
0
-

Třeba tam někdo najde chybu hned při prvním ohledání. Ono jak do toho člověk hledí příliš dlouho tak tu chybu ani nevidí.

#include <stdlib.h>
#include <avr/io.h>
#include <avr/pgmspace.h>
#include <avr/interrupt.h>
#include <stdio.h>
#include <util/delay.h>  

#include "lcd.h"

//DEsky
#define 	mala_dps		0
#define 	vetsi_dps		1
#define		nejvetsi_dps	6
#define		oboustrana		7
#define		viko			6
#define		tlacitko		3

//prednastaveni casu
volatile unsigned char  hodiny=0; 
volatile unsigned char  minuty=2; 
volatile unsigned char  sekundy=30;

//globalni a jiné proměnné
unsigned char temp;
char buffer[16];
int jednou=0;	//promenna pro zobrazeni upozorneni na nezavrene viko

volatile char encoder=0;		//hodnota enkoderu
volatile char rozmer_dps=0;
volatile char oboustr=0;

volatile unsigned char hod=0, min=0, sek=0, pom_h=0, pom_m=0, pom_s=0;

//============================================================================
//==============================INICIALIZACE==================================
//============================================================================
void inicializace()
{
	hod=hodiny; min=minuty; sek=sekundy;

	//nastaveni vstupnich pinu portu D
	DDRD &= ~(1 << PD0);	//enkoder	
	DDRD &= ~(1 << PD2);	//enkoder
	DDRD &= ~(1 << tlacitko);	
	DDRD &= ~(1 << viko);
		//povoleni vnitřních pull-up odporu
	PORTD |= (1 << PD0);
	PORTD |= (1 << PD2);
	PORTD |= (1 << tlacitko);
	PORTD |= (1 << viko);
		//zakazani vnitrnich pull-up odporu
	PORTC &= ~(1 << mala_dps);
	PORTC &= ~(1 << vetsi_dps);	
	PORTC &= ~(1 << nejvetsi_dps);
	PORTC &= ~(1 << oboustrana);
		//nastaveni vystupnich pinu portu D
	DDRC |= (1 << mala_dps) | (1 << vetsi_dps) | (1 << nejvetsi_dps) | (1 << oboustrana);
		//nastaveni PULL-UP odporu
	//PORTC |= (1 << mala_dps) | (1 << vetsi_dps) | (1 << nejvetsi_dps) | (1 << oboustrana);
		//nastaveni preruseni od enkoderu
	MCUCR|=(1<<ISC01)|(1<<ISC00);   //Nastaveni INT0 na "rising" signal na pinu PD2
	GICR |=(1<<INT0 );				//povoleni preruseni
		//nastaveni preruseni od citace casovace 1 (cas)
	TCCR1B |= (1 << CS12); 			//preddelička 256 (16us)
	TIMSK  |= (1 << TOIE1); 		//prerušeni pri pretečení TCNT1    
		//nastaveni preruseni od citace casovace 0 (tlacitko)
	TCCR0 |= (1<<WGM01)|(1<<CS02)|(1<<CS00); 	//CTC mode, preddelicka 1024 (64us)
	OCR0=255;						//cca 16,384ms pro kontrolu tlačítka
	TIMSK  |= (1 << OCIE0);
		//Nataveni displeje a prvni zobrazeni
	lcd_init(LCD_DISP_ON);            //Init LCD
	lcd_clrscr();

	//lcd_init(LCD_DISP_ON_CURSOR_BLINK);	//blikání kurzoru
	
	sei();    //povoleni přerušení
}

//============================================================================
//==================================PRERUSENI=================================
//============================================================================
volatile unsigned char 	tlac_prodleva,tlac_present;
volatile long int cas=0;
volatile unsigned int pomoc=5, pomoc_2=0;
volatile unsigned char flag=0, hotovo=0, zadej_cas=0;	//stisk tlacitka


ISR (INT0_vect)		//ratační enkoder (vlevo/vpravo) ======= PD0 & PD2
    {
		cli();
	if (((PIND&0x01)==0x00)&&(encoder<9999)) encoder=encoder+1;      //inc
	if (((PIND&0x01)==0x01)&&(encoder > 0 )) encoder=encoder-1;      //dec 
		sei();
    }

ISR (TIMER1_OVF_vect){ 
	TCNT1 = 3036;	//preteceni kazdou 1s
	if ( ((PIND & (1 << viko))==0) && (flag>=5)){
		if (cas!=0){cas--;} 
			else {
				void (*fn_ptr) (void) = (void (*) (void)) 0;	//reset MCU
				fn_ptr();
			}
	}
}

ISR(TIMER0_COMP_vect){ 		//přerušení od čítače časovače 0
	//ošetření tlačítka a jeho zákmitů
	  if((PIND & (1 << tlacitko))){
	        if(tlac_prodleva<20) tlac_prodleva++;
	        if(tlac_prodleva==19) tlac_present=1;  
      }
      else{	
	        if(tlac_prodleva==20){		//sem se dostane pouze pri stisku tlacitka
		    
				if (flag==0){rozmer_dps=encoder;encoder=0;}	//ulozeni rozmeru DPS
				if (flag==1){oboustr=encoder;encoder=hodiny;}	//ulozeni oboustrane DPS		
				if (flag==2){encoder=minuty;}					//resetuje hodnotu v enkoderu
				if (flag==3){encoder=sekundy;}
				if (flag==4){encoder=0;}

				flag++;		//zvyseni pri stisku tlacitka
	            }       
	        tlac_prodleva=0;
				
        }
			
			//nastaveni casu
		if (flag==2){	//nastaveni hodin
			hodiny=encoder;
			if (hodiny>=24){hodiny=0;encoder=0;}
		}
		if (flag==3){	//nastaveni minut
			minuty=encoder;
			if (minuty>=60){minuty=0;encoder=0;}
		}
		if (flag==4){	//nastaveni sekund
			sekundy=encoder;
			if (sekundy>=60){sekundy=0;encoder=0;}
		}
}

//============================================================================
//==================================FUNKCE====================================
//============================================================================


/****************************************************
****************fce pro zadani velikosti DPS*********
****************************************************/
void velikost_DPS(void)
{
	if (flag==0){	
	lcd_gotoxy(0,0);
	lcd_puts("  vyber rozmer  ");

		if(encoder==0){
			lcd_gotoxy(0,1);
			lcd_puts("1: 10x10 cm");
			}
		if(encoder==1){
			lcd_gotoxy(0,1);
			lcd_puts("2: 21x10 cm");
			}
		if(encoder==2){
			lcd_gotoxy(0,1);
			lcd_puts("3: 30x21 cm");
			}
		if(encoder>=3){
			encoder=0;
			}
	}
}
/****************************************************
****************fce pro vyber oboustrane DPS*********
****************************************************/
void oboustrana_DPS(void)
{
	if (flag==1){
	lcd_gotoxy(0,0);
	lcd_puts("oboustranou DPS?");
	
		if (encoder==0){
			lcd_gotoxy(0,1);
			lcd_puts("       NE       ");
			}
		if (encoder==1){
			lcd_gotoxy(0,1);
			lcd_puts("       ANO      ");
			}
		if(encoder>=2){
			encoder=0;
			}
	}
}
/****************************************************
***************fce pro nastaveni casu osvitu*********
****************************************************/
void nastaveni_casu(void)
{
		//hodiny
		if (flag==2){
			lcd_gotoxy(0,0);
			lcd_puts("nastaveni hodin ");
				//nastaveni sekund probiha v preruseni
			lcd_gotoxy(0,1);
			sprintf(buffer,"    %02d:%02d.%02d    ",hodiny,minuty,sekundy);
			lcd_puts(buffer);
		}
		//minuty
		if (flag==3){
			lcd_gotoxy(0,0);
			lcd_puts("nastaveni minut ");
				//nastaveni sekund probiha v preruseni
			lcd_gotoxy(0,1);
			sprintf(buffer,"    %02d:%02d.%02d    ",hodiny,minuty,sekundy);
			lcd_puts(buffer);
		}
			//sekundy
		if (flag==4){
			lcd_gotoxy(0,0);
			lcd_puts("nastaveni sekund");
				//nastaveni sekund probiha v preruseni
			lcd_gotoxy(0,1);
			sprintf(buffer,"    %02d:%02d.%02d    ",hodiny,minuty,sekundy);
			lcd_puts(buffer);

			//ulozani hodnoty hodiny,minuty, sekundy pro pozdejsi praci
				pom_h=hodiny;
				pom_m=minuty;
				pom_s=sekundy;
			//ulozani hodnoty hodiny,minuty, sekundy pro pozdejsi praci	
				hod=hodiny;
				min=minuty;
				sek=sekundy;

			cas=( 3600 * (long)hodiny) + ( 60 * (long)minuty) + (long)sekundy;	//prevod hodnot hod, min, sek na CAS
		}
}


/****************************************************
*****************fce pro rozsviceni DPS**************
****************************************************/
void rosviceni_DPS(void)
{
	if (oboustr==0){
		if (rozmer_dps==0){ 
			PORTC |= (1 << mala_dps);
			PORTC &= ~(1 << vetsi_dps);	
			PORTC &= ~(1 << nejvetsi_dps);	
		}
	
		if (rozmer_dps==1){ 
			PORTC |= (1 << mala_dps);
			PORTC |= (1 << vetsi_dps);	
			PORTC &= ~(1 << nejvetsi_dps);	
		}
	
		if (rozmer_dps==2){ 
			PORTC |= (1 << mala_dps);
			PORTC |= (1 << vetsi_dps);	
			PORTC |= (1 << nejvetsi_dps);	
		}
	}
	else{
	PORTC |= (1 << oboustrana);
		if (rozmer_dps==0){ 
			PORTC |= (1 << mala_dps);
			PORTC &= ~(1 << vetsi_dps);	
			PORTC &= ~(1 << nejvetsi_dps);	
		}

		if (rozmer_dps==1){ 
			PORTC |= (1 << mala_dps);
			PORTC |= (1 << vetsi_dps);	
			PORTC &= ~(1 << nejvetsi_dps);	
		}
	
		if (rozmer_dps==2){ 
			PORTC |= (1 << mala_dps);
			PORTC |= (1 << vetsi_dps);	
			PORTC |= (1 << nejvetsi_dps);	
		}
	}
}

/****************************************************
******************fce pro odpocitaveni***************
****************************************************/
void odpocet(void)
{
	if (flag==5){
			if ((PIND & (1 << viko))==0){
				rosviceni_DPS();
				sprintf(buffer,"nast:  %02d:%02d.%02d ",pom_h,pom_m,pom_s);
				lcd_gotoxy(0,0);
				lcd_puts(buffer);

				hod=cas/3600;
				min=(cas-((long)hod*3600))/60; 
				sek=cas%60;
				sprintf(buffer,"zbyva: %02d:%02d.%02d",hod,min,sek);
				lcd_gotoxy(0,1);
				lcd_puts(buffer);

				PORTC |= (1 << mala_dps);	//rozsviceni male DPSky
			}
			else{
				PORTC &= ~(1 << mala_dps);	//zhasnuti male DPSky	
				PORTC &= ~(1 << vetsi_dps);	//zhasnuti male DPSky
				PORTC &= ~(1 << nejvetsi_dps);	//zhasnuti male DPSky
				PORTC &= ~(1 << oboustrana);	//zhasnuti male DPSky
				
				lcd_gotoxy(0,0);
				lcd_puts("  otevrene viko ");
				lcd_gotoxy(0,1);
				sprintf(buffer,"zbyva: %02d:%02d.%02d",hod,min,sek);
				lcd_puts(buffer);
			}
		}
}
/****************************************************
*******************Restart MCU***********************
****************************************************/
void reboot(void) {
   void (*fn_ptr) (void) = (void (*) (void)) 0;

   fn_ptr();
}

/****************************************************
*************fce pro kontrolu tlacitka***************
****************************************************/
void kotrola(void)
{
	if (flag>=6){reboot();}
}
 
//============================================================================
//=====================================MAIN===================================
//============================================================================
int main(void)
{
    inicializace();           
	

while(1){	//nekonecnik
		
	//výběr velikosti DPSky
	velikost_DPS();
	
	//vyber oboustrane DPS
	oboustrana_DPS();

	//nastaveni casu osvitu
	nastaveni_casu();

	//nastaveni odpocitavani
	odpocet();

	//kontrola odpoctu (dokonceni osvitu)
	kotrola();

}//while
return 1;
}//main


Nahlásit jako SPAM
IP: 89.102.184.–
KIIV
~ Moderátor
+43
God of flame
21. 4. 2013   #7
-
0
-

Nic do oci bijiciho...

jen obdivuju jak dokazes do jednoho kodu narvat tolik odlisnejch stylu odsazovani... ruzny kombinace tab/mezer.. jako bych cetl kod z indie :)

to rozdelovani na sekundy, minuty a hodiny je taky vskutku dabelske :)

Nastavovat TCNT po kazdem preruseni, kdyz to procesor umi v jednom z rezimu uplne sam ... a jeste to zvlada i trosku presneji...

Jo a konstanty z #define je dobry psat velkejma pismenama .. clovek pak nemusi hledat co je to sakra za promennou ... hned vidi ze to bude asi konstanta

jinak bych se mozna zameril na ten reset... co to provadi po resetu ... taky vubec neni videt kde je zapojene lcd..

Nahlásit jako SPAM
IP: 94.113.92.–
Program vždy dělá to co naprogramujete, ne to co chcete...
jirkaj40
Newbie
21. 4. 2013   #8
-
0
-

No za ten kód se omlouvám. Teprve získávám nějakou štábní kulturu. Časem na to přijdu jak jej psát. :-)

No po resetu se program nastaví do původního nastavení a opět. Nastavím si velikost DPSky, vyberu jestli ji chci oboustranou a nakonec se dostanu na nastavení času. Tam si nastavuji hodiny,minuty, sekundy, ale chybné znaky se objevují stále.

Jinak LCD mám připojené takto:

#define LCD_PORT         PORTA        /**< port for the LCD lines   */
#define LCD_DATA0_PORT   LCD_PORT     /**< port for 4bit data bit 0 */
#define LCD_DATA1_PORT   LCD_PORT     /**< port for 4bit data bit 1 */
#define LCD_DATA2_PORT   LCD_PORT     /**< port for 4bit data bit 2 */
#define LCD_DATA3_PORT   LCD_PORT     /**< port for 4bit data bit 3 */
#define LCD_DATA0_PIN    3           /**< pin for 4bit data bit 0  */
#define LCD_DATA1_PIN    2            /**< pin for 4bit data bit 1  */
#define LCD_DATA2_PIN    1            /**< pin for 4bit data bit 2  */
#define LCD_DATA3_PIN    0            /**< pin for 4bit data bit 3  */
#define LCD_RS_PORT      PORTA    /**< port for RS line         */
#define LCD_RS_PIN       5            /**< pin  for RS line         */
#define LCD_E_PORT       PORTA     /**< port for Enable line     */
#define LCD_E_PIN        4            /**< pin  for Enable line     */
Nahlásit jako SPAM
IP: 89.102.184.–
KIIV
~ Moderátor
+43
God of flame
21. 4. 2013   #9
-
0
-

tak pak uz asi jen krokovat a sledovat co se tam deje

Nahlásit jako SPAM
IP: 94.113.92.–
Program vždy dělá to co naprogramujete, ne to co chcete...
jirkaj40
Newbie
21. 4. 2013   #10
-
0
-

Tak tento program se bude krokovat velice těžko. S tímto nemám zkušenosti. 

Nahlásit jako SPAM
IP: 89.102.184.–
jirkaj40
Newbie
21. 4. 2013   #11
-
0
-

A vždy se ta obrazovka zahltí nesmysly až po stisknutí tlačítka. Nikdy ne náhodně.

Nahlásit jako SPAM
IP: 89.102.184.–
jirkaj40
Newbie
22. 4. 2013   #12
-
0
-

Že by to byl tygr?? 

Ne teď vážně. V programu jsem měl asi špatně nastavený buffer. Měl jsem jej nastavený na hodnotu 16, ale správně má  být na 17 (páč 16+1 koncový znak). A hned to vypadá lépe. 

Nahlásit jako SPAM
IP: 89.102.184.–
KIIV
~ Moderátor
+43
God of flame
22. 4. 2013   #13
-
0
-

no jestli to vyoptimalizovalo tu promennou jednou co je za bufferem a nikde neni pouzita, tak si pak kolidoval s promennou encoder .. to by pak davalo smysl...

Nahlásit jako SPAM
IP: 62.168.56.–
Program vždy dělá to co naprogramujete, ne to co chcete...
jirkaj40
Newbie
22. 4. 2013   #14
-
0
-

#13 KIIV
Ojda. Tak teď jsem si to 2x přečetl, ale nějak jsem to nepochopil. Můžeš to trošku upřesnit?

Nahlásit jako SPAM
IP: 89.102.184.–
KIIV
~ Moderátor
+43
God of flame
22. 4. 2013   #15
-
0
-

mas:

//globalni a jiné proměnné
unsigned char temp;
char buffer[16];
int jednou=0;	//promenna pro zobrazeni upozorneni na nezavrene viko

volatile char encoder=0;		//hodnota enkoderu

a ani "temp" ani "jednou" neni pokud si pamatuju dobre pouzita...

a tim to muze kompilator klidne vyhodit.... tim padem ten ukoncovaci byte se zapisoval do promenne "encoder" a pokud byla treba vetsi nez 255, tak uz tam nebylo zadny ukonceni

Nahlásit jako SPAM
IP: 62.168.56.–
Program vždy dělá to co naprogramujete, ne to co chcete...
jirkaj40
Newbie
22. 4. 2013   #16
-
0
-

#15 KIIV
Jo takhle to je myšleno. No tak program ještě projdu a tyto proměnné odstraním. 

Ony vlastně vznikly při různých experimentech. A zapomněl jsem je vymazat.

Nahlásit jako SPAM
IP: 89.102.184.–
Zjistit počet nových příspěvků

Přidej příspěvek

Toto téma je starší jak čtvrt roku – přidej svůj příspěvek jen tehdy, máš-li k tématu opravdu co říct!

Ano, opravdu chci reagovat → zobrazí formulář pro přidání příspěvku

×Vložení zdrojáku

×Vložení obrázku

Vložit URL obrázku Vybrat obrázek na disku
Vlož URL adresu obrázku:
Klikni a vyber obrázek z počítače:

×Vložení videa

Aktuálně jsou podporována videa ze serverů YouTube, Vimeo a Dailymotion.
×
 
Podporujeme Gravatara.
Zadej URL adresu Avatara (40 x 40 px) nebo emailovou adresu pro použití Gravatara.
Email nikam neukládáme, po získání Gravatara je zahozen.
-
Pravidla pro psaní příspěvků, používej diakritiku. ENTER pro nový odstavec, SHIFT + ENTER pro nový řádek.
Sledovat nové příspěvky (pouze pro přihlášené)
Sleduj vlákno a v případě přidání nového příspěvku o tom budeš vědět mezi prvními.
Reaguješ na příspěvek:

Uživatelé prohlížející si toto vlákno

Uživatelé on-line: 0 registrovaných, 4 hosté

 

Hostujeme u Českého hostingu       ISSN 1801-1586       ⇡ Nahoru Webtea.cz logo © 20032024 Programujte.com
Zasadilo a pěstuje Webtea.cz, šéfredaktor Lukáš Churý