/***************************************************************************
 * trackpos.cpp: implementation of TrackPos class
 *
 * This file is part of KTabEdit, a KDE tabulature editor
 *
 * copyright (C) 2006- the KTabEdit development team <mrgwen@gmail.com>
 ***************************************************************************/

/***************************************************************************
 * 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 2 of the License, or
 * (at your option) any later version.
 *
 * See the file COPYING for more information.
 ***************************************************************************/

#include "trackpos.h"
#include "util/assert.h"

#include <limits>

TrackPos::TrackPos()
: curBarPos(0),
  curTimesPos(0),
  curPos(0)
{
}

TrackPos::TrackPos(int bar, int time, int note)
: curBarPos(bar),
  curTimesPos(time),
  curPos(note)
{
	POSTCONDITION( bar >= 0 && time >= 0 && note >= 0 );
}

TrackPos::~TrackPos()
{
}

void TrackPos::clone(const TrackPos& position)
{
	curPos = position.curPos;
	curBarPos = position.curBarPos;
	curTimesPos = position.curTimesPos;
}

void TrackPos::incChord()
{
	if (curPos < std::numeric_limits<int>::max())
		curPos++;
}

void TrackPos::decChord()
{
	if (curPos > 0)
		curPos--;
}

void TrackPos::setChord(int chord)
{
	PRECONDITION( chord >= 0 );
	
	curPos = chord;
}

int TrackPos::chord() const
{
	return curPos;
}

void TrackPos::incBar()
{
	if (curBarPos < std::numeric_limits<int>::max())
		curBarPos++;
}

void TrackPos::decBar()
{
	if (curBarPos > 0)
		curBarPos--;
}

void TrackPos::setBar(int bar)
{
	PRECONDITION( bar >= 0 );
	
	curBarPos = bar;
}

int TrackPos::bar() const
{
	return curBarPos;
}

void TrackPos::incTimes()
{
	if (curTimesPos < std::numeric_limits<int>::max())
		curTimesPos++;
}

void TrackPos::decTimes()
{
	if (curTimesPos > 0)
		curTimesPos--;
}

void TrackPos::setTimes(int notes)
{
	PRECONDITION( notes >= 0 );
	
	curTimesPos = notes;
}

int TrackPos::times() const
{
	return curTimesPos;
}

bool TrackPos::operator==(const TrackPos& trackPos) const
{
	return (curPos == trackPos.curPos && curBarPos == trackPos.curBarPos && curTimesPos == trackPos.curTimesPos);
}

bool TrackPos::operator!=(const TrackPos& trackPos) const
{
	return !(*this == trackPos);
}

bool TrackPos::operator<(const TrackPos& position) const
{
	bool result;
	
	if (curBarPos <= position.curBarPos)
		if (curBarPos == position.curBarPos)
			if (curTimesPos < position.curTimesPos)
				result = true;
			else
				result = false;
		else
			result = true;
	else
		result = false;
	
	return result;
}

bool TrackPos::operator<=(const TrackPos& position) const
{
	bool result;
	
	if (curBarPos <= position.curBarPos)
		if (curBarPos == position.curBarPos)
			if (curTimesPos <= position.curTimesPos)
				result = true;
			else
				result = false;
		else
			result = true;
	else
		result = false;
	
	return result;
}

bool TrackPos::operator>(const TrackPos& position) const
{
	return !this->operator<=(position);
}

bool TrackPos::operator>=(const TrackPos& position) const
{
	return !this->operator<(position);
}
