AtMega 328PU and 20x4 LCD pfleury libraries

Go To Last Post
148 posts / 0 new

Pages

  • 1
  • 2
  • 3
  • 4
  • 5
Total votes: 0

JohanEkdahl wrote:

Read the Hitachi document I linked to!!! There is an EXCELLENT table showing the bit patterns for EVERYTHING you can do with the 44780.

 

EDIT: Table 6 on pages 24-25.

 

I know about the CGRAM and DDRAM address... I know you guys probably gonna be flamed up because what I'm going to say, but it's what I feel sometimes too! I think sometimes my posts aren't also carefully read.

 

I said in my previous post that my question is that I can't see in any of the codes discussed up to now how to distinguish where we are going to write a custom char. I can see in MicroGyro code the CGRAM initial address being set, the 0x40. But then I can't see the 0x80 address being written prior to print the custom chars in DDRAM. Also in that link posted somewhere above (http://www.circuitvalley.com/201...) I see the 0x40 but I can't see the 0x80. So how the controller knows that we want to print chars in DDRAM? And in that link they say that the 0x80 needs to be sent but I can't see it in their code either.

 

now we are ready to display this font on to lcd. but keep one thing in mind you should get back to DD RAM, to display this data on to screen . this can be done by setting DD RAM address. like for 16x2 char lcd first, row first character send lcdCmd(0x80);

So, this is the 2nd time also that I'm asking the same. However, what I keep getting is "read the datasheet"! Datasheet doesn't address Peter's libraries or anyone's code! :(

  • 1
  • 2
  • 3
  • 4
  • 5
Total votes: 0

I'll answer what I posted.

 

PsySc0rpi0n wrote:
We use lcd_command() function to set the CGRRAM start address. This tells we are going to write data in that specific memory "area"/location/address. Then we actually write/store there the custom chars using the lcd_data() function.

That is correct.

 

"If you want to write you first custom character to 0x00 CG RAM location then you have to send lcd a command lcdCmd(0x40);
 After this now you are ready to send data to CG RAM location 0x00.

 After sending the whole pattern (1 custom char) for location 0x00  the location pointer will auto increase to 0x01 location. 

 Or if you want to store something to 0x03 location then send direct command lcdCmd(0x43);"

 

Example of whole pattern for 1 custom char (battery icon):

  1. lcdData(0x0E);
  2. lcdData(0x1B);
  3. lcdData(0x11);
  4. lcdData(0x11);
  5. lcdData(0x11);
  6. lcdData(0x11);
  7. lcdData(0x11);
  8. lcdData(0x1F);

 

PsySc0rpi0n wrote:
Then in MicroGyro's post, he simply uses the gotoXY() function to set the line and column where we want to print any of the custom chars of CGRAM and lcd_data() function to print the custom chars from CGRAM. My question here is how the HD44780 controller knows where to print custom chars from CGRAM if we use lcd_data() function to write chars both on CGRAM and DDRAM?

I used gotoXY() function to point to where I want to place my custom char then use lcd_data() to print to screen. That's for both CGRAM and CGROM (DDRAM holds what's on the screen)

 

For example: 

- I want to write a custom char to col 5 at row 1 then I simply use gotoXY(5, 1) and put my custom char number 4 on that location using lcd_data(0x03).

  You can put more custom char using gotoXY(5, 1) and then use lcd_data(0x03), lcd_data(0x03), lcd_data(0x03) which will place 3 same custom char which start  from col 5 row 1.

  First custom char saved is called using lcd_data(0x00) and so on. (LCD controller know which one you are call CGRAM or CGROM)

 

- After that custom char I want to print string so I simply use gotoXY(6, 1) and do print("My String") (or whatever your function to print string)

  I can put my gotoXY inside my print() to do it more easily, so I can use print(6, 1, "My String");

 

So how about back to CGROM after use custom char? Just simply do usual lcd_data() or print() after gotoXY() to overwrite what's in the screen. That's all.

 

One thing to be notice is even after you print string or custom char you can overwrite it using gotoXY() and lcd_data() or print(), but if the previous text is longer than new text then the previous text need to be erase first using lcd_clear (or you can easily overwrite it with blank char?) or it will remain in the screen which is not good.

 

Don't laugh at me, I can only do simple things, if it works it aint stupid. :)

That's an explanation from old guy doing LCD display. :)

 

 

MG

 

 

 

I don't know why I'm still doing this hobby

  • 1
  • 2
  • 3
  • 4
  • 5
Total votes: 0

Bad internet connection :(

Sorry.

I don't know why I'm still doing this hobby

Last Edited: Sat. Jul 29, 2017 - 01:16 PM
  • 1
  • 2
  • 3
  • 4
  • 5
Total votes: 0

PsySc0rpi0n wrote:
I can see in MicroGyro code the CGRAM initial address being set, the 0x40. But then I can't see the 0x80 address being written prior to print the custom chars in DDRAM.

 

No. You are not reading. Or reading but ignoring. A few posts ago I asked/hinted to have a look at what gotoXY() does. Did you do that?

 

I'll be explicit, and do the investigation you should have done. I do not have MicroGyros code for gotoXY, but I have Peter Fleurys code for lcd_gotoxy() (and any print positioning function for a 44780 LCD must do the same or something very similar). Here's Peters code:

 

void lcd_gotoxy(uint8_t x, uint8_t y)
{
#if LCD_LINES==1
    lcd_command((1<<LCD_DDRAM)+LCD_START_LINE1+x);
#endif
#if LCD_LINES==2
    if ( y==0 )
        lcd_command((1<<LCD_DDRAM)+LCD_START_LINE1+x);
    else
        lcd_command((1<<LCD_DDRAM)+LCD_START_LINE2+x);
#endif
#if LCD_LINES==4
    if ( y==0 )
        lcd_command((1<<LCD_DDRAM)+LCD_START_LINE1+x);
    else if ( y==1)
        lcd_command((1<<LCD_DDRAM)+LCD_START_LINE2+x);
    else if ( y==2)
        lcd_command((1<<LCD_DDRAM)+LCD_START_LINE3+x);
    else /* y==3 */
        lcd_command((1<<LCD_DDRAM)+LCD_START_LINE4+x);
#endif

}/* lcd_gotoxy */

I't's a bit convoluted because it has conditional compilation for different display sizes. Let's simplify it and see what it would look like for a 2-line display:

void lcd_gotoxy(uint8_t x, uint8_t y)
{
    if ( y==0 )
        lcd_command((1<<LCD_DDRAM)+LCD_START_LINE1+x);
    else
        lcd_command((1<<LCD_DDRAM)+LCD_START_LINE2+x);
}

So, regardless of if we want to go to line 0 or 1 (i.e. y == 0 or 1) we send a command to the display that has bit LCD_DDRAM set. This bit indicates that all data send after this command is to be written in DDRAM.

 

Conclusion: A gotoXY function always sets DDRAM address, and thus always selects DDRAM for data that follows.

 

Do you get it now?

As of January 15, 2018, Site fix-up work has begun! Now do your part and report any bugs or deficiencies here

No guarantees, but if we don't report problems they won't get much of  a chance to be fixed! Details/discussions at link given just above.

 

"Some questions have no answers."[C Baird] "There comes a point where the spoon-feeding has to stop and the independent thinking has to start." [C Lawson] "There are always ways to disagree, without being disagreeable."[E Weddington] "Words represent concepts. Use the wrong words, communicate the wrong concept." [J Morin] "Persistence only goes so far if you set yourself up for failure." [Kartman]

Last Edited: Sat. Jul 29, 2017 - 02:10 PM
  • 1
  • 2
  • 3
  • 4
  • 5
Total votes: 0

JohanEkdahl wrote:
A gotoXY function always sets DDRAM address, and thus always selects DDRAM for data that follows.

+1 yes

 

 

" 20 x 4 LCD - DDRAM Address            

  Row1     0x80 0x81 0x82 0x83 through 0x93
  Row2     0xCO 0xC1 0xC2 0xC3 through 0xD3
  Row3     0x94 0x95 0x96 0x97 through 0xA7
  Row4     0xD4 0xD5 0xD6 0xD7 through 0xE7 "

 

0x80 is address of DDRAM at row 1 col 1 to be specific. 0x81 is col 2 and so on. 

 

Edit: typo

 

MG

I don't know why I'm still doing this hobby

Last Edited: Sat. Jul 29, 2017 - 02:31 PM
  • 1
  • 2
  • 3
  • 4
  • 5
Total votes: 0

PsySc0rpi0n wrote:
We use lcd_command() function to set the CGRRAM start address. This tells we are going to write data in that specific memory "area"/location/address.

Correct

 

PsySc0rpi0n wrote:
Then we actually write/store there the custom chars using the lcd_data() function.

Correct

 

PsySc0rpi0n wrote:
Then in MicroGyro's post, he simply uses the gotoXY() function to set the line and column where we want to print any of the custom chars of CGRAM and lcd_data() function to print the custom chars from CGRAM. My question here is how the HD44780 controller knows where to print custom chars from CGRAM if we use lcd_data() function to write chars both on CGRAM and DDRAM?

And HERE is where you are missing what I posted in post #48

 

and:

 

in my MAIN code I display them by using Mr. Fleury's library function "lcd_putc":

lcd_putc(0);		//display first custom character

and:

lcd_putc(1);		//display second custom character

Which if you look at the memory map above are CGRAM cells '0', and '1'...Where I stored my fabulous Custom Characters!!

 

 

PsySc0rpi0n wrote:
lcd_command(0x40) says we are going to write in first address of CGRAM... Ok until here. lcd_data(........) says we are going to store/save/write the custom chars in the above 0x40 address and next addresses.

meaning the start of the custom character ram area is 0x40.  TO make one character you use 8 locations, so for the first character is stored in locations 0x40 thru 0x47.  The second starts at 0x48 thru 0x50, and so on.

 

PsySc0rpi0n wrote:
gotoXY() says what line and cloumn we want to print the above custom chars! lcd_data(.....) to print the custom chars from CGRAM.

WRONG!!

Goto_xy tells the display exactly where on the screen to print the next character.....Custom or standard.

 

PsySc0rpi0n wrote:
But there is no command saying we "got out" of 0x40 memory area (CGRAM). How it knows we are now going to print in DDRAM?

Ahhh!  I think I see your confusion.  The short answer is you do not have to worry about any of that.  If you look at me short example you will see I don't do anything in regards to DDRAM directly.

 

Take a look at the table I posted above with the red circle in it, or better yet, look at the datasheet for a clear view as the table comes from the datasheet.  Look at the '0' character.  I will use this for the example..

 

If you look at the table location where '0' is locates....just to the top are '0011', and to the left is '0000'  This is the address where the character '0' is located. 

 

When I write:

lcd_putc("0");

the "0" is converted to the ASCII by your compiler equivalent of '0' which is 0x30...in binary this is 00110000.  LOOK as the chart..... High byte 0011 low byte 0000...which is 0x30 in HEX

 

So I could write this:

lcd_putc(0x30);

and I will get the same result....the number '0' printed at the current location.  What the LCD manufacturer(Hitachi) did was to make the worlds life easy by mapping their character table - Both Custom and Standard to match the ASCII table. Google ASCII tables and you will see what I mean.  Now in the true ASCII table there is a null for 0x00 and other commands in the first eight locations...IGNORE this on the ASCII table as the LCD does and uses them as locations for storing your custom characters.

 

Confused?  I was.  I did not read up much on the DDRAM as quite frankly I do not see much in using it as I can print my characters and the standard ones by simply using Fleurys library right out of the box and the CGRAM table.  I would recommend you simply do the same.  Why make your head hurt?  I know I know...because you want to understand EVERYTHING.  I get it.  But for the purpose of getting your screen to do what you want, the example code, and the links I used and posted above do the trick(the first link for some reason does not work from this site directly, but a copy/paste did).  Once you get a few custom characters showing on the screen THEN start poking around.  Your choice.

 

Ok, now back to locations and how things are stored:

In the AVR at some place in FLASH I have stored 16 hex numbers by doing this:

static const PROGMEM unsigned char CustomChar1[] =
{
		0x19,0x2,0x4,0x8,0x4,0xa,0x19,0x10
};

static const PROGMEM unsigned char CustomChar2[] =
{
		0x13,0x8,0x4,0x2,0x11,0x12,0x4,0x3
};

eight hex values for each character.  Each character has a unique name - CustomChar1, and CustomChar2

 

At runtime, the application writes CustomChar1 to CGRAM starting at location 0x40 using this loop:

lcd_command(CGRAM_Base_Addr);	//set the CGRAM address pointer to first character location

		for(uint8_t i=0; i<sizeof CustomChar1; i++)
		{
			lcd_data(pgm_read_byte_near(&CustomChar1[i]));		//write the data
		}

This means my eight hex values will occupy CGRAM locations 0x40 thru 0x47

 

Next I tell the LCD to store the next Custom Character at the the base address + 8 location (0x48)

//load second custom character

	lcd_command(CGRAM_Base_Addr + 8);	//set the CGRAM address pointer to the second character location

	for(uint8_t i=0; i<sizeof CustomChar2; i++)
	{
		lcd_data(pgm_read_byte_near(&CustomChar2[i]));			//write the data
	}	

and once this loop is done I return to the MAIN loop.

 

from here the code simply prints characters from the CGRAM/CGROM based on what you put into

lcd_putc();

if you place a hex value in the () then it will jump to that location in the table.  If you put a letter inside "", then the compiler will convert the letter to the ASCII equivalent and print that from the table.

 

In the second link above the author makes an excellent explanation of the CG table I posted a snippet of explaining where the CGRAM(custom chaacters are located) and CGROM are in the table.

 

Each location is a character cell that is eight bytes deep containing the eight hex values for the eight rows that make up a character.

 

Hope this clears up some of your questions.

 

JIm

I would rather attempt something great and fail, than attempt nothing and succeed - Fortune Cookie

 

"The critical shortage here is not stuff, but time." - Johan Ekdahl

 

"Step N is required before you can do step N+1!" - ka7ehk

 

"If you want a career with a known path - become an undertaker. Dead people don't sue!" - Kartman

"Why is there a "Highway to Hell" and only a "Stairway to Heaven"? A prediction of the expected traffic load?"  - Lee "theusch"

 

Speak sweetly. It makes your words easier to digest when at a later date you have to eat them ;-)  - Source Unknown

Please Read: Code-of-Conduct

Atmel Studio6.2/AS7, DipTrace, Quartus, MPLAB, RSLogix user

  • 1
  • 2
  • 3
  • 4
  • 5
Total votes: 0

I see Johan ans Micro have posted while I was writing and I now understand what DDRAM is.  If my understanding is correct DDRAM are simply locations in the VISIBLE area of the display.

 

So when you use:

lcd_gotoxy(x,y);

the library converts your X/Y position to a HEX value for the location in DDRAM, and thats where your next character is printed.    The LCD will then increment the DDRAM counter to print the next character, unless you use the lcd_gotoxy() command to change this.

 

Thanks Johan and Micro!

 

Jim

I would rather attempt something great and fail, than attempt nothing and succeed - Fortune Cookie

 

"The critical shortage here is not stuff, but time." - Johan Ekdahl

 

"Step N is required before you can do step N+1!" - ka7ehk

 

"If you want a career with a known path - become an undertaker. Dead people don't sue!" - Kartman

"Why is there a "Highway to Hell" and only a "Stairway to Heaven"? A prediction of the expected traffic load?"  - Lee "theusch"

 

Speak sweetly. It makes your words easier to digest when at a later date you have to eat them ;-)  - Source Unknown

Please Read: Code-of-Conduct

Atmel Studio6.2/AS7, DipTrace, Quartus, MPLAB, RSLogix user

  • 1
  • 2
  • 3
  • 4
  • 5
Total votes: 0

The cells in DDRAM are single bytes, one per character position on the display. The CGRAM and CGROM contains bitmaps for rendering of characters, 8 bytes per character. You can think of the CGRAM+CGROM as one table with 128 bitmap entries. The 8 first bitmaps are writeable, the other 120 are read only. The table is used to translate a 1-byte value from DDRAM to a bitmask to render one character cell on the physical display .

As of January 15, 2018, Site fix-up work has begun! Now do your part and report any bugs or deficiencies here

No guarantees, but if we don't report problems they won't get much of  a chance to be fixed! Details/discussions at link given just above.

 

"Some questions have no answers."[C Baird] "There comes a point where the spoon-feeding has to stop and the independent thinking has to start." [C Lawson] "There are always ways to disagree, without being disagreeable."[E Weddington] "Words represent concepts. Use the wrong words, communicate the wrong concept." [J Morin] "Persistence only goes so far if you set yourself up for failure." [Kartman]

  • 1
  • 2
  • 3
  • 4
  • 5
Total votes: 0

I'll not be quoting because of the long post it become. I'll just tag each one of you that replied!

 

@MicroGyro I have already learned something else in your post! You said:

I used gotoXY() function to point to where I want to place my custom char then use lcd_data() to print to screen. That's for both CGRAM and CGROM (DDRAM holds what's on the screen)

I never thought about CGROM and other memory areas! Now I now that DDRAM is responsible be keeping the chars in the LCD. CGRAM is to store Custom Chars but still not absolutely clear about CGROM and not sure if a DDROM also exists. But it's ok for now. I think I don't need to know about those for what I'm trying to do.

 

 

@JohanEkdahl I have looked to almost every line of Peter Fleury's code. Of course I couldn't understand every and each line! About the specific lcd_gotoxy() I looked at it but nothing told me clearly that a 0x80 was being issued there. So maybe here you are right when you said I didn't looked carefully! I can take that on for sure! And yes, that was the answer I was looking to have!

 

Now I'm cleared about how the area where we are going to print chars is set! It's using lcd_gotocy() function for DDRM/CGROM and with lcd_command(0x40) for CGRAM.

 

 

@jgmdesign I also learned something new from your post although I think it wasn't what I was looking for! The stuff about "0" to be converted into a corresponding ASCII number, I know! But I understood how that table for datasheet is supposed to be read, upper bits and lower bits for each character and also that the Hitachi guys did that mapping with a 2nd purpose. The one you say that the Hitachi mapping of chars matches ASCII tables.

 

 

Thank you to you all!

 

  • 1
  • 2
  • 3
  • 4
  • 5
Total votes: 0

JohanEkdahl wrote:
The cells in DDRAM are single bytes, one per character position on the display. The CGRAM and CGROM contains bitmaps for rendering of characters, 8 bytes per character. You can think of the CGRAM+CGROM as one table with 128 bitmap entries. The 8 first bitmaps are writeable, the other 120 are read only. The table is used to translate a 1-byte value from DDRAM to a bitmask to render one character cell on the physical display .

 

Ah ok... Another very good piece of information These terms were not very clear yet in my mind!

  • 1
  • 2
  • 3
  • 4
  • 5
Total votes: 0

Ok, yesterday I made some custom chars and I was able to successfully print them. If I was the PROGMEM method instead of saving custom chars to CGRAM,will I be able to create and use more custom chars than the 8 the HD44780 can handle?

  • 1
  • 2
  • 3
  • 4
  • 5
Total votes: 0

There are only eight definable characters using eight bytes each so 64 bytes in total. It's your choice whether you want to waste RAM to hold them or save that and only locate in flash. Sort of depends if you plan to change the definitions during run time.
.
BTW this is 2017 so use __flash which will make it easier.

  • 1
  • 2
  • 3
  • 4
  • 5
Total votes: 0

And as for flash memory, how things works? Is there any specific documentation on how it works and how to implement custom chars and how to read them and print them into LCD?

 

Edited;

 

I'm trying to find stuff about PROGMEM and pgm_read_byte_near() but only the avr-gcc online manual comes up and there is no newbie explanation about it!

 

For instance, if I want to save my custom chars to FLASH memory, do I have to send any address prior to writing command like we do to CGRAM with the address 0x40?

 

Do I have limit of custom chars that I can save?

 

When I read one char from FLASH memory, and send it to DDRAM memory area, do I need to set the controller to the "next byte" to read the next custom char stored in FLASH memory does it also auto-increments?

 

If I overwrite some custom char in FLASH memory, does the old custom char gets updated in DDRAM with the new one that overwritten the old char?

 

These and probably a lot more questions will arise!

Last Edited: Sat. Jul 29, 2017 - 07:28 PM
  • 1
  • 2
  • 3
  • 4
  • 5
Total votes: 0

PsySc0rpi0n wrote:
And as for flash memory, how things works? Is there any specific documentation on how it works and how to implement custom chars and how to read them and print them into LCD? Edited; I'm trying to find stuff about PROGMEM and pgm_read_byte_near() but only the avr-gcc online manual comes up and there is no newbie explanation about it! For instance, if I want to save my custom chars to FLASH memory, do I have to send any address prior to writing command like we do to CGRAM with the address 0x40? Do I have limit of custom chars that I can save? When I read one char from FLASH memory, and send it to DDRAM memory area, do I need to set the controller to the "next byte" to read the next custom char stored in FLASH memory does it also auto-increments? If I overwrite some custom char in FLASH memory, does the old custom char gets updated in DDRAM with the new one that overwritten the old char? These and probably a lot more questions will arise!

 

SUGGESTION.....FORGET ABOUT __FLASH as you are still confused about simply creating, and writing custom characters to the CGRAM... As you are using the Fleury example code...I think Stick with that and get your questions on using the LCD straight BEFORE delving into using __FLASH.  For the moment PROGMEM is fine.

 

Otherwise this thread is going to become more complicated than it already is. 

 

Just my Opinion.

 

JIm

I would rather attempt something great and fail, than attempt nothing and succeed - Fortune Cookie

 

"The critical shortage here is not stuff, but time." - Johan Ekdahl

 

"Step N is required before you can do step N+1!" - ka7ehk

 

"If you want a career with a known path - become an undertaker. Dead people don't sue!" - Kartman

"Why is there a "Highway to Hell" and only a "Stairway to Heaven"? A prediction of the expected traffic load?"  - Lee "theusch"

 

Speak sweetly. It makes your words easier to digest when at a later date you have to eat them ;-)  - Source Unknown

Please Read: Code-of-Conduct

Atmel Studio6.2/AS7, DipTrace, Quartus, MPLAB, RSLogix user

  • 1
  • 2
  • 3
  • 4
  • 5
Total votes: 0

PsySc0rpi0n wrote:
About the specific lcd_gotoxy() I looked at it but nothing told me clearly that a 0x80 was being issued there.

lcd_command((1<<LCD_DDRAM)+LCD_START_LINE1+x);

LCD_DDRAM is 

#define LCD_DDRAM             7      /* DB7: set DD RAM address             */

and thus

1<<LCD_DDRAM

is binary 10000000 or hex 0x80 .

 

PsySc0rpi0n wrote:
It's using lcd_gotocy() function for DDRM/CGROM and with lcd_command(0x40) for CGRAM.

I'm not entirely sure what you mean here, but I think you're wrong:

  • lcd_gotoxy() will "select" DDRAM (since it sends an instruction/command with the high bit set, i.e. 1xxxxxxx)
  • lcd_command(0x40) will "select" CGRAM (since it sends an instruction/command with the two high bits set to 01, i.e. 01xxxxxx)

As of January 15, 2018, Site fix-up work has begun! Now do your part and report any bugs or deficiencies here

No guarantees, but if we don't report problems they won't get much of  a chance to be fixed! Details/discussions at link given just above.

 

"Some questions have no answers."[C Baird] "There comes a point where the spoon-feeding has to stop and the independent thinking has to start." [C Lawson] "There are always ways to disagree, without being disagreeable."[E Weddington] "Words represent concepts. Use the wrong words, communicate the wrong concept." [J Morin] "Persistence only goes so far if you set yourself up for failure." [Kartman]

  • 1
  • 2
  • 3
  • 4
  • 5
Total votes: 0

jgmdesign wrote:

PsySc0rpi0n wrote:
And as for flash memory, how things works? Is there any specific documentation on how it works and how to implement custom chars and how to read them and print them into LCD? Edited; I'm trying to find stuff about PROGMEM and pgm_read_byte_near() but only the avr-gcc online manual comes up and there is no newbie explanation about it! For instance, if I want to save my custom chars to FLASH memory, do I have to send any address prior to writing command like we do to CGRAM with the address 0x40? Do I have limit of custom chars that I can save? When I read one char from FLASH memory, and send it to DDRAM memory area, do I need to set the controller to the "next byte" to read the next custom char stored in FLASH memory does it also auto-increments? If I overwrite some custom char in FLASH memory, does the old custom char gets updated in DDRAM with the new one that overwritten the old char? These and probably a lot more questions will arise!

 

SUGGESTION.....FORGET ABOUT __FLASH as you are still confused about simply creating, and writing custom characters to the CGRAM... As you are using the Fleury example code...I think Stick with that and get your questions on using the LCD straight BEFORE delving into using __FLASH.  For the moment PROGMEM is fine.

 

Otherwise this thread is going to become more complicated than it already is. 

 

Just my Opinion.

 

JIm

 

So, I have no way of using more than 8 custom chars if I don't use flash memory, correct? I also think I might still missing some basic concepts. You said to leave flash for now and use only PROGMEM. right?

 

I think I already understood CGRAM creation, storing and printing. It's the same as I used to do with 8051. There was a lot of discussion because, probably of my poor explanation of my doubts, anybody was understanding my struggle. My struggle was just because I never noticed where was the 0x80 to get back to DDRAM memory area after issuing the 0x40 to get into CGRAM memory area...

 

Now about PROGMEM and FLASH. I thought that when PROGMEM was used, we were storing custom chars in LCD flash memory. But looks like it's not like that! Can you explain me a little bit about existing memory types in this HD44780 controller and how they can be used? Or point me out some link where I can read about it! I don't think that datasheet explains in a newbie way this matter!

 

Thanks

 

 

  • 1
  • 2
  • 3
  • 4
  • 5
Total votes: 0

JohanEkdahl wrote:

PsySc0rpi0n wrote:
About the specific lcd_gotoxy() I looked at it but nothing told me clearly that a 0x80 was being issued there.

lcd_command((1<<LCD_DDRAM)+LCD_START_LINE1+x);

LCD_DDRAM is 

#define LCD_DDRAM             7      /* DB7: set DD RAM address             */

and thus

1<<LCD_DDRAM

is binary 10000000 or hex 0x80 .

 

PsySc0rpi0n wrote:
It's using lcd_gotocy() function for DDRM/CGROM and with lcd_command(0x40) for CGRAM.

I'm not entirely sure what you mean here, but I think you're wrong:

  • lcd_gotoxy() will "select" DDRAM (since it sends an instruction/command with the high bit set, i.e. 1xxxxxxx)
  • lcd_command(0x40) will "select" CGRAM (since it sends an instruction/command with the two high bits set to 01, i.e. 01xxxxxx)

 

That was what I meant.

Inside gotoXY() there is that 0x80 command being issued implicitly. So it was that lcd_command(0x80) I was looking for that I also used with  8051 to select the DDRAM memory area.

And the other one is sent explicitly to select CGRAM memory area, so no questions about it!

 

Thanks!

  • 1
  • 2
  • 3
  • 4
  • 5
Total votes: 0

So, now about the custom chars.

 

I wanted to do something to show to my daughter. And it was to print her first name using a bunch of custom chars, a lot more than 8.

 

For instance, my daughter's first name is BIA! So I wanted to draw each character using 5 columns and 4 rows (LCD has 4 rows) for each char.

So, for instance an "A" would look like this:

 

So, would this be possible to do with an LCD?

  • 1
  • 2
  • 3
  • 4
  • 5
Total votes: 0

PsySc0rpi0n wrote:
So, I have no way of using more than 8 custom chars if I don't use flash memory, correct?

Incorrect.  You will have to load a new character, or set of characters into CGRAM.  Meaning you can have as many as you want, you only have eight at a time to work with.

 

PsySc0rpi0n wrote:
I also think I might still missing some basic concepts. You said to leave flash for now and use only PROGMEM. right?

Yes, you are missing a few basic concepts, that really have nothing to do with using PROGMEM, or __FLASH. I am only suggesting you hold off on jumping to another topic until you have understood the operation of the LCD first.  Using PROGMEM or __FLASH really has no impact on the way the CGRAM gets loaded in the end.

 

PsySc0rpi0n wrote:
I think I already understood CGRAM creation,

REally?  All these posts back and forth and you already knew what to do?

 

PsySc0rpi0n wrote:
Now about PROGMEM and FLASH. I thought that when PROGMEM was used, we were storing custom chars in LCD flash memory.

YOu are

 

PsySc0rpi0n wrote:
But looks like it's not like that!

Wrong! 

 

PsySc0rpi0n wrote:
Can you explain me a little bit about existing memory types in this HD44780 controller and how they can be used?

The datasheet mentions about using the space, but it's not worth it as the AVR has far more RAM available than a few bytes in a slow LCD.  In this case I strongly say forget about it....not worth the hassle.

 

 

If you are now all set on the LCD operation and no longer need our help on it, I suggest you start a new thread on the next item you do not understand.  If you have more questions on LCD, then add them to this thread.

 

Jim

I would rather attempt something great and fail, than attempt nothing and succeed - Fortune Cookie

 

"The critical shortage here is not stuff, but time." - Johan Ekdahl

 

"Step N is required before you can do step N+1!" - ka7ehk

 

"If you want a career with a known path - become an undertaker. Dead people don't sue!" - Kartman

"Why is there a "Highway to Hell" and only a "Stairway to Heaven"? A prediction of the expected traffic load?"  - Lee "theusch"

 

Speak sweetly. It makes your words easier to digest when at a later date you have to eat them ;-)  - Source Unknown

Please Read: Code-of-Conduct

Atmel Studio6.2/AS7, DipTrace, Quartus, MPLAB, RSLogix user

Last Edited: Sat. Jul 29, 2017 - 11:16 PM
  • 1
  • 2
  • 3
  • 4
  • 5
Total votes: 0

jgmdesign wrote:

PsySc0rpi0n wrote:
So, I have no way of using more than 8 custom chars if I don't use flash memory, correct?

Incorrect.  You will have to load a new character, or set of characters into CGRAM.  Meaning you can have as many as you want, you only have eight at a time to work with.

 

...

...

...

 

Jim

 

Hum, ok, I see but there is a catch I think!

 

If you print a custom char at DDRAM and after that you change that custom char in CGRAM, it will update the DDRAM printed char with the updated char in CGRAM automatically, no? I remember something like that!

  • 1
  • 2
  • 3
  • 4
  • 5
Total votes: 0

PsySc0rpi0n wrote:
If you print a custom char at DDRAM and after that you change that custom char in CGRAM, it will update the DDRAM printed char with the updated char in CGRAM automatically, no? I remember something like that!

CGRAM and DDRAM is 2 different memory area. So anything you do to CGRAM has no effect to DDRAM until you do gotoXY and lcd_data() or print().
.
DDRAM holds what on the screen means it holds the character so you won't be notice what's going on behind the screen. Or else you'll see flickering or blinking screen while you change the char.
.
So basically lcd_clear() doing is nothing than clearing DDRAM.
.
As other hint is to display some thing on the screen, say it temperature.
You don't have to change the whole text, just the value.
.
On screen: Temperature: 30 °C (assume this text placed on row 2)
.
You want to update the value 30 to 27 so what you should do is:
- gotoXY(13,1) - (13 is location of "3")
- print("27"). - overwrite it with 27
That's all. No need to print("Temperature: 27 °C")
.
I hope you know what I tried to explain. That's how DDRAM works.
.
But one thing to remember, RAM means it only holds when there's a vcc supply on it.
Once the vcc to LCD was cut (then powered back) and you only do gotoXY(13,1) and print("27") your "Temperature: °C" won't be there anymore. Except "27" at col 13 location.
.
I hope I make it clearer not more confusing. :)
.
Edit: - damn autocorrect

        - wrong answer about DDRAM refresh update. Changing at CGRAM which already displayed on the screen (inside DDRAM) will be updated (refreshed) by internal controller automatically.
.
MG

I don't know why I'm still doing this hobby

Last Edited: Sun. Jul 30, 2017 - 01:39 PM
  • 1
  • 2
  • 3
  • 4
  • 5
Total votes: 0

It has been brought to my attention that I may have misread a comment by the op:

 

jgmdesign wrote:
PsySc0rpi0n wrote: Now about PROGMEM and FLASH. I thought that when PROGMEM was used, we were storing custom chars in LCD flash memory. YOu are

 

My reply is INCORRECT as I thought the OP was referring to the Microcontroller FLASH, and NOT the LCD.....the LCD has no flash memory.  The custom characters are stored in the Micro's FLASH and are transferred to the LCD on demand.

 

My apologies for the mis-information.

 

Thanks to frog_jr for bringing this to my attention.

 

JIm

I would rather attempt something great and fail, than attempt nothing and succeed - Fortune Cookie

 

"The critical shortage here is not stuff, but time." - Johan Ekdahl

 

"Step N is required before you can do step N+1!" - ka7ehk

 

"If you want a career with a known path - become an undertaker. Dead people don't sue!" - Kartman

"Why is there a "Highway to Hell" and only a "Stairway to Heaven"? A prediction of the expected traffic load?"  - Lee "theusch"

 

Speak sweetly. It makes your words easier to digest when at a later date you have to eat them ;-)  - Source Unknown

Please Read: Code-of-Conduct

Atmel Studio6.2/AS7, DipTrace, Quartus, MPLAB, RSLogix user

  • 1
  • 2
  • 3
  • 4
  • 5
Total votes: 0

MicroGyro wrote:

PsySc0rpi0n wrote:
If you print a custom char at DDRAM and after that you change that custom char in CGRAM, it will update the DDRAM printed char with the updated char in CGRAM automatically, no? I remember something like that!

CGRAM and DDRAM is 2 different memory area. So anything you do to CGRAM has no effect to DDRAM until you do gotoXY and lcd_data() or print().
.
DDRAM holds what on the screen means it holds the character so you won't be notice what's going on behind the screen. Or else you'll see flickering or blinking screen while you change the char.
.
So basically lcd_clear() doing is nothing than clearing DDRAM.
.
As other hint is to display some thing on the screen, say it temperature.
You don't have to change the whole text, just the value.
.
On screen: Temperature: 30 °C (assume this text placed on row 2)
.
You want to update the value 30 to 27 so what you should do is:
- gotoXY(13,1) - (13 is location of "3")
- print("27"). - overwrite it with 27
That's all. No need to print("Temperature: 27 °C")
.
I hope you know what I tried to explain. That's how DDRAM works.
.
But one thing to remember, RAM means it only holds when there's a vcc supply on it.
Once the vcc to LCD was cut (then powered back) and you only do gotoXY(13,1) and print("27") your "Temperature: °C" won't be there anymore. Except "27" at col 13 location.
.
I hope I make it clearer not more confusing. :)
.
Edit: damn autocorrect
.
MG

 

 

Ok, I understood that! I just had the idea that when a custom char in CGRAM was changed, and if it was already somewhere printed in DDRAM, the one in DDRAM would be auto-updated to the new one saved in CGRAM.

 

Thanks for the explanation

Psy

  • 1
  • 2
  • 3
  • 4
  • 5
Total votes: 0

jgmdesign wrote:

It has been brought to my attention that I may have misread a comment by the op:

 

jgmdesign wrote:
PsySc0rpi0n wrote: Now about PROGMEM and FLASH. I thought that when PROGMEM was used, we were storing custom chars in LCD flash memory. YOu are

 

My reply is INCORRECT as I thought the OP was referring to the Microcontroller FLASH, and NOT the LCD.....the LCD has no flash memory.  The custom characters are stored in the Micro's FLASH and are transferred to the LCD on demand.

 

My apologies for the mis-information.

 

Thanks to frog_jr for bringing this to my attention.

 

JIm

 

I suspected of that! Thanks for correcting your reply!

And in that case you mean either to save directly into Mega328 flash or to have external memory device and store/read from there, right?

 

And if possible I would like anyone to explain me what is the difference between using the PROGMEM and pgm_read_byte_near() and not using. Where is the chars saved using and not using those functions/macros.

 

Thanks

Psy

Last Edited: Sun. Jul 30, 2017 - 09:27 AM
  • 1
  • 2
  • 3
  • 4
  • 5
Total votes: 0

You can never display more than 8 different custom characters at a time because there are only 8 definable. If you go back and change one then all already on the display will change.
.
Have you thought about getting a GLCD as that's clearly what you really need!

  • 1
  • 2
  • 3
  • 4
  • 5
Total votes: 0

clawson wrote:
You can never display more than 8 different custom characters at a time because there are only 8 definable. If you go back and change one then all already on the display will change. . Have you thought about getting a GLCD as that's clearly what you really need!

 

That's what I've been asking and some says it won't change and others says it will change!

 

So, what should I stick for?

  • 1
  • 2
  • 3
  • 4
  • 5
Total votes: 0

PsySc0rpi0n wrote:
So, what should I stick for?

Just test it yourself. It's not hard to do it don't it? It won't break your MCU or LCD anyway.

 

 

 

 

 

MG

I don't know why I'm still doing this hobby

  • 1
  • 2
  • 3
  • 4
  • 5
Total votes: 0

MicroGyro wrote:

PsySc0rpi0n wrote:
So, what should I stick for?

Just test it yourself. It's not hard to do it don't it? It won't break your MCU or LCD anyway.

 

 

MG

 

Sure, I'm writing the code to try it! I was just saying that you said it wouldn't change anything until lcd_gotoxy() or lcd_data() was used and clawson said it will!

 

clawson, I know about GLCD... You already said that to me in the past... I just don't have any of those GLCDs now!

  • 1
  • 2
  • 3
  • 4
  • 5
Total votes: 0

PsySc0rpi0n wrote:

clawson wrote:

You can never display more than 8 different custom characters at a time because there are only 8 definable. If you go back and change one then all already on the display will change. . Have you thought about getting a GLCD as that's clearly what you really need!

 

 

That's what I've been asking and some says it won't change and others says it will change!

 

So, what should I stick for?

 

It will change. The controller is always refreshing the display, updating characters from what is in the CGRAM at the moment of refresh. To do what you want, you would have to synchronize with the refresh cycle of the HD44780 and change the CGRAM immediately before the display is updated for each character. I don't even think that's possible, and if possible only a good hacker would be able to do it, certainly in ASM, not with some library.

 

So you need to buy a graphical display, not a character one.

 

Now, just a small note to improve your English, in you first post you wrote:

PsySc0rpi0n wrote:
Now, most of things have been forgotten but I pretend to get them back.

 

The translation of "pretendo" to English is "intend", not "pretend". Beware of false friends.

Last Edited: Sun. Jul 30, 2017 - 11:54 AM
  • 1
  • 2
  • 3
  • 4
  • 5
Total votes: 0

El Tangas wrote:

PsySc0rpi0n wrote:

clawson wrote:

You can never display more than 8 different custom characters at a time because there are only 8 definable. If you go back and change one then all already on the display will change. . Have you thought about getting a GLCD as that's clearly what you really need!

 

 

That's what I've been asking and some says it won't change and others says it will change!

 

So, what should I stick for?

 

It will change. The controller is always refreshing the display, updating characters from what is in the CGRAM at the moment of refresh. To do what you want, you would have to synchronize with the refresh cycle of the HD44780 and change the CGRAM immediately before the display is updated for each character. I don't even think that's possible, and if possible only a good hacker would be able to do it, certainly in ASM, not with some library.

 

So you need to buy a graphical display, not a character one.

 

Now, just a small note to improve your English, in you first post you wrote:

PsySc0rpi0n wrote:
Now, most of things have been forgotten but I pretend to get them back.

 

The translation of "pretendo" to English is "intend", not "pretend". Beware of false friends.

 

Ok, I'll consider the purchase of a GLCD in a near Future!

 

About the English note, thank you a lot! I'm some one that really intend and like to type and speak the best of my abilities! I rarely use "net" abbreviations such as "u" for "you" and "C" for "see" and stuff like that! I like the old fashioned way! 

  • 1
  • 2
  • 3
  • 4
  • 5
Total votes: 0

Ok, I think the code is almost ready! But I have a problem with the usage of the macro PROGMEM. Compiler just ignores it!

 

I'll paste the code in some other site that handles identation a lot better than this and will paste here the compilation result.

 

Code is here:

 

Compilation result is:

avr-gcc -g -Wall -Os -mmcu=atmega328p -std=c99 -DF_CPU=16000000UL   -c -o test_lcd_mine1.o test_lcd_mine1.c
test_lcd_mine1.c:7:1: warning: ‘__progmem__’ attribute ignored [-Wattributes]
 void writeCustomChars(const PROGMEM unsigned char customChars[][8], uint8_t customCharOffset){
 ^
avr-gcc -g -Wall -Os -mmcu=atmega328p -std=c99 -DF_CPU=16000000UL -Wl,-Map,test_lcd_mine1.map -o test_lcd_mine1.elf test_lcd_mine1.o lcd.c
avr-objdump -h -S test_lcd_mine1.elf > test_lcd_mine1.lst
avr-objcopy -j .text -j .data -O ihex test_lcd_mine1.elf test_lcd_mine1.hex
avr-objcopy -j .text -j .data -O binary test_lcd_mine1.elf test_lcd_mine1.bin
avr-objcopy -j .text -j .data -O srec test_lcd_mine1.elf test_lcd_mine1.srec
avr-objcopy -j .eeprom --change-section-lma .eeprom=0 -O ihex test_lcd_mine1.elf test_lcd_mine1_eeprom.hex \
|| { echo empty test_lcd_mine1_eeprom.hex not generated; exit 0; }
avr-objcopy: --change-section-lma .eeprom=0x0000000000000000 never used
avr-objcopy -j .eeprom --change-section-lma .eeprom=0 -O binary test_lcd_mine1.elf test_lcd_mine1_eeprom.bin \
|| { echo empty test_lcd_mine1_eeprom.bin not generated; exit 0; }
avr-objcopy: --change-section-lma .eeprom=0x0000000000000000 never used
avr-objcopy -j .eeprom --change-section-lma .eeprom=0 -O srec test_lcd_mine1.elf test_lcd_mine1_eeprom.srec \
|| { echo empty test_lcd_mine1_eeprom.srec not generated; exit 0; }
avr-objcopy: --change-section-lma .eeprom=0x0000000000000000 never used

 

 

I'm already reading something about PROGMEM from some link of this forum I found in Google, so yes, I already Googled it!

Last Edited: Sun. Jul 30, 2017 - 12:22 PM
  • 1
  • 2
  • 3
  • 4
  • 5
Total votes: 0

PsySc0rpi0n wrote:
But I have a problem with the usage of the macro PROGMEM. Compiler just ignores it!

Until you show some code here (not off-site) I bet one beer that the variables you are trying to store in PROGMEM are local to a function.

 

You can't do that.

 

They must be globals. (To be technically correct they need to be statically allocated but the simple way is to have them as "global" variables, i.e. outside of any function).

 

EDIT: Since you already googled it (supposing you used the error message as search term) you've already found this: https://www.avrfreaks.net/forum/w... . Quite clear.

As of January 15, 2018, Site fix-up work has begun! Now do your part and report any bugs or deficiencies here

No guarantees, but if we don't report problems they won't get much of  a chance to be fixed! Details/discussions at link given just above.

 

"Some questions have no answers."[C Baird] "There comes a point where the spoon-feeding has to stop and the independent thinking has to start." [C Lawson] "There are always ways to disagree, without being disagreeable."[E Weddington] "Words represent concepts. Use the wrong words, communicate the wrong concept." [J Morin] "Persistence only goes so far if you set yourself up for failure." [Kartman]

Last Edited: Sun. Jul 30, 2017 - 01:30 PM
  • 1
  • 2
  • 3
  • 4
  • 5
Total votes: 0

PsySc0rpi0n wrote:
I just had the idea that when a custom char in CGRAM was changed, and if it was already somewhere printed in DDRAM, the one in DDRAM would be auto-updated to the new one saved in CGRAM.

YES you are RIGHT and I'm COMPLETELY WRONG about this. I'm sorry for misleading you about this refreshing thing.

 

El Tangas wrote:
It will change. The controller is always refreshing the display, updating characters from what is in the CGRAM at the moment of refresh.

You are absolutely right!

 

I just tested this CGRAM thing, thank's to El Tangas which make me think to check it again. I feel stupid now. Sorry guys.

 

I edited my post #72 in case other reader will also get misleading by reading that.

 

 

 

MG

 

I don't know why I'm still doing this hobby

  • 1
  • 2
  • 3
  • 4
  • 5
Total votes: 0

MicroGyro wrote:

PsySc0rpi0n wrote:
I just had the idea that when a custom char in CGRAM was changed, and if it was already somewhere printed in DDRAM, the one in DDRAM would be auto-updated to the new one saved in CGRAM.

YES you are RIGHT and I'm COMPLETELY WRONG about this. I'm sorry for misleading you about this refreshing thing.

 

JohanEkdahl wrote:

PsySc0rpi0n wrote:
But I have a problem with the usage of the macro PROGMEM. Compiler just ignores it!

Until you show some code here (not off-site) I bet one beer that the variables you are trying to store in PROGMEM are local to a function.

 

You can't do that.

 

They must be globals. (To be technically correct they need to be statically allocated but the simple way is to have them as "global" variables, i.e. outside of any function).

 

EDIT: Since you already googled it (supposing you used the error message as search term) you've already found this: https://www.avrfreaks.net/forum/w... . Quite clear.

 

Yes, already fixed! I have one other experienced "net" friend in IRC channels that already helped me sorting this out! I worked with a lot of AVRs in the past!

And yes, I was reading that same link I found through Google but haven't finished the reading!

 

Thanks

Psy

 

 

 

El Tangas wrote:
It will change. The controller is always refreshing the display, updating characters from what is in the CGRAM at the moment of refresh.

You are absolutely right!

 

I just tested this CGRAM thing, thank's to El Tangas which make me think to check it again. I feel stupid now. Sorry guys.

 

I edited my post #72 in case other reader will also get misleading by reading that.

 

 

 

MG

 

 

No reason t feel stupid... The best also make mistakes. If it was to feel stupid, how do you think I should feel? Stupid to the power of 1000??? xD

 

Thanks

Psy

  • 1
  • 2
  • 3
  • 4
  • 5
Total votes: 0

So, let me explain how I conceptualize DDRAM and CGRAM.

 

DDRAM contains pointers to structures that are present in CGRAM (and ROM, for the default characters) and contain the actual characters. So DDRAM stores only the addresses of these structures. The actual data is in the structures.

 

Every refresh cycle, the controller follows those pointers, retrieves the associated structure and prints the data on screen. So if you change CGRAM, DDRAM doesn't change, but what is displayed does change.

  • 1
  • 2
  • 3
  • 4
  • 5
Total votes: 0

PsySc0rpi0n wrote:
No reason t feel stupid... The best also make mistakes. If it was to feel stupid, how do you think I should feel? Stupid to the power of 1000??? xD

I'm glad you had such a big heart. :D

 

 

Cheers

MG

I don't know why I'm still doing this hobby

  • 1
  • 2
  • 3
  • 4
  • 5
Total votes: 0

El Tangas wrote:
So if you change CGRAM, DDRAM doesn't change, but what is displayed does change.

I'm not sure I follow.

 

 

 

MG

I don't know why I'm still doing this hobby

  • 1
  • 2
  • 3
  • 4
  • 5
Total votes: 0

He's saying you might have defined char 3 as AA, AA, AA, AA, AA, AA, AA, AA and then written seventeen 03's to DDRAM so they are dotted all over the display. If you now go back and change those AA to BB's then nothing in DDRAM changes. There are still seventeen 03's there but what's displayed changes.

  • 1
  • 2
  • 3
  • 4
  • 5
Total votes: 0

MicroGyro wrote:

PsySc0rpi0n wrote:
No reason t feel stupid... The best also make mistakes. If it was to feel stupid, how do you think I should feel? Stupid to the power of 1000??? xD

I'm glad you had such a big heart. :D

 

 

Cheers

MG

 

No problem... I can understand that someone feels bad and I will always try to cheer him up!

 

MicroGyro wrote:

El Tangas wrote:
So if you change CGRAM, DDRAM doesn't change, but what is displayed does change.

I'm not sure I follow.

 

 

 

MG

 

I'm not following either!

Last Edited: Sun. Jul 30, 2017 - 02:15 PM
  • 1
  • 2
  • 3
  • 4
  • 5
Total votes: 1

See #89
.
(crikey, 89 posts for the simple concept of double indirection?)

  • 1
  • 2
  • 3
  • 4
  • 5
Total votes: 0

El Tangas wrote:
DDRAM contains pointers to structures that are present in CGRAM (and ROM, for the default characters) and contain the actual characters. So DDRAM stores only the addresses of these structures. The actual data is in the structures.

 

Yes. Close to what I suggested somewhere above. The combination of CGRAM and CGROM forms a LUT (look-up table) or mapping from a single char value to a 8x8 bytes bitmap.

 

El Tangas wrote:
Every refresh cycle, the controller follows those pointers, retrieves the associated structure and prints the data on screen. So if you change CGRAM, DDRAM doesn't change, but what is displayed does change.
 

 

Yes. Let try to visualize this. What follows is not code running in the AVR but a description of roughly what goes on in the 44780 controller. Roughly!

 

1) Think of the combination of CGRAM and CGROM as one array of bitmaps, i.e. an 128x8 array of bytes. Let's call it "CGMEM". (The first 8x8 bytes are the CGRAM and the following 120x8 bytes are the CGROM).

 

2) The DDRAM consists of 80 bytes.The HD44780 controller constantly loops over all DDRAM elements, picks the value of the element, uses that as an index into the "CGMEM", gets the bitmap (8 bytes) and uses that to set the individual pixels in the physical display.

 

If this was C code, how would it look? Well, roughly:

 

typedef uint8_t[8] bitmap_t;

bitmap_t cgmem[128];  // Actually 8 bitmaps in CGRAM and 120 bitmaps in CGROM

uint8_t ddram[80]; 

while (1) {
    for (int i = 0; i<128; i++) {
        bitmap_t bitmap = cgmem[ddram[i]];

        // Use bitmap to set pixels in character cell i in physical display
    }
}

A change in CGRAM will hve an immediate effect on what is displayed even if there is no change in DDRAM.

 

The above code is an illustration of parts of the "back-end" of the 44780. There's more to it - hidden in my simple comment "Use bitmap to set pixels...".

 

The CGRAM and DDRAM is (at least conceptually) double-ported. I.e. at the same time the back-end does what I sketch above, the front end can write to CGRAM and DDRAM. The "front-end" is what your AVR is communicating with. What your AVRwrite to the 44780 goes through it's front end into CGRAM or DDRAM (or is interpreted as an instruction which affects the state of the 44780 in some way).

 

Again, this is "sketch" but not so far from the detailed truth. .E.g. take a look at the block diagram on page 3 in thee Hitacchi data sheet.

 


 

A side observation regarding MicroGyros code, mentioned in #47 (linking to http://www.circuitvalley.com/201... ):

 

MicroGyro creates a battery status indicator. He does so by defining 8 separate battery icons, each with a different "filling factor". It uses up all of the CGRAM. Different battery levels are displayed by using one of the 8 different characters on CGRAM. There is no space left for any other special characters.

 

A better solution Designate just one of the CGRAM characters/bitmaps for a battery indicator. To display a battery indicator, use this CGRAM character. To vary the actual battery indicator displayed, write different bitmaps to the CGRAM bitmap. You now have 7 bitmaps freee for other special characters.

 

When you think about it for a while, you can actually expand this technique to have 8 different "animated characters" displayed all at once. One battery indicator, one hourglass, one signal level indicator, two forming a stereo VU level indicator, one blinking eye, one beer glass being emptied, one 8x8 snake game, and another 8x8 snake game (in a different state than the first one!).

 

If you want an animation in one character position, you only need to use one of the eight custom characters.

As of January 15, 2018, Site fix-up work has begun! Now do your part and report any bugs or deficiencies here

No guarantees, but if we don't report problems they won't get much of  a chance to be fixed! Details/discussions at link given just above.

 

"Some questions have no answers."[C Baird] "There comes a point where the spoon-feeding has to stop and the independent thinking has to start." [C Lawson] "There are always ways to disagree, without being disagreeable."[E Weddington] "Words represent concepts. Use the wrong words, communicate the wrong concept." [J Morin] "Persistence only goes so far if you set yourself up for failure." [Kartman]

Last Edited: Sun. Jul 30, 2017 - 02:53 PM
  • 1
  • 2
  • 3
  • 4
  • 5
Total votes: 0

clawson wrote:
See #89 . (crikey, 89 posts for the simple concept of double indirection?)

 

I saw it and that's what I said I was not following.

 

You said:

clawson wrote:
He's saying you might have defined char 3 as AA, AA, AA, AA, AA, AA, AA, AA ...

 

What does this means? What char 3 is that? DDRAM, CGRAM or what? Can you be more specific? And how that char 3 is declared?

  • 1
  • 2
  • 3
  • 4
  • 5
Total votes: 0

Oh come on. Just read and think for once. There's spoon feeding then there's spoon feeding!
.
If you just "can't get" this feature then forget about trying to use it. Already it's clear to me that it's not going to deliver your final goal here anyway.
.
The big 'A' you show in #69 looks like it would need 13 new characters all defined and onscreen at once. You have only 8.

Last Edited: Sun. Jul 30, 2017 - 03:09 PM
  • 1
  • 2
  • 3
  • 4
  • 5
Total votes: 0

Maybe an illustration can clear things up..

 

Taking your sketch of how you want to display a big "A" in 5x4 character cells, how many different special characters do you need? Lets put numbers on them!

 

 

Blank cells don't need any special characters. Next, some cells above have the same number because they use the same special character. Finally, your LCD probably already has a block character (all pixels set) in CGROM so you don't need a special character for the cells marked 14.

 

As Cliff says, you need 13 special characters, all at once. The 44780 on your display can only handle 8 at a time.

 

If you make 12 to instead look like 11 you've saved one special character.If you get rid of 7 and 8 you've saved two more. Make 3 look like 11 and that's another one. Then e.g. make 10 and 13 look like the 14s and you're home free.

But that is for one "big character" of your daughters name.

 

You either have to 

  • Get a GLCD, or
  • Devise a scheme where you use simpler character cell components. But eve "only horizontal and vertical lines - 4 angles, two lines and one cross" could not get you there. You'd need some non-vertical/horizontal also. And again you're over the limit of 8 special characters.

 

This falls back on the thing we repeat here ever so often: First plan what you want to do, investigate how it can be done and what hardware and software requirements you have, then acquire the hardware  and then do it. You've started at the wrong end.

 

If your requirement still stands (your daughters name in big letters) then get a GLCD. To get big letters you will need to pay more  (probably much more) for the GLCD than you did for  the character LCD.

As of January 15, 2018, Site fix-up work has begun! Now do your part and report any bugs or deficiencies here

No guarantees, but if we don't report problems they won't get much of  a chance to be fixed! Details/discussions at link given just above.

 

"Some questions have no answers."[C Baird] "There comes a point where the spoon-feeding has to stop and the independent thinking has to start." [C Lawson] "There are always ways to disagree, without being disagreeable."[E Weddington] "Words represent concepts. Use the wrong words, communicate the wrong concept." [J Morin] "Persistence only goes so far if you set yourself up for failure." [Kartman]

  • 1
  • 2
  • 3
  • 4
  • 5
Total votes: 0

Johan, but that's just the A. He said "BIA" and while the I may be possible with existing blocks a big B will require as much as A.
.
A GLCD could even have a picture of Bia.

Last Edited: Sun. Jul 30, 2017 - 04:07 PM
  • 1
  • 2
  • 3
  • 4
  • 5
Total votes: 0

clawson wrote:
Johan, but that's just the A.

Gee, I wish [etc]... ;-)

Wait..

JohanEkdahl wrote:
But that is for one "big character" of your daughters name.

As of January 15, 2018, Site fix-up work has begun! Now do your part and report any bugs or deficiencies here

No guarantees, but if we don't report problems they won't get much of  a chance to be fixed! Details/discussions at link given just above.

 

"Some questions have no answers."[C Baird] "There comes a point where the spoon-feeding has to stop and the independent thinking has to start." [C Lawson] "There are always ways to disagree, without being disagreeable."[E Weddington] "Words represent concepts. Use the wrong words, communicate the wrong concept." [J Morin] "Persistence only goes so far if you set yourself up for failure." [Kartman]

  • 1
  • 2
  • 3
  • 4
  • 5
Total votes: 0

Ok, I'll give up on this idea!

 

I'll think about something else to make with the LCD!

I'm doing this now because next year (school year that starts in September) I'll be finishing my graduation and I'll need an LCD to show some information of my project that, if teachers agree, will be an antenna analyser or a Direction Finder! So I'm trying to get myself a bit ahead of schedule in terms of getting some basic knowledge with Mega328 and LCD!

  • 1
  • 2
  • 3
  • 4
  • 5
Total votes: 0

I'm confused....

I was under the impression that you have 8051 knowledge - which should make using the AVR pretty easy, and you have used AVR...LOTS of them based on this:

 

PsySc0rpi0n wrote:
Yes, already fixed! I have one other experienced "net" friend in IRC channels that already helped me sorting this out! I worked with a lot of AVRs in the past! And yes, I was reading that same link I found through Google but haven't finished the reading!

To which storing stuff in the AVR FLASH memory should be a simple task.

 

PsySc0rpi0n wrote:
Ok, I'll give up on this idea! I'll think about something else to make with the LCD!

 

And after 98+ posts you elect to 'give up' on this and move on to a GLCD!? surpriseangry

 

Since it would appear that this whole thread was a waste of time in many respects how about you give us some background on what you DO know so we can answer accordingly in the future?

 

Jim

I would rather attempt something great and fail, than attempt nothing and succeed - Fortune Cookie

 

"The critical shortage here is not stuff, but time." - Johan Ekdahl

 

"Step N is required before you can do step N+1!" - ka7ehk

 

"If you want a career with a known path - become an undertaker. Dead people don't sue!" - Kartman

"Why is there a "Highway to Hell" and only a "Stairway to Heaven"? A prediction of the expected traffic load?"  - Lee "theusch"

 

Speak sweetly. It makes your words easier to digest when at a later date you have to eat them ;-)  - Source Unknown

Please Read: Code-of-Conduct

Atmel Studio6.2/AS7, DipTrace, Quartus, MPLAB, RSLogix user

  • 1
  • 2
  • 3
  • 4
  • 5
Total votes: 0

jgmdesign wrote:
And after 98+ posts you elect to 'give up' on this and move on to a GLCD!?

It has to be said that it was done on several resident 'freaks advice.

As of January 15, 2018, Site fix-up work has begun! Now do your part and report any bugs or deficiencies here

No guarantees, but if we don't report problems they won't get much of  a chance to be fixed! Details/discussions at link given just above.

 

"Some questions have no answers."[C Baird] "There comes a point where the spoon-feeding has to stop and the independent thinking has to start." [C Lawson] "There are always ways to disagree, without being disagreeable."[E Weddington] "Words represent concepts. Use the wrong words, communicate the wrong concept." [J Morin] "Persistence only goes so far if you set yourself up for failure." [Kartman]

  • 1
  • 2
  • 3
  • 4
  • 5
Total votes: 0

jgmdesign wrote:

I'm confused....

I was under the impression that you have 8051 knowledge - which should make using the AVR pretty easy, and you have used AVR...LOTS of them based on this:

 

PsySc0rpi0n wrote:
Yes, already fixed! I have one other experienced "net" friend in IRC channels that already helped me sorting this out! I worked with a lot of AVRs in the past! And yes, I was reading that same link I found through Google but haven't finished the reading!

To which storing stuff in the AVR FLASH memory should be a simple task.

 

PsySc0rpi0n wrote:
Ok, I'll give up on this idea! I'll think about something else to make with the LCD!

 

And after 98+ posts you elect to 'give up' on this and move on to a GLCD!? surpriseangry

 

Since it would appear that this whole thread was a waste of time in many respects how about you give us some background on what you DO know so we can answer accordingly in the future?

 

Jim

 

jgmdesign I mistyped that sentence you made red! I was saying that a friend of mine in IRC channels, that worked a lot in the past with AVRs, helped me fixing that problem! I'm sorry for my mistake typing!

 

I have worked with 8051 but maybe you understood it the wrong way! I worked with 8051 in school context! We did a small game using an 8051, an LCD (16 x 2) and a 2 digit 7 segment display. I never worked in this area except for school purposes!

 

I said I'm giving up because as far as I understood, I can't draw my daughters name (3 big chars) with an LCD. So, why bother with something that I know it cannot be done?

 

You guys are always saying you waste your precious time with me. Well, it might have been wasted time for you, but I learnt quite some stuff in this thread. And if you think like that, then you always waste time when you teach/help others with things you already know! In other words, you only wouldn't be wasting time if you were discussing subjects you also don't know!

 

Ok, and as a personal note, I never worked in this area, never had any knowledge on electronics/micro-controllers and I only got the interest after in school we learned about micro-controllers! I also never worked with programming, except when I learned in school! So basically, this all came because of school!

 

I work in the fabrics sector, I draw patterns for almost every piece of clothe you can think about with the help of dedicated CAD software! I started studying again at the age of 31 after over 11 years after leaving school! Now I'm trying to graduate in Electrical Engineering in the branch of Electronics and Telecomms! And probably next ear I'll complete graduation!

 

Sorry for not clearing this info sooner!

Pages