#include <iostream>
#include <limits>
#ifdef _WIN32
#include <Windows.h>
// Function to clear the console screen on Windows
void clearConsole() {
    system("cls");
}
#else
#include <unistd.h>
// Function to clear the console screen on Unix-like systems
void clearConsole() {
    system("clear");
}
#endif
using namespace std;

// Function to clear input buffer to prevent infinite loops from invalid input
void clearInput() {
    cin.clear();
    cin.ignore(numeric_limits<streamsize>::max(), '\n');
}

int main() {
    int choice;

    // Main loop for the menu system
    while (true) {
        // Clear the console and display the enhanced menu with designs
        clearConsole();
        cout << "****************************************" << endl;
        cout << "*                                      *" << endl;
        cout << "*              MAIN MENU               *" << endl;
        cout << "*                                      *" << endl;
        cout << "****************************************" << endl;
        cout << "* [1] Electric Bill                    *" << endl;
        cout << "* [2] Water Bill                       *" << endl;
        cout << "* [3] Calculator                       *" << endl;
        cout << "* [4] Exit                             *" << endl;
        cout << "* [0] Credits                          *" << endl;
        cout << "****************************************" << endl;
        cout << "Choose an option: ";
        
        // Check if input is a valid integer
        if (!(cin >> choice)) {
            cout << "\n****************************************" << endl;
            cout << "* Invalid input. Please enter a number *" << endl;
            cout << "* between 0 and 4.                     *" << endl;
            cout << "****************************************" << endl;
            cout << "Press Enter to continue!" << endl;
            cin.ignore();
            cin.get();
            clearInput();
            continue;
        }

        // Handle menu choices with switch statement
        switch (choice) {
        case 1: {
            // Electric bill calculation with enhanced interface
            clearConsole();
            cout << "****************************************" << endl;
            cout << "*           ELECTRIC BILL              *" << endl;
            cout << "****************************************" << endl;
            double prevReading, presReading;
            const double rate = 12.25;

            cout << "Enter previous electric meter reading: ";
            if (!(cin >> prevReading) || prevReading < 0) {
                cout << "\n****************************************" << endl;
                cout << "* Invalid input for previous reading.  *" << endl;
                cout << "****************************************" << endl;
                cout << "Press Enter to continue!" << endl;
                cin.ignore();
                cin.get();
                clearInput();
                break;
            }

            cout << "\nEnter present electric meter reading: ";
            if (!(cin >> presReading) || presReading < prevReading) {
                cout << "\n****************************************" << endl;
                cout << "* Invalid input for present reading.   *" << endl;
                cout << "* It must be >= previous reading.      *" << endl;
                cout << "****************************************" << endl;
                cout << "Press Enter to continue!" << endl;
                cin.get();
                clearInput();
                break;
            }

            double bill = (presReading - prevReading) * rate;
            cout << "\n****************************************" << endl;
            cout << "* Electric Bill: " << bill << "                    *" << endl;
            cout << "****************************************" << endl;
            cout << "Press Enter to continue!" << endl;
            cin.ignore();
            cin.get();
            break;
        }
        case 2: {
            // Water bill calculation with tiered rates and enhanced interface
            clearConsole();
            cout << "****************************************" << endl;
            cout << "*            WATER BILL                *" << endl;
            cout << "****************************************" << endl;
            double prevReading, presReading, rate;
            cout << "\nEnter previous water meter reading (cu.m): ";
            if (!(cin >> prevReading) || prevReading < 0) {
                cout << "\n****************************************" << endl;
                cout << "* Invalid input for previous reading.  *" << endl;
                cout << "****************************************" << endl;
                cout << "Press Enter to continue!" << endl;
                cin.ignore();
                cin.get();
                clearInput();
                break;
            }

            cout << "\nEnter present water meter reading (cu.m): ";
            if (!(cin >> presReading) || presReading < prevReading) {
                cout << "\n****************************************" << endl;
                cout << "* Invalid input for present reading.   *" << endl;
                cout << "* It must be >= previous reading.      *" << endl;
                cout << "****************************************" << endl;
                cout << "Press Enter to continue!" << endl;
                cin.get();
                clearInput();
                break;
            }

            double consumption = presReading - prevReading;

            // Determine rate based on consumption tiers
            if (consumption >= 0 && consumption <= 10) {
                rate = 10.00;
            } else if (consumption >= 11 && consumption <= 20) {
                rate = 20.00;
            } else if (consumption >= 21) {
                rate = 30.00;
            } else {
                cout << "\n****************************************" << endl;
                cout << "* Invalid consumption value.           *" << endl;
                cout << "****************************************" << endl;
                cout << "Press Enter to continue!" << endl;
                cin.ignore();
                cin.get();
                break;
            }

            double bill = consumption * rate;
            cout << "\n****************************************" << endl;
            cout << "* Water Bill: " << bill << "                      *" << endl;
            cout << "****************************************" << endl;
            cout << "Press Enter to continue!" << endl;
            cin.ignore();
            cin.get();
            break;
        }
        case 3: {
            // Simple calculator for basic operations with enhanced interface
            clearConsole();
            cout << "****************************************" << endl;
            cout << "*            CALCULATOR                *" << endl;
            cout << "****************************************" << endl;
            double num1, num2;
            char op;

            cout << "Enter first number: ";
            if (!(cin >> num1)) {
                cout << "\n****************************************" << endl;
                cout << "* Invalid input for first number.      *" << endl;
                cout << "****************************************" << endl;
                clearInput();
                cout << "Press Enter to continue!" << endl;
                cin.ignore();
                cin.get();
                break;
            }

            cout << "Enter operator (+, -, *, /): ";
            cin >> op;
            if (op != '+' && op != '-' && op != '*' && op != '/') {
                cout << "\n****************************************" << endl;
                cout << "* Invalid operator.                    *" << endl;
                cout << "****************************************" << endl;
                cout << "Press Enter to continue!" << endl;
                cin.ignore();
                cin.get();
                clearInput();
                break;
            }

            cout << "Enter second number: ";
            if (!(cin >> num2)) {
                cout << "\n****************************************" << endl;
                cout << "* Invalid input for second number.     *" << endl;
                cout << "****************************************" << endl;
                cout << "Press Enter to continue!" << endl;
                cin.ignore();
                cin.get();
                clearInput();
                break;
            }

            // Perform calculation based on operator
            cout << "\n****************************************" << endl;
            switch (op) {
            case '+':
                cout << "* Result: " << num1 + num2 << "                          *" << endl;
                break;
            case '-':
                cout << "* Result: " << num1 - num2 << "                          *" << endl;
                break;
            case '*':
                cout << "* Result: " << num1 * num2 << "                          *" << endl;
                break;
            case '/':
                if (num2 == 0) {
                    cout << "* Error: Division by zero is not allowed.*" << endl;
                } else {
                    cout << "* Result: " << num1 / num2 << "                          *" << endl;
                }
                break;
            }
            cout << "****************************************" << endl;
            cout << "Press Enter to continue!" << endl;
            cin.ignore();
            cin.get();
            break;
        }
        case 4:
            // Exit the program with a design
            cout << "****************************************" << endl;
            cout << "*              Goodbye!                *" << endl;
            cout << "****************************************" << endl;
            return 0;

        case 0:
            // Display credits with enhanced design
            clearConsole();
            cout << "****************************************" << endl;
            cout << "*               CREDITS                *" << endl;
            cout << "****************************************" << endl;
            cout << "* Made by: Regidor, Shokri Iam         *" << endl;
            cout << "* Source:https://pastebin.com/8Wb8ub3b *" << endl;
            cout << "* Thanks to you!                       *" << endl;
            cout << "****************************************" << endl;
            cout << "Press Enter to continue!" << endl;
            cin.ignore();
            cin.get();
            break;
        default:
            // Handle invalid menu choices with design
            cout << "****************************************" << endl;
            cout << "* Invalid choice. Please select        *" << endl;
            cout << "* between 0 and 4.                     *" << endl;
            cout << "****************************************" << endl;
            cout << "Press Enter to continue!" << endl;
            cin.ignore();
            cin.get();
        }
    }
}