Testkort för AVR, LCD + annat godis (nu med film)

Berätta om dina pågående projekt.
Nerre
Inlägg: 27188
Blev medlem: 19 maj 2008, 07:51:04
Ort: Upplands väsby

Inlägg av Nerre »

Är inte smidigaste lösningen för en sån grej att skriva sakerna till en "buffert" i RAM och sen ha en interruptrutin som uppdaterar displayen från den bufferten med en lagom hög frekvens (10 ggr i sekunden borde väl räcka?).

Visserligen drar det mer kraft eftersom displayen uppdateras hela tiden även om den inte ändrats, men det blir ju betydligt enklare att skriva på valfri plats på displayen.
Användarvisningsbild
Illuwatar
Inlägg: 2256
Blev medlem: 10 november 2003, 14:44:27
Skype: illuwatar70
Ort: Haninge
Kontakt:

Inlägg av Illuwatar »

För att slippa onödiga uppdateringar i interrupt-rutinen kan man ha en flagga som man sätter när en förändring i "off-screen"-RAM har skett. Man kolla flaggan - har uppdatering skett, dumpa RAM-datat till displayen, om inte - gör inget.

En nackdel med en separat RAM-buffert är just tillgången på RAM i en ATmega. Personligen skulle jag göra lokala uppdateringar direkt i displayen i stället. Du nämner inte vilken kontroller dina displayer använder, men jag antar att man skriver data till dem i byte-block. Då är det bara att skriva över existerande bytes med nya (man får förstås stänga av eventuell XOR-funktion).
zebs
Inlägg: 36
Blev medlem: 5 mars 2008, 22:55:07
Ort: Norrköping

Inlägg av zebs »

Jag är lite osäker på hur det där buffer och ram-tänket funkar...

Såsom jag gör nu är att jag får ett värde mellan 0-1023, och jag gör fyra kontroller:

Kod: Markera allt

while(temp>1000){pressure[0]++;temp-=1000;}
while(temp>100){pressure[01]++;temp-=100;}
while(temp>10){pressure[2]++;temp-=10;}
while(temp>1){pressure[3]++;temp-=1;}
Detta gör jag för att ta fram tusental, hundratal osv osv.. jag antar att det finns smartare sätt att göra det på.. men jag görsåhär bara så att jag kan skriva ut varje siffra för sig för att bilda talet mellan 0-1023...

Problemet blir ju att jag suddar mellan varje gång koden körs, och resultatet blir att ingenting syns istället... är det för att min kod för att styra displayen är för långsam? Eller är det så enkelt, att om jag både suddar och skriver text inom en while(1), så kommer jag aldrig att se ngt?

PS. det är en ks0108b-kontroller DS
Användarvisningsbild
AntiZ
Inlägg: 321
Blev medlem: 22 februari 2007, 13:34:14
Ort: V. Husby
Kontakt:

Inlägg av AntiZ »

Du råkar inte ha "sudd"funktionen direkt efter skrivfunktionen?

Har hänt mig ett par gånger att jag råkar sudda allt och sen väntar på AD etc. skriver ut allt på LCD, hoppar till början (direkt efter utskrift) och suddar allt. Vilket skapar en text/siffror som knappt skymtas...

Om inte annat blir man lite sugen på ett sånt där utvecklingskort...
zebs
Inlägg: 36
Blev medlem: 5 mars 2008, 22:55:07
Ort: Norrköping

Inlägg av zebs »

Jag har testat o kolla lite nu vad det kan vara... och, som jag gör nu är att jag först skriver ut, kör 1 sekunds delay, sen suddar, sen 1 sekunds delay... o grejer än att jag typ hinner se när det suddas och när det skrivs, precis som att först "lägger displayen ut mönstret" o då är pixlarna typ bruna, sen en kort stund efter blir dom vita, precis som dom ska... o tvärtom när man suddar, först är pixlarna vita, sen bruna, o sen försvinner dom... och om jag hinner med att se det där måste det ju innebära att det kanske är displayen som inte är tillräckligt snabb, eller? :S

EDIT: Kan det vara så att displayen tar mkt ström för att tända pixlarna eller nåt? Och att mina kondensatorer är för små?

EDIT2: Nu har jag filmat förloppet. Detta är koden som körs för att tända alla pixlar på displayen, rad för rad.

Kod: Markera allt

for(unsigned char y=0;y<64;y++){
for(unsigned char x=0;x<192;x++)LCD_Draw_Dot(x,y);}
http://z-berg.se/projekt/P6190169.AVI

Ska det ta så lång tid? :S 1-2 sekunder för att fylla displayen?
Användarvisningsbild
EagleSpirit
Inlägg: 1288
Blev medlem: 27 maj 2003, 23:15:48
Ort: Västerås
Kontakt:

Inlägg av EagleSpirit »

Bra jobbat. Häftigt projekt!

Vad gör LCD_Draw_Dot? Det kan vara så att varje gång du kör draw dot så kommer den först skicka ett kommando för att ändra X-koordinaten, sen Y-koordinaten och till slut bestämma vilket värde punkten ska ha, typ... Troligtvis så tar det väldigt lång tid att skicka dom kommandona. Jag har för mig att KS108 har automatisk ökning av position i steg av byte så du skulle ju kunna testa att fylla displayen genom att skicka nästa byte direkt, utan att köra några x,y-förflyttningar. Det jag försöker säga är att det kanske inte är displayen som gör att det tar så lång tid att fylla hela displayen. Men att du hinner se att de är bruna kan vara ett problem. Ett sätt att testa skulle ju kunna vara att växla "färg" på en yta, t.ex. 16*16 pixlar, med en viss frekvens. Frekvensen justerar du sen tills det att rutan är så vit som du vill ha den. Högre än den frekvensen bör du inte ha på att uppdatera LCDn.

På dom ställen där du behöver snabb uppdatering, testa att spara mönstret för siffrorna i en array av unsigned chars innan det skickas ut. Ordningen på byten ska vara så att de följer det sätt som displayen flyttar för varje byte. Förstår du hur jag menar? Om jag inte minns fel så skriver väl KS108 sina bytes i kolumner med 8 pixlar och stegar åt höger?

Hoppas det hjälpte något. Lycka till!
Användarvisningsbild
squiz3r
Inlägg: 5424
Blev medlem: 5 september 2006, 20:06:22
Ort: Lund
Kontakt:

Inlägg av squiz3r »

Om du har koden till LCD_Draw_Dot() funktionen så kan du lägga upp den. Har du inte koden borde du nog inte använda den funktionen om du vill ha någon prestanda.
zebs
Inlägg: 36
Blev medlem: 5 mars 2008, 22:55:07
Ort: Norrköping

Inlägg av zebs »

JAg lägger upp koden som en .txt istället för att posta i tråden, det blir så mkt! :)

http://z-berg.se/projekt/kod.txt

EDIT. Kan ju säga det att jag har tagit koden här från sidan ifrån en tråd. Så jag har inte skrivit den helt själv, och är inte till 100% på vad all kod gör...
Användarvisningsbild
squiz3r
Inlägg: 5424
Blev medlem: 5 september 2006, 20:06:22
Ort: Lund
Kontakt:

Inlägg av squiz3r »

Inte för att jag har någon koll på varken AVR eller grafiska displayer, men jag tror att fördröjningen ligger här:

Kod: Markera allt

void LCD_Wait(void)
{
	LCD_DATA_DDR = 0x00; 				// Set DDR to input.
	asm("nop");
	CLEAR_RS();					// Set Instruction/Data pin to low
	SET_RW();					// Set Read/Write to Read (high)
	SET_ENABLE();
	
	while((LCD_DATA_PIN & DISPLAY_STATUS_BUSY));    // Do loop until LCD isn't busy anymore
	
	CLEAR_ENABLE();
}
Det är en pause som (jag antar) man måste ha för att displayen ska hinna med när man tex. läser från den. Som någon annan sa tidigare så bör man nog inte bestämma en ny possition och skriva en bit (pixel) varje gång man ska skriva. Utan man ska skriva en hel byte till det stället där "cursorn" är, så flyttar den sig ett steg åt höger sen. Detta pga, att det tar en massa instruktioner (och tid) att flytta på "cursorn" och sen måste man skriva om samma byte 8ggr om man skriver en pixel åt gången när man ju bara behöver skriva en gång om man skriver dit hela på samma gång.

Från, "en uttråkad persson"
Användarvisningsbild
Illuwatar
Inlägg: 2256
Blev medlem: 10 november 2003, 14:44:27
Skype: illuwatar70
Ort: Haninge
Kontakt:

Inlägg av Illuwatar »

Om jag läser detta rätt så ritar du tecknen pixel för pixel? Det verkar enligt mig vara ett rätt så resursslösade sätt (då du för varje pixel måste både läsa en byte från displayen, sätta rätt pixel i den lästa byten och sedan skicka tillbaka denna). Mitt förslag är att du lägger upp alla tecken i en tabell med bitmönster, grupperade i byte-block. Använder du en 8 x 6 punkters font räcker det med sex skrivoperationer för tecknet och en eller två blanka bytes för mellanrummen.
Användarvisningsbild
EagleSpirit
Inlägg: 1288
Blev medlem: 27 maj 2003, 23:15:48
Ort: Västerås
Kontakt:

Inlägg av EagleSpirit »

Det man måste tänka på är när man vill ha text mellan två "rader" eller mellan två "sidor". Blir lite extra krångel men det går att fixa. För visst skriver man först till vänstra halvan av displayen, sen högra?

Som squiz3er säger, det är den där while-loopen som tar tid eftersom displayen behöver tid för att uppdatera sina register. Jag har för mig att det är några ms för varje instruktion = tar mycket tid.
Skriv svar