display change - Page 1
Forum section: electronics / general

author: m3vuv
author_rank: Super Contributor
timestamp: December 28, 2020, 08:49:49 am
content: Hi all,i have a project using a lcd display,heres the code://-----------------------------------------------------Youtube Channel Sasiskas------------------------------------------------------------------------//-----------------------------------------------------Battery Capacity tester and more V1.1-----------------------------------------------------------#include <SPI.h>#include <stdlib.h>#include <LiquidCrystal_I2C.h>LiquidCrystal_I2C lcd(0x27, 16, 2);unsigned long previousMillis = 0;unsigned long millisPassed = 0;unsigned long BatFull = 0;float BatVoltQuiescent = 0; // The battery voltage when there is no load on the batteryfloat Capacity = 0.0; // The calculated capacity of the battery, measured wile dischargingfloat mA=0;float SetI = 0; // The setpoint for the discharging current. Remember you can adjust the discharging current using the 500K trimpot.float ChargeI = 0;float CurTP4056 = 0;float ResTP4056 = 0;float ratioRI = 0;float BatLevel = 0; // The percentage of battery charge/levelfloat BatVoltCorrected = 0; // The voltage of the battery, measured based on the arduino internal referencefloat A2VoltCorrected = 0;float VoltTP4056Pin2 = 0;float Rprog = 0;float BatRes = 0; // The internal battery resistanceconst float RES = 1; // Value of your resistor. Suggested Value is 1 Ohm. Change it, if you use a different resistor value#define clk 2#define dt 3#define sw 4#define MOSFET_Discharge 9 // It is an N-MOSFET, so HIGH is ON and LOW is OFF#define MOSFET_Charge 8 // It is a P-MOSFET, so HIGH is OFF and LOW is ONchar screen = 0;char arrowpos = 0;char charging = 0;char discharging = 0;char storage = 0;char storagecharge = 0;char storagedischarge = 0;char BatVoltQuiescentValue = 0; // Whether there is a value for "the battery voltage with no load" (BatVoltQuiescent) or not. 1 for yes and 0 for no.//char nointermediate = 0;const unsigned char PS_128 = (1 << ADPS2) | (1 << ADPS1) | (1 << ADPS0);volatile boolean TurnDetected = false;volatile boolean up = false;volatile boolean button = false;byte OhmChar = {B00000,B01110,B10001,B10001,B10001,B01010,B11011,B00000};byte customChar1 = {0b10000,0b11000,0b11100,0b11110,0b11110,0b11100,0b11000,0b10000};ISR(PCINT2_vect) {if (digitalRead(sw) == LOW) {button = true;}}void isr0 () {TurnDetected = true;up = (digitalRead(clk) == digitalRead(dt));}void setup() {lcd.begin();lcd.setCursor(0, 0);pinMode(MOSFET_Discharge, OUTPUT);pinMode(MOSFET_Charge, OUTPUT);digitalWrite(MOSFET_Discharge, LOW);digitalWrite(MOSFET_Charge, HIGH);pinMode(sw, INPUT_PULLUP);pinMode(clk, INPUT);pinMode(dt, INPUT);PCICR |= 0b00000100;PCMSK2 |= 0b00010000; // turn o PCINT20(D4)attachInterrupt(0, isr0, RISING);lcd.createChar(0, customChar1);lcd.createChar(1, OhmChar);lcd.clear();screen0();lcd.setCursor(0, 0);lcd.write((uint8_t)0);}void loop() {int in0 = analogRead(A0); //read the A0 pin valueint sensorValue1 = analogRead(A1); //read the A1 pin valuefloat val0 = in0 * 5.0 / 1024.0;float supply = readVcc() / 1000.0;SetI = sensorValue1 * (5.00 / 1024.00) / RES * 1000; // Calculate the discharge rate of the batteryif (SetI <= 1200){SetI = SetI;}else{SetI = 1200;}BatVoltCorrected = supply / 5 * val0 * 4.35; //In case you use different voltage dividers, you need to change the number 4.3 accordingly.millisPassed = millis() - previousMillis;previousMillis = millis();//------------------------------------------------------------------- calculates the charging current ------------------------------------------------------------------------int in2 = analogRead(A2); //read the A2 pin valueint in3 = analogRead(A3); //read the A3 pin valuefloat val2 = in2 * 5.0 / 1024.0;float val3 = in3 * 5.0 / 1024.0;A2VoltCorrected = supply / 5 * val2; //calculates reading of pin A2 based on internal voltage referenceVoltTP4056Pin2 = supply / 5 * val3; //calculates reading of pin A3 based on internal voltage referenceRprog = 1220 + (A2VoltCorrected * 1220 / (VoltTP4056Pin2 - A2VoltCorrected)); //calculates the Rprog of TP4056 module//calculates the Charging current based on numbers from TP4056 datasheetif (Rprog >= 10000) {CurTP4056 =130 ;ResTP4056 =10000 ;ratioRI = 0.107 ;}else if (Rprog < 10000 && Rprog >= 5000){CurTP4056 = 250 ;ResTP4056 = 5000 ;ratioRI = 0.024 ;}else if (Rprog < 5000 && Rprog >= 4000){CurTP4056 = 300 ;ResTP4056 = 4000 ;ratioRI = 0.050 ;}else if (Rprog < 40000 && Rprog >= 3000){CurTP4056 = 400 ;ResTP4056 = 3000 ;ratioRI = 0.100 ;}else if (Rprog < 30000 && Rprog >= 2000){CurTP4056 = 580 ;ResTP4056 = 2000 ;ratioRI = 0.180 ;}else if (Rprog < 20000 && Rprog >= 1660){CurTP4056 = 690 ;ResTP4056 = 1660 ;ratioRI = 0.324 ;}else if (Rprog < 10000 && Rprog >= 1500){CurTP4056 = 780 ;ResTP4056 = 1500 ;ratioRI = 0.563 ;}else if (Rprog < 10000 && Rprog >= 1330){CurTP4056 = 900 ;ResTP4056 = 1330 ;ratioRI = 0.706 ;}else if (Rprog >= 1220){CurTP4056 = 995 ;ResTP4056 = 1220 ;ratioRI = 0.864 ;}if (Rprog < 1220){ChargeI = 1000 ;}else {ChargeI = (CurTP4056 - ((Rprog - ResTP4056) * ratioRI));}if (ChargeI > 0){ChargeI = ChargeI;}else{ChargeI = 0;}//------------------------------------------------------------------- battery percentage - linear calculation based on voltage (linear does NOT represent the REAL percentage)if (BatVoltCorrected < 2.5) {BatLevel = 0;}else if (BatVoltCorrected > 4.2){BatLevel = 100;}else {BatLevel = (BatVoltCorrected - 2.5 ) / 1.7 * 100 ;}//----------------------------------------------------------------------------------------------------------------------------------------------------------------------if (BatVoltCorrected <= 3.70 && BatVoltCorrected >= 3.65){ // For 3400mAh batteries storage voltage is 3.6-3.7V, for batteries below 2600mAh it should be higher.storagedischarge = 0;storagecharge = 0;}if (BatVoltCorrected <= 3.75 && BatVoltCorrected > 3.7){ // Set these numbers +0.5V of your batteries storage voltagestoragedischarge = 1;storage = 2;storagecharge = 0;}if (BatVoltCorrected >= 3.6 && BatVoltCorrected < 3.65){ // Set these numbers -0.5V of your batteries storage voltagestoragecharge = 1;storage = 2;storagedischarge = 0;}if (BatVoltCorrected > 3.75 || BatVoltCorrected < 3.6){ // Set these numbers +0.5V and -0.5V of your batteries storage voltagestorage = 0;storagedischarge = 0;storagecharge = 0;}if (BatVoltCorrected <= 3.75 && BatVoltCorrected >= 3.6){ // Set these numbers +0.5V and -0.5V of your batteries storage voltagestorage = 1;}//------------------------------------------------------------------------------------------------------------------------------------------------------if (screen == 0) {//delay(500);BatVoltQuiescent = BatVoltCorrected;BatVoltQuiescentValue = 1;BatFull = 0;}//----------------------------------------------------------------------------------------Capacity test mode-------------------------------------------------------if (screen == 1) {if (BatVoltCorrected <= 2.3){Capacity = Capacity;BatVoltQuiescentValue = 0;digitalWrite(MOSFET_Discharge, LOW);// buz();lcd.setCursor(0,0);lcd.print("V:");lcd.print(BatVoltCorrected);lcd.print("V ");lcd.setCursor(8,0);lcd.print("I:");lcd.print(SetI,0);lcd.print("mA ");lcd.setCursor(0,1);lcd.print("C:");lcd.print(Capacity,0);lcd.print("mAh ");lcd.setCursor(10,1);lcd.print("R:");lcd.print(BatRes,0);lcd.print("m");lcd.print(char(1));delay(100);}if (BatVoltCorrected > 2.3 && BatVoltQuiescentValue == 0 ) {BatRes = (BatVoltQuiescent - BatVoltCorrected) / (BatVoltCorrected / SetI); //Calculates the internal battery resistance in mOhmsCapacity = Capacity + (SetI * (millisPassed / 3600000.0));BatVoltQuiescent = BatVoltCorrected;BatVoltQuiescentValue = 1;digitalWrite(MOSFET_Discharge, HIGH);lcd.setCursor(0,0);lcd.print("V:");lcd.print(BatVoltCorrected);lcd.print("V ");lcd.setCursor(8,0);lcd.print("I:");lcd.print(SetI,0);lcd.print("mA ");lcd.setCursor(0,1);lcd.print("C:");lcd.print(Capacity,0);lcd.print("mAh ");lcd.setCursor(10,1);lcd.print("R:");lcd.print(BatRes,0);lcd.print("m");lcd.print(char(1));delay(500);}else if (BatVoltCorrected > 2.3 && BatVoltQuiescentValue == 1 ) {BatRes = (BatVoltQuiescent - BatVoltCorrected) / (BatVoltCorrected / SetI); //Calculates the internal battery resistance in mOhmsCapacity = Capacity + (SetI * (millisPassed / 3600000.0));digitalWrite(MOSFET_Discharge, HIGH);lcd.setCursor(0,0);lcd.print("V:");lcd.print(BatVoltCorrected);lcd.print("V ");lcd.setCursor(8,0);lcd.print("I:");lcd.print(SetI,0);lcd.print("mA ");lcd.setCursor(0,1);lcd.print("C:");lcd.print(Capacity,0);lcd.print("mAh ");lcd.setCursor(10,1);lcd.print("R:");lcd.print(BatRes,0);lcd.print("m");lcd.print(char(1));delay(500);}}//----------------------------------------------------------------------------------------Charge mode-------------------------------------------------------else if (screen == 2) {if (BatVoltCorrected >= 4.15) {lcd.setCursor(0,0);lcd.print("Full Battery");lcd.setCursor(12,0);lcd.print("100% ");lcd.setCursor(0,1);lcd.print("V:");lcd.print(BatVoltCorrected);lcd.print("V ");lcd.setCursor(8,1);lcd.print("I:");lcd.print(ChargeI,0);lcd.print("mA ");digitalWrite(MOSFET_Charge, HIGH);delay(500);BatFull = BatFull + 1;}else if (BatVoltCorrected == 0 ){BatFull = 0;lcd.setCursor(0,0);lcd.print("No Battery ");lcd.setCursor(12,0);lcd.print(BatLevel,0);lcd.print("% ");lcd.setCursor(0,1);lcd.print("V:");lcd.print(BatVoltCorrected);lcd.print("V ");lcd.setCursor(9,1);lcd.print("I:");lcd.print(ChargeI,0);lcd.print("mA ");digitalWrite(MOSFET_Charge, HIGH);//delay(9000);//digitalWrite(MOSFET_Charge, HIGH);delay(500);}else if (BatVoltCorrected < 4.15 && BatFull < 10 && BatVoltCorrected > 0 ) {lcd.setCursor(0,0);lcd.print("Charging... ");lcd.setCursor(12,0);lcd.print(BatLevel,0);lcd.print("% ");lcd.setCursor(0,1);lcd.print("V:");lcd.print(BatVoltCorrected);lcd.print("V ");lcd.setCursor(8,1);lcd.print("I:");lcd.print(ChargeI,0);lcd.print("mA ");digitalWrite(MOSFET_Charge, LOW);//delay(9000);//digitalWrite(MOSFET_Charge, HIGH);delay(500);}else if (BatVoltCorrected < 4.15 && BatFull >= 10) {lcd.setCursor(0,0);lcd.print("Full Battery");lcd.setCursor(12,0);lcd.print("100% ");lcd.setCursor(0,1);lcd.print("V:");lcd.print(BatVoltCorrected);lcd.print("V ");lcd.setCursor(8,1);lcd.print("I:");lcd.print(ChargeI,0);lcd.print("mA ");digitalWrite(MOSFET_Charge, HIGH);delay(500);}}//----------------------------------------------------------------------------------------Storage mode-----------------------------------------------------------------------------------------// You need to adjust your voltages according to your batteries, for 3400mAh batteries storage voltage (50% capacity) is 3.6-3.7V, for batteries below 2600mAh it should be higher.// For more info visit this:https://lygte-info.dk/info/BatteryChargePercent%20UK.htmlelse if (screen == 3) {delay(100);if (BatVoltCorrected <= 1.5 ) {lcd.setCursor(0,0);lcd.print("No battery ");lcd.setCursor(0,1);lcd.print("V:");lcd.print(BatVoltCorrected);lcd.print("V ");digitalWrite(MOSFET_Discharge, LOW);digitalWrite(MOSFET_Charge, HIGH);charging = 0;discharging = 0;storage = 0;storagecharge = 0;storagedischarge = 0;}else if (BatVoltCorrected > 3.75 && charging == 0) { // Checks if the "quiescent voltage" of the battery is above 3.7V and Starts the discharge.lcd.setCursor(0,0);lcd.print("Discharging ");lcd.setCursor(0,1);lcd.setCursor(0,1);lcd.print("V:");lcd.print(BatVoltCorrected);lcd.print("V ");lcd.setCursor(9,1);lcd.print("I:");lcd.print(SetI,0);lcd.print("mA ");digitalWrite(MOSFET_Charge, HIGH);delay(100);discharging = 1;digitalWrite(MOSFET_Discharge, HIGH);delay(9000);digitalWrite(MOSFET_Discharge, LOW);}else if (storagedischarge == 1 && discharging == 1){ // Intermediate step before stopping the dischargelcd.setCursor(0,0);lcd.print("RDY for storage");lcd.setCursor(0,1);lcd.print("V:");lcd.print(BatVoltCorrected);lcd.print("V ");discharging = 1;digitalWrite(MOSFET_Charge, HIGH);delay(100);digitalWrite(MOSFET_Discharge, HIGH);delay(9000);digitalWrite(MOSFET_Discharge, LOW);}else if (BatVoltCorrected >= 1.5 && BatVoltCorrected < 3.6) { // Checks if the "quiescent voltage" of the battery is between 1.5V and 3.6Vif (discharging == 1 && BatVoltCorrected < 3.0){ // Stops discharging if the "discharge voltage" of the battery is below 3.0Vlcd.setCursor(0,1);lcd.print("V:");lcd.print(BatVoltCorrected);lcd.print("V ");lcd.setCursor(9,1);lcd.print("I:");lcd.print(SetI,0);lcd.print("mA ");digitalWrite(MOSFET_Discharge, LOW);}if (discharging == 1 && BatVoltCorrected > 2){ // Prevents from charging (continues discharging) even if the "quiescent voltage" is below 3.6Vlcd.setCursor(0,1);lcd.print("V:");lcd.print(BatVoltCorrected);lcd.print("V ");lcd.setCursor(9,1);lcd.print("I:");lcd.print(SetI,0);lcd.print("mA ");}else if (discharging == 0 && BatVoltCorrected < 3.6){ // Starts to charge the batterylcd.setCursor(0,0);lcd.print("Charging ");lcd.setCursor(0,1);lcd.print("V:");lcd.print(BatVoltCorrected);lcd.print("V ");digitalWrite(MOSFET_Discharge, LOW);delay(100);digitalWrite(MOSFET_Charge, LOW);charging = 1;delay(1000);}else { // used for debugginglcd.setCursor(0,0);lcd.print("error? ");}}else if (storagecharge == 1 && charging == 1){ // Intermediate step before stopping the charge. (not actually stopping the charge)lcd.setCursor(0,0);lcd.print("RDY for storage");lcd.setCursor(0,1);lcd.print("V:");lcd.print(BatVoltCorrected);lcd.print("V ");charging = 1;//nointermediate = 1;digitalWrite(MOSFET_Discharge, LOW);delay(100);digitalWrite(MOSFET_Charge, LOW);delay(1000);}else if (charging == 1 && BatVoltCorrected > 3.65 ){ // Stops charge . This step is used if the Intermediate stop of charge was used.lcd.setCursor(0,0);lcd.print("RDY for storage");lcd.setCursor(0,1);lcd.print("V:");lcd.print(BatVoltCorrected);lcd.print("V ");digitalWrite(MOSFET_Discharge, LOW);digitalWrite(MOSFET_Charge, HIGH);delay(1000);}else if (storage == 1 && charging == 0){ // For 3400mAh batteries sorage voltage is 3.6-3.7V, for batteries below 2600mAh it should be higher.lcd.setCursor(0,0); // This step is used if the Intermediate stop of charge was NOT used. Or after intermadiate stop of discharge.lcd.print("RDY for storage");lcd.setCursor(0,1);lcd.print("V:");lcd.print(BatVoltCorrected);lcd.print("V ");digitalWrite(MOSFET_Discharge, LOW);digitalWrite(MOSFET_Charge, HIGH);delay(1000);}}//-------------------------------------------------------------------------------- TURN -------------------------------------------------------------------------------------------------------if (TurnDetected) {delay(200);switch (screen) {case 0:switch (arrowpos) {case 0:if (!up) {screen0();lcd.setCursor(0, 1);lcd.write((uint8_t)0);arrowpos = 1;}else {screen0();lcd.setCursor(8, 1);lcd.write((uint8_t)0);arrowpos = 2;}break;case 1:if (up) {screen0();lcd.setCursor(0, 0);lcd.write((uint8_t)0);arrowpos = 0;}else {screen0();lcd.setCursor(8, 1);lcd.write((uint8_t)0);arrowpos = 2;}break;case 2:if (up) {screen0();lcd.setCursor(0, 1);lcd.write((uint8_t)0);arrowpos = 1;}else {screen0();lcd.setCursor(0, 0);lcd.write((uint8_t)0);arrowpos = 0;}break;}break;}TurnDetected = false;}//-------------------------------------------------------------------------------------------- BUTTON PRESS --------------------------------------------------------------------------------------------if (button) {delay(200);switch (screen) {case 0:if (arrowpos == 0) {screen = 1;screen1();}else if (arrowpos == 1){screen = 2;screen2();}else {screen = 3;screen3();}break;case 1:screen = 0;screen0();lcd.setCursor(0, 0);lcd.write((uint8_t)0);break;case 2:screen = 0;screen0();lcd.setCursor(0, 0);lcd.write((uint8_t)0);break;case 3:screen = 0;screen0();lcd.setCursor(0, 0);lcd.write((uint8_t)0);break;}arrowpos = 0;button = false;}}//-----------------------------------------------------------------------------------------------------SCREENS-------------------------------------------------------------------------------------void screen0() {lcd.clear();lcd.setCursor(1, 0);lcd.print("Capacity test");lcd.setCursor(1, 1);lcd.print("Charge");lcd.setCursor(9, 1);lcd.print("Store");digitalWrite(MOSFET_Discharge, LOW);digitalWrite(MOSFET_Charge, HIGH);charging = 0;discharging = 0;storage = 0;storagecharge = 0;storagedischarge = 0;}void screen1() {lcd.clear();}void screen2() {lcd.clear();}void screen3() {lcd.clear();}//-------------------------------------------------------------------voltage based on internal reference-------------------------------------------------------------long readVcc() {long result;// Read 1.1V reference against AVcc#if defined(__AVR_ATmega32U4__) || defined(__AVR_ATmega1280__) || defined(__AVR_ATmega2560__)ADMUX = _BV(REFS0) | _BV(MUX4) | _BV(MUX3) | _BV(MUX2) | _BV(MUX1);#elif defined (__AVR_ATtiny24__) || defined(__AVR_ATtiny44__) || defined(__AVR_ATtiny84__)ADMUX = _BV(MUX5) | _BV(MUX0);#elif defined (__AVR_ATtiny25__) || defined(__AVR_ATtiny45__) || defined(__AVR_ATtiny85__)ADMUX = _BV(MUX3) | _BV(MUX2);#elseADMUX = _BV(REFS0) | _BV(MUX3) | _BV(MUX2) | _BV(MUX1);#endifdelay(2); // Wait for Vref to settleADCSRA |= _BV(ADSC); // Convertwhile (bit_is_set(ADCSRA, ADSC));result = ADCL;result |= ADCH << 8;result = 1126400L / result; // Calculate Vcc (in mV); 1126400 = 1.1*1024*1000return result;}//void buz()// {// digitalWrite(9, HIGH);// delay(100);// digitalWrite(9, LOW);// delay(10);//}i want to use a 1.3 inch oled using i2c interface, sh1106,what do i need to change in the code to do this?,i already have all the libraies etc,thanks in advance.

author: PlainName
author_rank: Super Contributor
timestamp: December 31, 2020, 11:28:22 am
content: You need to change the LiquidCrystal_I2C library code, not this stuff. Take a look at LiquidCrystal_I2C.h for info. As to how hard it might be, I'm afraid someone else will have to answer that (or you could find out yourself) - I am not an Arduino IDE developer and nor am I familiar with your display chip.

author: CJay
author_rank: Super Contributor
timestamp: December 31, 2020, 12:21:10 pm
content: I suggest you go and read the datasheets for the HD44780 controller and the SH1106/SSD1306 controller, they're significantly different, it's not just a library change, you'd need to rewrite significant portions of the code.

author: Ian.M
author_rank: Super Contributor
timestamp: December 31, 2020, 12:25:04 pm
content: OLED displays are almost invariably dot addressable graphics displays. The HD44780 compatible LCD displays the various variants of the LiquidCrystal library work with are NxM ASCII text displays where N is 1, 2, or 4 lines and M is typically 8 to 40 characters per line. As Cjay points out, the hardware and programming interface is very different.Your code uses the following LiquidCrystal methods:Code:lcd.begin()lcd.clear()lcd.createChar()lcd.print()lcd.setCursor()lcd.write()*IF* your OLED library has equivalent methods,you could go through the code replacing the LiquidCrystal ones with their OLED equivalents, maybe with some parameter tweaking, and rescaling the coordinates of lcd.setCursor().Otherwise you'll need to write a LCD emulation 'shim' library that translates LiquidCrystal alike method calls to something the OLED library can handle.P.S. *PLEASE* usecode tagswhen posting sourcecode!

author: ledtester
author_rank: Super Contributor
timestamp: December 31, 2020, 12:32:07 pm
content: I just googled "SH1106 arduino" and it came back with this library:https://github.com/durydevelop/arduino-lib-oledIt says it has these features:* Supports all print() and write() calls as the internal Serial lib of Arduino core* Supports also standard C/C++ printf() function* Added printf(x,y,...) to print directly at x,y coordinate with one callShould be relatively straightforward to translate the lcd.* calls to this library.You should first spend some time familiarizing yourself with the library, e.g. running the examples, trying out your own code, etc. as well as learning the lcd library so you know what the project code is doing.QuoteBetter yet, for a large amount of code like this make it an attachment to your post.

author: m3vuv
author_rank: Super Contributor
timestamp: December 31, 2020, 12:58:08 pm
content: it can stay as is,was just a thought.73 m3vuv.