#ifndef SOUTH_PORT_H
#define SOUTH_PORT_H

#include <stdio.h>
#include <stdint.h>

#include <klog/klog.h>
#include <objclient.h>
#include <object.h>
#include <dinput.h>
#include <doutput.h>
#include <ainput.h>
#include <aoutput.h>
#include <asample.h>
#include <capability.h>

#include "node_port.h"

/* == Digital Input Port == */
class DigitalInput : public cObjectDInput {
	NodeDigitalInput *mInput;
public:
    DigitalInput(uint32_t serial, uint32_t portNo, NodeDigitalInput* input);
    ~DigitalInput();

    void setInput(NodeDigitalInput *input){ mInput = input; }
    void syncStates(cObjectClient &client);

protected:
    cKlog logger;
    void sendEvent(cObjectClient &client);
};

/* == Digital Output Port == */
class DigitalOutput : public cObjectDOutput {
public:
    DigitalOutput(uint32_t serial, uint32_t portNo, const char *label);
    ~DigitalOutput();


protected:
    cKlog logger;
private:

};

typedef struct _AnalogueSample {
    uint8_t sequence;
    float value;
} AnalogueSample;

#define ANALOGUE_SAMPLE_SIZE 32

/* == Analogue Input Port == */
class AnalogueInput : public cObjectAInput {
public:
    AnalogueInput(uint32_t serial, uint32_t portNo, NodeAnalogInput *input, int sampleRate);
    ~AnalogueInput();
    void sample(cObjectClient &client);
    void setSamplingRate(uint32_t value);
    cObjectAnalogSample* hasSample(uint8_t sequence);
    void setSampleRate(uint32_t sampleRate);
protected:
    cKlog logger;
    void sendSampleEvent(cObjectClient &client, uint8_t sequence);
    cObjectAnalogSample* createSample(uint8_t seq);
private:
	NodeAnalogInput *mInput;
    uint32_t samplingRate; // Rate in seconds
    uint32_t rateCounter;
    // Circular samples
    uint8_t currentSequence;
    uint8_t currentIndex;
    AnalogueSample samples[ANALOGUE_SAMPLE_SIZE] = {};
};

/* == Analogue Output Port == */
class AnalogueOutput: public cObjectAOutput {
protected:
   cKlog logger;
public:
    AnalogueOutput(uint32_t serial, uint32_t portNo, const char *label, const char *unit, double gain, double offset, int sampleRate);
    ~AnalogueOutput();
};

#endif // SOUTH_PORT_H
