#include <stdio.h>
#include <stdlib.h>
#include <stdbool.h>

#define size 3

bool empty(int allocated) {
    return allocated == 0;
}

bool full(int allocated) {
    return allocated == size -1;
}

void state(int* fifo, int allocated) {
    if (empty(allocated)) printf("[?] Kolejka pusta\n");
    else if (full(allocated)) printf("[?] Kolejka pełna\n");
    else printf("[?] Kolejna niepełna i niepusta");
}

void show(int* fifo, int allocated) {
    printf("[?] Wypisywanie:\n");
    for (int i = 0; i < allocated; i++) {
        printf("fifo[%d] =\t%d\n", i, fifo[i]);
    }
}

bool push(int* fifo, int* allocated, int el) {
    if (*allocated + 1 > size) return 0;
    printf("[+] Dodwanie: %d\n", el);
    fifo[*allocated] = el;
    *allocated += 1;
    return 1;
}

bool pop(int* fifo, int* allocated) {
    if (*allocated == 0) return 0;
    fifo[0] = fifo[1];

    for (int i = 0; i < *allocated; i++) {
        fifo[i] = fifo[i+1];
    }

    *allocated = *allocated-1;
    return 1;
}

char menu();

int main() {
    int fifo[size];
    int allocated = 0;

    do {
        char opc = menu(allocated);
        switch (opc) {
            case 'W':
                printf ("\n---obsługa wypisania zawartości kolejki---\n");
                show(fifo, allocated);

            break;

            case 'S':
                printf ("\n---obsługa wypisania stanu kolejki (pusta/pelna)---\n");
                state(fifo, allocated);
            break;

            case 'A':
                int el;
                printf ("\n---obsluga dolozenia elementu do kolejki---\n");
                printf("Podaj element: ");
                scanf("%d", &el);
                if(!push(fifo, &allocated, el)) printf("[!] Brak miejsca w kolejce!");
            break;

            case 'Z':
                printf("\n---obsługa zebrania elementu z kolejki---\n");
                if(!pop(fifo, &allocated)) printf("[!] Kolejka jest pusta");
            break;

            case 'K':
                printf ("[?] Koniec\n");
                return 0;
            break;

        }
    } while (getchar(), getchar());

    return 0;
}

char menu (int allocated) {
    char opcja = 'X';

    while ((opcja != 'W') && (opcja != 'S') && (opcja != 'A') && (opcja != 'Z') && (opcja != 'K')) {
        system("@cls||clear");
        printf ("Wybierz opcje (%d/%d):\n", allocated, size);
        printf ("W - Wypisanie zawartosci kolejki\n");
        printf ("S - Wypisanie stanu kolejki (pusta/pelna)\n");
        printf ("A - Dolozenie elementu do kolejki\n");
        printf ("Z - Zebranie elementu z kolejki\n");
        printf ("K - Koniec \n");
        printf ("Podaj opcję: ");
        scanf ("%c", &opcja);
    }

    return opcja;
}
