};
////////////////////////////////////////////////////////////////////
-
Install::Install(PackageRef aPkg, const SGPath& aPath) :
m_package(aPkg),
m_path(aPath),
- m_download(NULL)
+ m_download(NULL),
+ _status(Delegate::FAIL_IN_PROGRESS)
{
parseRevision();
}
{
Dir d(m_path);
d.remove(true);
- delete this;
}
+//------------------------------------------------------------------------------
+Install* Install::done(const Callback& cb)
+{
+ if( _status == Delegate::FAIL_SUCCESS )
+ cb(this);
+ else
+ _cb_done = cb;
+
+ return this;
+}
+
+//------------------------------------------------------------------------------
+Install* Install::fail(const Callback& cb)
+{
+ if( _status != Delegate::FAIL_SUCCESS
+ && _status != Delegate::FAIL_IN_PROGRESS )
+ cb(this);
+ else
+ _cb_fail = cb;
+
+ return this;
+}
+
+//------------------------------------------------------------------------------
+Install* Install::always(const Callback& cb)
+{
+ if( _status != Delegate::FAIL_IN_PROGRESS )
+ cb(this);
+ else
+ _cb_always = cb;
+
+ return this;
+}
+
+//------------------------------------------------------------------------------
+Install* Install::progress(const ProgressCallback& cb)
+{
+ _cb_progress = cb;
+ return this;
+}
+
+//------------------------------------------------------------------------------
void Install::installResult(Delegate::FailureCode aReason)
{
if (aReason == Delegate::FAIL_SUCCESS) {
m_package->catalog()->root()->finishInstall(this);
+ if( _cb_done )
+ _cb_done(this);
} else {
m_package->catalog()->root()->failedInstall(this, aReason);
+ if( _cb_fail )
+ _cb_fail(this);
}
+
+ if( _cb_always )
+ _cb_always(this);
}
-
+
+//------------------------------------------------------------------------------
void Install::installProgress(unsigned int aBytes, unsigned int aTotal)
{
m_package->catalog()->root()->installProgress(this, aBytes, aTotal);
+ if( _cb_progress )
+ _cb_progress(this, aBytes, aTotal);
}
-
+
} // of namespace pkg
} // of namespace simgear
#include <simgear/structure/SGReferenced.hxx>
#include <simgear/structure/SGSharedPtr.hxx>
+#include <boost/bind.hpp>
+#include <boost/function.hpp>
+
namespace simgear
{
class Install : public SGReferenced
{
public:
+ typedef boost::function<void(Install*)> Callback;
+ typedef boost::function<void(Install*, unsigned int, unsigned int)>
+ ProgressCallback;
+
/**
* create from a directory on disk, or fail.
*/
void startUpdate();
void uninstall();
+
+ /**
+ * Set the handler to be called when the installation successfully
+ * completes.
+ *
+ * @note If the installation is already complete, the handler is called
+ * immediately.
+ */
+ Install* done(const Callback& cb);
+
+ template<class C>
+ Install* done(C* instance, void (C::*mem_func)(Install*))
+ {
+ return done(boost::bind(mem_func, instance, _1));
+ }
+
+ /**
+ * Set the handler to be called when the installation fails or is aborted.
+ *
+ * @note If the installation has already failed, the handler is called
+ * immediately.
+ */
+ Install* fail(const Callback& cb);
+
+ template<class C>
+ Install* fail(C* instance, void (C::*mem_func)(Install*))
+ {
+ return fail(boost::bind(mem_func, instance, _1));
+ }
+
+ /**
+ * Set the handler to be called when the installation either successfully
+ * completes or fails.
+ *
+ * @note If the installation is already complete or has already failed, the
+ * handler is called immediately.
+ */
+ Install* always(const Callback& cb);
+
+ template<class C>
+ Install* always(C* instance, void (C::*mem_func)(Install*))
+ {
+ return always(boost::bind(mem_func, instance, _1));
+ }
-// boost signals time?
- // failure
- // progress
- // completed
-
+ /**
+ * Set the handler to be called during downloading the installation file
+ * indicating the progress of the download.
+ *
+ */
+ Install* progress(const ProgressCallback& cb);
+
+ template<class C>
+ Install* progress(C* instance,
+ void (C::*mem_func)(Install*, unsigned int, unsigned int))
+ {
+ return progress(boost::bind(mem_func, instance, _1, _2, _3));
+ }
+
private:
friend class Package;
SGPath m_path; ///< installation point on disk
PackageArchiveDownloader* m_download;
+
+ Delegate::FailureCode _status;
+
+ Callback _cb_done,
+ _cb_fail,
+ _cb_always;
+ ProgressCallback _cb_progress;
+
};