// ----------------------------------------------------------------------------
//
//  Copyright (C) 2010-2015 Fons Adriaensen <fons@linuxaudio.org>
//    
//  This program is free software; you can redistribute it and/or modify
//  it under the terms of the GNU General Public License as published by
//  the Free Software Foundation; either version 3 of the License, or
//  (at your option) any later version.
//
//  This program is distributed in the hope that it will be useful,
//  but WITHOUT ANY WARRANTY; without even the implied warranty of
//  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
//  GNU General Public License for more details.
//
//  You should have received a copy of the GNU General Public License
//  along with this program.  If not, see <http://www.gnu.org/licenses/>.
//
// ----------------------------------------------------------------------------


#include <math.h>
#include <stdio.h>
#include "guiclass.h"


int Pbutt1::handle_press (void)
{
    _state |= 1;
    return PRESS;
}

int Pbutt1::handle_relse (void)
{
    _state &= ~1;
    return 0;
}



int Pbutt2::handle_press (void)
{
    _state |= 1;
    return PRESS;
}

int Pbutt2::handle_relse (void)
{
    _state &= ~1;
    return RELSE;
}



Rlevel100A::Rlevel100A (X_window    *parent,
                        X_callback  *cbobj,
                        int          cbind,
                        RotaryGeom  *rgeom,
                        int          xp,
                        int          yp,
                        int          maxdb) :
RotaryCtl (parent, cbobj, cbind, rgeom, xp, yp),
_maxdb (maxdb),    
_lastc (0)
{
    _count = -1;
    set_count (0);
}


void Rlevel100A::get_string (char *p, int n)
{
    snprintf (p, n, "%5.1lf", _value);
}


void Rlevel100A::set_value (double v)
{
    double u;

    v -= _maxdb;
    if       (v >= -40) u = 300 + 5 * v;
    else  if (v > -100) u = (1 - sqrt (1 - 16e-3 * (100 + v))) / 8e-3;
    else                u = 0;
    set_count ((int) floor (u + 0.5));
    render ();
}


int Rlevel100A::handle_button (void)
{
    int k;

    if (_button == 3)
    {
	if (_count) { k = 0; _lastc = _count; }
	else   	    { k = _lastc; _lastc = 0; }
        return set_count (k);
    }
    return PRESS;
}


int Rlevel100A::handle_motion (int dx, int dy)
{
    return set_count (_rcount + 2 * (dx - dy));
}


int Rlevel100A::handle_mwheel (int dw)
{
    if (! (_keymod & ShiftMask)) dw *= 5;
    return set_count (_count + dw);
}


int Rlevel100A::set_count (int u)
{
    if (u <   0) u = 0;
    if (u > 300) u = 300;
    if (u != _count)
    {
	_count = u;
	if      (u > 100) _value = 0.2 * (u - 300) + _maxdb;
        else if (u)       _value = (1 - 4e-3 * u) * u - 100 + _maxdb;
	else              _value = -1000;
	_angle = 0.9 * (u - 150);
        return DELTA;
    }
    return 0;
}

