//
// Created by jedi on 11/5/18.
//

#pragma once

#include "gfx/Canvas.h"

namespace micromenu {

    class node {
        private:
            node *parent_ = nullptr;
            node *child_ = nullptr;
            node *cursor_ = nullptr;
            node *next_ = nullptr;

            void addNodes(bool b) {
            }

            template<class ...Us>
            void addNodes(bool b, node *n, Us ... ns) {
                next_ = n;
                next_->parent_ = parent_;
                next_->addNodes(!b, ns...);
            }

        public:
            const char *title_ = 0;
            const int minsize;
            const int maxsize;

            virtual void render(Canvas &c) = 0;

            explicit node(int min = 24, int max = 48) : next_(nullptr), child_(nullptr), parent_(nullptr), minsize(min),
                                                        maxsize(max) {
            }

            explicit node(const char *t, int min = 24, int max = 48) : title_(t), minsize(min), maxsize(max),
                                                                       next_(nullptr),
                                                                       child_(nullptr),
                                                                       parent_(nullptr) {
            }

            template<typename ... Args>
            node(const char *t, node *n, Args ... ns) : title_(t), minsize(24), maxsize(48) {
                child_ = n;
                cursor_ = n;
                n->parent_ = this;
                child_->addNodes(true, ns...);
            }

            node *getChild() {
                return child_;
            }

            node *getNext() {
                return next_;
            }

            node *getCursor() {
                return cursor_;
            }

            node *getParent() {
                return parent_;
            }

            void setCursor(node *c) {
                cursor_ = c;
            }
    };


    class value : public node {
        public:
            const char *header;
            int state;

            value(const char *t, int val, int min = 64, int max = 96) : node(t, min, max), header(t), state(val) {
            }
    };


}