diff --git a/CMakeLists.txt b/CMakeLists.txt index 6ca62025a..d0db60c62 100644 --- a/CMakeLists.txt +++ b/CMakeLists.txt @@ -14,6 +14,9 @@ ELSE() ENDIF() FIND_PACKAGE( Taglib 1.6.0 REQUIRED ) +include( CheckTagLibFileName ) +check_taglib_filename( COMPLEX_TAGLIB_FILENAME ) + FIND_PACKAGE( LibLastFm 0.3.3 REQUIRED ) FIND_PACKAGE( LibEchonest 1.1.1 REQUIRED ) FIND_PACKAGE( CLucene REQUIRED ) @@ -29,4 +32,3 @@ ADD_SUBDIRECTORY( libportfwd ) ADD_SUBDIRECTORY( qxt ) ADD_SUBDIRECTORY( src/libtomahawk ) ADD_SUBDIRECTORY( src ) - diff --git a/CMakeModules/CheckTagLibFileName.cmake b/CMakeModules/CheckTagLibFileName.cmake new file mode 100644 index 000000000..e5b3706c9 --- /dev/null +++ b/CMakeModules/CheckTagLibFileName.cmake @@ -0,0 +1,15 @@ +# taglib changed filenames to be a char/wchar struct on some platforms, need to check for it +macro (CHECK_TAGLIB_FILENAME TAGLIB_FILENAME_COMPLEX) + include (CheckCXXSourceCompiles) + set (CMAKE_REQUIRED_FLAGS ${TAGLIB_CFLAGS}) + set (CMAKE_REQUIRED_INCLUDES ${TAGLIB_INCLUDES}) + set (CMAKE_REQUIRED_LIBRARIES ${TAGLIB_LIBRARIES}) + check_cxx_source_compiles( + "#include + int main() + { + TagLib::FileName fileName1(\"char\"); + TagLib::FileName fileName2(L\"wchar\"); + return 0; + }" ${TAGLIB_FILENAME_COMPLEX}) +endmacro (CHECK_TAGLIB_FILENAME) diff --git a/admin/win/revision.txt b/admin/win/revision.txt index eebd1d10b..4e9e28848 100644 --- a/admin/win/revision.txt +++ b/admin/win/revision.txt @@ -1 +1 @@ -61 \ No newline at end of file +63 \ No newline at end of file diff --git a/admin/win/tomahawk.nsi b/admin/win/tomahawk.nsi index 3212d7a51..0bc84cbaf 100755 --- a/admin/win/tomahawk.nsi +++ b/admin/win/tomahawk.nsi @@ -301,6 +301,8 @@ Section "Tomahawk Player" SEC_TOMAHAWK_PLAYER File "${MING_DLL_PATH}\libechonest.dll" File "${MING_DLL_PATH}\liblastfm.dll" + File "${MING_LIB}\libclucene-core.dll" + File "${QXTWEB_DLL_PATH}\libqxtweb-standalone.dll" SectionEnd diff --git a/src/libtomahawk/CMakeLists.txt b/src/libtomahawk/CMakeLists.txt index 965330da3..46f7418eb 100644 --- a/src/libtomahawk/CMakeLists.txt +++ b/src/libtomahawk/CMakeLists.txt @@ -364,7 +364,7 @@ target_link_libraries( tomahawklib ogg FLAC++ tomahawk_jdns - clucene + ${CLUCENE_LIBRARY} ) install( TARGETS tomahawklib DESTINATION lib ) diff --git a/src/libtomahawk/database/fuzzyindex.cpp b/src/libtomahawk/database/fuzzyindex.cpp index 8e85a72f2..7e1074c23 100644 --- a/src/libtomahawk/database/fuzzyindex.cpp +++ b/src/libtomahawk/database/fuzzyindex.cpp @@ -8,6 +8,15 @@ #include +#ifndef WIN32 +using namespace lucene::analysis; +using namespace lucene::document; +using namespace lucene::store; +using namespace lucene::index; +using namespace lucene::queryParser; +using namespace lucene::search; +#endif + FuzzyIndex::FuzzyIndex( DatabaseImpl& db ) : QObject() @@ -16,10 +25,10 @@ FuzzyIndex::FuzzyIndex( DatabaseImpl& db ) , m_luceneSearcher( 0 ) { QString lucenePath = TomahawkUtils::appDataDir().absoluteFilePath( "tomahawk.lucene" ); - bool create = !lucene::index::IndexReader::indexExists( lucenePath.toStdString().c_str() ); - m_luceneDir = lucene::store::FSDirectory::getDirectory( lucenePath.toStdString().c_str(), create ); + bool create = !IndexReader::indexExists( lucenePath.toStdString().c_str() ); + m_luceneDir = FSDirectory::getDirectory( lucenePath.toStdString().c_str(), create ); - m_analyzer = _CLNEW lucene::analysis::SimpleAnalyzer(); + m_analyzer = _CLNEW SimpleAnalyzer(); } @@ -36,7 +45,7 @@ void FuzzyIndex::beginIndexing() { m_mutex.lock(); - lucene::index::IndexWriter luceneWriter = lucene::index::IndexWriter( m_luceneDir, m_analyzer, true ); + IndexWriter luceneWriter = IndexWriter( m_luceneDir, m_analyzer, true ); } @@ -56,9 +65,9 @@ FuzzyIndex::appendFields( const QString& table, const QMap< unsigned int, QStrin m_luceneSearcher = 0; m_luceneReader = 0; - bool create = !lucene::index::IndexReader::indexExists( TomahawkUtils::appDataDir().absoluteFilePath( "tomahawk.lucene" ).toStdString().c_str() ); - lucene::index::IndexWriter luceneWriter = lucene::index::IndexWriter( m_luceneDir, m_analyzer, create ); - lucene::document::Document doc; + bool create = !IndexReader::indexExists( TomahawkUtils::appDataDir().absoluteFilePath( "tomahawk.lucene" ).toStdString().c_str() ); + IndexWriter luceneWriter = IndexWriter( m_luceneDir, m_analyzer, create ); + Document doc; QMapIterator< unsigned int, QString > it( fields ); while ( it.hasNext() ) @@ -68,14 +77,14 @@ FuzzyIndex::appendFields( const QString& table, const QMap< unsigned int, QStrin QString name = it.value(); { - lucene::document::Field* field = _CLNEW lucene::document::Field( table.toStdWString().c_str(), name.toStdWString().c_str(), - lucene::document::Field::STORE_YES | lucene::document::Field::INDEX_UNTOKENIZED ); + Field* field = _CLNEW Field( table.toStdWString().c_str(), name.toStdWString().c_str(), + Field::STORE_YES | Field::INDEX_UNTOKENIZED ); doc.add( *field ); } { - lucene::document::Field* field = _CLNEW lucene::document::Field( _T( "id" ), QString::number( id ).toStdWString().c_str(), - lucene::document::Field::STORE_YES | lucene::document::Field::INDEX_NO ); + Field* field = _CLNEW Field( _T( "id" ), QString::number( id ).toStdWString().c_str(), + Field::STORE_YES | Field::INDEX_NO ); doc.add( *field ); } @@ -102,29 +111,29 @@ FuzzyIndex::search( const QString& table, const QString& name ) QMap< int, float > resultsmap; if ( !m_luceneReader ) { - if ( !lucene::index::IndexReader::indexExists( TomahawkUtils::appDataDir().absoluteFilePath( "tomahawk.lucene" ).toStdString().c_str() ) ) + if ( !IndexReader::indexExists( TomahawkUtils::appDataDir().absoluteFilePath( "tomahawk.lucene" ).toStdString().c_str() ) ) { qDebug() << Q_FUNC_INFO << "index didn't exist."; return resultsmap; } - m_luceneReader = lucene::index::IndexReader::open( m_luceneDir ); - m_luceneSearcher = _CLNEW lucene::search::IndexSearcher( m_luceneReader ); + m_luceneReader = IndexReader::open( m_luceneDir ); + m_luceneSearcher = _CLNEW IndexSearcher( m_luceneReader ); } if ( name.isEmpty() ) return resultsmap; - lucene::analysis::SimpleAnalyzer analyzer; - lucene::queryParser::QueryParser parser( table.toStdWString().c_str(), m_analyzer ); - lucene::search::Hits* hits = 0; + SimpleAnalyzer analyzer; + QueryParser parser( table.toStdWString().c_str(), m_analyzer ); + Hits* hits = 0; - lucene::search::FuzzyQuery* qry = _CLNEW lucene::search::FuzzyQuery( _CLNEW lucene::index::Term( table.toStdWString().c_str(), name.toStdWString().c_str() ) ); + FuzzyQuery* qry = _CLNEW FuzzyQuery( _CLNEW Term( table.toStdWString().c_str(), name.toStdWString().c_str() ) ); hits = m_luceneSearcher->search( qry ); for ( int i = 0; i < hits->length(); i++ ) { - lucene::document::Document* d = &hits->doc( i ); + Document* d = &hits->doc( i ); float score = hits->score( i ); int id = QString::fromWCharArray( d->get( _T( "id" ) ) ).toInt(); diff --git a/src/libtomahawk/database/fuzzyindex.h b/src/libtomahawk/database/fuzzyindex.h index df49ba31b..036907ba7 100644 --- a/src/libtomahawk/database/fuzzyindex.h +++ b/src/libtomahawk/database/fuzzyindex.h @@ -7,26 +7,34 @@ #include #include +#ifndef WIN32 namespace lucene { namespace analysis { - class SimpleAnalyzer; + class SimpleAnalyzer; } namespace store { - class Directory; + class Directory; } namespace index { - class IndexReader; - class IndexWriter; + class IndexReader; + class IndexWriter; } namespace search { - class IndexSearcher; + class IndexSearcher; } } +#else +class SimpleAnalyzer; +class Directory; +class IndexReader; +class IndexWriter; +class IndexSearcher; +#endif class DatabaseImpl; @@ -54,10 +62,17 @@ private: DatabaseImpl& m_db; QMutex m_mutex; + #ifndef WIN32 lucene::analysis::SimpleAnalyzer* m_analyzer; lucene::store::Directory* m_luceneDir; lucene::index::IndexReader* m_luceneReader; lucene::search::IndexSearcher* m_luceneSearcher; + #else + SimpleAnalyzer* m_analyzer; + Directory* m_luceneDir; + IndexReader* m_luceneReader; + IndexSearcher* m_luceneSearcher; + #endif }; #endif // FUZZYINDEX_H diff --git a/src/libtomahawk/network/filetransferconnection.h b/src/libtomahawk/network/filetransferconnection.h index 4600ba137..660fc8507 100644 --- a/src/libtomahawk/network/filetransferconnection.h +++ b/src/libtomahawk/network/filetransferconnection.h @@ -9,10 +9,12 @@ #include "network/connection.h" #include "result.h" +#include "dllmacro.h" + class ControlConnection; class BufferIODevice; -class FileTransferConnection : public Connection +class DLLEXPORT FileTransferConnection : public Connection { Q_OBJECT diff --git a/src/libtomahawk/playlist/dynamic/DynamicPlaylist.h b/src/libtomahawk/playlist/dynamic/DynamicPlaylist.h index 00f68a647..e8884cd0d 100644 --- a/src/libtomahawk/playlist/dynamic/DynamicPlaylist.h +++ b/src/libtomahawk/playlist/dynamic/DynamicPlaylist.h @@ -25,6 +25,8 @@ #include "typedefs.h" #include "playlist/dynamic/DynamicControl.h" +#include "dllmacro.h" + class DatabaseCommand_LoadAllDynamicPlaylists; class DatabaseCommand_SetDynamicPlaylistRevision; class DatabaseCommand_CreateDynamicPlaylist; @@ -37,7 +39,7 @@ namespace Tomahawk { * It uses normal PlaylistEntries but also has a mode, a generator, and a list of controls */ -struct DynamicPlaylistRevision : PlaylistRevision +struct DLLEXPORT DynamicPlaylistRevision : PlaylistRevision { QList< dyncontrol_ptr > controls; Tomahawk::GeneratorMode mode; @@ -56,7 +58,7 @@ struct DynamicPlaylistRevision : PlaylistRevision DynamicPlaylistRevision() {} }; -class DynamicPlaylist : public Playlist +class DLLEXPORT DynamicPlaylist : public Playlist { Q_OBJECT diff --git a/src/libtomahawk/playlist/dynamic/GeneratorFactory.h b/src/libtomahawk/playlist/dynamic/GeneratorFactory.h index 9be120f90..5e2120bfd 100644 --- a/src/libtomahawk/playlist/dynamic/GeneratorFactory.h +++ b/src/libtomahawk/playlist/dynamic/GeneratorFactory.h @@ -7,12 +7,14 @@ #include "playlist/dynamic/GeneratorInterface.h" #include "typedefs.h" +#include "dllmacro.h" + namespace Tomahawk { /** * Generators should subclass this and have it create the custom Generator */ -class GeneratorFactoryInterface +class DLLEXPORT GeneratorFactoryInterface { public: GeneratorFactoryInterface() {} @@ -30,7 +32,7 @@ public: /** * Simple factory that generates Generators from string type descriptors */ -class GeneratorFactory +class DLLEXPORT GeneratorFactory { public: static geninterface_ptr create( const QString& type ); diff --git a/src/libtomahawk/playlist/dynamic/GeneratorInterface.h b/src/libtomahawk/playlist/dynamic/GeneratorInterface.h index aaaea697d..ac73d5bf2 100644 --- a/src/libtomahawk/playlist/dynamic/GeneratorInterface.h +++ b/src/libtomahawk/playlist/dynamic/GeneratorInterface.h @@ -25,6 +25,8 @@ #include "query.h" #include "playlist/dynamic/DynamicControl.h" +#include "dllmacro.h" + namespace Tomahawk { /** @@ -37,7 +39,7 @@ namespace Tomahawk { * - Statically (ask for X tracks, get X tracks) * - On Demand (as for next track, ask for next track again, etc) */ -class GeneratorInterface : public QObject +class DLLEXPORT GeneratorInterface : public QObject { Q_OBJECT Q_PROPERTY( QString type READ type ) diff --git a/src/libtomahawk/playlist/dynamic/echonest/EchonestGenerator.h b/src/libtomahawk/playlist/dynamic/echonest/EchonestGenerator.h index 7beedaa1d..dc5bd8420 100644 --- a/src/libtomahawk/playlist/dynamic/echonest/EchonestGenerator.h +++ b/src/libtomahawk/playlist/dynamic/echonest/EchonestGenerator.h @@ -24,12 +24,14 @@ #include "playlist/dynamic/GeneratorFactory.h" #include "playlist/dynamic/DynamicControl.h" +#include "dllmacro.h" + namespace Tomahawk { class EchonestSteerer; -class EchonestFactory : public GeneratorFactoryInterface +class DLLEXPORT EchonestFactory : public GeneratorFactoryInterface { public: EchonestFactory(); diff --git a/src/libtomahawk/result.h b/src/libtomahawk/result.h index ff764d2a2..1c15ab165 100644 --- a/src/libtomahawk/result.h +++ b/src/libtomahawk/result.h @@ -1,6 +1,6 @@ - #ifndef RESULT_H #define RESULT_H + #include #include @@ -18,7 +18,7 @@ class DLLEXPORT Result : public QObject Q_OBJECT public: - Result(); + Result(); explicit Result( const QVariant& v, const collection_ptr& collection ); virtual ~Result(); diff --git a/src/musicscanner.cpp b/src/musicscanner.cpp index 4e8b5ced8..2fa64f5d6 100644 --- a/src/musicscanner.cpp +++ b/src/musicscanner.cpp @@ -160,7 +160,14 @@ MusicScanner::readFile( const QFileInfo& fi ) if( m_scanned % 100 == 0 ) qDebug() << "SCAN" << m_scanned << fi.absoluteFilePath(); - TagLib::FileRef f( fi.absoluteFilePath().toUtf8().constData() ); + #ifdef COMPLEX_TAGLIB_FILENAME + const wchar_t *encodedName = reinterpret_cast< const wchar_t *>(fi.absoluteFilePath().utf16()); + #else + QByteArray fileName = QFile::encodeName( fi.absoluteFilePath() ); + const char *encodedName = fileName.constData(); + #endif + + TagLib::FileRef f( encodedName ); if ( f.isNull() || !f.tag() ) { // qDebug() << "Doesn't seem to be a valid audiofile:" << fi.absoluteFilePath(); diff --git a/src/sip/SipHandler.cpp b/src/sip/SipHandler.cpp index 1d8351e0c..5d7e10cc9 100644 --- a/src/sip/SipHandler.cpp +++ b/src/sip/SipHandler.cpp @@ -15,7 +15,7 @@ SipHandler::SipHandler( QObject* parent ) : QObject( parent ) { m_connected = false; - loadPlugins(); + loadPlugins( findPlugins() ); } @@ -24,29 +24,61 @@ SipHandler::~SipHandler() } -void -SipHandler::loadPlugins() +QStringList +SipHandler::findPlugins() { - QDir pluginsDir( qApp->applicationDirPath() ); + QStringList paths; + QList< QDir > pluginDirs; - #if defined(Q_OS_MAC) - if ( pluginsDir.dirName() == "MacOS" ) + QDir appDir( qApp->applicationDirPath() ); + #ifdef Q_OS_MAC + if ( appDir.dirName() == "MacOS" ) { - pluginsDir.cdUp(); - pluginsDir.cdUp(); - pluginsDir.cdUp(); + // Development convenience-hack + appDir.cdUp(); + appDir.cdUp(); + appDir.cdUp(); } #endif -// pluginsDir.cd( "plugins" ); - foreach ( QString fileName, pluginsDir.entryList( QDir::Files ) ) + QDir libDir( appDir ); + libDir.cdUp(); + libDir.cd( "lib" ); + + QDir lib64Dir( appDir ); + lib64Dir.cdUp(); + lib64Dir.cd( "lib64" ); + + pluginDirs << appDir << libDir << lib64Dir << QDir( qApp->applicationDirPath() ); + foreach ( const QDir& pluginDir, pluginDirs ) + { + qDebug() << "Checking directory for plugins:" << pluginDir; + foreach ( QString fileName, pluginDir.entryList( QDir::Files ) ) + { + if ( fileName.startsWith( "libsip_" ) ) + { + const QString path = pluginDir.absoluteFilePath( fileName ); + if ( !paths.contains( path ) ) + paths << path; + } + } + } + + return paths; +} + + +void +SipHandler::loadPlugins( const QStringList& paths ) +{ + foreach ( QString fileName, paths ) { if ( !QLibrary::isLibrary( fileName ) ) continue; - qDebug() << "Trying to load plugin:" << pluginsDir.absoluteFilePath( fileName ); + qDebug() << "Trying to load plugin:" << fileName; - QPluginLoader loader( pluginsDir.absoluteFilePath( fileName ) ); + QPluginLoader loader( fileName ); QObject* plugin = loader.instance(); if ( plugin ) { diff --git a/src/sip/SipHandler.h b/src/sip/SipHandler.h index 7055cdacd..b10847c44 100644 --- a/src/sip/SipHandler.h +++ b/src/sip/SipHandler.h @@ -35,7 +35,8 @@ private slots: void onError( int code, const QString& msg ); private: - void loadPlugins(); + QStringList findPlugins(); + void loadPlugins( const QStringList& paths ); void loadPlugin( QObject* plugin ); QList< SipPlugin* > m_plugins;