#include "TexturList.h"

#include "Text.h"
#include "Textur.h"

using namespace Framework;

int TexturList::id = 0;
Critical TexturList::cs;

// Inhalt der TexturList Klasse
// Konstruktor
TexturList::TexturList()
    : ReferenceCounter()
{
    textures = new RCArray<Textur>();
    names = new RCArray<Text>();
}

// Destruktor
TexturList::~TexturList()
{
    textures->release();
    names->release();
}

// Löscht alle Texturen
__declspec(dllexport) void TexturList::leeren()
{
    cs.lock();
    textures->leeren();
    names->leeren();
    cs.unlock();
}

// Fügt der Liste eine Textur hinzu
//  t: Die Textur
//  name: Der name, unter dem die Textur in der Liste gespeichert wird
bool TexturList::addTextur(Textur* t, const char* name)
{
    cs.lock();
    for (auto i : *names)
    {
        if (i->istGleich(name))
        {
            t->release();
            cs.unlock();
            return 0;
        }
    }
    t->id = id++;
    textures->add(t);
    names->add(new Text(name));
    cs.unlock();
    return 1;
}

// Entfernt eine Textur aus der Liste
//  name: Der Name der Textur
void TexturList::removeTextur(const char* name)
{
    cs.lock();
    int index = 0;
    for (auto i : *names)
    {
        if (i->istGleich(name))
        {
            names->remove(index);
            textures->remove(index);
            cs.unlock();
            return;
        }
        index++;
    }
    cs.unlock();
}

// Überprüft, ob unter einem bestimmten Namen eine Textur abgespeichert wurde
//  name: Der Name
//  return: true, wenn eine Textur mit dem Namen existiert
bool TexturList::hatTextur(const char* name) const
{
    cs.lock();
    for (auto i : *names)
    {
        if (i->istGleich(name))
        {
            cs.unlock();
            return 1;
        }
    }
    cs.unlock();
    return 0;
}

// Gibt eine bestimmte Textur zurück
//  name: Der Name der Textur
Textur* TexturList::getTextur(const char* name) const
{
    cs.lock();
    int index = 0;
    for (auto i : *names)
    {
        if (i->istGleich(name))
        {
            cs.unlock();
            return textures->get(index);
        }
        index++;
    }
    cs.unlock();
    return 0;
}

// Gibt eine bestimmte Textur zurück
//  id: Die Id der Textur
Textur* TexturList::getTextur(int id) const
{
    cs.lock();
    for (auto i : *textures)
    {
        if (i->getId() == id)
        {
            cs.unlock();
            return dynamic_cast<Textur*>(i->getThis());
        }
    }
    cs.unlock();
    return 0;
}

// Gibt eine bestimmte Textur ohne erhöhten Reference Counter zurück
//  name: Der Name der Textur
Textur* TexturList::zTextur(const char* name) const
{
    cs.lock();
    int index = 0;
    for (auto i : *names)
    {
        if (i->istGleich(name))
        {
            cs.unlock();
            return textures->z(index);
        }
        index++;
    }
    cs.unlock();
    return 0;
}

// Gibt eine bestimmte Textur ohne erhöhten Reference Counter zurück
//  id: Die Id der Textur
Textur* TexturList::zTextur(int id) const
{
    cs.lock();
    for (auto i : *textures)
    {
        if (i->getId() == id)
        {
            cs.unlock();
            return i;
        }
    }
    cs.unlock();
    return 0;
}

// statische Funktionen

// Initialisiert statische private member. Wird vom Framework automatisch
// aufgerufen.
void TexturList::init()
{
    id = 0;
}

// Löscht statische private member. Wird vom Framework automatisch aufgerufen.
void TexturList::destroy() {}