view sv/main/EasaierSessionManager.cpp @ 85:c8186c4942d6

support mp3 file reading
author lbajardsilogic
date Mon, 25 Jun 2007 13:52:25 +0000
parents 82c960dc79f7
children bb1f9473be99
line wrap: on
line source
/* -*- c-basic-offset: 4 indent-tabs-mode: nil -*-  vi:set ts=8 sts=4 sw=4: */

/*	Sound Access	
		EASAIER client application.	
		Silogic 2007. Laure Bajard. 
	
	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 included with this distribution for more information.
*/

#include "EasaierSessionManager.h"

#include <QUrl>
#include <QMessageBox>
#include <QTextStream>
#include <iostream>
#include <QStatusBar>
#include <vector>


#include "layer/Layer.h"
#include "base/TempDirectory.h"
#include "data/fileio/AudioSourceInfoReader.h"
#include "data/fileio/ModelReader.h"
#include "data/fileio/QueryConfigReader.h"
#include "data/fileio/SparqlResultsReader.h"
#include "data/model/WaveFileModel.h"
#include "main/MainWindow.h"
#include "widgets/QueryResultsWidget.h"
#include "base/PropertyContainer.h"
#include "data/fileio/AudioFileReaderFactory.h"

EasaierSessionManager::EasaierSessionManager(HttpClient* httpClient) : QObject(),
	m_fileName(""),
	m_httpClient(httpClient),
	m_document(0),
	m_audioSourceInfoModel(0),
	m_queryModel(0)
{
	connect(m_httpClient, SIGNAL(requestFinished(int, bool)), this, SLOT(fileLoaded(int, bool)));
}

EasaierSessionManager::~EasaierSessionManager()
{
	closeSession();
	m_httpClient = 0;
}

bool EasaierSessionManager::newSession()
{
	closeSession();

	m_queryModel = new QueryModel();
	loadFile("http://easaier.silogic.fr/data/query/queryfield.xml", LoadedFile::QUERY_CONFIG);

	return true;
}

bool EasaierSessionManager::openSession(Document *document)
{
	newSession();

	m_fileName = document->getAudioSourceInfoFileName();
	m_document = document;

	loadFile(m_fileName, LoadedFile::AUDIO_SOURCE_INFO );
	
	return true;
}

bool EasaierSessionManager::openAudioInfoFile(Document *document)
{
	closeFile();

	m_fileName = document->getAudioSourceInfoFileName();
	m_document = document;

	loadFile(m_fileName, LoadedFile::AUDIO_SOURCE_INFO);
	
	return true;
}

void EasaierSessionManager::closeFile()
{
	m_audioSourceInfoModel = 0;

	while (!m_loadFile.empty())
	{
		m_loadFile.begin()->second->close();
		delete m_loadFile.begin()->second;
	    m_loadFile.erase(m_loadFile.begin());
	}

	m_modelLoaded.clear();
}

void EasaierSessionManager::closeSession()
{
	closeFile();

	m_fileName = "";
	m_document = 0;
	
	if (m_queryModel)
	{
		delete m_queryModel;
		m_queryModel = 0;
	}
}

void EasaierSessionManager::loadFile(const QString& uri, LoadedFile::FileType type)
{
	if (uri == 0)
		return;

	if (m_httpClient->getHost() == "")
	{
		return;
	}

	QUrl url(uri);
	QString path = url.path();
	QString directory = path.left(path.lastIndexOf("/"));
	QString filename = path.right(path.length() - path.lastIndexOf("/"));

	if (directory.left(1) == "/")
	{
		directory.remove(0, 1);
	}

	//create the subdirectory in local
	QString localPath = TempDirectory::getInstance()->getSubDirectoryPath(directory);
	localPath.append(filename);

	LoadedFile* newFile = new LoadedFile(localPath);
	newFile->setFileType(type);
	newFile->setUri(uri);
	int index = m_httpClient->get(uri, newFile);

	std::cerr << "Ask for file : GET " << path.toStdString() << " - index : " << index << std::endl;

	m_loadFile[index] = newFile;

	if (type == LoadedFile::QUERY_RESULTS)
		MainWindow::instance()->statusBar()->showMessage(tr("Querying database..."));
	else if (type == LoadedFile::QUERY_CONFIG)
		MainWindow::instance()->statusBar()->showMessage(tr("Asking for query config..."));
	else
		MainWindow::instance()->statusBar()->showMessage(tr("Loading File : %1").arg(filename));
}

void EasaierSessionManager::fileLoaded(int index, bool error)
{
	QString errorString = m_httpClient->errorString();
	std::map<int , LoadedFile*>::iterator iter = m_loadFile.find(index);
	if (iter == m_loadFile.end())
	{
		std::cerr << "fileLoaded() : file " << index << " not found. " << std::endl;
		return;
	}
	if (error)
	{
		QMessageBox::critical(MainWindow::instance(), tr("Download Failed"), m_httpClient->errorString());
		return; 
	}
	bool read = false;
	
	//retreive loaded file
	LoadedFile* loadedFile = iter->second;
	loadedFile->close();
	
	//save type and filename for reading
	LoadedFile::FileType type = loadedFile->getFileType();
	QString filename = loadedFile->fileName();
	QString uri = loadedFile->getUri();

	//delete de file and erase from the loaded file queue
	delete loadedFile;
	m_loadFile.erase(iter);

	std::cerr << "fileLoaded() : file loaded, start to read file " << index << std::endl;

	if ((type == LoadedFile::QUERY_RESULTS) || (type == LoadedFile::QUERY_CONFIG))
	{
		MainWindow::instance()->statusBar()->clearMessage();
	}
	else
	{
		QString name = filename.right(filename.length() - filename.lastIndexOf("/"));
		MainWindow::instance()->statusBar()->showMessage(tr("File Loaded : %1").arg(name), 3000);
	}

	//read and load (in m_document) the file according to its type 
	switch (type) {

		case LoadedFile::AUDIO_SOURCE_INFO :
		{
		    m_audioSourceInfoModel = new AudioSourceInfoModel();
			AudioSourceInfoReader audioSourceInfoReader(m_audioSourceInfoModel);
			read = audioSourceInfoReader.parse(filename);
			if (read)
			{
				m_document->setAudioSourceInfoModel(m_audioSourceInfoModel);
				loadRelatedModel();
			}
		    break;
		}
		case LoadedFile::MODEL :
		{
			QString modelName = m_audioSourceInfoModel->getKey(uri);

			read = addModelToLayers(modelName, filename);

		    break;
		}
		case LoadedFile::METADATA :
		{
			ModelReader modelReader(m_document,0, m_currentPane);
			read = modelReader.parse(filename);

		    break;
		}
		case LoadedFile::QUERY_CONFIG :
		{
			QueryConfigReader reader(m_queryModel);
			bool ok = reader.parse(filename);

			if (ok)
				emit queryModelLoaded(m_queryModel);

			read = ok;
		    break;
		}
		case LoadedFile::QUERY_RESULTS :
		{
			QueryResultsWidget* resultsWidget = MainWindow::instance()->getQueryResultsWidget();
			resultsWidget->reset();

			if (resultsWidget)
			{
				SparqlResultsReader reader(resultsWidget);
				read = reader.parse(filename);
			}
		    break;
		}
		default: break;
	}

	//if the file could not be read by any reader
	if (!read)
	{
		QFile file(filename);
		if (file.open(QFile::ReadOnly)) {
			QMessageBox::critical(MainWindow::instance(), tr("Download Error"), file.readAll());
		}
	}
	else {
		std::cerr << "fileLoaded() : " << index << " all successful. " << std::endl;
	}
}

void EasaierSessionManager::loadRelatedModel()
{
	std::set<Layer *> layers = m_document->getLayers();
	std::set<Layer *>::iterator iter;

	std::set<QString> loadedModel;

	for (iter=layers.begin(); iter != layers.end(); iter++)
	{
		Layer * layer = *iter;

		QString modelName	= layer->getModelName();
		if (modelName != "")
		{
			QString modelId		= QString::number(layer->getModelId());
			modelName.append(modelId);

		} else if (layer->getLayerPresentationName() == "Waveform")
		{
			modelName = "audiofile";
			int modelId = 1;
			layer->setModelName(modelName);
			layer->setModelId(modelId);
			modelName.append(QString::number(modelId));
		} 
		
		if (modelName != "")
		{
			QString uri = m_audioSourceInfoModel->getInfo(modelName);
				
			std::set<QString>::iterator iterModel = m_modelLoaded.find(uri);

			if (iterModel == m_modelLoaded.end())
			{
				m_modelLoaded.insert(uri);
				loadFile(uri, LoadedFile::MODEL);
			}
		}
	}
}

bool EasaierSessionManager::addModelToLayers(const QString& name, const QString& filename)
{
	std::set<Layer *> layers = m_document->getLayers();
	std::set<Layer *>::iterator iter;

	std::map<QString, Model *> addedModel;

	bool ok = false;

	for (iter=layers.begin(); iter != layers.end(); iter++)
	{
		Layer * layer = *iter;

		QString modelName	= layer->getModelName();
		QString modelId		= QString::number(layer->getModelId());

		modelName.append(modelId);
		modelName = modelName.toLower();

		if (modelName == name)
		{
			std::map<QString, Model *>::iterator iterModel;
			iterModel = addedModel.find(modelName);

			if (iterModel == addedModel.end())
			{
				QString extension = filename.right(filename.length()-filename.lastIndexOf(".")-1);
				if (AudioFileReaderFactory::isKnownExtensions(extension))
				{
					WaveFileModel *model = new WaveFileModel(filename);
					m_document->setMainModel(model);
					addedModel[modelName] = (Model* ) model;
					ok = true;
				} else
				{
					ModelReader modelReader(m_document, layer);
					ok = modelReader.parse(filename);
				}
			}
			else
			{
				Model* model = iterModel->second;
				m_document->addImportedModel(model);
				m_document->setModel(layer, model);
			}
		}
	}

	return ok;
}

void EasaierSessionManager::importMetadata(const QString& filename, Pane* pane)
{
	loadFile(filename, LoadedFile::METADATA);
	m_currentPane = pane;
}

void EasaierSessionManager::queryDatabase(const QString& themeName)
{
	QString text = tr("Sorry query database information on the %1 theme is not yet available. All results are returned").arg(themeName);	
	QMessageBox::information( MainWindow::instance(), tr("Query database information"), text);
	
	QueryThemeModel *themeModel = (m_queryModel->getThemes()).find(themeName)->second;
	QString params = "";
	if(themeModel!=0){
		PropertyContainer::PropertyList propertyList = themeModel->getProperties();
		for(int i=0; i<propertyList.size();i++){
			params+= "&"+propertyList[i] + "="+themeModel->getPropertyValue(propertyList[i]);
		}
	}
	//QString filename = "http://easaier.silogic.fr/data/query/results.xml";
	QString filename = "http://easaier.silogic.fr:9876/easaier/servlet/MOQueryServlet?theme="+themeName+""+params;

	loadFile(filename, LoadedFile::QUERY_RESULTS);
}