/*
* This file is part of the TraKERS\Middleware package.
*
* (c) IRI <http://www.iri.centrepompidou.fr/>
*
* For the full copyright and license information, please view the LICENSE_MIDDLEWARE
* file that was distributed with this source code.
*/

/*
 * Projet : TraKERS
 * Module : MIDDLEWARE
 * Sous-Module : Tracking/Gestures
 * Classe : UserPositionDetector
 * 
 * Auteur : alexandre.bastien@iri.centrepompidou.fr
 * 
 * Fonctionnalités : Permet de détecter si l'utilisateur s'est déplacé dans la zone de détection, en se basant
 * sur la distance de l'utilisateur à Kinect.
 */

using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;

namespace Trakers.Tracking.Gestures
{
    public class UserPositionDetector
    {
        float minDistance, maxDistance, zeroPoint;
        float searchMinDistance, searchMaxDistance;

        static int n = 0;

        /*
         * Le constructeur prend en entrée le debug mais aussi les principales distances qui délimitent la
         * zone de détection.
         */
        public UserPositionDetector(float _minDistance, float _maxDistance, float _zeroPoint, float _searchMinDistance, float _searchMaxDistance)
        {
            minDistance = _minDistance;
            maxDistance = _maxDistance;
            searchMinDistance = _searchMinDistance;
            searchMaxDistance = _searchMaxDistance;
            zeroPoint = _zeroPoint;
        }

        public void setParams(float minDist, float maxDist, float minDistHands, float maxDistHands, float zero)
        {
            //On charge tous les paramètres d'un coup.
            minDistance = minDist;
            maxDistance = maxDist;
            searchMinDistance = minDistHands;
            searchMaxDistance = maxDistHands;
            zeroPoint = zero;
        }

        /*
         * Lit la position de l'utilisateur à Kinect et ressort un pourcentage de proximité.
         * Règles : Droite affine de coefficient négatif.
         * .
         */
        public float CalcProximity(float distance)
        {
            //Si on se trouve trop loin.
            if (distance > maxDistance)
                return 0.0f;
            //Si on se trouve trop près.
            if (distance < searchMinDistance)
                return 0.0f;
            //Si on n'est pas encore trop près mais qu'on dépasse le point zéro.
            if (distance < zeroPoint)
                return 100.0f;

            //Equation, de droite affine à partir de deux points.
            //Ici 99 tout simplement car 100 - 1, les limites de pourcentage de proximité.
            float a = 99/((float)zeroPoint - maxDistance);
            float b = 100 - a * zeroPoint;

            return a * distance + b;
        }

        /*
         * Estime le nombre de vidéos à afficher en fonction du pourcentage de proximité et du nombre de
         * vidéos dans la mosaïque.
         * .
         */
        public int ImagesToShow(float proximity, int N)
        {
            //Si la proximité est nulle, on retourne 0.
            if (proximity == 0f)
                return 0;
            //Si on n'est pas encore trop près mais qu'on dépasse le point zéro.
            if (proximity >= 90f)
                return N;

            //Pour chaque intervalle de déciles (dans les pourcentages), le nombre de dizaines
            //du pourcentage de proximité plus un, fois le nombre de dizaines d'images seront affichées.
            return (((int)proximity / 10) + 1) * ((int)N / 2);
        }
    }
}
