{"id":1233,"date":"2021-05-12T13:49:47","date_gmt":"2021-05-12T12:49:47","guid":{"rendered":"http:\/\/www.igfasouza.com\/blog\/?p=1233"},"modified":"2021-06-24T11:43:13","modified_gmt":"2021-06-24T10:43:13","slug":"spring-thymeleaf-raspberry-pi-lcd","status":"publish","type":"post","link":"http:\/\/www.igfasouza.com\/blog\/spring-thymeleaf-raspberry-pi-lcd\/","title":{"rendered":"Spring Thymeleaf Raspberry PI LCD"},"content":{"rendered":"<p><img loading=\"lazy\" decoding=\"async\" src=\"http:\/\/www.igfasouza.com\/blog\/wp-content\/uploads\/2021\/05\/spring_lcd.jpg\" alt=\"\" width=\"933\" height=\"515\" class=\"alignnone size-full wp-image-1234\" srcset=\"http:\/\/www.igfasouza.com\/blog\/wp-content\/uploads\/2021\/05\/spring_lcd.jpg 933w, http:\/\/www.igfasouza.com\/blog\/wp-content\/uploads\/2021\/05\/spring_lcd-300x166.jpg 300w, http:\/\/www.igfasouza.com\/blog\/wp-content\/uploads\/2021\/05\/spring_lcd-768x424.jpg 768w\" sizes=\"auto, (max-width: 933px) 100vw, 933px\" \/><\/p>\n<p><b>How\u2019s it going there?<\/b><\/p>\n<p>This post is to show how I created a web app to control an LCD with a Raspberry PI using Spring Boot and Thymeleaf. This is another blog about Java on Raspberry PI.<\/p>\n<p><a href=\"https:\/\/spring.io\/projects\/spring-boot\" rel=\"noopener\" target=\"_blank\">Spring Boot<\/a> is an extension of the Spring framework, which eliminates the boilerplate configurations required for setting up a Spring application.<\/p>\n<p><a href=\"https:\/\/www.thymeleaf.org\/\" rel=\"noopener\" target=\"_blank\">Thymeleaf<\/a> is a Java template engine for processing and creating HTML, XML, JavaScript, CSS, and text.<\/p>\n<p><img loading=\"lazy\" decoding=\"async\" src=\"http:\/\/www.igfasouza.com\/blog\/wp-content\/uploads\/2021\/05\/lcd_example01-1024x365.jpg\" alt=\"\" width=\"640\" height=\"228\" class=\"alignnone size-large wp-image-1235\" srcset=\"http:\/\/www.igfasouza.com\/blog\/wp-content\/uploads\/2021\/05\/lcd_example01-1024x365.jpg 1024w, http:\/\/www.igfasouza.com\/blog\/wp-content\/uploads\/2021\/05\/lcd_example01-300x107.jpg 300w, http:\/\/www.igfasouza.com\/blog\/wp-content\/uploads\/2021\/05\/lcd_example01-768x274.jpg 768w, http:\/\/www.igfasouza.com\/blog\/wp-content\/uploads\/2021\/05\/lcd_example01.jpg 1204w\" sizes=\"auto, (max-width: 640px) 100vw, 640px\" \/><br \/>\n<small>Picture 1: LCD example<\/small><\/p>\n<p>I have the <strong><em>St7920<\/em><\/strong> model. St7920 or 12864zw is probably the cheapest 128\u00d764 graphic LCD that you can find.<\/p>\n<h2>Schematics<\/h2>\n<p><img loading=\"lazy\" decoding=\"async\" src=\"http:\/\/www.igfasouza.com\/blog\/wp-content\/uploads\/2021\/05\/glcd-pinout-683x1024.jpg\" alt=\"\" width=\"640\" height=\"960\" class=\"alignnone size-large wp-image-1236\" srcset=\"http:\/\/www.igfasouza.com\/blog\/wp-content\/uploads\/2021\/05\/glcd-pinout-683x1024.jpg 683w, http:\/\/www.igfasouza.com\/blog\/wp-content\/uploads\/2021\/05\/glcd-pinout-200x300.jpg 200w, http:\/\/www.igfasouza.com\/blog\/wp-content\/uploads\/2021\/05\/glcd-pinout-768x1152.jpg 768w, http:\/\/www.igfasouza.com\/blog\/wp-content\/uploads\/2021\/05\/glcd-pinout.jpg 800w\" sizes=\"auto, (max-width: 640px) 100vw, 640px\" \/><br \/>\n<small>Picture 2: LCD Schematics<\/small><\/p>\n<p><img loading=\"lazy\" decoding=\"async\" src=\"http:\/\/www.igfasouza.com\/blog\/wp-content\/uploads\/2021\/05\/LCD_raspberry_map-300x164.png\" alt=\"\" width=\"300\" height=\"164\" class=\"alignnone size-medium wp-image-1237\" srcset=\"http:\/\/www.igfasouza.com\/blog\/wp-content\/uploads\/2021\/05\/LCD_raspberry_map-300x164.png 300w, http:\/\/www.igfasouza.com\/blog\/wp-content\/uploads\/2021\/05\/LCD_raspberry_map.png 548w\" sizes=\"auto, (max-width: 300px) 100vw, 300px\" \/><br \/>\n<small>Table 1: Raspberry PI PIN and GPIO map<\/small><\/p>\n<p>I\u2019m using this <a href=\"https:\/\/github.com\/ribasco\/ucgdisplay\" rel=\"noopener\" target=\"_blank\">Java API<\/a><\/p>\n<h2>Idea<\/h2>\n<p>A simple Spring Boot Thymeleaf app where it shows a form with a 128&#215;64 table. Each table position is the representation of the LCD graphic display. I created an Array of bits with all positions of this table.<\/p>\n<p><img loading=\"lazy\" decoding=\"async\" src=\"http:\/\/www.igfasouza.com\/blog\/wp-content\/uploads\/2021\/05\/spring_thymeleaf_app01.png\" alt=\"\" width=\"1784\" height=\"1242\" class=\"alignnone size-full wp-image-1238\" srcset=\"http:\/\/www.igfasouza.com\/blog\/wp-content\/uploads\/2021\/05\/spring_thymeleaf_app01.png 1784w, http:\/\/www.igfasouza.com\/blog\/wp-content\/uploads\/2021\/05\/spring_thymeleaf_app01-300x209.png 300w, http:\/\/www.igfasouza.com\/blog\/wp-content\/uploads\/2021\/05\/spring_thymeleaf_app01-1024x713.png 1024w, http:\/\/www.igfasouza.com\/blog\/wp-content\/uploads\/2021\/05\/spring_thymeleaf_app01-768x535.png 768w, http:\/\/www.igfasouza.com\/blog\/wp-content\/uploads\/2021\/05\/spring_thymeleaf_app01-1536x1069.png 1536w, http:\/\/www.igfasouza.com\/blog\/wp-content\/uploads\/2021\/05\/spring_thymeleaf_app01-250x175.png 250w\" sizes=\"auto, (max-width: 1784px) 100vw, 1784px\" \/><br \/>\n<small>Picture 3: end-to-end flow<\/small><\/p>\n<p>The Array button generates an Array of Bits, and preview creates a picture of the result.<\/p>\n<p><img loading=\"lazy\" decoding=\"async\" src=\"http:\/\/www.igfasouza.com\/blog\/wp-content\/uploads\/2021\/05\/PXL_20210502_193343880-scaled.jpg\" alt=\"\" width=\"2560\" height=\"1920\" class=\"alignnone size-full wp-image-1239\" srcset=\"http:\/\/www.igfasouza.com\/blog\/wp-content\/uploads\/2021\/05\/PXL_20210502_193343880-scaled.jpg 2560w, http:\/\/www.igfasouza.com\/blog\/wp-content\/uploads\/2021\/05\/PXL_20210502_193343880-300x225.jpg 300w\" sizes=\"auto, (max-width: 2560px) 100vw, 2560px\" \/><br \/>\n<small>Picture 4: Shows the form table that represents the 128&#215;64 bits positions<\/small><\/p>\n<p>The LCD graphic Display expects an Array of Bytes from the XBM format.<br \/>\nXBM is a monochrome bitmap format in which data is stored as a C language data array. Primarily used for the storage of cursor and icon bitmaps for use in the X graphical user interface. <\/p>\n<p>So I added a method to convert my Array of bits into an Array of Bytes.<\/p>\n<p>Many tools including GIMP can save an image as XBM. A nice step-by-step instruction that the API docs show is <a href=\"https:\/\/sandhansblog.wordpress.com\/2017\/04\/16\/interfacing-displaying-a-custom-graphic-on-an-0-96-i2c-oled\/\" rel=\"noopener\" target=\"_blank\">here<\/a>.<\/p>\n<h2>Code<\/h2>\n<div class=\"codecolorer-container java blackboard\" style=\"overflow:auto;white-space:nowrap;\"><table cellspacing=\"0\" cellpadding=\"0\"><tbody><tr><td class=\"line-numbers\"><div>1<br \/>2<br \/>3<br \/>4<br \/>5<br \/>6<br \/>7<br \/>8<br \/>9<br \/>10<br \/>11<br \/>12<br \/>13<br \/><\/div><\/td><td><div class=\"java codecolorer\">&nbsp; &nbsp; <span class=\"co1\">\/\/ - MOSI = 10<\/span><br \/>\n&nbsp; &nbsp;<span class=\"co1\">\/\/ - SCLK = 11<\/span><br \/>\n&nbsp; &nbsp;<span class=\"co1\">\/\/ - CE1 = 7<\/span><br \/>\n&nbsp; &nbsp;config <span class=\"sy0\">=<\/span> GlcdConfigBuilder<br \/>\n&nbsp; &nbsp; &nbsp; &nbsp;<span class=\"co1\">\/\/Use ST7920 - 128 x 64 display, SPI 4-wire Hardware<\/span><br \/>\n&nbsp; &nbsp; &nbsp; &nbsp;.<span class=\"me1\">create<\/span><span class=\"br0\">&#40;<\/span>Glcd.<span class=\"me1\">ST7920<\/span>.<span class=\"me1\">D_128x64<\/span>, GlcdCommProtocol.<span class=\"me1\">SPI_SW_4WIRE_ST7920<\/span><span class=\"br0\">&#41;<\/span><br \/>\n&nbsp; &nbsp; &nbsp; &nbsp;<span class=\"co1\">\/\/Set to 180 rotation<\/span><br \/>\n&nbsp; &nbsp; &nbsp; &nbsp;.<span class=\"me1\">option<\/span><span class=\"br0\">&#40;<\/span>GlcdOption.<span class=\"me1\">ROTATION<\/span>, GlcdRotation.<span class=\"me1\">ROTATION_180<\/span><span class=\"br0\">&#41;<\/span><br \/>\n&nbsp; &nbsp; &nbsp; &nbsp;.<span class=\"me1\">option<\/span><span class=\"br0\">&#40;<\/span>GlcdOption.<span class=\"me1\">PROVIDER<\/span>, <a href=\"http:\/\/www.google.com\/search?hl=en&amp;q=allinurl%3Adocs.oracle.com+javase+docs+api+provider\"><span class=\"kw3\">Provider<\/span><\/a>.<span class=\"me1\">SYSTEM<\/span><span class=\"br0\">&#41;<\/span><br \/>\n&nbsp; &nbsp; &nbsp; &nbsp;.<span class=\"me1\">mapPin<\/span><span class=\"br0\">&#40;<\/span>GlcdPin.<span class=\"me1\">SPI_MOSI<\/span>, <span class=\"nu0\">19<\/span><span class=\"br0\">&#41;<\/span><br \/>\n&nbsp; &nbsp; &nbsp; &nbsp;.<span class=\"me1\">mapPin<\/span><span class=\"br0\">&#40;<\/span>GlcdPin.<span class=\"me1\">SPI_CLOCK<\/span>, <span class=\"nu0\">13<\/span><span class=\"br0\">&#41;<\/span><br \/>\n&nbsp; &nbsp; &nbsp; &nbsp;.<span class=\"me1\">mapPin<\/span><span class=\"br0\">&#40;<\/span>GlcdPin.<span class=\"me1\">CS<\/span>, <span class=\"nu0\">26<\/span><span class=\"br0\">&#41;<\/span><br \/>\n&nbsp; &nbsp; &nbsp; &nbsp;.<span class=\"me1\">build<\/span><span class=\"br0\">&#40;<\/span><span class=\"br0\">&#41;<\/span><span class=\"sy0\">;<\/span><\/div><\/td><\/tr><\/tbody><\/table><\/div>\n<div class=\"codecolorer-container java blackboard\" style=\"overflow:auto;white-space:nowrap;\"><table cellspacing=\"0\" cellpadding=\"0\"><tbody><tr><td class=\"line-numbers\"><div>1<br \/>2<br \/>3<br \/>4<br \/>5<br \/>6<br \/>7<br \/>8<br \/><\/div><\/td><td><div class=\"java codecolorer\"><span class=\"kw1\">private<\/span> <span class=\"kw1\">static<\/span> <span class=\"kw4\">byte<\/span><span class=\"br0\">&#91;<\/span><span class=\"br0\">&#93;<\/span> encodeToByteArray<span class=\"br0\">&#40;<\/span><span class=\"kw4\">int<\/span><span class=\"br0\">&#91;<\/span><span class=\"br0\">&#93;<\/span> bits<span class=\"br0\">&#41;<\/span> <span class=\"br0\">&#123;<\/span><br \/>\n&nbsp; &nbsp; &nbsp; &nbsp; <a href=\"http:\/\/www.google.com\/search?hl=en&amp;q=allinurl%3Adocs.oracle.com+javase+docs+api+bitset\"><span class=\"kw3\">BitSet<\/span><\/a> bitSet <span class=\"sy0\">=<\/span> <span class=\"kw1\">new<\/span> <a href=\"http:\/\/www.google.com\/search?hl=en&amp;q=allinurl%3Adocs.oracle.com+javase+docs+api+bitset\"><span class=\"kw3\">BitSet<\/span><\/a><span class=\"br0\">&#40;<\/span>bits.<span class=\"me1\">length<\/span><span class=\"br0\">&#41;<\/span><span class=\"sy0\">;<\/span><br \/>\n&nbsp; &nbsp; &nbsp; &nbsp; <span class=\"kw1\">for<\/span> <span class=\"br0\">&#40;<\/span><span class=\"kw4\">int<\/span> index <span class=\"sy0\">=<\/span> <span class=\"nu0\">0<\/span><span class=\"sy0\">;<\/span> index <span class=\"sy0\">&lt;<\/span> bits.<span class=\"me1\">length<\/span><span class=\"sy0\">;<\/span> index<span class=\"sy0\">++<\/span><span class=\"br0\">&#41;<\/span> <span class=\"br0\">&#123;<\/span><br \/>\n&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; bitSet.<span class=\"me1\">set<\/span><span class=\"br0\">&#40;<\/span>index, bits<span class=\"br0\">&#91;<\/span>index<span class=\"br0\">&#93;<\/span> <span class=\"sy0\">&gt;<\/span> <span class=\"nu0\">0<\/span><span class=\"br0\">&#41;<\/span><span class=\"sy0\">;<\/span><br \/>\n&nbsp; &nbsp; &nbsp; &nbsp; <span class=\"br0\">&#125;<\/span><br \/>\n<br \/>\n&nbsp; &nbsp; &nbsp; &nbsp; <span class=\"kw1\">return<\/span> bitSet.<span class=\"me1\">toByteArray<\/span><span class=\"br0\">&#40;<\/span><span class=\"br0\">&#41;<\/span><span class=\"sy0\">;<\/span><br \/>\n&nbsp; &nbsp; <span class=\"br0\">&#125;<\/span><\/div><\/td><\/tr><\/tbody><\/table><\/div>\n<p>You can get the full code on my <a href=\"https:\/\/github.com\/igfasouza\/Spring-Thymeleaf-Raspberry-PI-LCD\" rel=\"noopener\" target=\"_blank\">GitHub<\/a>.<\/p>\n<h2>Result<\/h2>\n<p><img loading=\"lazy\" decoding=\"async\" src=\"http:\/\/www.igfasouza.com\/blog\/wp-content\/uploads\/2021\/05\/lcd_example02.jpg\" alt=\"\" width=\"1219\" height=\"481\" class=\"alignnone size-full wp-image-1241\" srcset=\"http:\/\/www.igfasouza.com\/blog\/wp-content\/uploads\/2021\/05\/lcd_example02.jpg 1219w, http:\/\/www.igfasouza.com\/blog\/wp-content\/uploads\/2021\/05\/lcd_example02-300x118.jpg 300w, http:\/\/www.igfasouza.com\/blog\/wp-content\/uploads\/2021\/05\/lcd_example02-1024x404.jpg 1024w, http:\/\/www.igfasouza.com\/blog\/wp-content\/uploads\/2021\/05\/lcd_example02-768x303.jpg 768w\" sizes=\"auto, (max-width: 1219px) 100vw, 1219px\" \/><br \/>\n<small>Picture 5: LCD examples<\/small><\/p>\n<p><img loading=\"lazy\" decoding=\"async\" src=\"http:\/\/www.igfasouza.com\/blog\/wp-content\/uploads\/2021\/05\/lcd_example03.jpg\" alt=\"\" width=\"1286\" height=\"457\" class=\"alignnone size-full wp-image-1242\" srcset=\"http:\/\/www.igfasouza.com\/blog\/wp-content\/uploads\/2021\/05\/lcd_example03.jpg 1286w, http:\/\/www.igfasouza.com\/blog\/wp-content\/uploads\/2021\/05\/lcd_example03-300x107.jpg 300w, http:\/\/www.igfasouza.com\/blog\/wp-content\/uploads\/2021\/05\/lcd_example03-1024x364.jpg 1024w, http:\/\/www.igfasouza.com\/blog\/wp-content\/uploads\/2021\/05\/lcd_example03-768x273.jpg 768w\" sizes=\"auto, (max-width: 1286px) 100vw, 1286px\" \/><br \/>\n<small>Picture 6: LCD examples<\/small><\/p>\n<p><iframe loading=\"lazy\" width=\"560\" height=\"315\" src=\"https:\/\/www.youtube.com\/embed\/57Si7NI6_b8\" title=\"YouTube video player\" frameborder=\"0\" allow=\"accelerometer; autoplay; clipboard-write; encrypted-media; gyroscope; picture-in-picture\" allowfullscreen><\/iframe><\/p>\n<p>There are some XBM files inside the resources folder and you can follow up on the API example to display these images.<\/p>\n<p>I started to add the logic for a Combobox to show all XMB files inside resources and once selected display that image on the LCD.<\/p>\n<p>The call to action is to go ahead and add this functionality to the application. Just need to add the Combobox and the rule on the java to submit the selected name. <\/p>\n<p>Remember to use the hashtag <strong><em>#JavaOnRaspberryPi<\/em><\/strong> on Twitter to show the world Raspberry Pi with Java.<\/p>\n<h2>Links<\/h2>\n<p><a href=\"https:\/\/en.wikipedia.org\/wiki\/X_BitMap\" rel=\"noopener\" target=\"_blank\">https:\/\/en.wikipedia.org\/wiki\/X_BitMap <\/a>   <\/p>\n<p><a href=\"https:\/\/www.fileformat.info\/format\/xbm\/egff.htm\" rel=\"noopener\" target=\"_blank\">https:\/\/www.fileformat.info\/format\/xbm\/egff.htm<\/a><\/p>\n<p><a href=\"https:\/\/arduino-tutorials.net\/tutorial\/control-graphic-lcd-display-spi-st7920-128x64-with-arduino\" rel=\"noopener\" target=\"_blank\">https:\/\/arduino-tutorials.net\/tutorial\/control-graphic-lcd-display-spi-st7920-128&#215;64-with-arduino<\/a><\/p>\n<p><a href=\"https:\/\/spring.io\/projects\/spring-boot\" rel=\"noopener\" target=\"_blank\">https:\/\/spring.io\/projects\/spring-boot<\/a><\/p>\n<p><a href=\"https:\/\/www.thymeleaf.org\/\" rel=\"noopener\" target=\"_blank\">https:\/\/www.thymeleaf.org\/<\/a><\/p>\n<p><a href=\"https:\/\/github.com\/ribasco\/ucgdisplay\" rel=\"noopener\" target=\"_blank\">https:\/\/github.com\/ribasco\/ucgdisplay<\/a><\/p>\n","protected":false},"excerpt":{"rendered":"<p>How\u2019s it going there? This post is to show how I created a web app to control an LCD with a Raspberry PI using Spring Boot and Thymeleaf. This is another blog about Java on Raspberry PI. Spring Boot is&hellip; <a href=\"http:\/\/www.igfasouza.com\/blog\/spring-thymeleaf-raspberry-pi-lcd\/\" class=\"more-link\">Continue Reading <span class=\"meta-nav\">&rarr;<\/span><\/a><\/p>\n","protected":false},"author":1,"featured_media":1234,"comment_status":"open","ping_status":"open","sticky":false,"template":"","format":"standard","meta":{"footnotes":""},"categories":[23,24],"tags":[17,13],"class_list":["post-1233","post","type-post","status-publish","format-standard","has-post-thumbnail","hentry","category-java","category-raspberry-pi","tag-java","tag-raspberry-pi"],"_links":{"self":[{"href":"http:\/\/www.igfasouza.com\/blog\/wp-json\/wp\/v2\/posts\/1233","targetHints":{"allow":["GET"]}}],"collection":[{"href":"http:\/\/www.igfasouza.com\/blog\/wp-json\/wp\/v2\/posts"}],"about":[{"href":"http:\/\/www.igfasouza.com\/blog\/wp-json\/wp\/v2\/types\/post"}],"author":[{"embeddable":true,"href":"http:\/\/www.igfasouza.com\/blog\/wp-json\/wp\/v2\/users\/1"}],"replies":[{"embeddable":true,"href":"http:\/\/www.igfasouza.com\/blog\/wp-json\/wp\/v2\/comments?post=1233"}],"version-history":[{"count":3,"href":"http:\/\/www.igfasouza.com\/blog\/wp-json\/wp\/v2\/posts\/1233\/revisions"}],"predecessor-version":[{"id":1259,"href":"http:\/\/www.igfasouza.com\/blog\/wp-json\/wp\/v2\/posts\/1233\/revisions\/1259"}],"wp:featuredmedia":[{"embeddable":true,"href":"http:\/\/www.igfasouza.com\/blog\/wp-json\/wp\/v2\/media\/1234"}],"wp:attachment":[{"href":"http:\/\/www.igfasouza.com\/blog\/wp-json\/wp\/v2\/media?parent=1233"}],"wp:term":[{"taxonomy":"category","embeddable":true,"href":"http:\/\/www.igfasouza.com\/blog\/wp-json\/wp\/v2\/categories?post=1233"},{"taxonomy":"post_tag","embeddable":true,"href":"http:\/\/www.igfasouza.com\/blog\/wp-json\/wp\/v2\/tags?post=1233"}],"curies":[{"name":"wp","href":"https:\/\/api.w.org\/{rel}","templated":true}]}}