700W Pure Sine Inverter with LCD — Arduino Uno simulation

Arduino Uno based 700W pure sine wave inverter with 20x4 I2C LCD, battery monitoring, temperature sensing, and menu system.

An interactive Arduino Uno circuit simulation you can run free in your browser on Velxio, by knlkmr2004.

Components

Sketch code

/*
 * ================================================================
 * ATmega328P PURE SINE UPS / BIDIRECTIONAL TRANSFORMER CONTROLLER
 * FIXED BENCH-TEST / INVERTER / CHARGING FIRMWARE
 * ================================================================
 *
 * Target: Arduino UNO / ATmega328P, 16 MHz
 * System: 12 V battery, ~900 VA target, 20x4 I2C LCD
 *
 * PIN MAP
 * ----------------------------------------------------------------
 * D9  (PB1/OC1A)  -> CH1-PWM
 * D10 (PB2/OC1B)  -> CH2-PWM
 * D8  (PB0)       -> H/L-LOGIC
 * D12             -> POWER_ENABLE
 * D11             -> CHANGEOVER RELAY
 *
 * A0              -> BATTERY VOLTAGE SENSE
 * A1              -> OUTPUT VOLTAGE FEEDBACK
 * A2              -> LOAD CURRENT SENSE
 * A3              -> CHARGING CURRENT SENSE
 *
 * D2              -> MAINS PRESENT (logic input)
 * D3              -> ZERO CROSS / CHARGE SYNC (logic input)
 *
 * A4              -> LCD SDA
 * A5              -> LCD SCL
 *
 * D4-D7           -> buttons (optional)
 *
 * IMPORTANT
 * ----------------------------------------------------------------
 * 1. This firmware fixes the original problem where the Timer1 ISR
 *    generated PWM only in INVERTER state.
 * 2. CHARGING now enables Timer1 and produces an AC-synchronised
 *    alternating PWM waveform on D9/D10 using the D3 zero-cross
 *    signal.
 * 3. For your present bench test, D2 can be forced HIGH and D3 can
 *    receive ~100 Hz logic pulses from another Arduino.
 * 4. The charging switching sequence must still be validated against
 *    the exact transformer/MOSFET/IR2110 hardware before connecting
 *    real mains or a real battery charging power path.
 * 5. Never connect 230 VAC directly to D2/D3/ATmega pins.
 *
 * ================================================================
 */

#include <Arduino.h>
#include <Wire.h>
#include <LiquidCrystal_I2C.h>
#include <EEPROM.h>

/* ================================================================
 * LCD
 * ================================================================ */
LiquidCrystal_I2C lcd(0x27, 20, 4);

/* ================================================================
 * POWER STAGE SIGNALS
 * ================================================================ */
#define CH1_PWM       9
#define CH2_PWM       10
#define HL_LOGIC      8
#define RELAY_PIN     11
#define POWER_ENABLE  12

/* ================================================================
 * ANALOG INPUTS
 * ================================================================ */
#define BATTERY_SENSE        A0
#define OUTPUT_SENSE         A1
#define LOAD_CURRENT_SENSE   A2
#define CHARGE_CURRENT_SENSE A3

/* ================================================================
 * DIGITAL INPUTS
 * ================================================================ */
#define MAINS_SENSE   2
#define ZERO_CROSS    3

/* ================================================================
 * BUTTONS
 * ================================================================