1
0
mirror of https://github.com/tomahawk-player/tomahawk.git synced 2025-07-31 11:20:22 +02:00

Merge remote-tracking branch 'origin' into phonon

This commit is contained in:
Christian Muehlhaeuser
2011-03-14 00:21:17 +01:00
59 changed files with 607 additions and 310 deletions

View File

@@ -44,6 +44,8 @@ macro_log_feature(QJSON_FOUND "QJson" "Qt library that maps JSON data to QVarian
macro_optional_find_package(Taglib 1.6.0) macro_optional_find_package(Taglib 1.6.0)
macro_log_feature(TAGLIB_FOUND "TagLib" "Audio Meta-Data Library" "http://developer.kde.org/~wheeler/taglib.html" TRUE "" "taglib is needed for reading meta data from audio files") macro_log_feature(TAGLIB_FOUND "TagLib" "Audio Meta-Data Library" "http://developer.kde.org/~wheeler/taglib.html" TRUE "" "taglib is needed for reading meta data from audio files")
# we need pthreads too
find_package(Threads)
FIND_PACKAGE( Taglib 1.6.0 REQUIRED ) FIND_PACKAGE( Taglib 1.6.0 REQUIRED )
include( CheckTagLibFileName ) include( CheckTagLibFileName )
@@ -64,6 +66,10 @@ IF( ENABLE_JREEN AND NOT LIBJREEN_FOUND )
MESSAGE(STATUS "Internal libjreen: ${LIBJREEN_INCLUDE_DIR}, ${LIBJREEN_LIBRARY}") MESSAGE(STATUS "Internal libjreen: ${LIBJREEN_INCLUDE_DIR}, ${LIBJREEN_LIBRARY}")
ENDIF( ENABLE_JREEN AND NOT LIBJREEN_FOUND ) ENDIF( ENABLE_JREEN AND NOT LIBJREEN_FOUND )
IF( WIN32 )
find_library(QTSPARKLE_LIBRARIES qtsparkle)
ENDIF( WIN32 )
macro_log_feature(JREEN_FOUND "Jreen" "Qt XMPP library" "http://gitorious.org/jreen" FALSE "" "Jreen is needed for the alternative/new Jabber SIP plugin. Built automatically inside Tomahawk, if not installed systemwide and ENABLE_JREEN is true") macro_log_feature(JREEN_FOUND "Jreen" "Qt XMPP library" "http://gitorious.org/jreen" FALSE "" "Jreen is needed for the alternative/new Jabber SIP plugin. Built automatically inside Tomahawk, if not installed systemwide and ENABLE_JREEN is true")
macro_optional_find_package(Gloox 1.0) macro_optional_find_package(Gloox 1.0)
@@ -79,6 +85,11 @@ MESSAGE("add checks for libmad, libvorbis and libflac. Make sure they are instal
MESSAGE("") MESSAGE("")
MESSAGE("-----------------------------------------------------------------------------") MESSAGE("-----------------------------------------------------------------------------")
IF( NOT APPLE )
# Make linking as strict on linux as it is on osx. Then we don't break linking on mac so often
SET( CMAKE_CXX_FLAGS "${CMAKE_CXX_FLAGS} -Wl,--no-undefined" )
ENDIF( NOT APPLE )
ADD_SUBDIRECTORY( thirdparty ) ADD_SUBDIRECTORY( thirdparty )
ADD_SUBDIRECTORY( src/libtomahawk ) ADD_SUBDIRECTORY( src/libtomahawk )
ADD_SUBDIRECTORY( src ) ADD_SUBDIRECTORY( src )

View File

@@ -4,7 +4,7 @@
# #
# CLUCENE_INCLUDE_DIR = where CLucene/StdHeader.h can be found # CLUCENE_INCLUDE_DIR = where CLucene/StdHeader.h can be found
# CLUCENE_LIBRARY_DIR = where CLucene/clucene-config.h can be found # CLUCENE_LIBRARY_DIR = where CLucene/clucene-config.h can be found
# CLUCENE_LIBRARY = the library to link against CLucene # CLUCENE_LIBRARIES = the libraries to link against CLucene
# CLUCENE_VERSION = The CLucene version string # CLUCENE_VERSION = The CLucene version string
# CLucene_FOUND = set to 1 if clucene is found # CLucene_FOUND = set to 1 if clucene is found
# #
@@ -37,13 +37,25 @@ SET(TRIAL_INCLUDE_PATHS
/sw/include /sw/include
/usr/pkg/include /usr/pkg/include
) )
FIND_LIBRARY_WITH_DEBUG(CLUCENE_LIBRARY FIND_LIBRARY_WITH_DEBUG(CLUCENE_CORE_LIBRARY
WIN32_DEBUG_POSTFIX d WIN32_DEBUG_POSTFIX d
NAMES clucene clucene-core NAMES clucene-core
PATHS ${TRIAL_LIBRARY_PATHS}) PATHS ${TRIAL_LIBRARY_PATHS})
IF (CLUCENE_LIBRARY) IF (CLUCENE_CORE_LIBRARY)
MESSAGE(STATUS "Found CLucene library: ${CLUCENE_LIBRARY}") MESSAGE(STATUS "Found CLucene core library: ${CLUCENE_CORE_LIBRARY}")
ENDIF (CLUCENE_LIBRARY) ENDIF (CLUCENE_CORE_LIBRARY)
FIND_LIBRARY_WITH_DEBUG(CLUCENE_SHARED_LIBRARY
WIN32_DEBUG_POSTFIX d
NAMES clucene-shared
PATHS ${TRIAL_LIBRARY_PATHS})
IF (CLUCENE_SHARED_LIBRARY)
MESSAGE(STATUS "Found CLucene shared library: ${CLUCENE_SHARED_LIBRARY}")
ENDIF (CLUCENE_SHARED_LIBRARY)
IF(CLUCENE_CORE_LIBRARY AND CLUCENE_SHARED_LIBRARY)
SET(CLUCENE_LIBRARIES ${CLUCENE_CORE_LIBRARY} ${CLUCENE_SHARED_LIBRARY})
ENDIF(CLUCENE_CORE_LIBRARY AND CLUCENE_SHARED_LIBRARY)
FIND_PATH(CLUCENE_INCLUDE_DIR FIND_PATH(CLUCENE_INCLUDE_DIR
NAMES CLucene.h NAMES CLucene.h
PATHS ${TRIAL_INCLUDE_PATHS}) PATHS ${TRIAL_INCLUDE_PATHS})
@@ -59,31 +71,28 @@ ENDIF(WIN32)
SET(CLUCENE_GOOD_VERSION TRUE) SET(CLUCENE_GOOD_VERSION TRUE)
FIND_PATH(CLUCENE_LIBRARY_DIR FIND_PATH(CLUCENE_LIBRARY_DIR
NAMES CLucene/clucene-config.h PATHS ${TRIAL_LIBRARY_PATHS} ${TRIAL_INCLUDE_PATHS} NO_DEFAULT_PATH) NAMES CLuceneConfig.cmake/CLuceneConfig.cmake
PATHS ${TRIAL_LIBRARY_PATHS} ${TRIAL_INCLUDE_PATHS} NO_DEFAULT_PATH)
IF (CLUCENE_LIBRARY_DIR) IF (CLUCENE_LIBRARY_DIR)
MESSAGE(STATUS "Found CLucene library dir: ${CLUCENE_LIBRARY_DIR}") MESSAGE(STATUS "Found CLucene library dir: ${CLUCENE_LIBRARY_DIR}")
FILE(READ ${CLUCENE_LIBRARY_DIR}/CLucene/clucene-config.h CLCONTENT) #INCLUDE(${CLUCENE_LIBRARY_DIR}/CLuceneConfig.cmake/CLuceneConfig.cmake)
STRING(REGEX MATCH "_CL_VERSION +\".*\"" CLMATCH ${CLCONTENT}) IF (CLUCENE_VERSION STRLESS "${CLUCENE_MIN_VERSION}")
IF (CLMATCH) MESSAGE(ERROR " CLucene version ${CLUCENE_VERSION} is less than the required minimum ${CLUCENE_MIN_VERSION}")
STRING(REGEX REPLACE "_CL_VERSION +\"(.*)\"" "\\1" CLUCENE_VERSION ${CLMATCH}) SET(CLUCENE_GOOD_VERSION FALSE)
IF (CLUCENE_VERSION STRLESS "${CLUCENE_MIN_VERSION}") ENDIF (CLUCENE_VERSION STRLESS "${CLUCENE_MIN_VERSION}")
MESSAGE(ERROR " CLucene version ${CLUCENE_VERSION} is less than the required minimum ${CLUCENE_MIN_VERSION}") IF (CLUCENE_VERSION STREQUAL "0.9.17")
SET(CLUCENE_GOOD_VERSION FALSE) MESSAGE(ERROR "CLucene version 0.9.17 is not supported.")
ENDIF (CLUCENE_VERSION STRLESS "${CLUCENE_MIN_VERSION}") SET(CLUCENE_GOOD_VERSION FALSE)
IF (CLUCENE_VERSION STREQUAL "0.9.17") ENDIF (CLUCENE_VERSION STREQUAL "0.9.17")
MESSAGE(ERROR "CLucene version 0.9.17 is not supported.")
SET(CLUCENE_GOOD_VERSION FALSE)
ENDIF (CLUCENE_VERSION STREQUAL "0.9.17")
ENDIF (CLMATCH)
ENDIF (CLUCENE_LIBRARY_DIR) ENDIF (CLUCENE_LIBRARY_DIR)
IF(CLUCENE_INCLUDE_DIR AND CLUCENE_LIBRARY AND CLUCENE_LIBRARY_DIR AND CLUCENE_GOOD_VERSION) IF(CLUCENE_INCLUDE_DIR AND CLUCENE_LIBRARIES AND CLUCENE_LIBRARY_DIR AND CLUCENE_GOOD_VERSION)
SET(CLucene_FOUND TRUE) SET(CLucene_FOUND TRUE)
ENDIF(CLUCENE_INCLUDE_DIR AND CLUCENE_LIBRARY AND CLUCENE_LIBRARY_DIR AND CLUCENE_GOOD_VERSION) ENDIF(CLUCENE_INCLUDE_DIR AND CLUCENE_LIBRARIES AND CLUCENE_LIBRARY_DIR AND CLUCENE_GOOD_VERSION)
IF(CLucene_FOUND) IF(CLucene_FOUND)
IF(NOT CLucene_FIND_QUIETLY) IF(NOT CLucene_FIND_QUIETLY)
MESSAGE(STATUS "Found CLucene: ${CLUCENE_LIBRARY} version ${CLUCENE_VERSION}") MESSAGE(STATUS "Found CLucene: ${CLUCENE_LIBRARIES} version ${CLUCENE_VERSION}")
ENDIF(NOT CLucene_FIND_QUIETLY) ENDIF(NOT CLucene_FIND_QUIETLY)
ELSE(CLucene_FOUND) ELSE(CLucene_FOUND)
IF(CLucene_FIND_REQUIRED) IF(CLucene_FIND_REQUIRED)
@@ -94,5 +103,5 @@ ENDIF(CLucene_FOUND)
MARK_AS_ADVANCED( MARK_AS_ADVANCED(
CLUCENE_INCLUDE_DIR CLUCENE_INCLUDE_DIR
CLUCENE_LIBRARY_DIR CLUCENE_LIBRARY_DIR
CLUCENE_LIBRARY CLUCENE_LIBRARIES
) )

3
ChangeLog Normal file
View File

@@ -0,0 +1,3 @@
Version 0.0.1:
Features:
* Knocks your socks off

View File

@@ -47,7 +47,9 @@ CREATEDMG='1'
header deposx header deposx
$ROOT/../admin/mac/deposx.sh $ROOT/../admin/mac/deposx.sh
header "Copying Sparkle pubkey" header "Copying Sparkle pubkey and framework, and qt.conf"
cp $ROOT/../admin/mac/sparkle_pub.pem Contents/Resources cp $ROOT/../admin/mac/sparkle_pub.pem Contents/Resources
cp -R /Library/Frameworks/Sparkle.framework Contents/Frameworks
cp $ROOT/../admin/mac/qt.conf Contents/Resources
header Done! header Done!

View File

@@ -61,7 +61,7 @@ function deposx_change
function deplib_change function deplib_change
{ {
install_name_tool -change /usr/local/Cellar/liblastfm/0.3.1/lib/liblastfm.0.dylib @executable_path/liblastfm.0.dylib $1 install_name_tool -change /usr/local/Cellar/liblastfm/0.3.3/lib/liblastfm.0.dylib @executable_path/liblastfm.0.dylib $1
install_name_tool -change /usr/local/Cellar/qjson/0.7.1/lib/libqjson.0.dylib @executable_path/libqjson.0.dylib $1 install_name_tool -change /usr/local/Cellar/qjson/0.7.1/lib/libqjson.0.dylib @executable_path/libqjson.0.dylib $1
install_name_tool -change /usr/local/lib/libechonest.1.1.dylib @executable_path/libechonest.1.1.dylib $1 install_name_tool -change /usr/local/lib/libechonest.1.1.dylib @executable_path/libechonest.1.1.dylib $1
install_name_tool -change /usr/local/lib/libclucene-core.0.9.23.dylib @executable_path/libclucene-core.0.9.23.dylib $1 install_name_tool -change /usr/local/lib/libclucene-core.0.9.23.dylib @executable_path/libclucene-core.0.9.23.dylib $1
@@ -100,7 +100,7 @@ do
done done
import_lib /usr/local/Cellar/qjson/0.7.1/lib/libqjson.0.dylib import_lib /usr/local/Cellar/qjson/0.7.1/lib/libqjson.0.dylib
import_lib /usr/local/Cellar/liblastfm/0.3.1/lib/liblastfm.0.dylib import_lib /usr/local/Cellar/liblastfm/0.3.3/lib/liblastfm.0.dylib
import_lib /usr/local/Cellar/gloox/1.0/lib/libgloox.8.dylib import_lib /usr/local/Cellar/gloox/1.0/lib/libgloox.8.dylib
import_lib /usr/local/Cellar/taglib/1.6.3/lib/libtag.1.dylib import_lib /usr/local/Cellar/taglib/1.6.3/lib/libtag.1.dylib
import_lib /usr/local/Cellar/libogg/1.2.0/lib/libogg.0.dylib import_lib /usr/local/Cellar/libogg/1.2.0/lib/libogg.0.dylib

2
admin/mac/qt.conf Normal file
View File

@@ -0,0 +1,2 @@
[Paths]
Plugins = PlugIns

14
admin/mac/sign_bundle.rb Executable file
View File

@@ -0,0 +1,14 @@
#!/usr/bin/ruby
if ARGV.length < 2
puts "Usage: ruby sign_update.rb version private_key_file"
puts "\nCall this from the build directory."
puts "If you don't have the tomahawk private key and you think you should, ask leo :)"
exit
end
tarball = "tomahawk#{ARGV[0]}.tar.bz2"
puts "Zipping: #{tarball}..."
`tar jcvf "#{tarball}" tomahawk.app`
puts "Signing..."
puts `openssl dgst -sha1 -binary < "#{tarball}" | openssl dgst -dss1 -sign "#{ARGV[1]}" | openssl enc -base64`

17
admin/mac/sparkle-beta.rss Executable file
View File

@@ -0,0 +1,17 @@
<?xml version="1.0" encoding="utf-8"?>
<rss version="2.0" xmlns:sparkle="http://www.andymatuschak.org/xml-namespaces/sparkle" xmlns:dc="http://purl.org/dc/elements/1.1/">
<channel>
<title>Tomahawk Player Changelog</title>
<link>http://download.tomahawk-player.org/sparkle</link>
<description>Most recent changes with links to updates.</description>
<language>en</language>
<item>
<title>Version 0.0.1 (Tomahawk Player - It Lives!)</title>
<sparkle:releaseNotesLink>
https://github.com/tomahawk-player/tomahawk/raw/master/ChangeLog
</sparkle:releaseNotesLink>
<pubDate>Fri, 04 Mar 2011 16:05:15 -0500</pubDate>
<enclosure url="http://download.tomahawk-player.org/sparkle-debug/updates/tomahawk0.0.1.tar.bz2" sparkle:version="0.0.1" length="10627176" type="application/octet-stream" sparkle:dsaSignature="MC0CFAyYNZq58X7hPC7Qn+DtotVgym7pAhUA5hkLGllYxjOwwCf7i2LxUsvGyps=" />
</item>
</channel>
</rss>

View File

@@ -8,7 +8,7 @@
<item> <item>
<title>Version 0.0.1 (Tomahawk Player - It Lives!)</title> <title>Version 0.0.1 (Tomahawk Player - It Lives!)</title>
<sparkle:releaseNotesLink> <sparkle:releaseNotesLink>
<!-- http://you.com/app/2.0.html --> https://github.com/tomahawk-player/tomahawk/raw/master/ChangeLog
</sparkle:releaseNotesLink> </sparkle:releaseNotesLink>
<pubDate>Fri, 04 Mar 2011 16:05:15 -0500</pubDate> <pubDate>Fri, 04 Mar 2011 16:05:15 -0500</pubDate>
<enclosure url="http://download.tomahawk-player.org/sparkle/updates/tomahawk0.1.tar.bz2" sparkle:version="0.0.1" length="10627176" type="application/octet-stream" sparkle:dsaSignature="MC0CFAyYNZq58X7hPC7Qn+DtotVgym7pAhUA5hkLGllYxjOwwCf7i2LxUsvGyps=" /> <enclosure url="http://download.tomahawk-player.org/sparkle/updates/tomahawk0.1.tar.bz2" sparkle:version="0.0.1" length="10627176" type="application/octet-stream" sparkle:dsaSignature="MC0CFAyYNZq58X7hPC7Qn+DtotVgym7pAhUA5hkLGllYxjOwwCf7i2LxUsvGyps=" />

View File

@@ -0,0 +1,17 @@
<?xml version="1.0" encoding="utf-8"?>
<rss version="2.0" xmlns:sparkle="http://www.andymatuschak.org/xml-namespaces/sparkle" xmlns:dc="http://purl.org/dc/elements/1.1/">
<channel>
<title>Tomahawk Player</title>
<link>http://www.gettomahawk.com</link>
<description>Tomahawk Player</description>
<language>en</language>
<item>
<title>Version 0.0.1 (Tomahawk Player - It Lives!)</title>
<sparkle:releaseNotesLink>
https://github.com/tomahawk-player/tomahawk/blob/master/ChangeLog
</sparkle:releaseNotesLink>
<pubDate>Fri, 04 Mar 2011 16:05:15 -0500</pubDate>
<enclosure url="http://download.tomahawk-player.org/sparklewin/updates/tomahawk0.0.1.exe" sparkle:version="0.0.1" />
</item>
</channel>
</rss>

17
admin/win/sparklewin.rss Normal file
View File

@@ -0,0 +1,17 @@
<?xml version="1.0" encoding="utf-8"?>
<rss version="2.0" xmlns:sparkle="http://www.andymatuschak.org/xml-namespaces/sparkle" xmlns:dc="http://purl.org/dc/elements/1.1/">
<channel>
<title>Tomahawk Player</title>
<link>http://www.gettomahawk.com</link>
<description>Tomahawk Player</description>
<language>en</language>
<item>
<title>Version 0.0.1 (Tomahawk Player - It Lives!)</title>
<sparkle:releaseNotesLink>
https://github.com/tomahawk-player/tomahawk/blob/master/ChangeLog
</sparkle:releaseNotesLink>
<pubDate>Fri, 04 Mar 2011 16:05:15 -0500</pubDate>
<enclosure url="http://download.tomahawk-player.org/sparklewin/updates/tomahawk0.0.1.exe" sparkle:version="0.0.1" />
</item>
</channel>
</rss>

View File

@@ -44,7 +44,7 @@
</head> </head>
<body> <body>
<a href="http://www.playdar.org/" title="Tomahawk - Powered by Playdar" id="head"> <a href="http://www.playdar.org/" title="Tomahawk - Powered by Playdar" id="head">
<img alt="Tomahawk - Powered by Playdar" src="/staticdata/tomahawk_auth_logo.png" width="233" height="68"/> <img alt="Tomahawk - Powered by Playdar" src="/staticdata/tomahawk_auth_logo.png" width="196" height="45"/>
</a> </a>
<div id="content"> <div id="content">

View File

@@ -32,8 +32,8 @@
</style> </style>
</head> </head>
<body> <body>
<a href="http://www.playdar.org/" title="Tomahawk - Powered by Playdar" id="head"> <a href="http://www.gettomahawk.com/" title="Tomahawk - Powered by Playdar" id="head">
<img alt="Tomahawk - Powered by Playdar" src="/static/playdar_auth_logo.gif" width="233" height="68"/> <img alt="Tomahawk - Powered by Playdar" src="/staticdata/tomahawk_auth_logo.png" width="196" height="45"/>
</a> </a>
<div id="content"> <div id="content">

View File

@@ -30,4 +30,18 @@ if (APPLE)
elseif (DARWIN_VERSION GREATER 8) elseif (DARWIN_VERSION GREATER 8)
SET(LEOPARD 1) SET(LEOPARD 1)
endif (DARWIN_VERSION GREATER 9) endif (DARWIN_VERSION GREATER 9)
# Use two different sparkle update tracks for debug and release
# We have to change the URL in the Info.plist file :-/
IF( NOT CMAKE_BUILD_TYPE STREQUAL "Release" )
FILE(READ ${CMAKE_SOURCE_DIR}/admin/mac/Info.plist plist)
STRING( REPLACE "http://download.tomahawk-player.org/sparkle" # match this
"http://download.tomahawk-player.org/sparkle-debug" #replace with debug url
edited_plist # save in this variable
"${plist}" # from the contents of this var
)
FILE( WRITE ${CMAKE_BINARY_DIR}/Info.plist "${edited_plist}" )
ELSE() # Just copy the release one
FILE( COPY ${CMAKE_SOURCE_DIR}/admin/mac/Info.plist DESTINATION ${CMAKE_BINARY_DIR} )
ENDIF()
endif (APPLE) endif (APPLE)

View File

@@ -18,6 +18,10 @@ SET( CMAKE_RUNTIME_OUTPUT_DIRECTORY "${CMAKE_BINARY_DIR}" )
SET( CMAKE_LIBRARY_OUTPUT_DIRECTORY "${CMAKE_BINARY_DIR}" ) SET( CMAKE_LIBRARY_OUTPUT_DIRECTORY "${CMAKE_BINARY_DIR}" )
SET( CMAKE_ARCHIVE_OUTPUT_DIRECTORY "${CMAKE_BINARY_DIR}" ) SET( CMAKE_ARCHIVE_OUTPUT_DIRECTORY "${CMAKE_BINARY_DIR}" )
SET( TOMAHAWK_INC_DIR "${CMAKE_SOURCE_DIR}/include/" ) SET( TOMAHAWK_INC_DIR "${CMAKE_SOURCE_DIR}/include/" )
IF( NOT CMAKE_BUILD_TYPE STREQUAL "Release" )
MESSAGE( "Building in debug mode, enabling all debug updates" )
SET( DEBUG_BUILD ON )
ENDIF()
# build plugins # build plugins
# use glob, but hardcoded list for now: # use glob, but hardcoded list for now:
@@ -152,7 +156,7 @@ IF( APPLE )
SET( tomahawkSources ${tomahawkSources} mac/tomahawkapp_mac.mm mac/macshortcuthandler.cpp ) SET( tomahawkSources ${tomahawkSources} mac/tomahawkapp_mac.mm mac/macshortcuthandler.cpp )
IF(HAVE_SPARKLE) IF(HAVE_SPARKLE)
SET( tomahawkHeaders ${tomahawkHeaders} ${SPARKLE}/Headers ) SET( tomahawkHeaders ${tomahawkHeaders} ${SPARKLE}/Headers )
ENDIF(HAVE_SPARKLE) ENDIF(HAVE_SPARKLE)
ENDIF( APPLE ) ENDIF( APPLE )
@@ -184,7 +188,7 @@ IF( UNIX AND NOT APPLE )
ENDIF( UNIX AND NOT APPLE ) ENDIF( UNIX AND NOT APPLE )
IF( APPLE ) IF( APPLE )
ADD_EXECUTABLE( tomahawk MACOSX_BUNDLE ${final_src} ) ADD_EXECUTABLE( tomahawk MACOSX_BUNDLE ${final_src} )
SET_TARGET_PROPERTIES(tomahawk PROPERTIES MACOSX_BUNDLE_INFO_PLIST "../admin/mac/Info.plist" SET_TARGET_PROPERTIES(tomahawk PROPERTIES MACOSX_BUNDLE_INFO_PLIST "${CMAKE_BINARY_DIR}/Info.plist"
) )
ENDIF( APPLE ) ENDIF( APPLE )
IF( WIN32 ) IF( WIN32 )
@@ -204,15 +208,16 @@ ENDIF(GLOOX_FOUND)
TARGET_LINK_LIBRARIES( tomahawk TARGET_LINK_LIBRARIES( tomahawk
${LINK_LIBRARIES} ${LINK_LIBRARIES}
${TOMAHAWK_LIBRARIES} ${TOMAHAWK_LIBRARIES}
${OS_SPECIFIC_LINK_LIBRARIES}
${QT_LIBRARIES} ${QT_LIBRARIES}
${MAC_EXTRA_LIBS} ${MAC_EXTRA_LIBS}
${OS_SPECIFIC_LINK_LIBRARIES}
${LIBECHONEST_LIBRARY} ${LIBECHONEST_LIBRARY}
${QXTWEB_LIBRARIES} ${QXTWEB_LIBRARIES}
${QTWEETLIB_LIBRARIES} ${QTWEETLIB_LIBRARIES}
${QJSON_LIBRARIES} ${QJSON_LIBRARIES}
${TAGLIB_LIBRARIES} ${TAGLIB_LIBRARIES}
${QTWEETLIB_LIBRARIES} ${QTWEETLIB_LIBRARIES}
${CLUCENE_LIBRARIES}
) )
@@ -220,7 +225,7 @@ IF( APPLE )
IF(HAVE_SPARKLE) IF(HAVE_SPARKLE)
MESSAGE("Sparkle Found, installing framekwork in bundle") MESSAGE("Sparkle Found, installing framekwork in bundle")
INSTALL(DIRECTORY "${SPARKLE}/Versions/Current/Resources" DESTINATION "${CMAKE_BINARY_DIR}/tomahawk.app/Contents/Frameworks/Sparkle.framework") INSTALL(DIRECTORY "${SPARKLE}/Versions/Current/Resources" DESTINATION "${CMAKE_BINARY_DIR}/tomahawk.app/Contents/Frameworks/Sparkle.framework")
INSTALL(FILES "${CMAKE_SOURCE_DIR}/admin/mac/sparkle_pub.pem" DESTINATION "${CMAKE_BINARY_DIR}/tomahawk.app/Contents/Resources")
ENDIF(HAVE_SPARKLE) ENDIF(HAVE_SPARKLE)
ENDIF( APPLE ) ENDIF( APPLE )

View File

@@ -12,6 +12,8 @@ SET( QXTWEB_LIBRARIES ${CMAKE_BINARY_DIR}/thirdparty/qxt/qxtweb-standalone/libq
SET( OS_SPECIFIC_LINK_LIBRARIES SET( OS_SPECIFIC_LINK_LIBRARIES
${OS_SPECIFIC_LINK_LIBRARIES} ${OS_SPECIFIC_LINK_LIBRARIES}
${QTSPARKLE_LIBRARIES}
# third party shipped with tomahawk # third party shipped with tomahawk
# system libs # system libs

View File

@@ -6,6 +6,7 @@
#cmakedefine APPLICATION_NAME "${APPLICATION_NAME}" #cmakedefine APPLICATION_NAME "${APPLICATION_NAME}"
#cmakedefine VERSION "${VERSION}" #cmakedefine VERSION "${VERSION}"
#cmakedefine DEBUG_BUILD
#define CMAKE_INSTALL_PREFIX "${CMAKE_INSTALL_PREFIX}" #define CMAKE_INSTALL_PREFIX "${CMAKE_INSTALL_PREFIX}"

View File

@@ -371,10 +371,11 @@ target_link_libraries( tomahawklib
# External deps # External deps
${TAGLIB_LIBRARIES} ${TAGLIB_LIBRARIES}
${QJSON_LIBRARIES} ${QJSON_LIBRARIES}
${CLUCENE_LIBRARY} ${CLUCENE_LIBRARIES}
${LIBECHONEST_LIBRARY} ${LIBECHONEST_LIBRARY}
${QT_LIBRARIES} ${QT_LIBRARIES}
${OS_SPECIFIC_LINK_LIBRARIES} ${OS_SPECIFIC_LINK_LIBRARIES}
${CMAKE_THREAD_LIBS_INIT}
) )
install( TARGETS tomahawklib DESTINATION lib ) install( TARGETS tomahawklib DESTINATION lib )

View File

@@ -40,12 +40,12 @@ Album::Album( unsigned int id, const QString& name, const Tomahawk::artist_ptr&
void void
Album::onTracksAdded( const QList<Tomahawk::query_ptr>& tracks, const Tomahawk::collection_ptr& collection ) Album::onTracksAdded( const QList<Tomahawk::query_ptr>& tracks )
{ {
qDebug() << Q_FUNC_INFO; qDebug() << Q_FUNC_INFO;
m_queries << tracks; m_queries << tracks;
emit tracksAdded( tracks, collection ); emit tracksAdded( tracks );
} }
@@ -75,8 +75,8 @@ Album::tracks()
cmd->setAlbum( this ); cmd->setAlbum( this );
cmd->setSortOrder( DatabaseCommand_AllTracks::AlbumPosition ); cmd->setSortOrder( DatabaseCommand_AllTracks::AlbumPosition );
connect( cmd, SIGNAL( tracks( QList<Tomahawk::query_ptr>, Tomahawk::collection_ptr ) ), connect( cmd, SIGNAL( tracks( QList<Tomahawk::query_ptr> ) ),
SLOT( onTracksAdded( QList<Tomahawk::query_ptr>, Tomahawk::collection_ptr ) ) ); SLOT( onTracksAdded( QList<Tomahawk::query_ptr> ) ) );
Database::instance()->enqueue( QSharedPointer<DatabaseCommand>( cmd ) ); Database::instance()->enqueue( QSharedPointer<DatabaseCommand>( cmd ) );
} }

View File

@@ -47,12 +47,12 @@ signals:
void repeatModeChanged( PlaylistInterface::RepeatMode mode ); void repeatModeChanged( PlaylistInterface::RepeatMode mode );
void shuffleModeChanged( bool enabled ); void shuffleModeChanged( bool enabled );
void tracksAdded( const QList<Tomahawk::query_ptr>& tracks, const Tomahawk::collection_ptr& ); void tracksAdded( const QList<Tomahawk::query_ptr>& tracks );
void trackCountChanged( unsigned int tracks ); void trackCountChanged( unsigned int tracks );
void sourceTrackCountChanged( unsigned int tracks ); void sourceTrackCountChanged( unsigned int tracks );
private slots: private slots:
void onTracksAdded( const QList<Tomahawk::query_ptr>& tracks, const Tomahawk::collection_ptr& collection ); void onTracksAdded( const QList<Tomahawk::query_ptr>& tracks );
private: private:
unsigned int m_id; unsigned int m_id;

View File

@@ -44,16 +44,17 @@ Artist::Artist( unsigned int id, const QString& name, const Tomahawk::collection
Tomahawk::collection_ptr Tomahawk::collection_ptr
Artist::collection() const Artist::collection() const
{ {
return m_collection; return m_collection;
} }
void void
Artist::onTracksAdded( const QList<Tomahawk::query_ptr>& tracks, const Tomahawk::collection_ptr& collection ) Artist::onTracksAdded( const QList<Tomahawk::query_ptr>& tracks )
{ {
qDebug() << Q_FUNC_INFO; qDebug() << Q_FUNC_INFO;
m_queries << tracks; m_queries << tracks;
emit tracksAdded( tracks, collection ); emit tracksAdded( tracks );
} }
@@ -83,8 +84,8 @@ Artist::tracks()
cmd->setArtist( this ); cmd->setArtist( this );
cmd->setSortOrder( DatabaseCommand_AllTracks::Album ); cmd->setSortOrder( DatabaseCommand_AllTracks::Album );
connect( cmd, SIGNAL( tracks( QList<Tomahawk::query_ptr>, Tomahawk::collection_ptr ) ), connect( cmd, SIGNAL( tracks( QList<Tomahawk::query_ptr> ) ),
SLOT( onTracksAdded( QList<Tomahawk::query_ptr>, Tomahawk::collection_ptr ) ) ); SLOT( onTracksAdded( QList<Tomahawk::query_ptr> ) ) );
Database::instance()->enqueue( QSharedPointer<DatabaseCommand>( cmd ) ); Database::instance()->enqueue( QSharedPointer<DatabaseCommand>( cmd ) );
} }

View File

@@ -23,11 +23,11 @@ public:
Artist(); Artist();
virtual ~Artist(); virtual ~Artist();
unsigned int id() const { return m_id; } unsigned int id() const { return m_id; }
QString name() const { return m_name; } QString name() const { return m_name; }
Tomahawk::collection_ptr collection() const; Tomahawk::collection_ptr collection() const;
virtual QList<Tomahawk::query_ptr> tracks(); virtual QList<Tomahawk::query_ptr> tracks();
@@ -48,12 +48,12 @@ signals:
void repeatModeChanged( PlaylistInterface::RepeatMode mode ); void repeatModeChanged( PlaylistInterface::RepeatMode mode );
void shuffleModeChanged( bool enabled ); void shuffleModeChanged( bool enabled );
void tracksAdded( const QList<Tomahawk::query_ptr>& tracks, const Tomahawk::collection_ptr& ); void tracksAdded( const QList<Tomahawk::query_ptr>& tracks );
void trackCountChanged( unsigned int tracks ); void trackCountChanged( unsigned int tracks );
void sourceTrackCountChanged( unsigned int tracks ); void sourceTrackCountChanged( unsigned int tracks );
private slots: private slots:
void onTracksAdded( const QList<Tomahawk::query_ptr>& tracks, const Tomahawk::collection_ptr& collection ); void onTracksAdded( const QList<Tomahawk::query_ptr>& tracks );
private: private:
unsigned int m_id; unsigned int m_id;

View File

@@ -13,9 +13,10 @@ Collection::Collection( const source_ptr& source, const QString& name, QObject*
: QObject( parent ) : QObject( parent )
, m_name( name ) , m_name( name )
, m_lastmodified( 0 ) , m_lastmodified( 0 )
, m_isLoaded( false )
, m_source( source ) , m_source( source )
{ {
// qDebug() << Q_FUNC_INFO; qDebug() << Q_FUNC_INFO << name << source->friendlyName();
} }
@@ -127,7 +128,7 @@ Collection::dynamicPlaylist( const QString& guid )
if( pp->guid() == guid ) if( pp->guid() == guid )
return pp; return pp;
} }
return dynplaylist_ptr(); return dynplaylist_ptr();
} }
@@ -146,26 +147,27 @@ void
Collection::setDynamicPlaylists( const QList< Tomahawk::dynplaylist_ptr >& plists ) Collection::setDynamicPlaylists( const QList< Tomahawk::dynplaylist_ptr >& plists )
{ {
qDebug() << Q_FUNC_INFO << plists.count(); qDebug() << Q_FUNC_INFO << plists.count();
m_dynplaylists.append( plists ); m_dynplaylists.append( plists );
emit dynamicPlaylistsAdded( plists ); emit dynamicPlaylistsAdded( plists );
} }
void void
Collection::setTracks( const QList<Tomahawk::query_ptr>& tracks, const Tomahawk::collection_ptr& collection ) Collection::setTracks( const QList<Tomahawk::query_ptr>& tracks )
{ {
qDebug() << Q_FUNC_INFO << tracks.count() << collection->name(); qDebug() << Q_FUNC_INFO << tracks.count() << name();
m_isLoaded = true;
m_tracks << tracks; m_tracks << tracks;
emit tracksAdded( tracks, collection ); emit tracksAdded( tracks );
} }
void void
Collection::delTracks( const QStringList& files, const Tomahawk::collection_ptr& collection ) Collection::delTracks( const QStringList& files )
{ {
qDebug() << Q_FUNC_INFO << files.count() << collection->name(); qDebug() << Q_FUNC_INFO << files.count() << name();
QList<Tomahawk::query_ptr> tracks; QList<Tomahawk::query_ptr> tracks;
@@ -188,5 +190,5 @@ Collection::delTracks( const QStringList& files, const Tomahawk::collection_ptr&
i++; i++;
} }
emit tracksRemoved( tracks, collection ); emit tracksRemoved( tracks );
} }

View File

@@ -33,6 +33,7 @@ public:
Collection( const source_ptr& source, const QString& name, QObject* parent = 0 ); Collection( const source_ptr& source, const QString& name, QObject* parent = 0 );
virtual ~Collection(); virtual ~Collection();
virtual bool isLoaded() const { return m_isLoaded; }
virtual QString name() const; virtual QString name() const;
virtual void loadPlaylists() { qDebug() << Q_FUNC_INFO; } virtual void loadPlaylists() { qDebug() << Q_FUNC_INFO; }
@@ -41,13 +42,13 @@ public:
virtual Tomahawk::playlist_ptr playlist( const QString& guid ); virtual Tomahawk::playlist_ptr playlist( const QString& guid );
virtual Tomahawk::dynplaylist_ptr dynamicPlaylist( const QString& guid ); virtual Tomahawk::dynplaylist_ptr dynamicPlaylist( const QString& guid );
virtual void addPlaylist( const Tomahawk::playlist_ptr& p ); virtual void addPlaylist( const Tomahawk::playlist_ptr& p );
virtual void deletePlaylist( const Tomahawk::playlist_ptr& p ); virtual void deletePlaylist( const Tomahawk::playlist_ptr& p );
virtual void addDynamicPlaylist( const Tomahawk::dynplaylist_ptr& p ); virtual void addDynamicPlaylist( const Tomahawk::dynplaylist_ptr& p );
virtual void deleteDynamicPlaylist( const Tomahawk::dynplaylist_ptr& p ); virtual void deleteDynamicPlaylist( const Tomahawk::dynplaylist_ptr& p );
virtual QList< Tomahawk::playlist_ptr > playlists() { return m_playlists; } virtual QList< Tomahawk::playlist_ptr > playlists() { return m_playlists; }
virtual QList< Tomahawk::dynplaylist_ptr > dynamicPlaylists() { return m_dynplaylists; } virtual QList< Tomahawk::dynplaylist_ptr > dynamicPlaylists() { return m_dynplaylists; }
virtual QList< Tomahawk::query_ptr > tracks() { return m_tracks; } virtual QList< Tomahawk::query_ptr > tracks() { return m_tracks; }
@@ -56,13 +57,12 @@ public:
unsigned int lastmodified() const { return m_lastmodified; } unsigned int lastmodified() const { return m_lastmodified; }
signals: signals:
void tracksAdded( const QList<Tomahawk::query_ptr>& tracks, const Tomahawk::collection_ptr& ); void tracksAdded( const QList<Tomahawk::query_ptr>& tracks );
void tracksRemoved( const QList<Tomahawk::query_ptr>& tracks, const Tomahawk::collection_ptr& ); void tracksRemoved( const QList<Tomahawk::query_ptr>& tracks );
void tracksFinished( const Tomahawk::collection_ptr& );
void playlistsAdded( const QList<Tomahawk::playlist_ptr>& ); void playlistsAdded( const QList<Tomahawk::playlist_ptr>& );
void playlistsDeleted( const QList<Tomahawk::playlist_ptr>& ); void playlistsDeleted( const QList<Tomahawk::playlist_ptr>& );
void dynamicPlaylistsAdded( const QList<Tomahawk::dynplaylist_ptr>& ); void dynamicPlaylistsAdded( const QList<Tomahawk::dynplaylist_ptr>& );
void dynamicPlaylistsDeleted( const QList<Tomahawk::dynplaylist_ptr>& ); void dynamicPlaylistsDeleted( const QList<Tomahawk::dynplaylist_ptr>& );
@@ -72,15 +72,17 @@ public slots:
void setPlaylists( const QList<Tomahawk::playlist_ptr>& plists ); void setPlaylists( const QList<Tomahawk::playlist_ptr>& plists );
void setDynamicPlaylists( const QList< Tomahawk::dynplaylist_ptr >& dynplists ); void setDynamicPlaylists( const QList< Tomahawk::dynplaylist_ptr >& dynplists );
void setTracks( const QList<Tomahawk::query_ptr>& tracks, const Tomahawk::collection_ptr& collection ); void setTracks( const QList<Tomahawk::query_ptr>& tracks );
void delTracks( const QStringList& files, const Tomahawk::collection_ptr& collection ); void delTracks( const QStringList& files );
protected: protected:
QString m_name; QString m_name;
unsigned int m_lastmodified; // unix time of last change to collection unsigned int m_lastmodified; // unix time of last change to collection
private: private:
bool m_isLoaded;
source_ptr m_source; source_ptr m_source;
QList< Tomahawk::query_ptr > m_tracks; QList< Tomahawk::query_ptr > m_tracks;
QList< Tomahawk::playlist_ptr > m_playlists; QList< Tomahawk::playlist_ptr > m_playlists;

View File

@@ -51,8 +51,8 @@ DatabaseCollection::loadTracks()
m_loadedTracks = true; m_loadedTracks = true;
DatabaseCommand_AllTracks* cmd = new DatabaseCommand_AllTracks( source()->collection() ); DatabaseCommand_AllTracks* cmd = new DatabaseCommand_AllTracks( source()->collection() );
connect( cmd, SIGNAL( tracks( QList<Tomahawk::query_ptr>, Tomahawk::collection_ptr ) ), connect( cmd, SIGNAL( tracks( QList<Tomahawk::query_ptr> ) ),
SLOT( setTracks( QList<Tomahawk::query_ptr>, Tomahawk::collection_ptr ) ) ); SLOT( setTracks( QList<Tomahawk::query_ptr> ) ) );
Database::instance()->enqueue( QSharedPointer<DatabaseCommand>( cmd ) ); Database::instance()->enqueue( QSharedPointer<DatabaseCommand>( cmd ) );
} }
@@ -73,7 +73,7 @@ DatabaseCollection::removeTracks( const QDir& dir )
{ {
qDebug() << Q_FUNC_INFO << dir; qDebug() << Q_FUNC_INFO << dir;
DatabaseCommand_DeleteFiles* cmd = new DatabaseCommand_DeleteFiles( dir, source() ); DatabaseCommand_DeleteFiles* cmd = new DatabaseCommand_DeleteFiles( dir, source() );
Database::instance()->enqueue( QSharedPointer<DatabaseCommand>( cmd ) ); Database::instance()->enqueue( QSharedPointer<DatabaseCommand>( cmd ) );
} }

View File

@@ -31,7 +31,7 @@ public:
public slots: public slots:
virtual void addTracks( const QList<QVariant>& newitems ); virtual void addTracks( const QList<QVariant>& newitems );
virtual void removeTracks( const QDir& dir ); virtual void removeTracks( const QDir& dir );
private slots: private slots:
void dynamicPlaylistCreated( const Tomahawk::source_ptr& source, const QVariantList& data ); void dynamicPlaylistCreated( const Tomahawk::source_ptr& source, const QVariantList& data );

View File

@@ -60,6 +60,7 @@ DatabaseCommand_AllTracks::exec( DatabaseImpl* dbi )
while( query.next() ) while( query.next() )
{ {
Tomahawk::result_ptr result = Tomahawk::result_ptr( new Tomahawk::Result() ); Tomahawk::result_ptr result = Tomahawk::result_ptr( new Tomahawk::Result() );
QVariantMap attr; QVariantMap attr;
TomahawkSqlQuery attrQuery = dbi->newquery(); TomahawkSqlQuery attrQuery = dbi->newquery();
@@ -89,7 +90,7 @@ DatabaseCommand_AllTracks::exec( DatabaseImpl* dbi )
result->setAlbumPos( query.value( 11 ).toUInt() ); result->setAlbumPos( query.value( 11 ).toUInt() );
result->setScore( 1.0 ); result->setScore( 1.0 );
result->setCollection( m_collection ); result->setCollection( m_collection );
attrQuery.prepare( "SELECT k, v FROM track_attributes WHERE id = ?" ); attrQuery.prepare( "SELECT k, v FROM track_attributes WHERE id = ?" );
attrQuery.bindValue( 0, result->dbid() ); attrQuery.bindValue( 0, result->dbid() );
attrQuery.exec(); attrQuery.exec();
@@ -105,16 +106,10 @@ DatabaseCommand_AllTracks::exec( DatabaseImpl* dbi )
qry->addResults( results ); qry->addResults( results );
ql << qry; ql << qry;
if ( ++i % 5000 == 0 )
{
emit tracks( ql, m_collection );
ql.clear();
}
} }
qDebug() << Q_FUNC_INFO << ql.length(); qDebug() << Q_FUNC_INFO << ql.length();
emit tracks( ql, m_collection ); emit tracks( ql );
emit done( m_collection ); emit done( m_collection );
} }

View File

@@ -45,7 +45,7 @@ public:
void setSortDescending( bool descending ) { m_sortDescending = descending; } void setSortDescending( bool descending ) { m_sortDescending = descending; }
signals: signals:
void tracks( const QList<Tomahawk::query_ptr>&, const Tomahawk::collection_ptr& ); void tracks( const QList<Tomahawk::query_ptr>& );
void done( const Tomahawk::collection_ptr& ); void done( const Tomahawk::collection_ptr& );
private: private:

View File

@@ -29,6 +29,8 @@ DatabaseCommand_RenamePlaylist::exec( DatabaseImpl* lib )
cre.bindValue( ":id", m_playlistguid ); cre.bindValue( ":id", m_playlistguid );
cre.bindValue( ":title", m_playlistTitle ); cre.bindValue( ":title", m_playlistTitle );
qDebug() << Q_FUNC_INFO << m_playlistTitle << m_playlistguid;
cre.exec(); cre.exec();
} }
@@ -46,6 +48,7 @@ DatabaseCommand_RenamePlaylist::postCommitHook()
playlist_ptr playlist = source()->collection()->playlist( m_playlistguid ); playlist_ptr playlist = source()->collection()->playlist( m_playlistguid );
Q_ASSERT( !playlist.isNull() ); Q_ASSERT( !playlist.isNull() );
qDebug() << "Renaming old playlist" << playlist->title() << "to" << m_playlistTitle << m_playlistguid;
playlist->setTitle( m_playlistTitle ); playlist->setTitle( m_playlistTitle );
if( source()->isLocal() ) if( source()->isLocal() )

View File

@@ -389,7 +389,7 @@ Playlist::setNewRevision( const QString& rev,
source_ptr source_ptr
Playlist::author() Playlist::author() const
{ {
return m_source; return m_source;
} }

View File

@@ -33,10 +33,10 @@ Q_PROPERTY( QVariant query READ queryVariant WRITE setQueryVariant )
public: public:
PlaylistEntry(); PlaylistEntry();
virtual ~PlaylistEntry(); virtual ~PlaylistEntry();
void setQuery( const Tomahawk::query_ptr& q ); void setQuery( const Tomahawk::query_ptr& q );
const Tomahawk::query_ptr& query() const; const Tomahawk::query_ptr& query() const;
// I wish Qt did this for me once i specified the Q_PROPERTIES: // I wish Qt did this for me once i specified the Q_PROPERTIES:
void setQueryVariant( const QVariant& v ); void setQueryVariant( const QVariant& v );
QVariant queryVariant() const; QVariant queryVariant() const;
@@ -59,7 +59,7 @@ public:
source_ptr lastSource() const; source_ptr lastSource() const;
void setLastSource( source_ptr s ); void setLastSource( source_ptr s );
private: private:
QString m_guid; QString m_guid;
Tomahawk::query_ptr m_query; Tomahawk::query_ptr m_query;
QString m_annotation; QString m_annotation;
@@ -97,7 +97,7 @@ friend class ::DatabaseCommand_CreatePlaylist;
public: public:
~Playlist(); ~Playlist();
static Tomahawk::playlist_ptr load( const QString& guid ); static Tomahawk::playlist_ptr load( const QString& guid );
// one CTOR is private, only called by DatabaseCommand_LoadAllPlaylists // one CTOR is private, only called by DatabaseCommand_LoadAllPlaylists
@@ -113,14 +113,14 @@ public:
virtual void loadRevision( const QString& rev = "" ); virtual void loadRevision( const QString& rev = "" );
source_ptr author(); source_ptr author() const;
const QString& currentrevision() { return m_currentrevision; } QString currentrevision() const { return m_currentrevision; }
const QString& title() { return m_title; } QString title() const { return m_title; }
const QString& info() { return m_info; } QString info() const { return m_info; }
const QString& creator() { return m_creator; } QString creator() const { return m_creator; }
unsigned int lastmodified() { return m_lastmodified; } QString guid() const { return m_guid; }
const QString& guid() { return m_guid; } bool shared() const { return m_shared; }
bool shared() const { return m_shared; } unsigned int lastmodified() const { return m_lastmodified; }
const QList< plentry_ptr >& entries() { return m_entries; } const QList< plentry_ptr >& entries() { return m_entries; }
virtual void addEntry( const Tomahawk::query_ptr& query, const QString& oldrev ); virtual void addEntry( const Tomahawk::query_ptr& query, const QString& oldrev );
@@ -132,7 +132,7 @@ public:
// maybe friend QObjectHelper and make them private? // maybe friend QObjectHelper and make them private?
explicit Playlist( const source_ptr& author ); explicit Playlist( const source_ptr& author );
void setCurrentrevision( const QString& s ) { m_currentrevision = s; } void setCurrentrevision( const QString& s ) { m_currentrevision = s; }
void setTitle( const QString& s ) { m_title = s; } void setTitle( const QString& s ) { m_title = s; emit changed(); }
void setInfo( const QString& s ) { m_info = s; } void setInfo( const QString& s ) { m_info = s; }
void setCreator( const QString& s ) { m_creator = s; } void setCreator( const QString& s ) { m_creator = s; }
void setGuid( const QString& s ) { m_guid = s; } void setGuid( const QString& s ) { m_guid = s; }
@@ -148,12 +148,12 @@ public:
virtual PlaylistInterface::RepeatMode repeatMode() const { return PlaylistInterface::NoRepeat; } virtual PlaylistInterface::RepeatMode repeatMode() const { return PlaylistInterface::NoRepeat; }
virtual bool shuffled() const { return false; } virtual bool shuffled() const { return false; }
virtual void setRepeatMode( PlaylistInterface::RepeatMode ) {} virtual void setRepeatMode( PlaylistInterface::RepeatMode ) {}
virtual void setShuffled( bool ) {} virtual void setShuffled( bool ) {}
virtual void setFilter( const QString& pattern ) {} virtual void setFilter( const QString& pattern ) {}
signals: signals:
/// emitted when the playlist revision changes (whenever the playlist changes) /// emitted when the playlist revision changes (whenever the playlist changes)
void revisionLoaded( Tomahawk::PlaylistRevision ); void revisionLoaded( Tomahawk::PlaylistRevision );
@@ -161,6 +161,9 @@ signals:
/// watch for this to see when newly created playlist is synced to DB (if you care) /// watch for this to see when newly created playlist is synced to DB (if you care)
void created(); void created();
/// renamed etc.
void changed();
void repeatModeChanged( PlaylistInterface::RepeatMode mode ); void repeatModeChanged( PlaylistInterface::RepeatMode mode );
void shuffleModeChanged( bool enabled ); void shuffleModeChanged( bool enabled );
@@ -201,24 +204,24 @@ protected:
const QString& info, const QString& info,
const QString& creator, const QString& creator,
bool shared ); bool shared );
QList< plentry_ptr > newEntries( const QList< plentry_ptr >& entries ); QList< plentry_ptr > newEntries( const QList< plentry_ptr >& entries );
PlaylistRevision setNewRevision( const QString& rev, PlaylistRevision setNewRevision( const QString& rev,
const QList<QString>& neworderedguids, const QList<QString>& neworderedguids,
const QList<QString>& oldorderedguids, const QList<QString>& oldorderedguids,
bool is_newest_rev, bool is_newest_rev,
const QMap< QString, Tomahawk::plentry_ptr >& addedmap ); const QMap< QString, Tomahawk::plentry_ptr >& addedmap );
QList<plentry_ptr> addEntriesInternal( const QList<Tomahawk::query_ptr>& queries ); QList<plentry_ptr> addEntriesInternal( const QList<Tomahawk::query_ptr>& queries );
private slots: private slots:
void onResultsFound( const QList<Tomahawk::result_ptr>& results ); void onResultsFound( const QList<Tomahawk::result_ptr>& results );
void onResolvingFinished(); void onResolvingFinished();
private: private:
Playlist(); Playlist();
void init(); void init();
source_ptr m_source; source_ptr m_source;
QString m_currentrevision; QString m_currentrevision;
QString m_guid, m_title, m_info, m_creator; QString m_guid, m_title, m_info, m_creator;

View File

@@ -52,17 +52,16 @@ CollectionFlatModel::addCollection( const collection_ptr& collection )
<< collection->source()->id() << collection->source()->id()
<< collection->source()->userName(); << collection->source()->userName();
emit loadingStarts(); connect( collection.data(), SIGNAL( tracksAdded( QList<Tomahawk::query_ptr> ) ),
SLOT( onTracksAdded( QList<Tomahawk::query_ptr> ) ) );
connect( collection.data(), SIGNAL( tracksRemoved( QList<Tomahawk::query_ptr> ) ),
SLOT( onTracksRemoved( QList<Tomahawk::query_ptr> ) ) );
onTracksAdded( collection->tracks(), collection ); if ( collection->isLoaded() )
onTracksAdded( collection->tracks() );
else
collection->tracks(); // data will arrive via signals
connect( collection.data(), SIGNAL( tracksAdded( QList<Tomahawk::query_ptr>, Tomahawk::collection_ptr ) ),
SLOT( onTracksAdded( QList<Tomahawk::query_ptr>, Tomahawk::collection_ptr ) ) );
connect( collection.data(), SIGNAL( tracksFinished( Tomahawk::collection_ptr ) ),
SLOT( onTracksAddingFinished( Tomahawk::collection_ptr ) ) );
connect( collection.data(), SIGNAL( tracksRemoved( QList<Tomahawk::query_ptr>, Tomahawk::collection_ptr ) ),
SLOT( onTracksRemoved( QList<Tomahawk::query_ptr>, Tomahawk::collection_ptr ) ) );
if ( collection->source()->isLocal() ) if ( collection->source()->isLocal() )
setTitle( tr( "Your Collection" ) ); setTitle( tr( "Your Collection" ) );
else else
@@ -78,8 +77,6 @@ CollectionFlatModel::addFilteredCollection( const collection_ptr& collection, un
<< collection->source()->userName() << collection->source()->userName()
<< amount << order; << amount << order;
emit loadingStarts();
DatabaseCommand_AllTracks* cmd = new DatabaseCommand_AllTracks( collection ); DatabaseCommand_AllTracks* cmd = new DatabaseCommand_AllTracks( collection );
cmd->setLimit( amount ); cmd->setLimit( amount );
cmd->setSortOrder( order ); cmd->setSortOrder( order );
@@ -97,10 +94,8 @@ CollectionFlatModel::removeCollection( const collection_ptr& collection )
{ {
return; // FIXME return; // FIXME
disconnect( collection.data(), SIGNAL( tracksAdded( QList<Tomahawk::query_ptr>, Tomahawk::collection_ptr ) ), disconnect( collection.data(), SIGNAL( tracksAdded( QList<Tomahawk::query_ptr> ) ),
this, SLOT( onTracksAdded( QList<Tomahawk::query_ptr>, Tomahawk::collection_ptr ) ) ); this, SLOT( onTracksAdded( QList<Tomahawk::query_ptr> ) ) );
disconnect( collection.data(), SIGNAL( tracksFinished( Tomahawk::collection_ptr ) ),
this, SLOT( onTracksAddingFinished( Tomahawk::collection_ptr ) ) );
QTime timer; QTime timer;
timer.start(); timer.start();
@@ -160,56 +155,62 @@ CollectionFlatModel::removeCollection( const collection_ptr& collection )
qDebug() << "Collection removed, time elapsed:" << timer.elapsed(); qDebug() << "Collection removed, time elapsed:" << timer.elapsed();
emit trackCountChanged( rowCount( QModelIndex() ) ); // emit trackCountChanged( rowCount( QModelIndex() ) );
} }
void void
CollectionFlatModel::onTracksAdded( const QList<Tomahawk::query_ptr>& tracks, const Tomahawk::collection_ptr& collection ) CollectionFlatModel::onTracksAdded( const QList<Tomahawk::query_ptr>& tracks )
{ {
qDebug() << Q_FUNC_INFO; qDebug() << Q_FUNC_INFO << tracks.count() << rowCount( QModelIndex() );
if ( !tracks.count() ) bool kickOff = m_tracksToAdd.isEmpty();
{ m_tracksToAdd << tracks;
emit trackCountChanged( rowCount( QModelIndex() ) );
return;
}
emit trackCountChanged( trackCount() );
if ( m_tracksToAdd.count() && kickOff )
processTracksToAdd();
}
void
CollectionFlatModel::processTracksToAdd()
{
int chunkSize = 500000;
int maxc = qMin( chunkSize, m_tracksToAdd.count() );
int c = rowCount( QModelIndex() ); int c = rowCount( QModelIndex() );
QPair< int, int > crows;
crows.first = c;
crows.second = c + tracks.count() - 1;
emit beginInsertRows( QModelIndex(), crows.first, crows.second ); //emit beginInsertRows( QModelIndex(), c, c + maxc - 1 );
beginResetModel();
PlItem* plitem; PlItem* plitem;
foreach( const query_ptr& query, tracks ) QList< Tomahawk::query_ptr >::iterator iter = m_tracksToAdd.begin();
for( int i = 0; i < maxc; ++i )
{ {
plitem = new PlItem( query, m_rootItem );
plitem = new PlItem( *iter, m_rootItem );
plitem->index = createIndex( m_rootItem->children.count() - 1, 0, plitem ); plitem->index = createIndex( m_rootItem->children.count() - 1, 0, plitem );
connect( plitem, SIGNAL( dataChanged() ), SLOT( onDataChanged() ) ); connect( plitem, SIGNAL( dataChanged() ), SLOT( onDataChanged() ) );
++iter;
} }
m_collectionRows.insertMulti( collection, crows ); m_tracksToAdd.erase( m_tracksToAdd.begin(), iter );
emit endInsertRows();
emit trackCountChanged( rowCount( QModelIndex() ) ); endResetModel();
//emit endInsertRows();
qDebug() << Q_FUNC_INFO << rowCount( QModelIndex() ); qDebug() << Q_FUNC_INFO << rowCount( QModelIndex() );
if ( m_tracksToAdd.count() )
QTimer::singleShot( 250, this, SLOT( processTracksToAdd() ) );
} }
void void
CollectionFlatModel::onTracksAddingFinished( const Tomahawk::collection_ptr& collection ) CollectionFlatModel::onTracksRemoved( const QList<Tomahawk::query_ptr>& tracks )
{
qDebug() << "Finished loading tracks" << collection->source()->friendlyName();
emit loadingFinished();
}
void
CollectionFlatModel::onTracksRemoved( const QList<Tomahawk::query_ptr>& tracks, const Tomahawk::collection_ptr& collection )
{ {
QList<Tomahawk::query_ptr> t = tracks; QList<Tomahawk::query_ptr> t = tracks;
for ( int i = rowCount( QModelIndex() ); i >= 0 && t.count(); i-- ) for ( int i = rowCount( QModelIndex() ); i >= 0 && t.count(); i-- )
@@ -235,8 +236,8 @@ CollectionFlatModel::onTracksRemoved( const QList<Tomahawk::query_ptr>& tracks,
j++; j++;
} }
} }
emit trackCountChanged( rowCount( QModelIndex() ) ); // emit trackCountChanged( rowCount( QModelIndex() ) );
qDebug() << Q_FUNC_INFO << rowCount( QModelIndex() ); qDebug() << Q_FUNC_INFO << rowCount( QModelIndex() );
} }

View File

@@ -29,6 +29,8 @@ public:
int columnCount( const QModelIndex& parent = QModelIndex() ) const; int columnCount( const QModelIndex& parent = QModelIndex() ) const;
virtual int trackCount() const { return rowCount( QModelIndex() ) + m_tracksToAdd.count(); }
QVariant data( const QModelIndex& index, int role ) const; QVariant data( const QModelIndex& index, int role ) const;
QVariant headerData( int section, Qt::Orientation orientation, int role ) const; QVariant headerData( int section, Qt::Orientation orientation, int role ) const;
@@ -45,21 +47,19 @@ signals:
void itemSizeChanged( const QModelIndex& index ); void itemSizeChanged( const QModelIndex& index );
void loadingStarts();
void loadingFinished();
private slots: private slots:
void onDataChanged(); void onDataChanged();
void onTracksAdded( const QList<Tomahawk::query_ptr>& tracks, const Tomahawk::collection_ptr& collection ); void onTracksAdded( const QList<Tomahawk::query_ptr>& tracks );
void onTracksAddingFinished( const Tomahawk::collection_ptr& collection ); void onTracksRemoved( const QList<Tomahawk::query_ptr>& tracks );
void onTracksRemoved( const QList<Tomahawk::query_ptr>& tracks, const Tomahawk::collection_ptr& collection );
void onSourceOffline( const Tomahawk::source_ptr& src ); void onSourceOffline( const Tomahawk::source_ptr& src );
void processTracksToAdd();
private: private:
QMap< Tomahawk::collection_ptr, QPair< int, int > > m_collectionRows; QMap< Tomahawk::collection_ptr, QPair< int, int > > m_collectionRows;
QList<Tomahawk::query_ptr> m_tracksToAdd;
}; };
#endif // COLLECTIONFLATMODEL_H #endif // COLLECTIONFLATMODEL_H

View File

@@ -23,10 +23,11 @@ using namespace Tomahawk;
DynamicModel::DynamicModel( QObject* parent ) DynamicModel::DynamicModel( QObject* parent )
: PlaylistModel( parent ) : PlaylistModel( parent )
, m_startOnResolved( false )
, m_onDemandRunning( false ) , m_onDemandRunning( false )
, m_changeOnNext( false ) , m_changeOnNext( false )
, m_searchingForNext( false )
, m_filterUnresolvable( true ) , m_filterUnresolvable( true )
, m_startingAfterFailed( false )
, m_currentAttempts( 0 ) , m_currentAttempts( 0 )
, m_lastResolvedRow( 0 ) , m_lastResolvedRow( 0 )
{ {
@@ -68,9 +69,6 @@ DynamicModel::startOnDemand()
m_playlist->generator()->startOnDemand(); m_playlist->generator()->startOnDemand();
m_onDemandRunning = true; m_onDemandRunning = true;
m_startOnResolved = false; // not anymore---user clicks a track to start it
m_currentAttempts = 0;
m_lastResolvedRow = rowCount( QModelIndex() );
} }
void void
@@ -78,7 +76,7 @@ DynamicModel::newTrackGenerated( const Tomahawk::query_ptr& query )
{ {
if( m_onDemandRunning ) { if( m_onDemandRunning ) {
connect( query.data(), SIGNAL( resolvingFinished( bool ) ), this, SLOT( trackResolveFinished( bool ) ) ); connect( query.data(), SIGNAL( resolvingFinished( bool ) ), this, SLOT( trackResolveFinished( bool ) ) );
connect( query.data(), SIGNAL( resultsAdded( QList<Tomahawk::result_ptr> ) ), this, SLOT( trackResolved() ) ); connect( query.data(), SIGNAL( solvedStateChanged( bool ) ), this, SLOT( trackResolved( bool ) ) );
append( query ); append( query );
} }
@@ -105,20 +103,20 @@ DynamicModel::changeStation()
void void
DynamicModel::trackResolved() DynamicModel::trackResolved( bool resolved )
{ {
if( !resolved )
return;
Query* q = qobject_cast<Query*>(sender()); Query* q = qobject_cast<Query*>(sender());
qDebug() << "Got successful resolved track:" << q->track() << q->artist() << m_lastResolvedRow << m_currentAttempts; qDebug() << "Got successful resolved track:" << q->track() << q->artist() << m_lastResolvedRow << m_currentAttempts;
if( m_startOnResolved ) { // on first start
m_startOnResolved = false;
AudioEngine::instance()->play();
}
if( m_currentAttempts > 0 ) { if( m_currentAttempts > 0 ) {
qDebug() << "EMITTING AN ASK FOR COLLAPSE:" << m_lastResolvedRow << m_currentAttempts; qDebug() << "EMITTING AN ASK FOR COLLAPSE:" << m_lastResolvedRow << m_currentAttempts;
emit collapseFromTo( m_lastResolvedRow, m_currentAttempts ); emit collapseFromTo( m_lastResolvedRow, m_currentAttempts );
} }
m_currentAttempts = 0; m_currentAttempts = 0;
m_searchingForNext = false;
emit checkForOverflow(); emit checkForOverflow();
} }
@@ -130,9 +128,13 @@ DynamicModel::trackResolveFinished( bool success )
Query* q = qobject_cast<Query*>(sender()); Query* q = qobject_cast<Query*>(sender());
qDebug() << "Got not resolved track:" << q->track() << q->artist() << m_lastResolvedRow << m_currentAttempts; qDebug() << "Got not resolved track:" << q->track() << q->artist() << m_lastResolvedRow << m_currentAttempts;
m_currentAttempts++; m_currentAttempts++;
if( m_currentAttempts < 20 ) {
int curAttempts = m_startingAfterFailed ? m_currentAttempts - 20 : m_currentAttempts; // if we just failed, m_currentAttempts includes those failures
if( curAttempts < 20 ) {
qDebug() << "FETCHING MORE!";
m_playlist->generator()->fetchNext(); m_playlist->generator()->fetchNext();
} else { } else {
m_startingAfterFailed = true;
emit trackGenerationFailure( tr( "Could not find a playable track.\n\nPlease change the filters or try again." ) ); emit trackGenerationFailure( tr( "Could not find a playable track.\n\nPlease change the filters or try again." ) );
} }
} }
@@ -142,11 +144,15 @@ DynamicModel::trackResolveFinished( bool success )
void void
DynamicModel::newTrackLoading() DynamicModel::newTrackLoading()
{ {
qDebug() << "Got NEW TRACK LOADING signal";
if( m_changeOnNext ) { // reset instead of getting the next one if( m_changeOnNext ) { // reset instead of getting the next one
m_lastResolvedRow = rowCount( QModelIndex() ); m_lastResolvedRow = rowCount( QModelIndex() );
m_searchingForNext = true;
m_playlist->generator()->startOnDemand(); m_playlist->generator()->startOnDemand();
} else if( m_onDemandRunning && m_currentAttempts == 0 ) { // if we're in dynamic mode and we're also currently idle } else if( m_onDemandRunning && m_currentAttempts == 0 && !m_searchingForNext ) { // if we're in dynamic mode and we're also currently idle
m_lastResolvedRow = rowCount( QModelIndex() ); m_lastResolvedRow = rowCount( QModelIndex() );
m_searchingForNext = true;
qDebug() << "IDLE fetching new track!";
m_playlist->generator()->fetchNext(); m_playlist->generator()->fetchNext();
} }
} }
@@ -154,11 +160,15 @@ DynamicModel::newTrackLoading()
void void
DynamicModel::tracksGenerated( const QList< query_ptr > entries, int limitResolvedTo ) DynamicModel::tracksGenerated( const QList< query_ptr > entries, int limitResolvedTo )
{ {
if( m_filterUnresolvable ) { // wait till we get them resolved if( m_filterUnresolvable && m_playlist->mode() == OnDemand ) { // wait till we get them resolved (for previewing stations)
m_limitResolvedTo = limitResolvedTo; m_limitResolvedTo = limitResolvedTo;
filterUnresolved( entries ); filterUnresolved( entries );
} else { } else {
addToPlaylist( entries, m_playlist->mode() == OnDemand ); // if ondemand, we're previewing, so clear old addToPlaylist( entries, m_playlist->mode() == OnDemand ); // if ondemand, we're previewing, so clear old
if( m_playlist->mode() == OnDemand ) {
m_lastResolvedRow = rowCount( QModelIndex() );
}
} }
} }
@@ -202,6 +212,10 @@ DynamicModel::filteringTrackResolved( bool successful )
addToPlaylist( m_resolvedList, true ); addToPlaylist( m_resolvedList, true );
m_toResolveList.clear(); m_toResolveList.clear();
m_resolvedList.clear(); m_resolvedList.clear();
if( m_playlist->mode() == OnDemand ) {
m_lastResolvedRow = rowCount( QModelIndex() );
}
} }
} }

View File

@@ -64,7 +64,7 @@ private slots:
void newTrackGenerated( const Tomahawk::query_ptr& query ); void newTrackGenerated( const Tomahawk::query_ptr& query );
void trackResolveFinished( bool ); void trackResolveFinished( bool );
void trackResolved(); void trackResolved( bool );
void newTrackLoading(); void newTrackLoading();
void filteringTrackResolved( bool successful ); void filteringTrackResolved( bool successful );
@@ -78,12 +78,12 @@ private:
QList< query_ptr > m_toResolveList; QList< query_ptr > m_toResolveList;
QList< query_ptr > m_resolvedList; QList< query_ptr > m_resolvedList;
bool m_startOnResolved;
bool m_onDemandRunning; bool m_onDemandRunning;
bool m_changeOnNext; bool m_changeOnNext;
bool m_searchingForNext; bool m_searchingForNext;
bool m_firstTrackGenerated; bool m_firstTrackGenerated;
bool m_filterUnresolvable; bool m_filterUnresolvable;
bool m_startingAfterFailed;
int m_currentAttempts; int m_currentAttempts;
int m_lastResolvedRow; int m_lastResolvedRow;
}; };

View File

@@ -75,7 +75,7 @@ DynamicWidget::DynamicWidget( const Tomahawk::dynplaylist_ptr& playlist, QWidget
m_setup = new DynamicSetupWidget( playlist, this ); m_setup = new DynamicSetupWidget( playlist, this );
m_setup->fadeIn(); m_setup->fadeIn();
connect( m_model, SIGNAL( tracksAdded() ), m_setup, SLOT( fadeOut() ) ); connect( m_model, SIGNAL( tracksAdded() ), this, SLOT( tracksAdded() ) );
loadDynamicPlaylist( playlist ); loadDynamicPlaylist( playlist );
@@ -262,6 +262,14 @@ DynamicWidget::trackStarted()
} }
} }
void
DynamicWidget::tracksAdded()
{
if( m_playlist->mode() == OnDemand && m_runningOnDemand && m_setup->isVisible() )
m_setup->fadeOut();
}
void void
DynamicWidget::stopStation( bool stopPlaying ) DynamicWidget::stopStation( bool stopPlaying )
{ {
@@ -348,8 +356,8 @@ DynamicWidget::controlChanged( const Tomahawk::dyncontrol_ptr& control )
void void
DynamicWidget::showPreview() DynamicWidget::showPreview()
{ {
if( m_playlist->mode() == OnDemand && !m_runningOnDemand ) { // if this is a not running station, preview matching tracks if( m_playlist->mode() == OnDemand && !m_runningOnDemand && m_model->rowCount( QModelIndex() ) == 0 ) { // if this is a not running station, preview matching tracks
generate( 40 ); // ask for more, we'll filter how many we actually want generate( 20 ); // ask for more, we'll filter how many we actually want
} }
} }

View File

@@ -89,6 +89,7 @@ public slots:
void stationFailed( const QString& ); void stationFailed( const QString& );
void playlistStopped( PlaylistInterface* ); void playlistStopped( PlaylistInterface* );
void tracksAdded();
private slots: private slots:
void generate( int = -1 ); void generate( int = -1 );

View File

@@ -22,6 +22,7 @@
#include "albummodel.h" #include "albummodel.h"
#include "sourcelist.h" #include "sourcelist.h"
#include "tomahawksettings.h" #include "tomahawksettings.h"
#include "utils/widgetdragfilter.h"
#include "dynamic/widgets/DynamicWidget.h" #include "dynamic/widgets/DynamicWidget.h"
@@ -57,6 +58,8 @@ PlaylistManager::PlaylistManager( QObject* parent )
m_infobar = new InfoBar(); m_infobar = new InfoBar();
m_stack = new QStackedWidget(); m_stack = new QStackedWidget();
m_infobar->installEventFilter( new WidgetDragFilter( m_infobar ) );
QFrame* line = new QFrame(); QFrame* line = new QFrame();
line->setFrameStyle( QFrame::HLine ); line->setFrameStyle( QFrame::HLine );
line->setStyleSheet( "border: 1px solid gray;" ); line->setStyleSheet( "border: 1px solid gray;" );
@@ -576,7 +579,12 @@ PlaylistManager::updateView()
if ( currentPage()->showStatsBar() && currentPlaylistInterface() ) if ( currentPage()->showStatsBar() && currentPlaylistInterface() )
{ {
emit numTracksChanged( currentPlaylistInterface()->unfilteredTrackCount() ); emit numTracksChanged( currentPlaylistInterface()->unfilteredTrackCount() );
emit numShownChanged( currentPlaylistInterface()->trackCount() );
if ( !currentPlaylistInterface()->filter().isEmpty() )
emit numShownChanged( currentPlaylistInterface()->trackCount() );
else
emit numShownChanged( currentPlaylistInterface()->unfilteredTrackCount() );
emit repeatModeChanged( currentPlaylistInterface()->repeatMode() ); emit repeatModeChanged( currentPlaylistInterface()->repeatMode() );
emit shuffleModeChanged( currentPlaylistInterface()->shuffled() ); emit shuffleModeChanged( currentPlaylistInterface()->shuffled() );
emit modeChanged( currentPlaylistInterface()->viewMode() ); emit modeChanged( currentPlaylistInterface()->viewMode() );
@@ -586,7 +594,7 @@ PlaylistManager::updateView()
m_queueView->show(); m_queueView->show();
else else
m_queueView->hide(); m_queueView->hide();
emit statsAvailable( currentPage()->showStatsBar() ); emit statsAvailable( currentPage()->showStatsBar() );
emit modesAvailable( currentPage()->showModes() ); emit modesAvailable( currentPage()->showModes() );
@@ -687,7 +695,7 @@ PlaylistManager::positionInHistory( ViewPage* page ) const
if ( page == m_pageHistory.at( i ) ) if ( page == m_pageHistory.at( i ) )
return i; return i;
} }
return -1; return -1;
} }
@@ -747,7 +755,7 @@ PlaylistManager::dynamicPlaylistForInterface( PlaylistInterface* interface ) con
return m_dynamicWidgets.key( view ); return m_dynamicWidgets.key( view );
} }
} }
return dynplaylist_ptr(); return dynplaylist_ptr();
} }
@@ -769,7 +777,7 @@ PlaylistManager::collectionForInterface( PlaylistInterface* interface ) const
return m_collectionAlbumViews.key( view ); return m_collectionAlbumViews.key( view );
} }
} }
return collection_ptr(); return collection_ptr();
} }

View File

@@ -155,10 +155,10 @@ PlaylistModel::append( const Tomahawk::album_ptr& album )
if ( album.isNull() ) if ( album.isNull() )
return; return;
connect( album.data(), SIGNAL( tracksAdded( QList<Tomahawk::query_ptr>, Tomahawk::collection_ptr ) ), connect( album.data(), SIGNAL( tracksAdded( QList<Tomahawk::query_ptr> ) ),
SLOT( onTracksAdded( QList<Tomahawk::query_ptr>, Tomahawk::collection_ptr ) ) ); SLOT( onTracksAdded( QList<Tomahawk::query_ptr> ) ) );
onTracksAdded( album->tracks(), album->collection() ); onTracksAdded( album->tracks() );
} }
@@ -168,10 +168,10 @@ PlaylistModel::append( const Tomahawk::artist_ptr& artist )
if ( artist.isNull() ) if ( artist.isNull() )
return; return;
connect( artist.data(), SIGNAL( tracksAdded( QList<Tomahawk::query_ptr>, Tomahawk::collection_ptr ) ), connect( artist.data(), SIGNAL( tracksAdded( QList<Tomahawk::query_ptr> ) ),
SLOT( onTracksAdded( QList<Tomahawk::query_ptr>, Tomahawk::collection_ptr ) ) ); SLOT( onTracksAdded( QList<Tomahawk::query_ptr> ) ) );
onTracksAdded( artist->tracks(), artist->collection() ); onTracksAdded( artist->tracks() );
} }
@@ -189,14 +189,14 @@ PlaylistModel::insert( unsigned int row, const Tomahawk::query_ptr& query )
void void
PlaylistModel::onTracksAdded( const QList<Tomahawk::query_ptr>& tracks, const Tomahawk::collection_ptr& collection ) PlaylistModel::onTracksAdded( const QList<Tomahawk::query_ptr>& tracks )
{ {
onTracksInserted( rowCount( QModelIndex() ), tracks, collection ); onTracksInserted( rowCount( QModelIndex() ), tracks );
} }
void void
PlaylistModel::onTracksInserted( unsigned int row, const QList<Tomahawk::query_ptr>& tracks, const Tomahawk::collection_ptr& collection ) PlaylistModel::onTracksInserted( unsigned int row, const QList<Tomahawk::query_ptr>& tracks )
{ {
if ( !tracks.count() ) if ( !tracks.count() )
{ {

View File

@@ -37,7 +37,7 @@ public:
void loadHistory( const Tomahawk::source_ptr& source, unsigned int amount = 50 ); void loadHistory( const Tomahawk::source_ptr& source, unsigned int amount = 50 );
void clear(); void clear();
void append( const Tomahawk::query_ptr& query ); void append( const Tomahawk::query_ptr& query );
void append( const Tomahawk::album_ptr& album ); void append( const Tomahawk::album_ptr& album );
void append( const Tomahawk::artist_ptr& artist ); void append( const Tomahawk::artist_ptr& artist );
@@ -61,8 +61,8 @@ private slots:
void onRevisionLoaded( Tomahawk::PlaylistRevision revision ); void onRevisionLoaded( Tomahawk::PlaylistRevision revision );
void onPlaylistChanged( bool waitForUpdate = true ); void onPlaylistChanged( bool waitForUpdate = true );
void onTracksAdded( const QList<Tomahawk::query_ptr>& tracks, const Tomahawk::collection_ptr& collection = Tomahawk::collection_ptr() ); void onTracksAdded( const QList<Tomahawk::query_ptr>& tracks );
void onTracksInserted( unsigned int row, const QList<Tomahawk::query_ptr>& tracks, const Tomahawk::collection_ptr& collection = Tomahawk::collection_ptr() ); void onTracksInserted( unsigned int row, const QList<Tomahawk::query_ptr>& tracks );
private: private:
QList<Tomahawk::plentry_ptr> playlistEntries() const; QList<Tomahawk::plentry_ptr> playlistEntries() const;

View File

@@ -39,7 +39,7 @@ public:
virtual void setTitle( const QString& title ) { m_title = title; } virtual void setTitle( const QString& title ) { m_title = title; }
virtual QString description() const { return m_description; } virtual QString description() const { return m_description; }
virtual void setDescription( const QString& description ) { m_description = description; } virtual void setDescription( const QString& description ) { m_description = description; }
virtual int trackCount() const { return rowCount( QModelIndex() ); } virtual int trackCount() const { return rowCount( QModelIndex() ); }
virtual int rowCount( const QModelIndex& parent ) const; virtual int rowCount( const QModelIndex& parent ) const;

View File

@@ -118,7 +118,7 @@ TrackProxyModel::siblingItem( int itemsAway )
{ {
PlItem* item = itemFromIndex( mapToSource( idx ) ); PlItem* item = itemFromIndex( mapToSource( idx ) );
qDebug() << item->query()->toString(); qDebug() << item->query()->toString();
if ( item && item->query()->numResults() ) if ( item && item->query()->solved() )
{ {
qDebug() << "Next PlaylistItem found:" << item->query()->toString() << item->query()->results().at( 0 )->url(); qDebug() << "Next PlaylistItem found:" << item->query()->toString() << item->query()->results().at( 0 )->url();
setCurrentItem( idx ); setCurrentItem( idx );
@@ -137,9 +137,6 @@ TrackProxyModel::siblingItem( int itemsAway )
bool bool
TrackProxyModel::filterAcceptsRow( int sourceRow, const QModelIndex& sourceParent ) const TrackProxyModel::filterAcceptsRow( int sourceRow, const QModelIndex& sourceParent ) const
{ {
if ( filterRegExp().isEmpty() )
return true;
PlItem* pi = itemFromIndex( sourceModel()->index( sourceRow, 0, sourceParent ) ); PlItem* pi = itemFromIndex( sourceModel()->index( sourceRow, 0, sourceParent ) );
if ( !pi ) if ( !pi )
return false; return false;
@@ -147,34 +144,39 @@ TrackProxyModel::filterAcceptsRow( int sourceRow, const QModelIndex& sourceParen
const Tomahawk::query_ptr& q = pi->query(); const Tomahawk::query_ptr& q = pi->query();
Tomahawk::result_ptr r; Tomahawk::result_ptr r;
if ( q->numResults() ) if ( q->numResults() )
r = q->results().at( 0 ); r = q->results().first();
// if ( !r.isNull() && !r->collection()->source()->isOnline() )
// return false;
if ( filterRegExp().isEmpty() )
return true;
QStringList sl = filterRegExp().pattern().split( " ", QString::SkipEmptyParts ); QStringList sl = filterRegExp().pattern().split( " ", QString::SkipEmptyParts );
bool found = true; foreach( QString s, sl )
foreach( const QString& s, sl )
{ {
s = s.toLower();
if ( !r.isNull() ) if ( !r.isNull() )
{ {
if ( !r->artist()->name().contains( s, Qt::CaseInsensitive ) && if ( !r->artist()->name().toLower().contains( s ) &&
!r->album()->name().contains( s, Qt::CaseInsensitive ) && !r->album()->name().toLower().contains( s ) &&
!r->track() .contains( s, Qt::CaseInsensitive ) ) !r->track().toLower().contains( s ) )
{ {
found = false; return false;
} }
} }
else else
{ {
if ( !q->artist().contains( s, Qt::CaseInsensitive ) && if ( !q->artist().toLower().contains( s ) &&
!q->album() .contains( s, Qt::CaseInsensitive ) && !q->album().toLower().contains( s ) &&
!q->track() .contains( s, Qt::CaseInsensitive ) ) !q->track().toLower().contains( s ) )
{ {
found = false; return false;
} }
} }
} }
return found; return true;
} }

View File

@@ -23,7 +23,7 @@ public:
virtual QList<Tomahawk::query_ptr> tracks(); virtual QList<Tomahawk::query_ptr> tracks();
virtual int unfilteredTrackCount() const { return sourceModel()->rowCount( QModelIndex() ); } virtual int unfilteredTrackCount() const { return sourceModel()->trackCount(); }
virtual int trackCount() const { return rowCount( QModelIndex() ); } virtual int trackCount() const { return rowCount( QModelIndex() ); }
virtual void removeIndex( const QModelIndex& index ); virtual void removeIndex( const QModelIndex& index );

View File

@@ -44,7 +44,7 @@ Query::addResults( const QList< Tomahawk::result_ptr >& newresults )
{ {
bool becameSolved = false; bool becameSolved = false;
{ {
QMutexLocker lock( &m_mut ); // QMutexLocker lock( &m_mut );
m_results.append( newresults ); m_results.append( newresults );
qStableSort( m_results.begin(), m_results.end(), Query::resultSorter ); qStableSort( m_results.begin(), m_results.end(), Query::resultSorter );
@@ -70,7 +70,8 @@ Query::refreshResults()
void void
Query::onResultStatusChanged() Query::onResultStatusChanged()
{ {
qStableSort( m_results.begin(), m_results.end(), Query::resultSorter ); if ( m_results.count() )
qStableSort( m_results.begin(), m_results.end(), Query::resultSorter );
checkResults(); checkResults();
emit resultsChanged(); emit resultsChanged();
@@ -81,7 +82,7 @@ void
Query::removeResult( const Tomahawk::result_ptr& result ) Query::removeResult( const Tomahawk::result_ptr& result )
{ {
{ {
QMutexLocker lock( &m_mut ); // QMutexLocker lock( &m_mut );
m_results.removeAll( result ); m_results.removeAll( result );
} }
@@ -94,14 +95,14 @@ void
Query::onResolvingFinished() Query::onResolvingFinished()
{ {
// qDebug() << Q_FUNC_INFO << "Finished resolving." << toString(); // qDebug() << Q_FUNC_INFO << "Finished resolving." << toString();
emit resolvingFinished( !m_results.isEmpty() ); emit resolvingFinished( m_solved );
} }
QList< result_ptr > QList< result_ptr >
Query::results() const Query::results() const
{ {
QMutexLocker lock( &m_mut ); // QMutexLocker lock( &m_mut );
return m_results; return m_results;
} }
@@ -109,7 +110,7 @@ Query::results() const
unsigned int unsigned int
Query::numResults() const Query::numResults() const
{ {
QMutexLocker lock( &m_mut ); // QMutexLocker lock( &m_mut );
return m_results.length(); return m_results.length();
} }
@@ -148,16 +149,16 @@ Query::checkResults()
{ {
bool becameSolved = false; bool becameSolved = false;
bool becameUnsolved = true; bool becameUnsolved = true;
// hook up signals, and check solved status // hook up signals, and check solved status
foreach( const result_ptr& rp, m_results ) foreach( const result_ptr& rp, m_results )
{ {
if ( !m_solved && rp->score() > 0.99 ) if ( !m_solved && rp->score() > 0.99 && rp->collection()->source()->isOnline() )
{ {
m_solved = true; m_solved = true;
becameSolved = true; becameSolved = true;
} }
if ( rp->score() > 0.99 ) if ( rp->score() > 0.99 && rp->collection()->source()->isOnline() )
{ {
becameUnsolved = false; becameUnsolved = false;
} }
@@ -166,7 +167,7 @@ Query::checkResults()
if ( m_solved && becameUnsolved ) if ( m_solved && becameUnsolved )
{ {
m_solved = false; m_solved = false;
emit solvedStateChanged( true ); emit solvedStateChanged( false );
} }
if( becameSolved ) if( becameSolved )

View File

@@ -84,8 +84,7 @@ private slots:
private: private:
void clearResults(); void clearResults();
void checkResults(); void checkResults();
mutable QMutex m_mut;
QList< Tomahawk::result_ptr > m_results; QList< Tomahawk::result_ptr > m_results;
bool m_solved; bool m_solved;
mutable QID m_qid; mutable QID m_qid;

View File

@@ -19,7 +19,7 @@ SourceList::instance()
{ {
s_instance = new SourceList(); s_instance = new SourceList();
} }
return s_instance; return s_instance;
} }
@@ -43,10 +43,10 @@ SourceList::loadSources()
{ {
qDebug() << Q_FUNC_INFO; qDebug() << Q_FUNC_INFO;
DatabaseCommand_LoadAllSources* cmd = new DatabaseCommand_LoadAllSources(); DatabaseCommand_LoadAllSources* cmd = new DatabaseCommand_LoadAllSources();
connect( cmd, SIGNAL( done( const QList<Tomahawk::source_ptr>& ) ), connect( cmd, SIGNAL( done( QList<Tomahawk::source_ptr> ) ),
SLOT( setSources( const QList<Tomahawk::source_ptr>& ) ) ); SLOT( setSources( QList<Tomahawk::source_ptr> ) ) );
Database::instance()->enqueue( QSharedPointer<DatabaseCommand>( cmd ) ); Database::instance()->enqueue( QSharedPointer<DatabaseCommand>( cmd ) );
} }
@@ -70,7 +70,7 @@ SourceList::setLocal( const Tomahawk::source_ptr& localSrc )
{ {
Q_ASSERT( localSrc->isLocal() ); Q_ASSERT( localSrc->isLocal() );
Q_ASSERT( m_local.isNull() ); Q_ASSERT( m_local.isNull() );
{ {
QMutexLocker lock( &m_mut ); QMutexLocker lock( &m_mut );
m_sources.insert( localSrc->userName(), localSrc ); m_sources.insert( localSrc->userName(), localSrc );
@@ -92,11 +92,11 @@ SourceList::add( const source_ptr& source )
if ( source->id() > 0 ) if ( source->id() > 0 )
m_sources_id2name.insert( source->id(), source->userName() ); m_sources_id2name.insert( source->id(), source->userName() );
connect( source.data(), SIGNAL( syncedWithDatabase() ), SLOT( sourceSynced() ) ); connect( source.data(), SIGNAL( syncedWithDatabase() ), SLOT( sourceSynced() ) );
collection_ptr coll( new RemoteCollection( source ) ); collection_ptr coll( new RemoteCollection( source ) );
source->addCollection( coll ); source->addCollection( coll );
source->collection()->tracks(); // source->collection()->tracks();
emit sourceAdded( source ); emit sourceAdded( source );
} }

View File

@@ -76,36 +76,66 @@ XSPFLoader::gotBody()
qDebug() << Q_FUNC_INFO; qDebug() << Q_FUNC_INFO;
QDomDocument xmldoc; QDomDocument xmldoc;
xmldoc.setContent( m_body ); bool namespaceProcessing = true;
xmldoc.setContent( m_body, namespaceProcessing );
QDomElement docElement( xmldoc.documentElement() ); QDomElement docElement( xmldoc.documentElement() );
QString origTitle; QString origTitle;
origTitle = docElement.firstChildElement( "title" ).text(); QDomNodeList tracklist;
m_info = docElement.firstChildElement( "creator" ).text(); QDomElement n = docElement.firstChildElement();
m_creator = docElement.firstChildElement( "info" ).text(); for ( ; !n.isNull(); n = n.nextSiblingElement() ) {
if (n.namespaceURI() == m_NS && n.localName() == "title") {
origTitle = n.text();
} else if (n.namespaceURI() == m_NS && n.localName() == "creator") {
m_creator = n.text();
} else if (n.namespaceURI() == m_NS && n.localName() == "info") {
m_info = n.text();
} else if (n.namespaceURI() == m_NS && n.localName() == "trackList") {
tracklist = n.childNodes();
}
}
m_title = origTitle; m_title = origTitle;
if ( m_title.isEmpty() ) if ( m_title.isEmpty() )
m_title = tr( "New Playlist" ); m_title = tr( "New Playlist" );
QDomNodeList tracklist = docElement.elementsByTagName( "track" ); bool shownError = false;
for ( unsigned int i = 0; i < tracklist.length(); i++ ) for ( unsigned int i = 0; i < tracklist.length(); i++ )
{ {
QDomNode e = tracklist.at( i ); QDomNode e = tracklist.at( i );
QString artist, album, track, duration, annotation;
QDomElement n = e.firstChildElement();
for ( ; !n.isNull(); n = n.nextSiblingElement() ) {
if (n.namespaceURI() == m_NS && n.localName() == "duration") {
duration = n.text();
} else if (n.namespaceURI() == m_NS && n.localName() == "annotation") {
annotation = n.text();
} else if (n.namespaceURI() == m_NS && n.localName() == "creator") {
artist = n.text();
} else if (n.namespaceURI() == m_NS && n.localName() == "album") {
album = n.text();
} else if (n.namespaceURI() == m_NS && n.localName() == "title") {
track = n.text();
}
}
if( artist.isEmpty() || track.isEmpty() ) {
if( !shownError ) {
QMessageBox::warning( 0, tr( "Failed to save tracks" ), tr( "Some tracks in the playlist do not contain an artist and a title. They will be ignored." ), QMessageBox::Ok );
shownError = true;
}
continue;
}
plentry_ptr p( new PlaylistEntry ); plentry_ptr p( new PlaylistEntry );
p->setGuid( uuid() ); p->setGuid( uuid() );
p->setDuration( e.firstChildElement( "duration" ).text().toInt() / 1000 ); p->setDuration( duration.toInt() / 1000 );
p->setLastmodified( 0 ); p->setLastmodified( 0 );
p->setAnnotation( e.firstChildElement( "annotation" ).text() ); p->setAnnotation( annotation );
QString artist, album, track;
artist = e.firstChildElement( "creator" ).text();
album = e.firstChildElement( "album" ).text();
track = e.firstChildElement( "title" ).text();
p->setQuery( Tomahawk::Query::get( artist, track, album, uuid() ) ); p->setQuery( Tomahawk::Query::get( artist, track, album, uuid() ) );
p->query()->setDuration( e.firstChildElement( "duration" ).text().toInt() / 1000 ); p->query()->setDuration( duration.toInt() / 1000 );
m_entries << p; m_entries << p;
} }

View File

@@ -25,6 +25,7 @@ public:
explicit XSPFLoader( bool autoCreate = true, QObject* parent = 0 ) explicit XSPFLoader( bool autoCreate = true, QObject* parent = 0 )
: QObject( parent ) : QObject( parent )
, m_autoCreate( autoCreate ) , m_autoCreate( autoCreate )
, m_NS("http://xspf.org/ns/0/")
{} {}
virtual ~XSPFLoader() virtual ~XSPFLoader()
@@ -51,6 +52,7 @@ private:
void gotBody(); void gotBody();
bool m_autoCreate; bool m_autoCreate;
QString m_NS;
QList< Tomahawk::plentry_ptr > m_entries; QList< Tomahawk::plentry_ptr > m_entries;
QString m_title, m_info, m_creator; QString m_title, m_info, m_creator;

View File

@@ -12,6 +12,7 @@ ScriptResolver::ScriptResolver(const QString& exe) :
, m_num_restarts( 0 ) , m_num_restarts( 0 )
, m_msgsize( 0 ) , m_msgsize( 0 )
, m_ready( false ) , m_ready( false )
, m_stopped( false )
{ {
qDebug() << Q_FUNC_INFO << exe; qDebug() << Q_FUNC_INFO << exe;
connect( &m_proc, SIGNAL(readyReadStandardError()), SLOT(readStderr()) ); connect( &m_proc, SIGNAL(readyReadStandardError()), SLOT(readStderr()) );
@@ -116,6 +117,14 @@ void ScriptResolver::cmdExited(int code, QProcess::ExitStatus status)
qDebug() << Q_FUNC_INFO << "SCRIPT EXITED, code" << code << "status" << status << m_cmd; qDebug() << Q_FUNC_INFO << "SCRIPT EXITED, code" << code << "status" << status << m_cmd;
Tomahawk::Pipeline::instance()->removeResolver( this ); Tomahawk::Pipeline::instance()->removeResolver( this );
if( m_stopped )
{
qDebug() << "*** Script resolver stopped ";
emit finished();
return;
}
if( m_num_restarts < 10 ) if( m_num_restarts < 10 )
{ {
m_num_restarts++; m_num_restarts++;
@@ -154,3 +163,11 @@ void ScriptResolver::doSetup( const QVariantMap& m )
m_ready = true; m_ready = true;
Tomahawk::Pipeline::instance()->addResolver( this ); Tomahawk::Pipeline::instance()->addResolver( this );
} }
void
ScriptResolver::stop()
{
m_stopped = true;
m_proc.kill();
}

View File

@@ -25,9 +25,12 @@ public:
virtual void resolve( const Tomahawk::query_ptr& query ); virtual void resolve( const Tomahawk::query_ptr& query );
void stop();
QString exe() const { return m_cmd; } QString exe() const { return m_cmd; }
signals: signals:
void finished();
public slots: public slots:
private slots: private slots:
@@ -47,7 +50,7 @@ private:
quint32 m_msgsize; quint32 m_msgsize;
QByteArray m_msg; QByteArray m_msg;
bool m_ready; bool m_ready, m_stopped;
QJson::Parser m_parser; QJson::Parser m_parser;
QJson::Serializer m_serializer; QJson::Serializer m_serializer;

View File

@@ -8,9 +8,12 @@
#include <QLineEdit> #include <QLineEdit>
JabberPlugin::JabberPlugin() JabberPlugin::JabberPlugin()
: p( 0 ) : p( 0 ),
m_menu ( 0 )
{ {
m_menu = new QMenu(QString("Jabber (").append(accountName()).append(")")); if( !accountName().isEmpty() )
m_menu = new QMenu(QString("Jabber (").append(accountName()).append(")"));
m_addFriendAction = m_menu->addAction("Add Friend..."); m_addFriendAction = m_menu->addAction("Add Friend...");
connect(m_addFriendAction, SIGNAL(triggered()), connect(m_addFriendAction, SIGNAL(triggered()),

View File

@@ -148,12 +148,11 @@ Jabber_p::go()
// Handle proxy // Handle proxy
qDebug() << "Connecting to the XMPP server..."; qDebug() << "Connecting to the XMPP server...";
//FIXME: This call blocks and locks up the whole GUI if the network is down
if( m_client->connect( false ) ) if( m_client->connect( false ) )
{ {
qDebug() << "Connected to the XMPP server"; int sock = static_cast<ConnectionTCPClient*>( m_client->connectionImpl() )->socket();
emit connected(); m_notifier.reset( new QSocketNotifier( sock, QSocketNotifier::Read ) );
QTimer::singleShot( 0, this, SLOT( doJabberRecv() ) ); connect( m_notifier.data(), SIGNAL( activated(int) ), SLOT( doJabberRecv() ));
} }
else else
qDebug() << "Could not connect to the XMPP server!"; qDebug() << "Could not connect to the XMPP server!";
@@ -171,10 +170,6 @@ Jabber_p::doJabberRecv()
{ {
qDebug() << "Jabber_p::Recv failed, disconnected"; qDebug() << "Jabber_p::Recv failed, disconnected";
} }
else
{
QTimer::singleShot( 100, this, SLOT( doJabberRecv() ) );
}
} }
@@ -260,6 +255,7 @@ Jabber_p::addContact( const QString& jid, const QString& msg )
void void
Jabber_p::onConnect() Jabber_p::onConnect()
{ {
qDebug() << "Connected to the XMPP server";
// update jid resource, servers like gtalk use resource binding and may // update jid resource, servers like gtalk use resource binding and may
// have changed our requested /resource // have changed our requested /resource
if ( m_client->resource() != m_jid.resource() ) if ( m_client->resource() != m_jid.resource() )
@@ -270,6 +266,7 @@ Jabber_p::onConnect()
} }
qDebug() << "Connected as:" << m_jid.full().c_str(); qDebug() << "Connected as:" << m_jid.full().c_str();
emit connected();
} }

View File

@@ -7,7 +7,9 @@
#define JABBER_P_H #define JABBER_P_H
#include <QObject> #include <QObject>
#include <QScopedPointer>
#include <QSharedPointer> #include <QSharedPointer>
#include <QSocketNotifier>
#include <QMap> #include <QMap>
#include <QNetworkProxy> #include <QNetworkProxy>
@@ -137,6 +139,7 @@ private:
QMap<QString, gloox::Presence::PresenceType> m_peers; QMap<QString, gloox::Presence::PresenceType> m_peers;
QSharedPointer<gloox::VCardManager> m_vcardManager; QSharedPointer<gloox::VCardManager> m_vcardManager;
QString m_server; QString m_server;
QScopedPointer<QSocketNotifier> m_notifier;
}; };
#endif // JABBER_H #endif // JABBER_H

View File

@@ -41,7 +41,7 @@ SourceTreeItem::SourceTreeItem( const source_ptr& source, QObject* parent )
SLOT( onPlaylistsAdded( QList<Tomahawk::playlist_ptr> ) ) ); SLOT( onPlaylistsAdded( QList<Tomahawk::playlist_ptr> ) ) );
connect( source->collection().data(), SIGNAL( playlistsDeleted( QList<Tomahawk::playlist_ptr> ) ), connect( source->collection().data(), SIGNAL( playlistsDeleted( QList<Tomahawk::playlist_ptr> ) ),
SLOT( onPlaylistsDeleted( QList<Tomahawk::playlist_ptr> ) ) ); SLOT( onPlaylistsDeleted( QList<Tomahawk::playlist_ptr> ) ) );
connect( source->collection().data(), SIGNAL( dynamicPlaylistsAdded( QList<Tomahawk::dynplaylist_ptr> ) ), connect( source->collection().data(), SIGNAL( dynamicPlaylistsAdded( QList<Tomahawk::dynplaylist_ptr> ) ),
SLOT( onDynamicPlaylistsAdded( QList<Tomahawk::dynplaylist_ptr> ) ) ); SLOT( onDynamicPlaylistsAdded( QList<Tomahawk::dynplaylist_ptr> ) ) );
connect( source->collection().data(), SIGNAL( dynamicPlaylistsDeleted( QList<Tomahawk::dynplaylist_ptr> ) ), connect( source->collection().data(), SIGNAL( dynamicPlaylistsDeleted( QList<Tomahawk::dynplaylist_ptr> ) ),
@@ -88,14 +88,14 @@ SourceTreeItem::onPlaylistsAdded( const QList<playlist_ptr>& playlists )
{ {
m_playlists.append( p ); m_playlists.append( p );
qlonglong ptr = reinterpret_cast<qlonglong>( &m_playlists.last() ); qlonglong ptr = reinterpret_cast<qlonglong>( &m_playlists.last() );
qDebug() << "Setting playlist ptr to:" << ptr;
connect( p.data(), SIGNAL( revisionLoaded( Tomahawk::PlaylistRevision ) ), connect( p.data(), SIGNAL( revisionLoaded( Tomahawk::PlaylistRevision ) ),
SLOT( onPlaylistLoaded( Tomahawk::PlaylistRevision ) ), SLOT( onPlaylistLoaded( Tomahawk::PlaylistRevision ) ), Qt::QueuedConnection );
Qt::QueuedConnection); connect( p.data(), SIGNAL( changed() ),
SLOT( onPlaylistChanged() ), Qt::QueuedConnection );
qDebug() << "Playlist added:" << p->title() << p->creator() << p->info() << ptr; qDebug() << "Playlist added:" << p->title() << p->creator() << p->info() << ptr;
playlistAddedInternal( ptr, p, false ); playlistAddedInternal( ptr, p, false );
} }
} }
@@ -109,7 +109,7 @@ SourceTreeItem::onPlaylistsDeleted( const QList<playlist_ptr>& playlists )
{ {
qlonglong ptr = qlonglong( p.data() ); qlonglong ptr = qlonglong( p.data() );
qDebug() << "Playlist removed:" << p->title() << p->creator() << p->info() << ptr; qDebug() << "Playlist removed:" << p->title() << p->creator() << p->info() << ptr;
QStandardItem* item = m_columns.at( 0 ); QStandardItem* item = m_columns.at( 0 );
int rows = item->rowCount(); int rows = item->rowCount();
for ( int i = rows - 1; i >= 0; i-- ) for ( int i = rows - 1; i >= 0; i-- )
@@ -118,7 +118,7 @@ SourceTreeItem::onPlaylistsDeleted( const QList<playlist_ptr>& playlists )
qlonglong piptr = pi->data( PlaylistPointer ).toLongLong(); qlonglong piptr = pi->data( PlaylistPointer ).toLongLong();
playlist_ptr* pl = reinterpret_cast<playlist_ptr*>(piptr); playlist_ptr* pl = reinterpret_cast<playlist_ptr*>(piptr);
SourcesModel::SourceType type = static_cast<SourcesModel::SourceType>( pi->data( Type ).toInt() ); SourcesModel::SourceType type = static_cast<SourcesModel::SourceType>( pi->data( Type ).toInt() );
if ( type == SourcesModel::PlaylistSource && ptr == qlonglong( pl->data() ) ) if ( type == SourcesModel::PlaylistSource && ptr == qlonglong( pl->data() ) )
{ {
m_playlists.removeAll( p ); m_playlists.removeAll( p );
@@ -133,8 +133,7 @@ void
SourceTreeItem::onPlaylistLoaded( Tomahawk::PlaylistRevision revision ) SourceTreeItem::onPlaylistLoaded( Tomahawk::PlaylistRevision revision )
{ {
qlonglong ptr = reinterpret_cast<qlonglong>( sender() ); qlonglong ptr = reinterpret_cast<qlonglong>( sender() );
qDebug() << "sender ptr:" << ptr;
QStandardItem* item = m_columns.at( 0 ); QStandardItem* item = m_columns.at( 0 );
int rows = item->rowCount(); int rows = item->rowCount();
for ( int i = 0; i < rows; i++ ) for ( int i = 0; i < rows; i++ )
@@ -143,10 +142,9 @@ SourceTreeItem::onPlaylistLoaded( Tomahawk::PlaylistRevision revision )
qlonglong piptr = pi->data( PlaylistPointer ).toLongLong(); qlonglong piptr = pi->data( PlaylistPointer ).toLongLong();
playlist_ptr* pl = reinterpret_cast<playlist_ptr*>(piptr); playlist_ptr* pl = reinterpret_cast<playlist_ptr*>(piptr);
SourcesModel::SourceType type = static_cast<SourcesModel::SourceType>( pi->data( Type ).toInt() ); SourcesModel::SourceType type = static_cast<SourcesModel::SourceType>( pi->data( Type ).toInt() );
if ( type == SourcesModel::PlaylistSource && ptr == qlonglong( pl->data() ) ) if ( type == SourcesModel::PlaylistSource && ptr == qlonglong( pl->data() ) )
{ {
qDebug() << "Found normal playlist!";
pi->setEnabled( true ); pi->setEnabled( true );
m_current_revisions.insert( pl->data()->guid(), revision.revisionguid ); m_current_revisions.insert( pl->data()->guid(), revision.revisionguid );
} }
@@ -154,6 +152,38 @@ SourceTreeItem::onPlaylistLoaded( Tomahawk::PlaylistRevision revision )
} }
void
SourceTreeItem::onPlaylistChanged()
{
qlonglong ptr = reinterpret_cast<qlonglong>( sender() );
QStandardItem* item = m_columns.at( 0 );
int rows = item->rowCount();
for ( int i = 0; i < rows; i++ )
{
QStandardItem* pi = item->child( i );
SourcesModel::SourceType type = static_cast<SourcesModel::SourceType>( pi->data( Type ).toInt() );
if ( type == SourcesModel::PlaylistSource )
{
qlonglong piptr = pi->data( PlaylistPointer ).toLongLong();
playlist_ptr* pl = reinterpret_cast<playlist_ptr*>(piptr);
if ( ptr == qlonglong( pl->data() ) )
pi->setText( pl->data()->title() );
}
if ( type == SourcesModel::DynamicPlaylistSource )
{
qlonglong piptr = pi->data( DynamicPlaylistPointer ).toLongLong();
dynplaylist_ptr* pl = reinterpret_cast<dynplaylist_ptr*>(piptr);
if ( ptr == qlonglong( pl->data() ) )
pi->setText( pl->data()->title() );
}
}
}
void void
SourceTreeItem::onDynamicPlaylistsAdded( const QList< dynplaylist_ptr >& playlists ) SourceTreeItem::onDynamicPlaylistsAdded( const QList< dynplaylist_ptr >& playlists )
{ {
@@ -162,13 +192,14 @@ SourceTreeItem::onDynamicPlaylistsAdded( const QList< dynplaylist_ptr >& playlis
{ {
m_dynplaylists.append( p ); m_dynplaylists.append( p );
qlonglong ptr = reinterpret_cast<qlonglong>( &m_dynplaylists.last() ); qlonglong ptr = reinterpret_cast<qlonglong>( &m_dynplaylists.last() );
// qDebug() << "Setting dynamic ptr to:" << ptr;
connect( p.data(), SIGNAL( dynamicRevisionLoaded( Tomahawk::DynamicPlaylistRevision) ), connect( p.data(), SIGNAL( dynamicRevisionLoaded( Tomahawk::DynamicPlaylistRevision) ),
SLOT( onDynamicPlaylistLoaded( Tomahawk::DynamicPlaylistRevision ) ), SLOT( onDynamicPlaylistLoaded( Tomahawk::DynamicPlaylistRevision ) ), Qt::QueuedConnection );
Qt::QueuedConnection); connect( p.data(), SIGNAL( changed() ),
SLOT( onPlaylistChanged() ), Qt::QueuedConnection );
// qDebug() << "Dynamic Playlist added:" << p->title() << p->creator() << p->info() << p->currentrevision() << ptr; // qDebug() << "Dynamic Playlist added:" << p->title() << p->creator() << p->info() << p->currentrevision() << ptr;
playlistAddedInternal( ptr, p, true ); playlistAddedInternal( ptr, p, true );
} }
} }
@@ -182,7 +213,7 @@ SourceTreeItem::onDynamicPlaylistsDeleted( const QList< dynplaylist_ptr >& playl
{ {
qlonglong ptr = qlonglong( p.data() ); qlonglong ptr = qlonglong( p.data() );
// qDebug() << "dynamic playlist removed:" << p->title() << p->creator() << p->info() << ptr; // qDebug() << "dynamic playlist removed:" << p->title() << p->creator() << p->info() << ptr;
QStandardItem* item = m_columns.at( 0 ); QStandardItem* item = m_columns.at( 0 );
int rows = item->rowCount(); int rows = item->rowCount();
for ( int i = rows - 1; i >= 0; i-- ) for ( int i = rows - 1; i >= 0; i-- )
@@ -191,7 +222,8 @@ SourceTreeItem::onDynamicPlaylistsDeleted( const QList< dynplaylist_ptr >& playl
qlonglong piptr = pi->data( DynamicPlaylistPointer ).toLongLong(); qlonglong piptr = pi->data( DynamicPlaylistPointer ).toLongLong();
dynplaylist_ptr* pl = reinterpret_cast<dynplaylist_ptr*>(piptr); dynplaylist_ptr* pl = reinterpret_cast<dynplaylist_ptr*>(piptr);
SourcesModel::SourceType type = static_cast<SourcesModel::SourceType>( pi->data( Type ).toInt() ); SourcesModel::SourceType type = static_cast<SourcesModel::SourceType>( pi->data( Type ).toInt() );
//qDebug() << "Deleting dynamic playlsit:" << pl->isNull();
//qDebug() << "Deleting dynamic playlist:" << pl->isNull();
if ( type == SourcesModel::DynamicPlaylistSource && ptr == qlonglong( pl->data() ) ) if ( type == SourcesModel::DynamicPlaylistSource && ptr == qlonglong( pl->data() ) )
{ {
m_dynplaylists.removeAll( p ); m_dynplaylists.removeAll( p );
@@ -206,7 +238,7 @@ void
SourceTreeItem::onDynamicPlaylistLoaded( DynamicPlaylistRevision revision ) SourceTreeItem::onDynamicPlaylistLoaded( DynamicPlaylistRevision revision )
{ {
qlonglong ptr = reinterpret_cast<qlonglong>( sender() ); qlonglong ptr = reinterpret_cast<qlonglong>( sender() );
QStandardItem* item = m_columns.at( 0 ); QStandardItem* item = m_columns.at( 0 );
int rows = item->rowCount(); int rows = item->rowCount();
for ( int i = 0; i < rows; i++ ) for ( int i = 0; i < rows; i++ )
@@ -215,10 +247,9 @@ SourceTreeItem::onDynamicPlaylistLoaded( DynamicPlaylistRevision revision )
qlonglong piptr = pi->data( DynamicPlaylistPointer ).toLongLong(); qlonglong piptr = pi->data( DynamicPlaylistPointer ).toLongLong();
playlist_ptr* pl = reinterpret_cast<playlist_ptr*>(piptr); playlist_ptr* pl = reinterpret_cast<playlist_ptr*>(piptr);
SourcesModel::SourceType type = static_cast<SourcesModel::SourceType>( pi->data( Type ).toInt() ); SourcesModel::SourceType type = static_cast<SourcesModel::SourceType>( pi->data( Type ).toInt() );
// qDebug() << "found dynamic playlist:" << (*pl)->title() << type;
if ( type == SourcesModel::DynamicPlaylistSource && ptr == qlonglong( pl->data() ) ) if ( type == SourcesModel::DynamicPlaylistSource && ptr == qlonglong( pl->data() ) )
{ {
//qDebug() << "Found dynamicplaylist!";
pi->setEnabled( true ); pi->setEnabled( true );
m_current_dynamic_revisions.insert( pl->data()->guid(), revision.revisionguid ); m_current_dynamic_revisions.insert( pl->data()->guid(), revision.revisionguid );
} }
@@ -235,10 +266,10 @@ void SourceTreeItem::playlistAddedInternal( qlonglong ptr, const Tomahawk::playl
subitem->setData( ptr, dynamic ? DynamicPlaylistPointer : PlaylistPointer ); subitem->setData( ptr, dynamic ? DynamicPlaylistPointer : PlaylistPointer );
subitem->setData( dynamic ? SourcesModel::DynamicPlaylistSource : SourcesModel::PlaylistSource, Type ); subitem->setData( dynamic ? SourcesModel::DynamicPlaylistSource : SourcesModel::PlaylistSource, Type );
subitem->setData( (qlonglong)this, SourceItemPointer ); subitem->setData( (qlonglong)this, SourceItemPointer );
m_columns.at( 0 )->appendRow( subitem ); m_columns.at( 0 )->appendRow( subitem );
// Q_ASSERT( qobject_cast<QTreeView*>((parent()->parent()) ) ); // Q_ASSERT( qobject_cast<QTreeView*>((parent()->parent()) ) );
// qobject_cast<QTreeView*>((parent()->parent()))->expandAll(); // qobject_cast<QTreeView*>((parent()->parent()))->expandAll();
p->loadRevision(); p->loadRevision();
} }

View File

@@ -47,13 +47,15 @@ private slots:
void onPlaylistsAdded( const QList<Tomahawk::playlist_ptr>& playlists ); void onPlaylistsAdded( const QList<Tomahawk::playlist_ptr>& playlists );
void onPlaylistsDeleted( const QList<Tomahawk::playlist_ptr>& playlists ); void onPlaylistsDeleted( const QList<Tomahawk::playlist_ptr>& playlists );
void onPlaylistLoaded( Tomahawk::PlaylistRevision revision ); void onPlaylistLoaded( Tomahawk::PlaylistRevision revision );
void onPlaylistChanged();
void onDynamicPlaylistsAdded( const QList<Tomahawk::dynplaylist_ptr>& playlists ); void onDynamicPlaylistsAdded( const QList<Tomahawk::dynplaylist_ptr>& playlists );
void onDynamicPlaylistsDeleted( const QList<Tomahawk::dynplaylist_ptr>& playlists ); void onDynamicPlaylistsDeleted( const QList<Tomahawk::dynplaylist_ptr>& playlists );
void onDynamicPlaylistLoaded( Tomahawk::DynamicPlaylistRevision revision ); void onDynamicPlaylistLoaded( Tomahawk::DynamicPlaylistRevision revision );
private: private:
void playlistAddedInternal( qlonglong ptr, const Tomahawk::playlist_ptr& pl, bool dynamic ); void playlistAddedInternal( qlonglong ptr, const Tomahawk::playlist_ptr& pl, bool dynamic );
QList<QStandardItem*> m_columns; QList<QStandardItem*> m_columns;
Tomahawk::source_ptr m_source; Tomahawk::source_ptr m_source;
SourceTreeItemWidget* m_widget; SourceTreeItemWidget* m_widget;

View File

@@ -407,8 +407,8 @@ TomahawkApp::removeScriptResolver( const QString& path )
foreach( ScriptResolver* r, m_scriptResolvers ) { foreach( ScriptResolver* r, m_scriptResolvers ) {
if( r->exe() == path ) { if( r->exe() == path ) {
m_scriptResolvers.removeAll( r ); m_scriptResolvers.removeAll( r );
connect( r, SIGNAL( finished() ), r, SLOT( deleteLater() ) );
delete r; r->stop();
return; return;
} }
} }
@@ -422,7 +422,7 @@ TomahawkApp::initLocalCollection()
src->addCollection( coll ); src->addCollection( coll );
SourceList::instance()->setLocal( src ); SourceList::instance()->setLocal( src );
src->collection()->tracks(); // src->collection()->tracks();
// to make the stats signal be emitted by our local source // to make the stats signal be emitted by our local source
// this will update the sidebar, etc. // this will update the sidebar, etc.

View File

@@ -39,6 +39,10 @@
#include "playlist/dynamic/GeneratorInterface.h" #include "playlist/dynamic/GeneratorInterface.h"
#include "scanmanager.h" #include "scanmanager.h"
#ifdef Q_OS_WIN32
#include <qtsparkle/Updater>
#endif
using namespace Tomahawk; using namespace Tomahawk;
@@ -123,11 +127,25 @@ TomahawkWindow::TomahawkWindow( QWidget* parent )
toolbar->setIconSize( QSize( 32, 32 ) ); toolbar->setIconSize( QSize( 32, 32 ) );
toolbar->setToolButtonStyle( Qt::ToolButtonFollowStyle ); toolbar->setToolButtonStyle( Qt::ToolButtonFollowStyle );
toolbar->installEventFilter( new WidgetDragFilter( toolbar ) ); toolbar->installEventFilter( new WidgetDragFilter( toolbar ) );
#if defined( Q_OS_DARWIN ) && defined( HAVE_SPARKLE ) #if defined( Q_OS_DARWIN ) && defined( HAVE_SPARKLE )
QAction* checkForUpdates = ui->menu_Help->addAction( tr( "Check for updates...") ); QAction* checkForUpdates = ui->menu_Help->addAction( tr( "Check for updates...") );
checkForUpdates->setMenuRole( QAction::ApplicationSpecificRole ); checkForUpdates->setMenuRole( QAction::ApplicationSpecificRole );
connect(checkForUpdates, SIGNAL( triggered( bool ) ), SLOT( checkForUpdates() ) ); connect(checkForUpdates, SIGNAL( triggered( bool ) ), SLOT( checkForUpdates() ) );
#elif defined( WIN32 )
QUrl updaterUrl;
#ifdef DEBUG_BUILD
updaterUrl.setUrl( "http://download.tomahawk-player.org/sparklewin-debug" );
#else
updaterUrl.setUrl( "http://download.tomahawk-player.org/sparklewin" );
#endif
qtsparkle::Updater* updater = new qtsparkle::Updater( updaterUrl, this );
updater->SetNetworkAccessManager( TomahawkUtils::nam() );
updater->SetVersion( VERSION );
ui->menu_Help->addSeparator();
QAction* checkForUpdates = ui->menu_Help->addAction( tr( "Check for updates...") );
connect( checkForUpdates, SIGNAL( triggered() ), updater, SLOT( CheckNow() ) );
#endif #endif
m_backAvailable = toolbar->addAction( QIcon( RESPATH "images/back.png" ), tr( "Back" ), PlaylistManager::instance(), SLOT( historyBack() ) ); m_backAvailable = toolbar->addAction( QIcon( RESPATH "images/back.png" ), tr( "Back" ), PlaylistManager::instance(), SLOT( historyBack() ) );
@@ -163,12 +181,33 @@ TomahawkWindow::loadSettings()
{ {
TomahawkSettings* s = TomahawkSettings::instance(); TomahawkSettings* s = TomahawkSettings::instance();
// Workaround for broken window geometry restoring on Qt Cocoa when setUnifiedTitleAndToolBarOnMac is true.
// See http://bugreports.qt.nokia.com/browse/QTBUG-3116 and
// http://lists.qt.nokia.com/pipermail/qt-interest/2009-August/011491.html
// for the 'fix'
#ifdef QT_MAC_USE_COCOA
bool workaround = !isVisible();
if( workaround ) {
// make "invisible"
setWindowOpacity( 0 );
// let Qt update its frameStruts
show();
}
#endif
if ( !s->mainWindowGeometry().isEmpty() ) if ( !s->mainWindowGeometry().isEmpty() )
restoreGeometry( s->mainWindowGeometry() ); restoreGeometry( s->mainWindowGeometry() );
if ( !s->mainWindowState().isEmpty() ) if ( !s->mainWindowState().isEmpty() )
restoreState( s->mainWindowState() ); restoreState( s->mainWindowState() );
if ( !s->mainWindowSplitterState().isEmpty() ) if ( !s->mainWindowSplitterState().isEmpty() )
ui->splitter->restoreState( s->mainWindowSplitterState() ); ui->splitter->restoreState( s->mainWindowSplitterState() );
#ifdef QT_MAC_USE_COCOA
if( workaround ) {
// Make it visible again
setWindowOpacity( 1 );
}
#endif
} }
@@ -329,6 +368,7 @@ TomahawkWindow::createAutomaticPlaylist()
dynplaylist_ptr playlist = DynamicPlaylist::create( author, id, name, info, creator, false ); dynplaylist_ptr playlist = DynamicPlaylist::create( author, id, name, info, creator, false );
playlist->setMode( Static ); playlist->setMode( Static );
playlist->createNewRevision( uuid(), playlist->currentrevision(), playlist->type(), playlist->generator()->controls(), playlist->entries() ); playlist->createNewRevision( uuid(), playlist->currentrevision(), playlist->type(), playlist->generator()->controls(), playlist->entries() );
PlaylistManager::instance()->show( playlist );
} }
@@ -347,6 +387,7 @@ TomahawkWindow::createStation()
dynplaylist_ptr playlist = DynamicPlaylist::create( author, id, name, info, creator, false ); dynplaylist_ptr playlist = DynamicPlaylist::create( author, id, name, info, creator, false );
playlist->setMode( OnDemand ); playlist->setMode( OnDemand );
playlist->createNewRevision( uuid(), playlist->currentrevision(), playlist->type(), playlist->generator()->controls() ); playlist->createNewRevision( uuid(), playlist->currentrevision(), playlist->type(), playlist->generator()->controls() );
PlaylistManager::instance()->show( playlist );
} }
@@ -425,7 +466,7 @@ TomahawkWindow::showAboutTomahawk()
{ {
QMessageBox::about( this, "About Tomahawk", QMessageBox::about( this, "About Tomahawk",
tr( "<h2><b>Tomahawk %1</h2>Copyright 2010, 2011<br/>Christian Muehlhaeuser &lt;muesli@tomahawk-player.org&gt;<br/><br/>" tr( "<h2><b>Tomahawk %1</h2>Copyright 2010, 2011<br/>Christian Muehlhaeuser &lt;muesli@tomahawk-player.org&gt;<br/><br/>"
"Thanks to: Leo Franchi, Jeff Mitchell, Dominik Schmidt, Alejandro Wainzinger, Harald Sitter and Steve Robertson" ) "Thanks to: Leo Franchi, Jeff Mitchell, Dominik Schmidt, Jason Herskowitz, Alejandro Wainzinger, Harald Sitter and Steve Robertson" )
.arg( qApp->applicationVersion() ) ); .arg( qApp->applicationVersion() ) );
} }

View File

@@ -1,10 +1,11 @@
#include "api_v1.h" #include "api_v1.h"
#include <QHash>
void void
Api_v1::auth_1( QxtWebRequestEvent* event ) Api_v1::auth_1( QxtWebRequestEvent* event, QString arg )
{ {
qDebug() << "AUTH_1 HTTP" << event->url.toString(); qDebug() << "AUTH_1 HTTP" << event->url.toString() << arg;
if ( !event->url.hasQueryItem( "website" ) || !event->url.hasQueryItem( "name" ) ) if ( !event->url.hasQueryItem( "website" ) || !event->url.hasQueryItem( "name" ) )
{ {
@@ -38,29 +39,37 @@ Api_v1::auth_1( QxtWebRequestEvent* event )
void void
Api_v1::auth_2( QxtWebRequestEvent* event ) Api_v1::auth_2( QxtWebRequestEvent* event, QString arg )
{ {
qDebug() << "AUTH_2 HTTP" << event->url.toString(); qDebug() << "AUTH_2 HTTP" << event->url.toString() << arg;
QUrl url = event->url; QString params = QUrl::fromPercentEncoding( event->content->readAll() );
url.setEncodedQuery( event->content->readAll() ); params = params.mid( params.indexOf( '?' ) );
QStringList pieces = params.split( '&' );
if( !url.hasQueryItem( "website" ) || !url.hasQueryItem( "name" ) || !url.hasQueryItem( "formtoken" ) ) QHash< QString, QString > queryItems;
foreach( const QString& part, pieces ) {
QStringList keyval = part.split( '=' );
if( keyval.size() == 2 )
queryItems.insert( keyval.first(), keyval.last() );
else
qDebug() << "Failed parsing url parameters: " << part;
}
qDebug() << "has query items:" << pieces;
if( !params.contains( "website" ) || !params.contains( "name" ) || !params.contains( "formtoken" ) )
{ {
qDebug() << "Malformed HTTP resolve request"; qDebug() << "Malformed HTTP resolve request";
qDebug() << url.hasQueryItem( "website" ) << url.hasQueryItem( "name" ) << url.hasQueryItem( "formtoken" );
send404( event ); send404( event );
return; return;
} }
QString website = QUrl::fromPercentEncoding( url.queryItemValue( "website" ).toUtf8() ); QString website = queryItems[ "website" ];
QString name = QUrl::fromPercentEncoding( url.queryItemValue( "name" ).toUtf8() ); QString name = queryItems[ "name" ];
QByteArray authtoken = uuid().toLatin1(); QByteArray authtoken = uuid().toLatin1();
qDebug() << "HEADERS:" << event->headers; qDebug() << "HEADERS:" << event->headers;
if( !url.hasQueryItem( "receiverurl" ) && url.queryItemValue( "receiverurl" ).isEmpty() ) if( !queryItems.contains( "receiverurl" ) || queryItems.value( "receiverurl" ).isEmpty() )
{ {
//no receiver url, so do it ourselves //no receiver url, so do it ourselves
QString receiverUrl = QUrl::fromPercentEncoding( url.queryItemValue( "receiverurl" ).toUtf8() ); if( queryItems.contains( "json" ) )
if( url.hasQueryItem( "json" ) )
{ {
QVariantMap m; QVariantMap m;
m[ "authtoken" ] = authtoken; m[ "authtoken" ] = authtoken;
@@ -71,16 +80,16 @@ Api_v1::auth_2( QxtWebRequestEvent* event )
{ {
QString authPage = RESPATH "www/auth.na.html"; QString authPage = RESPATH "www/auth.na.html";
QHash< QString, QString > args; QHash< QString, QString > args;
args[ "authcode" ] = authPage; args[ "authcode" ] = authtoken;
args[ "website" ] = QUrl::fromPercentEncoding( url.queryItemValue( "website" ).toUtf8() ); args[ "website" ] = website;
args[ "name" ] = QUrl::fromPercentEncoding( url.queryItemValue( "name" ).toUtf8() ); args[ "name" ] = name;
sendWebpageWithArgs( event, authPage, args ); sendWebpageWithArgs( event, authPage, args );
} }
} }
else else
{ {
// do what the client wants // do what the client wants
QUrl receiverurl = QUrl( url.queryItemValue( "receiverurl" ).toUtf8(), QUrl::TolerantMode ); QUrl receiverurl = QUrl( queryItems.value( "receiverurl" ), QUrl::TolerantMode );
receiverurl.addEncodedQueryItem( "authtoken", "#" + authtoken ); receiverurl.addEncodedQueryItem( "authtoken", "#" + authtoken );
qDebug() << "Got receiver url:" << receiverurl.toString(); qDebug() << "Got receiver url:" << receiverurl.toString();
@@ -308,6 +317,10 @@ Api_v1::sendWebpageWithArgs( QxtWebRequestEvent* event, const QString& filenameS
{ {
html.replace( QString( "<%%1%>" ).arg( param.toUpper() ), args.value( param ).toUtf8() ); html.replace( QString( "<%%1%>" ).arg( param.toUpper() ), args.value( param ).toUtf8() );
} }
// workaround for receiverurl
if( !args.keys().contains( "URL" ) )
html.replace( QString( "<%URL%>" ).toLatin1(), QByteArray() );
QxtWebPageEvent* e = new QxtWebPageEvent( event->sessionID, event->requestID, html ); QxtWebPageEvent* e = new QxtWebPageEvent( event->sessionID, event->requestID, html );
postEvent( e ); postEvent( e );

View File

@@ -41,8 +41,8 @@ public:
public slots: public slots:
// authenticating uses /auth_1 // authenticating uses /auth_1
// we redirect to /auth_2 for the callback // we redirect to /auth_2 for the callback
void auth_1( QxtWebRequestEvent* event ); void auth_1( QxtWebRequestEvent* event, QString unused = QString() );
void auth_2( QxtWebRequestEvent* event ); void auth_2( QxtWebRequestEvent* event, QString unused = QString() );
// all v1 api calls go to /api/ // all v1 api calls go to /api/
void api( QxtWebRequestEvent* event ); void api( QxtWebRequestEvent* event );