{"id":1832,"date":"2020-04-21T06:04:23","date_gmt":"2020-04-21T06:04:23","guid":{"rendered":"https:\/\/www.sabulo.com\/sb\/?p=1832"},"modified":"2020-10-29T12:10:07","modified_gmt":"2020-10-29T10:10:07","slug":"using-7-segment-led-displays-part-4-dual-quadruple-units","status":"publish","type":"post","link":"https:\/\/www.sabulo.com\/sb\/led\/using-7-segment-led-displays-part-4-dual-quadruple-units\/","title":{"rendered":"Using 7 Segment LED displays, Part 4 &#8211; dual quadruple units"},"content":{"rendered":"\n<p class=\"wp-block-paragraph\">Okay, I thought the series on 7 segment LED displays would run into three parts, but it has turned out to be a Douglas Adams-esque trilogy in four parts. I had completely forgotten to write about a clock based on a unit of two 4 digit, 7 segment, red-color displays. These have somewhat different method of being run from the prevous instalments. <\/p>\n\n\n\n<p class=\"wp-block-paragraph\">In the past, you saw how to run a <a rel=\"noreferrer noopener\" href=\"https:\/\/www.sabulo.com\/sb\/arduino\/using-7-segment-led-displays-part-1\/\" target=\"_blank\">single digit display with a 74HC595 shift register<\/a>, then how to do a <a rel=\"noreferrer noopener\" href=\"https:\/\/www.sabulo.com\/sb\/excel\/using-7-segment-led-displays-part-2\/\" target=\"_blank\">four-digit system with the same chip<\/a>, and then how to run giant 10 cm single digit displays so that you get a <a rel=\"noreferrer noopener\" href=\"https:\/\/www.sabulo.com\/sb\/arduino\/using-7-segment-led-displays-part-3\/\" target=\"_blank\">four digit countdown timer<\/a>. These had shift registers, which were chained.  <\/p>\n\n\n\n<p class=\"wp-block-paragraph\">The unit that I will discuss in this blog post is different. It looks like this:<\/p>\n\n\n\n<div class=\"wp-block-image\"><figure class=\"aligncenter size-large\"><img data-recalc-dims=\"1\" loading=\"lazy\" decoding=\"async\" width=\"825\" height=\"313\" src=\"https:\/\/i0.wp.com\/www.sabulo.com\/sb\/wp-content\/uploads\/2020\/04\/dual-Seven-segment_1.jpg?resize=825%2C313&#038;ssl=1\" alt=\"\" class=\"wp-image-1833\" srcset=\"https:\/\/i0.wp.com\/www.sabulo.com\/sb\/wp-content\/uploads\/2020\/04\/dual-Seven-segment_1.jpg?w=1024&amp;ssl=1 1024w, https:\/\/i0.wp.com\/www.sabulo.com\/sb\/wp-content\/uploads\/2020\/04\/dual-Seven-segment_1.jpg?resize=300%2C114&amp;ssl=1 300w, https:\/\/i0.wp.com\/www.sabulo.com\/sb\/wp-content\/uploads\/2020\/04\/dual-Seven-segment_1.jpg?resize=768%2C291&amp;ssl=1 768w\" sizes=\"auto, (max-width: 825px) 100vw, 825px\" \/><figcaption>Dual 4 digit, 7 segment display. Image courtesy hub360<\/figcaption><\/figure><\/div>\n\n\n\n<p class=\"wp-block-paragraph\">It is called a MAX7219 dual display, and as you see, it comes mounted on a printed circuit board, and there are only five pins to the entire unit. This is very handy when you start setting this up. Here&#8217;s how my system looks before being mounted on a 3D printed plate:<\/p>\n\n\n\n<div class=\"wp-block-image\"><figure class=\"aligncenter size-large\"><img data-recalc-dims=\"1\" loading=\"lazy\" decoding=\"async\" width=\"703\" height=\"937\" src=\"https:\/\/i0.wp.com\/www.sabulo.com\/sb\/wp-content\/uploads\/2020\/04\/2x4-display.jpg?resize=703%2C937&#038;ssl=1\" alt=\"\" class=\"wp-image-1834\" srcset=\"https:\/\/i0.wp.com\/www.sabulo.com\/sb\/wp-content\/uploads\/2020\/04\/2x4-display.jpg?w=703&amp;ssl=1 703w, https:\/\/i0.wp.com\/www.sabulo.com\/sb\/wp-content\/uploads\/2020\/04\/2x4-display.jpg?resize=225%2C300&amp;ssl=1 225w\" sizes=\"auto, (max-width: 703px) 100vw, 703px\" \/><figcaption>Device showing date and time, using an ESP32 and MAX71219 dual<\/figcaption><\/figure><\/div>\n\n\n\n<p class=\"wp-block-paragraph\"><a href=\"https:\/\/github.com\/HeikkiHietala\/ESP32-MAX7219-eight-LED-digit-clock\" target=\"_blank\" rel=\"noreferrer noopener\">The full code is available on my Github page.<\/a><\/p>\n\n\n\n<p class=\"wp-block-paragraph\">Let&#8217;s have a look at the constituent parts of this contraption.<\/p>\n\n\n\n<h3 class=\"wp-block-heading\">MAX7219 Display Driver<\/h3>\n\n\n\n<p class=\"wp-block-paragraph\">This nifty little integrated circuit is really powerful, yet costs only 8 euros. <a rel=\"noreferrer noopener\" href=\"https:\/\/www.adafruit.com\/product\/453\" target=\"_blank\">On Adafruit&#8217;s site<\/a>, it is described thus: <\/p>\n\n\n\n<blockquote class=\"wp-block-quote is-layout-flow wp-block-quote-is-layout-flow\"><p>When you need some help driving a lot of LEDs, the MAX7219 is the best friend you could hope for. Many of us know that if you want to control a lot of LEDs, you&#8217;ll want to use&nbsp;<a href=\"http:\/\/www.arduino.cc\/playground\/Main\/LEDMatrix\">multiplexing<\/a>, a technique that lets you control 64 LEDs (say) with only 16 pins (8&#215;8). The annoying thing about &#8216;plexing is that you need to use&nbsp;<a href=\"http:\/\/s3.amazonaws.com\/evilmadscience\/KitInstrux\/peggy1_1s.pdf\">8 power transistors<\/a>&nbsp;(or a power register\/latch, that can supply over 100mA per pin) AND you have to constantly refresh the display to keep the image stable. If you need to get something together quickly, or don&#8217;t want to bother with writing all that code, and especially if you want clean wiring, this chip is the one-stop-solution!<\/p><p>The MAX7219 does all the control and refresh work for you in driving either an 8&#215;8 matrix display or 8 x 7-segment displays (usually these also have a dot so its really an 8-segment display) &#8211; 64 LEDs total. All you have to do is send it serial commands via the 4-pin SPI interface and it will auto-magically take care of the rest. <\/p><cite>Courtesy adafruit.com<\/cite><\/blockquote>\n\n\n\n<p class=\"wp-block-paragraph\">This means that you can do this unit with a single MAX7219 display driver. <a rel=\"noreferrer noopener\" href=\"https:\/\/cdn-shop.adafruit.com\/datasheets\/MAX7219.pdf\" target=\"_blank\">The datasheet is here<\/a> and in it, there is this  picture of the connectors, and a typical use:<\/p>\n\n\n\n<div class=\"wp-block-image\"><figure class=\"aligncenter size-large\"><img loading=\"lazy\" decoding=\"async\" width=\"1082\" height=\"574\" src=\"https:\/\/i0.wp.com\/www.sabulo.com\/sb\/wp-content\/uploads\/2020\/04\/maxim-pins.png?fit=825%2C437&amp;ssl=1\" alt=\"\" class=\"wp-image-1835\" srcset=\"https:\/\/i0.wp.com\/www.sabulo.com\/sb\/wp-content\/uploads\/2020\/04\/maxim-pins.png?w=1082&amp;ssl=1 1082w, https:\/\/i0.wp.com\/www.sabulo.com\/sb\/wp-content\/uploads\/2020\/04\/maxim-pins.png?resize=300%2C159&amp;ssl=1 300w, https:\/\/i0.wp.com\/www.sabulo.com\/sb\/wp-content\/uploads\/2020\/04\/maxim-pins.png?resize=1024%2C543&amp;ssl=1 1024w, https:\/\/i0.wp.com\/www.sabulo.com\/sb\/wp-content\/uploads\/2020\/04\/maxim-pins.png?resize=768%2C407&amp;ssl=1 768w\" sizes=\"auto, (max-width: 825px) 100vw, 825px\" \/><figcaption>MAX7219 wiring, courtesy of adafruit<\/figcaption><\/figure><\/div>\n\n\n\n<p class=\"wp-block-paragraph\">As you can see, all you need to bring in from the Arduino or ESP32 (as in my case) is three pins. This is a whopping improvement over the previous episodes, when you want to run eight digits. The connections are DIN (Serial Data IN), Load CS (Load Data Input and Chip Select, these deal with passing data into the registers), and CLK (clock signal to tell the device when to load and when to display). <\/p>\n\n\n\n<p class=\"wp-block-paragraph\">You can use the MAX7219 for driving a very large amount of LEDs and add even more by chaining them <\/p>\n\n\n\n<p class=\"wp-block-paragraph\">This display has five pins or holes for pins. It also has the MAX7219 chip buried underneath the displays. This way you can just lead these five wires to it from the controller unit.<\/p>\n\n\n\n<ul class=\"wp-block-list\"><li>VCC, 5 volts in<\/li><li>GND, ground<\/li><li>DIN, data in<\/li><li>LOAD, load data to displays<\/li><li>CLK, clock signal to time the works<\/li><\/ul>\n\n\n\n<p class=\"wp-block-paragraph\">VCC and Ground are connected to ESP32&#8217;s 5V and Ground pins. The others are programmatically selected when writing the code. <\/p>\n\n\n\n<h2 class=\"wp-block-heading\">The DHT11 sensor<\/h2>\n\n\n\n<p class=\"wp-block-paragraph\">The DHT11 is a standard piece of equipment when working with Arduinos or ESP32s, and there is a need for temperature and humidity sensing. It&#8217;s a four pin sensor that takes a 10K resistor to work properly. Its setup is <a rel=\"noreferrer noopener\" href=\"https:\/\/www.circuitbasics.com\/how-to-set-up-the-dht11-humidity-sensor-on-an-arduino\/\" target=\"_blank\">amply described in this page<\/a>, and I will not redo it here. <\/p>\n\n\n\n<div class=\"wp-block-image\"><figure class=\"aligncenter size-large\"><img data-recalc-dims=\"1\" loading=\"lazy\" decoding=\"async\" width=\"500\" height=\"457\" src=\"https:\/\/i0.wp.com\/www.sabulo.com\/sb\/wp-content\/uploads\/2020\/04\/dht11-temperature-and-humidity-sensor-500x500-1.png?resize=500%2C457&#038;ssl=1\" alt=\"\" class=\"wp-image-1837\" srcset=\"https:\/\/i0.wp.com\/www.sabulo.com\/sb\/wp-content\/uploads\/2020\/04\/dht11-temperature-and-humidity-sensor-500x500-1.png?w=500&amp;ssl=1 500w, https:\/\/i0.wp.com\/www.sabulo.com\/sb\/wp-content\/uploads\/2020\/04\/dht11-temperature-and-humidity-sensor-500x500-1.png?resize=300%2C274&amp;ssl=1 300w\" sizes=\"auto, (max-width: 500px) 100vw, 500px\" \/><figcaption>Basic DHT11. Image courtesy indiamart.com<\/figcaption><\/figure><\/div>\n\n\n\n<p class=\"wp-block-paragraph\">The VCC is five volts from ESP32, and GND is ground. NC is left unconnected, but the DATA pin is also connected to the VCC via a 10 K resistor. I soldered a resistor between the two pins and it works nicely. <\/p>\n\n\n\n<h3 class=\"wp-block-heading\">Code structure<\/h3>\n\n\n\n<p class=\"wp-block-paragraph\">This program has a few functions in it, but the general outline is as follows, but you may want to get the<a rel=\"noreferrer noopener\" href=\"https:\/\/github.com\/HeikkiHietala\/ESP32-MAX7219-eight-LED-digit-clock\" target=\"_blank\"> entire file from Github<\/a> to see the whole code.<\/p>\n\n\n\n<ul class=\"wp-block-list\"><li>initialise variables and setup<\/li><li>go get the time from the Internet and turn off WLAN <\/li><li>go into the main loop: <\/li><li>once a second, check to see whether the mode switch is in the DATE, TEMP or HUMI position<\/li><li>based on that, set the first four digits to show the selected value<\/li><li>set the last four digits to show the time<\/li><li>push the values to the MAX7219 and on to the digits<\/li><li>every five days, reinitialise the clock to fix any eventual drift in the ESP32 real time clock, which isn&#8217;t as accurate as the Swiss clocks.<\/li><\/ul>\n\n\n\n<p class=\"wp-block-paragraph\">The initials are as always in any Arduino\/ESP32 project, but there are some interesting parts.<\/p>\n\n\n\n<pre class=\"wp-block-preformatted\">define MAX2719_DIN 27 \/\/ Pins connected to the MAX chip\ndefine MAX2719_CS 25\ndefine MAX2719_CLK 26\ndefine DHTTYPE DHT11 \/\/ DHT 11\ndefine DHTPIN 16 \/\/ Digital pin connected to the DHT sensor\ninclude \"DHT.h\" \/\/ temp and humidity sensor library\ninclude \"WiFi.h\" \/\/ wifi library\ninclude \"time.h\" \/\/ time functions library\nDHT dht(DHTPIN, DHTTYPE);<\/pre>\n\n\n\n<p class=\"wp-block-paragraph\">The MAX2719 can be set to listen to almost any pins, but I set them as such in this app. DHTs come in two flavors, DHT11 and DHT16, and as the library can use both, it must be explicitly stated as above. Also, DHTPIN must be selected for use here.   WiFi.h and time.h are needed to connect to the WLAN and get the time from the Network Time Server.<\/p>\n\n\n\n<p class=\"wp-block-paragraph\">The next bit gets the time structures in place:<\/p>\n\n\n\n<pre class=\"wp-block-preformatted\">\/\/ time service settings\nconst char* ntpServer = \"pool.ntp.org\"; \/\/ server address\n\/\/ timezone setting. GMT+1 = 3600 GMT+2 = 7200 etc.\nconst long gmtOffset_sec = 7200;\n\/\/ in effect when Daylight Saving Time is in effect\nconst int daylightOffset_sec = 3600;\nstruct tm timeinfo;<\/pre>\n\n\n\n<p class=\"wp-block-paragraph\">After this, you have an object called timeinfo that has the time for further reference. It is loaded using the function goGetTime:<\/p>\n\n\n\n<pre class=\"wp-block-preformatted\"> void goGetTime() {\n\/\/ connect to WiFi\nSerial.printf(\"Connecting to %s \", ssid);\nWiFi.begin(ssid, password);\nwhile (WiFi.status() != WL_CONNECTED) {\ndelay(500);\nSerial.print(\".\");\n}\nSerial.println(\" CONNECTED\");\n\/\/ init and get the time\nconfigTime(gmtOffset_sec, daylightOffset_sec, ntpServer);\nstruct tm timeinfo;\nif (!getLocalTime(&amp;timeinfo)) {\nSerial.println(\"Failed to obtain time\");\nreturn;\n}\n\/\/ disconnect WiFi as it's no longer needed\nWiFi.disconnect(true);\nWiFi.mode(WIFI_OFF);\n}<\/pre>\n\n\n\n<p class=\"wp-block-paragraph\">So now you have the function to get the Real Time Clock initialised and running. <\/p>\n\n\n\n<p class=\"wp-block-paragraph\">The setup starts the DHT, gets the LEDs initialised and goes to get the time.<\/p>\n\n\n\n<pre class=\"wp-block-preformatted\">void setup() {\ndht.begin(); \/\/ start the temp-humi sensor\nSerial.begin(115200); \/\/ start serial to device\n\/\/ set pin modes\npinMode(modePinTemp, INPUT_PULLUP);\npinMode(modePinHumi, INPUT_PULLUP);\npinMode(resetButtonPin, INPUT_PULLUP);\npinMode(ledPinHumi, OUTPUT);\npinMode(ledPinTemp, OUTPUT);\npinMode(ledPinDate, OUTPUT);\ninitialise(); \/\/ function for starting LED displays\ngoGetTime(); \/\/ update system time from Network Time\n}<\/pre>\n\n\n\n<p class=\"wp-block-paragraph\">Then there are a few functions to help figure out what the user wants to see. I have a three way switch rigged in the system, and two pins are connected to the switch. If it is in the up position, you see the date, if down, you see the temperature, and if in the middle and both pins are off, you see the humidity.<\/p>\n\n\n\n<pre class=\"wp-block-preformatted\">\/\/ function to check if the mode switch is in TEMP setting\nboolean checkModePinTemp() {\nif (digitalRead(modePinTemp) == HIGH) {\nSerial.println(\"Temp mode\");\nreturn true;\n}\nelse {\nreturn false;\n}\n}\n\n\/\/ function to check if the mode switch is in HUMIDITY setting\nboolean checkModePinHumi() {\nif (digitalRead(modePinHumi) == HIGH) {\nSerial.println(\"Humidity mode\");\nreturn true;\n}\nelse {\nreturn false;\n}\n}\n\n\/\/ function to check if the RESET button is pushed\nboolean checkResetButton() {\nif (digitalRead(resetButtonPin) == HIGH) {\nSerial.println(\"Reset request\");\nreturn true;\n}\nelse {\nreturn false;\n}\n}<\/pre>\n\n\n\n<h3 class=\"wp-block-heading\">The main loop<\/h3>\n\n\n\n<p class=\"wp-block-paragraph\">The main loop is longish, so I&#8217;ll just illustrate a few points from it. <\/p>\n\n\n\n<p class=\"wp-block-paragraph\">The DHT is read using the following code:<\/p>\n\n\n\n<pre class=\"wp-block-preformatted\">float h = dht.readHumidity(); \/\/ Read humidity\nString humiStr = String(h);\nfloat t = dht.readTemperature();\/\/ Read temperature as Celsius (the default)\nString tempStr = String(t);\nfloat f = dht.readTemperature(true);\/\/ Read temperature as Fahrenheit (isFahrenheit = true)\n\/\/ error handling routine\nif (isnan(h) || isnan(t) || isnan(f)) {\nSerial.println(F(\"Failed to read from DHT sensor!\"));\ndelay(1000);\nreturn;\n}<\/pre>\n\n\n\n<p class=\"wp-block-paragraph\">They are converted into strings, because later on, the numbers must be picked out into tens, ones, decimal tens, and decimal ones, for both the humidity and the temperature displays. For temperature, it looks like this:<\/p>\n\n\n\n<pre class=\"wp-block-preformatted\">\/\/ this returns the tens of the temperature as Integer\ntempTens = tempStr.substring(0, 1).toInt();\n\/\/ this returns the ones of the temperature as Integer\ntempOnes = tempStr.substring(1, 2).toInt();\n\/\/ this returns the decimal tens of the temperature as Integer\ntempDeciOnes = tempStr.substring(2, 3).toInt();\n\/\/ this returns the decimal ones of the temperature as Integer\ntempDeciTens = tempStr.substring(3, 4).toInt();<\/pre>\n\n\n\n<p class=\"wp-block-paragraph\">Now I have four integer variables that can be passed to the display unit as single digits. <strong>tempTens<\/strong> is picked from the string that contains the temperature with the <strong>substring <\/strong>structure. Picking the substring of character 0 to 1  gives you the single digit, but it is in the datatype String. Therefore you need to add the function <strong>.toInt()<\/strong> to it, before you pass it on to the LED later on &#8211; the digit has to be Integer, not String. <\/p>\n\n\n\n<p class=\"wp-block-paragraph\">Figuring that out took me a loooong time.<\/p>\n\n\n\n<p class=\"wp-block-paragraph\">Before actually lighting up the eight LED digits, I will buffer values into variables once more, to make the actual data passage understandable.<\/p>\n\n\n\n<pre class=\"wp-block-preformatted\">\/\/ for showing temperature\nif ((boolTempPin == true) &amp;&amp; (boolHumiPin == false)) {\n\/\/ if (loopCounter&lt;10) {\nledLeft1 = tempTens;\nledLeft2 = tempOnes + 128; \/\/ +128 gives the decimal point \nledLeft3 = tempDeciTens;\nledLeft4 = tempDeciOnes ;\ndigitalWrite(ledPinTemp, HIGH);\ndigitalWrite(ledPinHumi, LOW);\ndigitalWrite(ledPinDate, LOW);\n}<\/pre>\n\n\n\n<p class=\"wp-block-paragraph\">Here you also see that I have three LEDs, which indicate the mode of the display. In this IF clause, I pull the ledPinTemp UP HIGH and the others remain LOW. <\/p>\n\n\n\n<p class=\"wp-block-paragraph\">If the switch is in the middle position, both pins are LOW and the system is set up to show temperature. And when the switch is in the up position, the ledPinHumi is HIGH, and the system displays the humidity in the left digits.<\/p>\n\n\n\n<p class=\"wp-block-paragraph\">The time is always passed to the right side 4 LEDS, hence the time is also parsed into separate digits as thus:<\/p>\n\n\n\n<pre class=\"wp-block-preformatted\">\/\/ tens digit of day\ndayTens = timeinfo.tm_mday \/ 10;\n\/\/ ones digit of day\ndayOnes = timeinfo.tm_mday % 10;\n\/\/ tens digit of month\nmonthTens = timeinfo.tm_mon \/ 10;\n\/\/ ones digit of month, +1 needed to adjust\nmonthOnes = timeinfo.tm_mon % 10 + 1;\n\/\/ tens digit of hour\nhourTens = timeinfo.tm_hour \/ 10;\n\/\/ ones digit of hour\nhourOnes = timeinfo.tm_hour % 10;\n\/\/ tens digit of minutes\nminuteTens = timeinfo.tm_min \/ 10;\n\/\/ ones digit of minutes\nminuteOnes = timeinfo.tm_min % 10;\n\/\/ set the right LED values for time\n\/\/ ths happens every time, because clock is always on\nledRight1 = hourTens;\nledRight2 = hourOnes + 128;\nledRight3 = minuteTens;\nledRight4 = minuteOnes;<\/pre>\n\n\n\n<h3 class=\"wp-block-heading\">Pushing the digits to the display<\/h3>\n\n\n\n<p class=\"wp-block-paragraph\">Once all the data is set in single digit variables, ie. ledLeft1-4 and rightLed1-4, they can be pushed out to be displayed by the dual LED display. This is achieved by using this function:<\/p>\n\n\n\n<pre class=\"wp-block-preformatted\">void output(byte address, byte data)<br>{<br>digitalWrite(MAX2719_CS, LOW);<br>\/\/ Send out two bytes (16 bit)<br>\/\/ parameters: shiftOut(dataPin, clockPin, bitOrder, value)<br>shiftOut(MAX2719_DIN, MAX2719_CLK, MSBFIRST, address);<br>shiftOut(MAX2719_DIN, MAX2719_CLK, MSBFIRST, data);<br>digitalWrite(MAX2719_CS, HIGH);<br>}<\/pre>\n\n\n\n<p class=\"wp-block-paragraph\"> It is given a address as a byte as well as a piece of data as a byte. First the clock pin of the chip is pulled LOW to reset it, then it does two shiftOut operations. Then it is pulled HIGH to display the byte. When this is done eight times, all eight digits are loaded by the shift register, and then displayed at one go.<\/p>\n\n\n\n<pre class=\"wp-block-preformatted\">\/\/ send all data to LED units\noutput(0x08, ledLeft1); \/\/ Left led 1 value\noutput(0x07, ledLeft2); \/\/ Left led 2 value\noutput(0x06, ledLeft3); \/\/ Left led 3 value\noutput(0x05, ledLeft4); \/\/ Left led 4 value\noutput(0x04, ledRight1); \/\/ Time value in hours, tens\noutput(0x03, ledRight2); \/\/ Time value in hours, ones\noutput(0x02, ledRight3); \/\/ Time value in minutes, tens\noutput(0x01, ledRight4); \/\/ Time value in minutes, ones<\/pre>\n\n\n\n<h3 class=\"wp-block-heading\">Wiring the system<\/h3>\n\n\n\n<p class=\"wp-block-paragraph\">I&#8217;ll describe the wiring in writing here because this is a rather simple system. Remember to prepare the DHT11 so that you have a 10K resistor between the data lead and the 5V lead  &#8211; there are still three leads from it, voltage, data, and ground.<\/p>\n\n\n\n<p class=\"wp-block-paragraph\">The parts you need are<\/p>\n\n\n\n<ul class=\"wp-block-list\"><li>ESP32<\/li><li>MAX7219 dual 4 digit display<\/li><li>three LEDS<\/li><li>a power supply &#8211; I used an old phone charger of which I cut off the connector and added two female connectors for 5V and Ground <\/li><li>one three position switch<\/li><li>one two position switch for power<\/li><li>one push button for resetting the device.<\/li><li>You can build a box for this from dense cardboard or use a 3D printer<\/li><li>Shared leads for both 5V and ground pins &#8211; you need to supply voltage to the display, and the DHT11.<\/li><\/ul>\n\n\n\n<p class=\"wp-block-paragraph\">The connections are:<\/p>\n\n\n\n<ul class=\"wp-block-list\"><li>DIN pin of the display to the ESP32 pin 27<\/li><li>CS pin of the display to the ESP32 pin 25<\/li><li>CLK pin of the display to the ESP32 pin 26<\/li><li>VIN pin to 5V<\/li><li>GND pin to Ground<\/li><li>Humidity LED positive pin to ESP32 pin 20, negative to ground<\/li><li>Temperature LED positive pin to ESP32 pin 17, negative to ground<\/li><li>Date LED positive pin to ESP32 pin 21, negative to ground  <\/li><li>Humidity switch lead to ESP32 pin 19<\/li><li>Temperature switch lead to ESP32 pin 18<\/li><li>Humidity-temperature switch common to ground  <\/li><li>ESP32 pin 16 to DHT sensor data pin<\/li><\/ul>\n\n\n\n<p class=\"wp-block-paragraph\">It is easier for you to understand how this thing works if you take down the code from Github, assemble the parts, and do the connections carefully. This is a video showing you how it works.<\/p>\n\n\n\n<figure class=\"wp-block-embed-youtube wp-block-embed is-type-video is-provider-youtube wp-embed-aspect-4-3 wp-has-aspect-ratio\"><div class=\"wp-block-embed__wrapper\">\n<span class=\"embed-youtube\" style=\"text-align:center; display: block;\"><iframe loading=\"lazy\" class=\"youtube-player\" width=\"825\" height=\"465\" src=\"https:\/\/www.youtube.com\/embed\/bS9dt8CGfA0?version=3&#038;rel=1&#038;showsearch=0&#038;showinfo=1&#038;iv_load_policy=1&#038;fs=1&#038;hl=en-GB&#038;autohide=2&#038;wmode=transparent\" allowfullscreen=\"true\" style=\"border:0;\" sandbox=\"allow-scripts allow-same-origin allow-popups allow-presentation allow-popups-to-escape-sandbox\"><\/iframe><\/span>\n<\/div><\/figure>\n<div class=\"pvc_clear\"><\/div><p id=\"pvc_stats_1832\" class=\"pvc_stats all  \" data-element-id=\"1832\" style=\"\"><i class=\"pvc-stats-icon medium\" aria-hidden=\"true\"><svg aria-hidden=\"true\" focusable=\"false\" data-prefix=\"far\" data-icon=\"chart-bar\" role=\"img\" xmlns=\"http:\/\/www.w3.org\/2000\/svg\" viewBox=\"0 0 512 512\" class=\"svg-inline--fa fa-chart-bar fa-w-16 fa-2x\"><path fill=\"currentColor\" d=\"M396.8 352h22.4c6.4 0 12.8-6.4 12.8-12.8V108.8c0-6.4-6.4-12.8-12.8-12.8h-22.4c-6.4 0-12.8 6.4-12.8 12.8v230.4c0 6.4 6.4 12.8 12.8 12.8zm-192 0h22.4c6.4 0 12.8-6.4 12.8-12.8V140.8c0-6.4-6.4-12.8-12.8-12.8h-22.4c-6.4 0-12.8 6.4-12.8 12.8v198.4c0 6.4 6.4 12.8 12.8 12.8zm96 0h22.4c6.4 0 12.8-6.4 12.8-12.8V204.8c0-6.4-6.4-12.8-12.8-12.8h-22.4c-6.4 0-12.8 6.4-12.8 12.8v134.4c0 6.4 6.4 12.8 12.8 12.8zM496 400H48V80c0-8.84-7.16-16-16-16H16C7.16 64 0 71.16 0 80v336c0 17.67 14.33 32 32 32h464c8.84 0 16-7.16 16-16v-16c0-8.84-7.16-16-16-16zm-387.2-48h22.4c6.4 0 12.8-6.4 12.8-12.8v-70.4c0-6.4-6.4-12.8-12.8-12.8h-22.4c-6.4 0-12.8 6.4-12.8 12.8v70.4c0 6.4 6.4 12.8 12.8 12.8z\" class=\"\"><\/path><\/svg><\/i> <img data-recalc-dims=\"1\" loading=\"lazy\" decoding=\"async\" width=\"16\" height=\"16\" alt=\"Loading\" src=\"https:\/\/i0.wp.com\/www.sabulo.com\/sb\/wp-content\/plugins\/page-views-count\/ajax-loader-2x.gif?resize=16%2C16&#038;ssl=1\" border=0 \/><\/p><div class=\"pvc_clear\"><\/div>","protected":false},"excerpt":{"rendered":"<p>Okay, I thought the series on 7 segment LED displays would run into three parts, but it has turned out &hellip; <a href=\"https:\/\/www.sabulo.com\/sb\/led\/using-7-segment-led-displays-part-4-dual-quadruple-units\/\" class=\"more-link\">More <span class=\"screen-reader-text\">Using 7 Segment LED displays, Part 4 &#8211; dual quadruple units<\/span> <span class=\"meta-nav\">&rarr;<\/span><\/a><\/p>\n<div class=\"pvc_clear\"><\/div>\n<p id=\"pvc_stats_1832\" class=\"pvc_stats all  \" data-element-id=\"1832\" style=\"\"><i class=\"pvc-stats-icon medium\" aria-hidden=\"true\"><svg aria-hidden=\"true\" focusable=\"false\" data-prefix=\"far\" data-icon=\"chart-bar\" role=\"img\" xmlns=\"http:\/\/www.w3.org\/2000\/svg\" viewBox=\"0 0 512 512\" class=\"svg-inline--fa fa-chart-bar fa-w-16 fa-2x\"><path fill=\"currentColor\" d=\"M396.8 352h22.4c6.4 0 12.8-6.4 12.8-12.8V108.8c0-6.4-6.4-12.8-12.8-12.8h-22.4c-6.4 0-12.8 6.4-12.8 12.8v230.4c0 6.4 6.4 12.8 12.8 12.8zm-192 0h22.4c6.4 0 12.8-6.4 12.8-12.8V140.8c0-6.4-6.4-12.8-12.8-12.8h-22.4c-6.4 0-12.8 6.4-12.8 12.8v198.4c0 6.4 6.4 12.8 12.8 12.8zm96 0h22.4c6.4 0 12.8-6.4 12.8-12.8V204.8c0-6.4-6.4-12.8-12.8-12.8h-22.4c-6.4 0-12.8 6.4-12.8 12.8v134.4c0 6.4 6.4 12.8 12.8 12.8zM496 400H48V80c0-8.84-7.16-16-16-16H16C7.16 64 0 71.16 0 80v336c0 17.67 14.33 32 32 32h464c8.84 0 16-7.16 16-16v-16c0-8.84-7.16-16-16-16zm-387.2-48h22.4c6.4 0 12.8-6.4 12.8-12.8v-70.4c0-6.4-6.4-12.8-12.8-12.8h-22.4c-6.4 0-12.8 6.4-12.8 12.8v70.4c0 6.4 6.4 12.8 12.8 12.8z\" class=\"\"><\/path><\/svg><\/i> <img loading=\"lazy\" decoding=\"async\" width=\"16\" height=\"16\" alt=\"Loading\" src=\"https:\/\/www.sabulo.com\/sb\/wp-content\/plugins\/page-views-count\/ajax-loader-2x.gif\" border=0 \/><\/p>\n<div class=\"pvc_clear\"><\/div>\n","protected":false},"author":1,"featured_media":0,"comment_status":"open","ping_status":"open","sticky":false,"template":"","format":"standard","meta":{"_jetpack_newsletter_access":"","_jetpack_dont_email_post_to_subs":false,"_jetpack_newsletter_tier_id":0,"_jetpack_memberships_contains_paywalled_content":false,"_jetpack_memberships_contains_paid_content":false,"footnotes":"","jetpack_publicize_message":"","jetpack_publicize_feature_enabled":true,"jetpack_social_post_already_shared":true,"jetpack_social_options":{"image_generator_settings":{"template":"highway","default_image_id":0,"font":"","enabled":false},"version":2},"jetpack_post_was_ever_published":false},"categories":[80,79,91,88],"tags":[],"class_list":["post-1832","post","type-post","status-publish","format-standard","hentry","category-7-segment-display","category-led","category-max7219","category-shift-registers"],"a3_pvc":{"activated":true,"total_views":2101,"today_views":0},"jetpack_publicize_connections":[],"jetpack_featured_media_url":"","jetpack_sharing_enabled":true,"jetpack_shortlink":"https:\/\/wp.me\/p6vhqE-ty","_links":{"self":[{"href":"https:\/\/www.sabulo.com\/sb\/wp-json\/wp\/v2\/posts\/1832","targetHints":{"allow":["GET"]}}],"collection":[{"href":"https:\/\/www.sabulo.com\/sb\/wp-json\/wp\/v2\/posts"}],"about":[{"href":"https:\/\/www.sabulo.com\/sb\/wp-json\/wp\/v2\/types\/post"}],"author":[{"embeddable":true,"href":"https:\/\/www.sabulo.com\/sb\/wp-json\/wp\/v2\/users\/1"}],"replies":[{"embeddable":true,"href":"https:\/\/www.sabulo.com\/sb\/wp-json\/wp\/v2\/comments?post=1832"}],"version-history":[{"count":10,"href":"https:\/\/www.sabulo.com\/sb\/wp-json\/wp\/v2\/posts\/1832\/revisions"}],"predecessor-version":[{"id":1965,"href":"https:\/\/www.sabulo.com\/sb\/wp-json\/wp\/v2\/posts\/1832\/revisions\/1965"}],"wp:attachment":[{"href":"https:\/\/www.sabulo.com\/sb\/wp-json\/wp\/v2\/media?parent=1832"}],"wp:term":[{"taxonomy":"category","embeddable":true,"href":"https:\/\/www.sabulo.com\/sb\/wp-json\/wp\/v2\/categories?post=1832"},{"taxonomy":"post_tag","embeddable":true,"href":"https:\/\/www.sabulo.com\/sb\/wp-json\/wp\/v2\/tags?post=1832"}],"curies":[{"name":"wp","href":"https:\/\/api.w.org\/{rel}","templated":true}]}}