#ifndef SENSORFACTORY_H
#define SENSORFACTORY_H

#include "Sensor.h"

#include "WiFiSensor.h"
#include "dummy/WiFiSensorDummy.h"
#include "linux/WiFiSensorLinux.h"
#include "android/WiFiSensorAndroid.h"

#include "AccelerometerSensor.h"
#include "dummy/AccelerometerSensorDummy.h"
#include "android/AccelerometerSensorAndroid.h"

#include "GyroscopeSensor.h"
#include "android/GyroscopeSensorAndroid.h"
#include "dummy/GyroscopeSensorDummy.h"

#include "BarometerSensor.h"
#include "android/BarometerSensorAndroid.h"
#include "dummy/BarometerSensorDummy.h"

#include "StepSensor.h"
#include "TurnSensor.h"
#include "ActivitySensor.h"


class SensorFactory {

private:

	/** this one is a dirty hack, as static class member variables do not work header-only */
	static SensorFactory** getPtr() {
		static SensorFactory* ptr = nullptr;
		return &ptr;
	}

public:

	/** set the to-be-used sensor-fatory */
	static void set(SensorFactory* fac) {
		Assert::isNull(*getPtr(), "set() was already called. currentely this is not intended");
		*getPtr() = fac;
	}

	/** get the currently configured sensory factory */
	static SensorFactory& get() {
		Assert::isNotNull(*getPtr(), "call set() first to set an actual factory instance!");
		return **getPtr();
	}

public:

	/** get the WiFi sensor */
	virtual WiFiSensor& getWiFi() = 0;

	/** get the Accelerometer sensor */
	virtual AccelerometerSensor& getAccelerometer() = 0;

	/** get the Gyroscope sensor */
	virtual GyroscopeSensor& getGyroscope() = 0;

	/** get the Barometer sensor */
	virtual BarometerSensor& getBarometer() = 0;

	/** get the Step sensor */
	StepSensor& getSteps() {
		static StepSensor steps(getAccelerometer());
		return steps;
	}

	/** get the Turn sensor */
	TurnSensor& getTurns() {
		static TurnSensor turns(getAccelerometer(), getGyroscope());
		return turns;
	}

	/** get the Activity sensor */
	ActivitySensor& getActivity() {
		static ActivitySensor activity(getBarometer(), getAccelerometer());
		return activity;
	}

};

#endif // SENSORFACTORY_H
