[Telepathy-commits] [telepathy-qt4/master] Import library code for a prototype Qt4 Telepathy convenience library

Simon McVittie simon.mcvittie at collabora.co.uk
Thu Nov 20 09:48:55 PST 2008


This will be merged into the main telepathy-qt4 code over time; the goal
is for the Prototype directory to end up either empty, or populated with
trivial wrapper classes.
---
 TelepathyQt4/Makefile.am                        |   21 +-
 TelepathyQt4/Prototype/Account.cpp              |  274 +++++++
 TelepathyQt4/Prototype/Account.h                |  172 ++++
 TelepathyQt4/Prototype/AccountManager.cpp       |  310 ++++++++
 TelepathyQt4/Prototype/AccountManager.h         |  141 ++++
 TelepathyQt4/Prototype/AvatarManager.cpp        |  320 ++++++++
 TelepathyQt4/Prototype/AvatarManager.h          |  174 ++++
 TelepathyQt4/Prototype/CapabilitiesManager.cpp  |  321 ++++++++
 TelepathyQt4/Prototype/CapabilitiesManager.h    |  129 +++
 TelepathyQt4/Prototype/ChatChannel.cpp          |  223 ++++++
 TelepathyQt4/Prototype/ChatChannel.h            |  119 +++
 TelepathyQt4/Prototype/Client/ChannelHandler    |    6 +
 TelepathyQt4/Prototype/Connection.cpp           |  434 ++++++++++
 TelepathyQt4/Prototype/Connection.h             |  256 ++++++
 TelepathyQt4/Prototype/ConnectionFacade.cpp     |  265 +++++++
 TelepathyQt4/Prototype/ConnectionFacade.h       |  137 ++++
 TelepathyQt4/Prototype/Constants                |    6 +
 TelepathyQt4/Prototype/Contact.cpp              |  189 +++++
 TelepathyQt4/Prototype/Contact.h                |  247 ++++++
 TelepathyQt4/Prototype/ContactManager.cpp       |  965 +++++++++++++++++++++++
 TelepathyQt4/Prototype/ContactManager.h         |  304 +++++++
 TelepathyQt4/Prototype/DBusInterface.cpp        |   47 ++
 TelepathyQt4/Prototype/DBusInterface.h          |   51 ++
 TelepathyQt4/Prototype/Makefile.am              |  161 ++++
 TelepathyQt4/Prototype/PresenceManager.cpp      |  620 +++++++++++++++
 TelepathyQt4/Prototype/PresenceManager.h        |  151 ++++
 TelepathyQt4/Prototype/StreamedMediaChannel.cpp |  578 ++++++++++++++
 TelepathyQt4/Prototype/StreamedMediaChannel.h   |  229 ++++++
 TelepathyQt4/Prototype/TpQt4Prototype.pc.in     |   11 +
 TelepathyQt4/Prototype/Types                    |    6 +
 TelepathyQt4/Prototype/all.xml                  |    9 +
 TelepathyQt4/Prototype/channel-handler.xml      |    9 +
 TelepathyQt4/Prototype/constants.h              |   27 +
 TelepathyQt4/Prototype/types.cpp                |   22 +
 TelepathyQt4/Prototype/types.h                  |   27 +
 configure.ac                                    |    2 +
 36 files changed, 6956 insertions(+), 7 deletions(-)
 create mode 100644 TelepathyQt4/Prototype/Account.cpp
 create mode 100644 TelepathyQt4/Prototype/Account.h
 create mode 100644 TelepathyQt4/Prototype/AccountManager.cpp
 create mode 100644 TelepathyQt4/Prototype/AccountManager.h
 create mode 100644 TelepathyQt4/Prototype/AvatarManager.cpp
 create mode 100644 TelepathyQt4/Prototype/AvatarManager.h
 create mode 100644 TelepathyQt4/Prototype/CapabilitiesManager.cpp
 create mode 100644 TelepathyQt4/Prototype/CapabilitiesManager.h
 create mode 100644 TelepathyQt4/Prototype/ChatChannel.cpp
 create mode 100644 TelepathyQt4/Prototype/ChatChannel.h
 create mode 100644 TelepathyQt4/Prototype/Client/ChannelHandler
 create mode 100644 TelepathyQt4/Prototype/Connection.cpp
 create mode 100644 TelepathyQt4/Prototype/Connection.h
 create mode 100644 TelepathyQt4/Prototype/ConnectionFacade.cpp
 create mode 100644 TelepathyQt4/Prototype/ConnectionFacade.h
 create mode 100644 TelepathyQt4/Prototype/Constants
 create mode 100644 TelepathyQt4/Prototype/Contact.cpp
 create mode 100644 TelepathyQt4/Prototype/Contact.h
 create mode 100644 TelepathyQt4/Prototype/ContactManager.cpp
 create mode 100644 TelepathyQt4/Prototype/ContactManager.h
 create mode 100644 TelepathyQt4/Prototype/DBusInterface.cpp
 create mode 100644 TelepathyQt4/Prototype/DBusInterface.h
 create mode 100644 TelepathyQt4/Prototype/Makefile.am
 create mode 100644 TelepathyQt4/Prototype/PresenceManager.cpp
 create mode 100644 TelepathyQt4/Prototype/PresenceManager.h
 create mode 100644 TelepathyQt4/Prototype/StreamedMediaChannel.cpp
 create mode 100644 TelepathyQt4/Prototype/StreamedMediaChannel.h
 create mode 100644 TelepathyQt4/Prototype/TpQt4Prototype.pc.in
 create mode 100644 TelepathyQt4/Prototype/Types
 create mode 100644 TelepathyQt4/Prototype/all.xml
 create mode 100644 TelepathyQt4/Prototype/channel-handler.xml
 create mode 100644 TelepathyQt4/Prototype/constants.h
 create mode 100644 TelepathyQt4/Prototype/types.cpp
 create mode 100644 TelepathyQt4/Prototype/types.h

diff --git a/TelepathyQt4/Makefile.am b/TelepathyQt4/Makefile.am
index 0ac9f23..86022a0 100644
--- a/TelepathyQt4/Makefile.am
+++ b/TelepathyQt4/Makefile.am
@@ -1,3 +1,6 @@
+# We need to build this directory before the Prototype subdirectory
+SUBDIRS = . Prototype
+
 tpqt4includedir=$(includedir)/telepathy-1.0/TelepathyQt4
 tpqt4clientincludedir=$(tpqt4includedir)/Client
 genincludedir=$(tpqt4includedir)/_gen
@@ -142,15 +145,17 @@ _gen/spec-stamp: $(wildcard $(top_srcdir)/spec/*.xml)
 _gen/stable-stamp: $(wildcard *.xml) _gen/spec-stamp
 	touch $@
 
-_gen/stable-spec.xml: stable-interfaces.xml _gen/stable-stamp \
-	../tools/xincludator.py
+_gen/stable-spec.xml: $(srcdir)/stable-interfaces.xml _gen/stable-stamp \
+	$(top_srcdir)/tools/xincludator.py \
+	Makefile.am
 	$(PYTHON) $(top_srcdir)/tools/xincludator.py \
 		$< > $@
 
 # Things generated from the whole spec at once
 
 _gen/constants.h: _gen/stable-spec.xml \
-		../tools/qt4-constants-gen.py
+		$(top_srcdir)/tools/qt4-constants-gen.py \
+		Makefile.am
 	$(PYTHON) $(top_srcdir)/tools/qt4-constants-gen.py \
 		--namespace='Telepathy' \
 		--str-constant-prefix='TELEPATHY_' \
@@ -158,7 +163,8 @@ _gen/constants.h: _gen/stable-spec.xml \
 		> $@.tmp && mv $@.tmp $@
 
 _gen/types.h _gen/types-body.hpp: _gen/stable-spec.xml \
-		../tools/qt4-types-gen.py
+		$(top_srcdir)/tools/qt4-types-gen.py \
+		Makefile.am
 	$(PYTHON) $(top_srcdir)/tools/qt4-types-gen.py \
 		--namespace='Telepathy' \
 		--declfile='_gen/types.h' \
@@ -169,13 +175,14 @@ _gen/types.h _gen/types-body.hpp: _gen/stable-spec.xml \
 
 # Things generated per interface group
 
-_gen/spec-%.xml: %.xml ../tools/xincludator.py _gen/spec-stamp
+_gen/spec-%.xml: %.xml $(top_srcdir)/tools/xincludator.py _gen/spec-stamp
 	$(PYTHON) $(top_srcdir)/tools/xincludator.py \
 		$< > $@
 
 _gen/cli-%.h _gen/cli-%-body.hpp: _gen/spec-%.xml \
 		_gen/stable-spec.xml \
-		../tools/qt4-client-gen.py
+		$(top_srcdir)/tools/qt4-client-gen.py \
+		Makefile.am
 	set -e; \
 	namespace='Telepathy::Client'; \
 	group= ; \
@@ -218,7 +225,7 @@ _gen/cli-%.h _gen/cli-%-body.hpp: _gen/spec-%.xml \
 			group='clientprops'; \
 			prettyinclude='Properties';; \
 	esac; \
-	$(PYTHON) $(srcdir)/../tools/qt4-client-gen.py \
+	$(PYTHON) $(top_srcdir)/tools/qt4-client-gen.py \
 		--group=$$group \
 		--namespace=$$namespace \
 		--typesnamespace='Telepathy' \
diff --git a/TelepathyQt4/Prototype/Account.cpp b/TelepathyQt4/Prototype/Account.cpp
new file mode 100644
index 0000000..efa1be6
--- /dev/null
+++ b/TelepathyQt4/Prototype/Account.cpp
@@ -0,0 +1,274 @@
+/*
+ * This file is part of TelepathyQt4
+ *
+ * Copyright (C) 2008 basysKom GmbH
+ * Copyright (C) 2008 Collabora Ltd. <http://www.collabora.co.uk/>
+ * Copyright (C) 2008 Nokia Corporation
+ *
+ * This library is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU Lesser General Public
+ * License as published by the Free Software Foundation; either
+ * version 2.1 of the License, or (at your option) any later version.
+ *
+ * This library is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
+ * Lesser General Public License for more details.
+ *
+ * You should have received a copy of the GNU Lesser General Public
+ * License along with this library; if not, write to the Free Software
+ * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA  02110-1301  USA
+ */
+
+#include "TelepathyQt4/Prototype/Account.h"
+
+#include <QDebug>
+#include <QMetaProperty>
+
+#include <TelepathyQt4/Client/AccountManager>
+
+#include <TelepathyQt4/Prototype/Connection.h>
+#include <TelepathyQt4/Prototype/PresenceManager.h>
+
+#define ENABLE_SALUT_WORKAROUND_ // Salut shows incorrect object path.
+
+namespace {
+    const int   g_protocolPosition = 6;
+    const int   g_connectionManagerPosition = 5;
+    const char* g_offline = "offline";
+}
+
+using namespace TpPrototype;
+
+class TpPrototype::AccountPrivate
+{
+public:
+    AccountPrivate()
+    { init(); }
+    
+    QString m_handle;
+    bool m_isValid;
+    Telepathy::Client::AccountInterface* m_pInterface;
+    QVariantMap                     m_parameters;
+    QVariantMap                     m_properties;
+    QString                         m_connectionManagerName;
+    QString                         m_protocolName;
+    QPointer<TpPrototype::Connection> m_pConnection;
+
+    void init()
+    {
+        m_isValid    = true;
+        m_pInterface = NULL;
+        m_pConnection= NULL;
+    }
+};
+
+Account::Account( const QString& handle, QObject* parent ):
+    QObject( parent ),
+    d( new AccountPrivate )
+{
+    init( handle );
+}
+
+Account::~Account()
+{
+#ifdef ENABLE_DEBUG_OUTPUT_
+    qDebug() << "D'tor Account:" << this;
+#endif
+    delete d;
+}
+
+QVariantMap Account::parameters()
+{
+    if ( d->m_parameters.isEmpty() )
+    {
+        d->m_parameters = d->m_pInterface->Parameters();
+    }
+
+    return d->m_parameters;
+}
+
+QVariantMap Account::properties()
+{
+    Q_ASSERT( d->m_pInterface );
+    if ( d->m_properties.isEmpty() )
+    {
+        for ( int i = 0; i < d->m_pInterface->metaObject()->propertyCount(); ++i )
+        {
+            const char* property_name = d->m_pInterface->metaObject()->property( i ).name();
+            if ( QString( property_name ) == "objectName" )
+            { continue; }
+            d->m_properties.insert( property_name, d->m_pInterface->property( property_name ) );
+        }
+    }
+                 
+    return d->m_properties;
+}
+
+void Account::setProperties( const QVariantMap& properties )
+{
+    // Update local property cache and save property to DBUS service
+    QStringList keys = properties.keys();
+    foreach( const QString& key, keys )
+    {
+        d->m_pInterface->setProperty( qPrintable( key ), properties.value( key ) );
+        d->m_properties.insert( key, properties.value( key ) );
+    }
+}
+
+bool Account::setParameters( const QVariantMap& parameters )
+{
+    if ( parameters.isEmpty() )
+    { return false; }
+    
+    QDBusPendingReply<> reply = d->m_pInterface->UpdateParameters( parameters, QStringList() );
+    reply.waitForFinished();
+
+    if ( !reply.isValid() )
+    {
+        QDBusError error = reply.error();
+
+        qWarning() << "setParameters: error type:" << error.type()
+                << "error name:" << error.name()
+                << "error message:" << error.message();
+
+        return false;
+    }
+
+    // Update local cache.
+    QStringList keys = parameters.keys();
+    foreach( const QString& key, keys )
+    {
+        d->m_parameters.insert( key, parameters.value( key ) );
+    }
+    // fall through..
+    return true;
+}
+
+TpPrototype::Connection* Account::connection( QObject *parent )
+{
+    if ( !d->m_pConnection )
+    {
+        d->m_pConnection = new Connection( this, parent ? parent : this );
+    }
+    return d->m_pConnection;
+}
+
+bool Account::remove()
+{
+    Q_ASSERT( d->m_pInterface );
+
+    emit signalAboutToRemove();
+    
+    QDBusPendingReply<> remove_reply = d->m_pInterface->Remove();
+    remove_reply.waitForFinished();
+
+    if ( !remove_reply.isValid() )
+    {
+        QDBusError error = remove_reply.error();
+
+        qWarning() << "Remove: error type:" << error.type()
+                << "error name:" << error.name()
+                << "error message:" << error.message();
+
+        return false;
+    }
+
+    // slotRemoved();
+
+    emit signalRemoved();
+    
+    // Fall through
+    return true;
+}
+
+bool Account::isValid()
+{
+    return d->m_isValid;
+}
+
+QString Account::connectionManagerName()
+{
+    return d->m_connectionManagerName;
+}
+
+QString Account::protocolName()
+{
+    return d->m_protocolName;
+}
+
+QString Account::currentPresence()
+{
+    if ( !connection()->presenceManager() )
+    {
+        return g_offline;
+    }
+    return connection()->presenceManager()->currentPresence().status;
+}
+
+QString Account::handle() const
+{
+    return d->m_handle;
+}
+
+Telepathy::Client::AccountInterface* Account::interface()
+{
+    return d->m_pInterface;
+}
+
+void Account::slotPropertiesChanged( const QVariantMap& properties )
+{
+#ifdef ENABLE_DEBUG_OUTPUT_
+    qDebug() << "Account::slotPropertiesChanged(): " << properties;
+#endif
+    QStringList keys = properties.keys();
+    foreach( const QString& key, keys )
+    {
+        d->m_properties.insert( key, properties.value( key ) );
+    }
+}
+
+void Account::slotRemoved()
+{
+#ifdef ENABLE_DEBUG_OUTPUT_
+    qDebug() << "Account::slotRemoved(): sender:" << sender();
+#endif
+    d->m_isValid = false;
+}
+
+void Account::init( const QString handle )
+{
+    d->m_handle = handle;
+#ifdef ENABLE_DEBUG_OUTPUT_
+    qDebug() << "Handle:" << d->m_handle;
+#endif
+    d->m_pInterface = new Telepathy::Client::AccountInterface( "org.freedesktop.Telepathy.AccountManager",
+                                                                    d->m_handle,
+                                                                    this );
+
+    QStringList object_path_elements = d->m_pInterface->path().split('/');
+#ifdef ENABLE_DEBUG_OUTPUT_
+    qDebug() << "Object path: " << d->m_pInterface->path();
+    qDebug() << "Elements   : " << object_path_elements;
+#endif
+    d->m_connectionManagerName = object_path_elements.at( g_connectionManagerPosition );
+    d->m_protocolName          = object_path_elements.at( g_protocolPosition );
+
+#ifdef ENABLE_SALUT_WORKAROUND_
+    // Salut workaround..
+    // Salut has a corrupt object path that results in an invalid protocol name
+    if ( d->m_protocolName == "local_2dxmpp" )
+    { d->m_protocolName = "local_xmpp"; }
+#endif
+
+    // "-" is not allowed on as DBus object path. Thus "-" is mapped to "_".
+    // Revert the mapping to get a correct protocol name
+    d->m_protocolName.replace( '_', '-' );
+
+    connect( d->m_pInterface, SIGNAL( AccountPropertyChanged( const QVariantMap& ) ),
+             this, SLOT( slotPropertiesChanged( const QVariantMap& ) ) );
+    connect( d->m_pInterface, SIGNAL( AccountPropertyChanged( const QVariantMap& ) ),
+             this, SIGNAL( signalPropertiesChanged( const QVariantMap& ) ) );
+    connect( d->m_pInterface, SIGNAL( Removed() ),
+             this, SLOT( slotRemoved() ) );
+}
diff --git a/TelepathyQt4/Prototype/Account.h b/TelepathyQt4/Prototype/Account.h
new file mode 100644
index 0000000..6c049f4
--- /dev/null
+++ b/TelepathyQt4/Prototype/Account.h
@@ -0,0 +1,172 @@
+/*
+ * This file is part of TelepathyQt4
+ *
+ * Copyright (C) 2008 basysKom GmbH
+ * Copyright (C) 2008 Collabora Ltd. <http://www.collabora.co.uk/>
+ * Copyright (C) 2008 Nokia Corporation
+ *
+ * This library is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU Lesser General Public
+ * License as published by the Free Software Foundation; either
+ * version 2.1 of the License, or (at your option) any later version.
+ *
+ * This library is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
+ * Lesser General Public License for more details.
+ *
+ * You should have received a copy of the GNU Lesser General Public
+ * License along with this library; if not, write to the Free Software
+ * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA  02110-1301  USA
+ */
+
+#ifndef TelepathyQt4_Prototype_Account_H_
+#define TelepathyQt4_Prototype_Account_H_
+
+#include <QObject>
+#include <QPointer>
+#include <QVariantMap>
+
+namespace Telepathy {
+namespace Client {
+class AccountInterface;
+}
+}
+
+namespace TpPrototype {
+
+class Connection;
+class AccountPrivate;
+
+/**
+ * @ingroup qt_accountmgm
+ * This class manages an account.
+ * @todo: Account should be more like QPersistantModelIndex. Thus we don't have to use pointer of it.
+ * @todo In order to allow custom extensions, we need a support to register proxies in the AccountManager
+ */
+class Account : public QObject
+{
+    Q_OBJECT
+public:
+   /**
+    * The parameters of this account.
+    * Returns a list of all parameters of this account that were explicitly set by AccountManager::createAccount().
+    * @return The properties as key,value pair.
+    */
+    QVariantMap parameters();
+
+   /**
+    * Properties of this account
+    */
+    QVariantMap properties();
+
+    /**
+     * Set Properties. Changes the given list of Properties.
+     * @param properties The list of changed or new properties.
+     */
+    void setProperties( const QVariantMap& properties );
+
+    /**
+     * Set Parameters. Changes the given list of parameters.
+     * @param parameters The list of changed or new parameters
+     * @return True if successful.
+     */
+    bool setParameters( const QVariantMap& parameters );
+
+    /**
+     * Connection.
+     * Returns a connection object that belongs to this account.<br>
+     * <b>Info:</b> This class keeps ownership of this class.
+     * @param parent The parent of this object. If NULL the connection is used as parent.
+     * @return Connection object.
+     */
+    TpPrototype::Connection* connection( QObject* parent = NULL );
+
+   /**
+    * Remove account. Removes the given account.
+    * <b>Note:</b> Although this call is synchronous, the internal book keeping of valid accounts is
+    *              updated by DBUS signals that might need some time. Thus, calling AccountManager::count() emmediately
+    *              after removing might return an incorrect value. Wait until AccountManager::signalAccountsUpdated() is emitted.
+    * @return true if remove operation was successful.
+    */
+    bool remove();
+
+    /**
+     * Validity check.
+     * Do not access any functions if this account is invalid.
+     */
+    bool isValid();
+
+    /**
+     * Get connection manager for this account.
+     * Returns the connection manager that belongs to this account
+     * @return The name of the connection manager (like gabble, ..).
+     */
+    QString connectionManagerName();
+
+    /**
+     * Get protocol for this account.
+     * Returns the protocol that belongs to this account
+     * @return The name of the protocol (like jabber, ..)
+     */
+    QString protocolName();
+    
+    /**
+     * Get the current presence.
+     * The presence for the current connection is returned.
+     * @return The current aggregated presence.
+     */
+    QString currentPresence();
+
+signals:
+    /** Property were changed. This signal is emitted when properties were changed. */
+    void signalPropertiesChanged( const QVariantMap& properties );
+
+    /** About to remove. This signal is emmitted before the account is removed. */
+    void signalAboutToRemove();
+
+    /** Removed. This signal is emmitted after the account is removed. */
+    void signalRemoved();
+
+    /** Account presence was changed. Signal is emitted after the account changed its presence state.
+     * @todo Implement this..
+     */
+    void signalPresenceChanged();
+    
+
+protected slots:
+    void slotPropertiesChanged( const QVariantMap& properties );
+    void slotRemoved();
+
+protected:
+    /**
+     * Constructor. The account manager cannot be instantiated directly. Use AccountManager::account() for it!
+     */
+    Account( const QString& handle, QObject* parent );
+    ~Account();
+
+    /**
+     * D-BUS interface.
+     * This protected access to the D-BUS interface can be used to extend this class with special features.
+     */
+    Telepathy::Client::AccountInterface* interface();
+
+    /**
+     * Returns the handle.
+     * The handle is an internal representation to access the real data. Its format should
+     * not be interpreted.
+     */
+    QString handle() const;
+    
+private:
+    void init( const QString handle );
+    
+    AccountPrivate * const d;
+    friend class AccountManager; // TODO: Remove this friend class
+    friend class AccountManagerPrivate;
+};
+
+}
+
+
+#endif
diff --git a/TelepathyQt4/Prototype/AccountManager.cpp b/TelepathyQt4/Prototype/AccountManager.cpp
new file mode 100644
index 0000000..285ea1d
--- /dev/null
+++ b/TelepathyQt4/Prototype/AccountManager.cpp
@@ -0,0 +1,310 @@
+/*
+ * This file is part of TelepathyQt4
+ *
+ * Copyright (C) 2008 basysKom GmbH
+ * Copyright (C) 2008 Collabora Ltd. <http://www.collabora.co.uk/>
+ * Copyright (C) 2008 Nokia Corporation
+ *
+ * This library is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU Lesser General Public
+ * License as published by the Free Software Foundation; either
+ * version 2.1 of the License, or (at your option) any later version.
+ *
+ * This library is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
+ * Lesser General Public License for more details.
+ *
+ * You should have received a copy of the GNU Lesser General Public
+ * License along with this library; if not, write to the Free Software
+ * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA  02110-1301  USA
+ */
+
+#include "TelepathyQt4/Prototype/AccountManager.h"
+
+#include <QCoreApplication>
+#include <QDBusObjectPath>
+#include <QDBusPendingReply>
+#include <QDebug>
+#include <QMap>
+#include <QPointer>
+
+#include <TelepathyQt4/Client/AccountManager>
+#include <TelepathyQt4/Types>
+
+#include <TelepathyQt4/Prototype/Account.h>
+
+// #define ENABLE_DEBUG_OUTPUT_
+
+using namespace TpPrototype;
+
+AccountManager* TpPrototype::AccountManager::m_pInstance = NULL;
+
+class TpPrototype::AccountManagerPrivate
+{
+public:
+    AccountManagerPrivate()
+    { init(); }
+
+    Telepathy::Client::AccountManagerInterface* m_pInterface;
+    QMap<QString, QPointer<Account> >  m_validAccountHandles;
+
+    void init()
+    {
+        m_pInterface = NULL;
+    }
+
+    void removeAccount( const QString& handle )
+    {
+        if ( m_validAccountHandles.contains( handle ) )
+        {
+            delete m_validAccountHandles.value( handle );
+            m_validAccountHandles.remove( handle );
+        }
+    }
+};
+
+AccountManager::AccountManager( QObject* parent ):
+    QObject( parent ),
+    d( new AccountManagerPrivate )
+{
+    init();
+}
+
+AccountManager* AccountManager::instance()
+{
+    if ( NULL == m_pInstance )
+    {
+        m_pInstance = new AccountManager( QCoreApplication::instance() );
+        Q_ASSERT( m_pInstance );
+    }
+
+    return m_pInstance;
+}
+
+
+AccountManager::~AccountManager()
+{
+    delete d;
+}
+
+int AccountManager::count()
+{
+    return d->m_validAccountHandles.count();
+}
+
+//  TODO: Define a accountlist container class that stores the accounts and is doing the book keeping..
+QList<QPointer<Account> > AccountManager::accountList()
+{
+    QList<QPointer<Account> > ret_list;
+
+    Account* account = NULL;
+    QStringList handles = d->m_validAccountHandles.keys(); 
+    foreach( const QString& handle, handles )
+    {
+        account = d->m_validAccountHandles.value( handle );
+        Q_ASSERT( account );
+        if ( !account )
+        {
+            qWarning() << "Found handles that points to no object!";
+            d->removeAccount( handle );
+            continue;
+        }
+        ret_list.append( QPointer<Account>( account ) );
+    }
+
+    return ret_list;
+}
+
+#if 0
+TpPrototype::Account* account( int num )
+{
+    if ( d->m_validAccountHandles.at(
+}
+#endif
+
+
+QList<QPointer<Account> > AccountManager::accountListOfEnabledAccounts()
+{
+    QList<QPointer<Account> > ret_list;
+    
+    if ( accountList().count() != 0)
+    {
+        foreach (const QPointer<Account>& account, accountList() )
+        {
+            if ( account->properties().value( "Enabled" ) == true )
+            {
+                ret_list.append( account );
+            }
+        }
+    }
+    return ret_list;
+}
+
+bool AccountManager::createAccount( const QString& connectionManager, const QString& protocol, const QString& displayName, const QVariantMap& _parameters )
+{
+    QVariantMap parameters = _parameters;
+
+    //HACK: Set server for google talk which cannot be set after the account was created.
+    //     This should be removed after fixing the create account workflow!
+    if ( parameters.value( "account" ).toString().contains( "google" ) )
+    {  parameters.insert( "server", "talk.google.com" ); }
+
+    if ( parameters.contains( "port" ) && parameters.value( "port" ).type() != QVariant::UInt )
+    {
+        qWarning() << "We got the wrong type of the port. We correct it here manually";
+        parameters.insert( "port", qvariant_cast<uint>( parameters.value( "port" ) ) );
+    }
+
+    // empty Parameterlists should not be send to create account. Otherwise strange things may happen.. 
+    if ( parameters.size() > 0 )
+    {
+        QStringList keys = parameters.keys();
+        foreach( const QString& key, keys )
+        {
+#ifdef ENABLE_DEBUG_OUTPUT_
+            qDebug() << "createAccount--> Key:" << key << "value:" << parameters.value( key );
+#endif
+            if (parameters.value(key).toString().isEmpty() )
+            {
+#ifdef ENABLE_DEBUG_OUTPUT_
+                qDebug() << "Remove Key:" << key << "value:" << parameters.value( key );
+#endif
+                parameters.remove( key );
+            }
+        }
+    }
+
+    QDBusPendingReply<QDBusObjectPath> create_reply = d->m_pInterface->CreateAccount( connectionManager,
+                                                                                      protocol,
+                                                                                      displayName,
+                                                                                      parameters );
+    create_reply.waitForFinished();
+        
+    if ( !create_reply.isValid() )
+    {
+        QDBusError error = create_reply.error();
+    
+        qWarning() << "Disconnect: error type:" << error.type()
+                << "Disconnect: error name:" << error.name()
+                << "error message:" << error.message();
+
+        return false;
+    }
+
+    // Fall through
+    return true;
+}
+
+void AccountManager::slotAccountValidityChanged( const QDBusObjectPath& account, bool valid )
+{
+#ifdef ENABLE_DEBUG_OUTPUT_
+    qDebug() << "AccountManager::slotAccountValidityChanged: " << valid;
+#endif
+    bool update_occurred = false;
+    if ( valid )
+    {
+        // Add account to the list if it is not already stored
+        if ( !d->m_validAccountHandles.contains( account.path() )
+             || !d->m_validAccountHandles.value( account.path() ) )
+        {
+#ifdef ENABLE_DEBUG_OUTPUT_
+            qDebug() << "AccountManager::slotAccountValidityChanged: Add new account to list";
+#endif
+            TpPrototype::Account* new_account = new Account( account.path(), this );
+            connect( new_account, SIGNAL( signalRemoved() ),
+                    this, SLOT( slotAccountRemoved() ) );
+            connect( new_account, SIGNAL( signalPropertiesChanged( const QVariantMap& ) ),
+                     this, SLOT( slotPropertiesChanged() ) );
+            d->m_validAccountHandles.insert( account.path(), QPointer<Account>( new_account ) );
+            update_occurred = true;
+            emit signalNewAccountAvailable( new_account );
+        }
+    }
+    else
+    {
+        if ( d->m_validAccountHandles.contains( account.path() ) )
+        {
+#ifdef ENABLE_DEBUG_OUTPUT_
+            qDebug() << "AccountManager::slotAccountValidityChanged: Remove account from list";
+#endif
+            d->removeAccount( account.path() );
+            update_occurred = true;
+        }
+    }
+    if ( update_occurred )
+    { emit signalAccountsUpdated(); }
+}
+
+void AccountManager::slotAccountRemoved( const QDBusObjectPath& account )
+{
+#ifdef ENABLE_DEBUG_OUTPUT_
+    qDebug() << "AccountManager::slotAccountRemoved() <external>";
+#endif
+    d->removeAccount( account.path() );
+    emit signalAccountsUpdated();
+}
+
+
+void AccountManager::slotPropertiesChanged()
+{
+#ifdef ENABLE_DEBUG_OUTPUT_
+    qDebug() << "AccountManager::slotPropertiesChanged()";
+#endif
+    emit signalAccountsUpdated();
+}
+
+// Called when an Account was removed
+void AccountManager::slotAccountRemoved()
+{
+#ifdef ENABLE_DEBUG_OUTPUT_
+    qDebug() << "AccountManager::slotAccountRemoved sender:" << sender();
+#endif
+    Account* account = qobject_cast<Account*>( sender() );
+    Q_ASSERT( account );
+    if ( account )
+    {
+        QString handle = account->handle();
+        d->removeAccount( handle );
+        emit signalAccountsUpdated();
+    }
+}
+
+void AccountManager::init()
+{
+    Telepathy::registerTypes();
+    d->m_pInterface = new Telepathy::Client::AccountManagerInterface( "org.freedesktop.Telepathy.AccountManager",
+                                                                           "/org/freedesktop/Telepathy/AccountManager",
+                                                                           this );
+    Q_ASSERT( d->m_pInterface );
+    if ( ! d->m_pInterface )
+    { return; }
+        
+    if ( !d->m_pInterface->isValid() )
+    {
+        qWarning() << "Unable to connect to AccountManagerInterface: MissionControl seems to be missing!";
+    }
+    //Q_ASSERT( d->m_pInterface->isValid() );
+                                                                           
+    // It might be better to use layzy initializing here.. (ses)
+    Telepathy::ObjectPathList account_handles = d->m_pInterface->ValidAccounts();
+    foreach( const QDBusObjectPath& account_handle, account_handles )
+    {
+
+        Account* account = new Account( account_handle.path(), this );
+        connect( account, SIGNAL( signalRemoved() ),
+                 this, SLOT( slotAccountRemoved() ) );
+        connect( account, SIGNAL( signalPropertiesChanged( const QVariantMap& ) ),
+                 this, SLOT( slotPropertiesChanged() ) );
+        d->m_validAccountHandles.insert( account_handle.path(), QPointer<Account>( account ) );
+        emit signalAccountsUpdated();
+    }
+
+    connect( d->m_pInterface, SIGNAL( AccountValidityChanged( const QDBusObjectPath&, bool ) ),
+             this, SLOT( slotAccountValidityChanged( const QDBusObjectPath&, bool ) ) );
+    connect( d->m_pInterface, SIGNAL( AccountRemoved(const QDBusObjectPath& ) ),
+             this, SLOT( slotAccountRemoved( const QDBusObjectPath& ) ) );
+  
+
+}
+            
diff --git a/TelepathyQt4/Prototype/AccountManager.h b/TelepathyQt4/Prototype/AccountManager.h
new file mode 100644
index 0000000..12304d3
--- /dev/null
+++ b/TelepathyQt4/Prototype/AccountManager.h
@@ -0,0 +1,141 @@
+/*
+ * This file is part of TelepathyQt4
+ *
+ * Copyright (C) 2008 basysKom GmbH
+ * Copyright (C) 2008 Collabora Ltd. <http://www.collabora.co.uk/>
+ * Copyright (C) 2008 Nokia Corporation
+ *
+ * This library is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU Lesser General Public
+ * License as published by the Free Software Foundation; either
+ * version 2.1 of the License, or (at your option) any later version.
+ *
+ * This library is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
+ * Lesser General Public License for more details.
+ *
+ * You should have received a copy of the GNU Lesser General Public
+ * License along with this library; if not, write to the Free Software
+ * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA  02110-1301  USA
+ */
+#ifndef TelepathyQt4_Prototype_AccountManager_H_
+#define TelepathyQt4_Prototype_AccountManager_H_
+
+#include <QDBusObjectPath>
+#include <QObject>
+#include <QPointer>
+
+#include <TelepathyQt4/Prototype/Account.h>
+
+#ifdef DEPRECATED_ENABLED__
+#define ATTRIBUTE_DEPRECATED __attribute__((deprecated))
+#else
+#define ATTRIBUTE_DEPRECATED
+#endif
+
+
+namespace TpPrototype {
+// 
+class AccountManagerPrivate;
+
+/**
+ * @defgroup qt_accountmgm Account Management
+ * @ingroup qt_style_api
+ * Classes that provide functions to handle accounts.
+ */
+
+
+/**
+ * This class manages all accounts.
+ * The account manager provides access to the list of accounts. Additionally you can create and remove accounts.<br>
+ * Use the Connectionfacade to obtain a list of valid parameters for a protocol or the list of available connection managers.<br>
+ * @see ConnectionFacade
+ * @ingroup qt_accountmgm
+ * @todo Integrate all functions related to Accounts from the ConnectionFacade into this class.
+ */
+class AccountManager : public QObject
+{
+    Q_OBJECT
+public:
+    /**
+     * Returns pointer to the instance of this class.
+     * @return Instance pointer.
+     */
+    static AccountManager* instance();
+    
+    /**
+     * Number of Accounts. Returns how many accounts are available.
+     * @return Number of accounts available.
+     * @deprecated Use accountList().count() instead.
+     */
+    int count() ATTRIBUTE_DEPRECATED;
+
+     /**
+      * List of accounts. The account pointer is stored in a QPointer. If the account is removed it is deleted
+      * by the account manager. Thus, the pointer is set to 0.
+      * @todo: Return QList<Account> here, instead of a pointer. 
+      */
+     QList<QPointer<Account> > accountList();
+
+     /**
+      * List of enabled accounts
+      */
+     QList<QPointer<Account> > accountListOfEnabledAccounts();
+
+     /**
+      * Create account. This function creates an account with the given parameters.<br>
+      * <b>Note:</b> Although this call is synchronous, the internal book keeping of valid accounts is
+      *              updated by DBUS signals that might need some time. Thus, calling count() emmediately after create might
+      *              return an incorrect value. Wait until signalAccountsUpdated() is emitted.
+      * @param connectionManager The name of the connection manager, e.g. &quot;salut&quot;.
+      * @param protocol The protocol, e.g. &quot;local-xmpp&quot;. 
+      * @param parameters List of parameters needed to create the account
+      * @param displayName The name of the account to display.
+      * @return true when creating was successful.
+      */
+     bool createAccount( const QString& connectionManager, const QString& protocol, const QString& displayName, const QVariantMap& parameters );
+      
+     /**
+      * Remove account. Removes the given account.
+      * @param account The pointer to the account. The pointer is not accessable after this call!
+      * @return true if remove operation was successful.
+      */
+     bool removeAccount( Account* account );
+       
+signals:
+    /**
+     * Some changes occurred on the account data. This signal is emitted if the internal data of the account manager
+     * is changed (accounts were created or removed).<br>
+     * It is suggested to refetch all locally stored data after this signal.
+     */
+    void signalAccountsUpdated();
+
+    /**
+     * A new account is available.
+     * This signal is emitted if a new account was created by a contact manager
+     */
+    void signalNewAccountAvailable( TpPrototype::Account* account );
+protected:
+    /**
+     * Constructor. The account manager cannot be instantiated directly. Use instance() for it!
+     */
+    AccountManager( QObject* parent = NULL );
+    ~AccountManager();
+
+protected slots:
+    void slotAccountValidityChanged( const QDBusObjectPath& account, bool valid );
+    void slotAccountRemoved( const QDBusObjectPath& account );
+    void slotAccountRemoved();
+    void slotPropertiesChanged();
+
+private:
+    void init();
+    
+    AccountManagerPrivate * const d;
+    static AccountManager* m_pInstance;
+};
+
+}
+
+#endif
diff --git a/TelepathyQt4/Prototype/AvatarManager.cpp b/TelepathyQt4/Prototype/AvatarManager.cpp
new file mode 100644
index 0000000..6d7ff15
--- /dev/null
+++ b/TelepathyQt4/Prototype/AvatarManager.cpp
@@ -0,0 +1,320 @@
+/*
+ * This file is part of TelepathyQt4
+ *
+ * Copyright (C) 2008 basysKom GmbH
+ * Copyright (C) 2008 Collabora Ltd. <http://www.collabora.co.uk/>
+ * Copyright (C) 2008 Nokia Corporation
+ *
+ * This library is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU Lesser General Public
+ * License as published by the Free Software Foundation; either
+ * version 2.1 of the License, or (at your option) any later version.
+ *
+ * This library is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
+ * Lesser General Public License for more details.
+ *
+ * You should have received a copy of the GNU Lesser General Public
+ * License along with this library; if not, write to the Free Software
+ * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA  02110-1301  USA
+ */
+
+#include "TelepathyQt4/Prototype/AvatarManager.h"
+
+#include <QCoreApplication>
+#include <QDBusObjectPath>
+#include <QDBusPendingReply>
+#include <QDebug>
+#include <QMap>
+#include <QPointer>
+
+#include <TelepathyQt4/Client/Connection>
+
+#include <TelepathyQt4/Prototype/Account.h>
+#include <TelepathyQt4/Prototype/AccountManager.h>
+#include <TelepathyQt4/Prototype/ConnectionFacade.h>
+#include <TelepathyQt4/Prototype/Connection.h>
+#include <TelepathyQt4/Prototype/Contact.h>
+#include <TelepathyQt4/Prototype/ContactManager.h>
+
+// #define ENABLE_DEBUG_OUTPUT_
+
+using namespace TpPrototype;
+
+class TpPrototype::AvatarManagerPrivate
+{
+public:
+    AvatarManagerPrivate( Connection* connection,
+                          Telepathy::Client::ConnectionInterface* interface )
+    { init( connection, interface ); }
+
+    Telepathy::Client::ConnectionInterface* m_pConnectionInterface;
+    Telepathy::Client::ConnectionInterfaceAvatarsInterface* m_pAvatarsInterface;
+    QPointer<Connection> m_pConnection;
+    
+    bool m_isValid;
+    void init( Connection* connection,
+               Telepathy::Client::ConnectionInterface* interface )
+    {
+        m_pConnection            = connection;
+        m_pConnectionInterface   = interface;
+        m_pAvatarsInterface      = NULL;
+        m_isValid                = true;
+    }
+
+};
+
+AvatarManager::AvatarManager( Connection* connection,
+                              Telepathy::Client::ConnectionInterface* interface,
+                              QObject* parent ):
+    QObject( parent ),
+    d( new AvatarManagerPrivate( connection, interface ) )
+{
+    init( connection, interface );
+}
+
+AvatarManager::~AvatarManager()
+{
+#ifdef ENABLE_DEBUG_OUTPUT_
+    qDebug() << "D'tor AvatarManager (" << this << ")";
+#endif
+    delete d;
+}
+
+bool AvatarManager::isValid()
+{
+    return d->m_isValid;
+}
+
+
+
+TpPrototype::Connection* AvatarManager::connection()
+{
+    return d->m_pConnection;
+}
+
+bool AvatarManager::setAvatar( const TpPrototype::AvatarManager::Avatar& newValue  )
+{
+    QDBusPendingReply<QString> set_avatar_reply = d->m_pAvatarsInterface->SetAvatar( newValue.avatar, newValue.mimeType );
+    set_avatar_reply.waitForFinished();
+    
+    if ( !set_avatar_reply.isValid() )
+    {
+        QDBusError error = set_avatar_reply.error();
+    
+        qWarning() << "AvatarManager::setAvatar: error type:" << error.type()
+                << "error name:" << error.name()
+                << "error message:" << error.message();
+
+        d->m_isValid = false;
+        return false;
+    }
+
+#ifdef ENABLE_DEBUG_OUTPUT_
+    qDebug() << "AvatarManager::setAvatar: token " << set_avatar_reply.value();
+#endif
+    
+    return true;
+}
+
+void AvatarManager::requestAvatar()
+{
+    uint self_handle = TpPrototype::ConnectionFacade::instance()->selfHandleForConnectionInterface( d->m_pConnectionInterface );
+    QList<uint> contact_ids;
+    contact_ids << self_handle;
+    
+    QDBusPendingReply<> avatars_reply = d->m_pAvatarsInterface->RequestAvatars( contact_ids );
+    
+    // slotAvatarRetrieved is called after this point.
+}
+
+TpPrototype::AvatarManager::AvatarRequirements AvatarManager::avatarRequirements()
+{
+    Q_ASSERT( d->m_pAvatarsInterface );
+
+    TpPrototype::AvatarManager::AvatarRequirements return_data;
+    return_data.isValid = false;
+
+    QDBusPendingReply<QStringList, ushort, ushort, ushort, ushort, uint> requirements_reply = d->m_pAvatarsInterface->GetAvatarRequirements();
+    requirements_reply.waitForFinished();
+
+    if ( !requirements_reply.isValid() )
+    {
+        QDBusError error = requirements_reply.error();
+    
+        qWarning() << "AvatarManager::GetAvatarRequirements: error type:" << error.type()
+                << "error name:" << error.name()
+                << "error message:" << error.message();
+
+        d->m_isValid = false;
+        return return_data;
+    }
+
+    TpPrototype::AvatarManager::AvatarRequirements ret_requirement;
+    ret_requirement.mimeTypes     = qvariant_cast<QStringList>( requirements_reply.argumentAt( 0 ) );
+    ret_requirement.minimumWidth  = qvariant_cast<ushort>(requirements_reply.argumentAt( 1 ) );
+    ret_requirement.minimumHeight = qvariant_cast<ushort>(requirements_reply.argumentAt( 2 ) );
+    ret_requirement.maximumWidth  = qvariant_cast<ushort>(requirements_reply.argumentAt( 3 ) );
+    ret_requirement.maximumHeight = qvariant_cast<ushort>(requirements_reply.argumentAt( 4 ) );
+    ret_requirement.maxSize       = qvariant_cast<uint>(requirements_reply.argumentAt( 5 ) );
+    return_data.isValid = true;
+    
+    return ret_requirement;
+}
+
+void AvatarManager::avatarForContactList( const QList<QPointer<Contact> >& contacts )
+{
+    Q_ASSERT( d->m_pAvatarsInterface );
+    Telepathy::UIntList contact_ids;
+    foreach( Contact* contact, contacts )
+    {
+        if ( !contact )
+        { continue; }
+        contact_ids.append( contact->telepathyHandle() );
+    }
+
+    QDBusPendingReply<> avatars_reply = d->m_pAvatarsInterface->RequestAvatars( contact_ids );
+   
+    // slotAvatarRetrieved is called after this point.
+}
+
+
+void AvatarManager::slotAvatarUpdated( uint contactHandle, const QString& newAvatarToken )
+{
+#ifdef ENABLE_DEBUG_OUTPUT_
+    qDebug() << "AvatarManager::slotAvatarUpdated(" << contactHandle << "," << newAvatarToken << ")";
+#endif
+    if ( !d->m_pConnection )
+    {
+        qWarning() << "AvatarManager::slotAvatarUpdated(): Received a Avatar changed signal but no connection object exists!";
+        return;
+    }
+
+    Q_ASSERT( d->m_pAvatarsInterface );
+    Q_ASSERT( d->m_pAvatarsInterface->isValid() );
+    Q_ASSERT( d->m_pConnection );
+    Q_ASSERT( d->m_pConnection->contactManager() );
+
+    if ( !d->m_pConnection
+         || !d->m_pConnection->contactManager() )
+    {
+        qWarning() << "AvatarManager::slotAvatarUpdated(): Unable to request contact manager or connection is not valid!";
+        return;
+    }
+
+    uint self_handle = ConnectionFacade::instance()->selfHandleForConnectionInterface( d->m_pConnectionInterface );
+
+    if ( self_handle == contactHandle )
+    {
+#ifdef ENABLE_DEBUG_OUTPUT_
+        qDebug() << "AvatarManager::slotAvatarUpdated(): Ignored that my avatar is updated.";
+#endif
+
+        //emit void signalOwnAvatarChanged();
+    }
+    else
+    {
+        foreach( TpPrototype::Contact* contact, d->m_pConnection->contactManager()->contactList() )
+        {
+            if ( ( contact->telepathyHandle() == contactHandle )
+                  && ( contact->avatar().token != newAvatarToken ) )
+            {
+                // Request avatar for this contact.
+                avatarForContactList( QList<QPointer<Contact> >() << QPointer<Contact>( contact ) );
+            }
+        }
+    }
+}
+
+// Called after avatarForContactList() is called.
+void AvatarManager::slotAvatarRetrieved( uint contactHandle, const QString& token, const QByteArray& avatar, const QString& type )
+{
+#ifdef ENABLE_DEBUG_OUTPUT_
+    qDebug() << "slotAvatarRetrieved: Handle: " << contactHandle << "Token:" << token << "Type: " << type;
+#endif
+    
+    TpPrototype::AvatarManager::Avatar new_avatar;
+    new_avatar.avatar   = avatar;
+    new_avatar.token    = token;
+    new_avatar.mimeType = type;
+
+    uint self_handle = ConnectionFacade::instance()->selfHandleForConnectionInterface( d->m_pConnectionInterface );
+    if ( self_handle == contactHandle )
+    {
+        emit signalOwnAvatarChanged( new_avatar );
+        return;
+    }   
+
+    foreach( TpPrototype::Contact* contact, d->m_pConnection->contactManager()->contactList() )
+    {
+        // Find contact for handle and check whether the token has changed. If not, the avatar was not changed.
+        if ( ( contact->telepathyHandle() == contactHandle )
+               && ( contact->avatar().token != token ) )
+        {
+            contact->setAvatar( new_avatar );
+            emit signalAvatarChanged( contact );
+        }
+    }   
+}
+
+void AvatarManager::init( Connection* connection,
+                          Telepathy::Client::ConnectionInterface* interface )
+{
+    Q_ASSERT( interface );
+
+    if ( !interface || !connection )
+    {
+        d->m_isValid = false;
+        return;
+    }
+    
+    Telepathy::registerTypes();
+    qRegisterMetaType<TpPrototype::AvatarManager::Avatar>();
+    
+    QDBusPendingReply<QStringList> interfaces_reply = d->m_pConnectionInterface->GetInterfaces();
+    interfaces_reply.waitForFinished();
+
+    if ( !interfaces_reply.isValid() )
+    {
+        QDBusError error = interfaces_reply.error();
+    
+        qWarning() << "GetInterfaces: error type:" << error.type()
+                << "error name:" << error.name()
+                << "error message:" << error.message();
+
+        d->m_isValid = false;
+        return;
+    }
+    
+    QString avatar_interface_name;
+    bool found_avatar_support = false;
+    foreach( const QString& interface, interfaces_reply.value() )
+    {
+        if ( interface.endsWith( ".Avatars" ) )
+        {
+            found_avatar_support = true;
+            avatar_interface_name = interface;
+            break;
+        }     
+    }
+    if ( !found_avatar_support )
+    {
+        d->m_isValid = false;
+        qWarning( "AvatarManager::init(): Connection Manager does not support the Interface \"Avatars\". Other interfaces are not supported!" );
+        return;
+    }
+
+#ifdef ENABLE_DEBUG_OUTPUT_
+    qDebug() << "Interface Name: " << avatar_interface_name;
+#endif
+    d->m_pAvatarsInterface = new Telepathy::Client::ConnectionInterfaceAvatarsInterface( d->m_pConnectionInterface->service(), d->m_pConnectionInterface->path(), this );
+    
+    connect( d->m_pAvatarsInterface, SIGNAL( AvatarUpdated(uint, const QString&) ),
+             this, SLOT( slotAvatarUpdated(uint, const QString&) ) );
+    connect( d->m_pAvatarsInterface, SIGNAL( AvatarRetrieved(uint , const QString& , const QByteArray& , const QString& ) ),
+             this, SLOT( slotAvatarRetrieved( uint , const QString& , const QByteArray& , const QString& ) ) );
+   
+}
+            
+
diff --git a/TelepathyQt4/Prototype/AvatarManager.h b/TelepathyQt4/Prototype/AvatarManager.h
new file mode 100644
index 0000000..085a281
--- /dev/null
+++ b/TelepathyQt4/Prototype/AvatarManager.h
@@ -0,0 +1,174 @@
+/*
+ * This file is part of TelepathyQt4
+ *
+ * Copyright (C) 2008 basysKom GmbH
+ * Copyright (C) 2008 Collabora Ltd. <http://www.collabora.co.uk/>
+ * Copyright (C) 2008 Nokia Corporation
+ *
+ * This library is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU Lesser General Public
+ * License as published by the Free Software Foundation; either
+ * version 2.1 of the License, or (at your option) any later version.
+ *
+ * This library is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
+ * Lesser General Public License for more details.
+ *
+ * You should have received a copy of the GNU Lesser General Public
+ * License along with this library; if not, write to the Free Software
+ * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA  02110-1301  USA
+ */
+#ifndef TelepathyQt4_Prototype_AvatarManager_H_
+#define TelepathyQt4_Prototype_AvatarManager_H_
+
+#include <QDBusObjectPath>
+#include <QObject>
+#include <QPointer>
+
+#include <TelepathyQt4/Types>
+
+namespace Telepathy
+{
+    namespace Client
+    {
+        class ConnectionInterface;
+    }
+}
+
+namespace TpPrototype {
+
+class AvatarManagerPrivate;
+class Connection;
+class Contact;
+class Account;
+
+/**
+ * @ingroup qt_connection
+ * This class manages avatar information for one connection.
+ * Whenever a contact avatar changes, the signal signalAvatarChanged() is emitted. This signal provides the related contact object
+ * obtained from the ContactManager.
+ * In order to keep the contacts updated, you just have to instantiate this class (by requesting the object with Connection::avatarManager())
+ * and initialize the list of contacts once (by calling avatarForContactList() ). After this point, the avatar of the contact
+ * is updated automatically if a change is signalled by the backend.
+ * @see Connection
+ */
+class AvatarManager : public QObject
+{
+    Q_OBJECT
+    
+public:
+    /**
+     * The required Avatar format.
+     */
+    struct AvatarRequirements
+    {
+        /** The list of supported Mimetypes */
+        QStringList mimeTypes;
+        /** The minimum image width */
+        uint      minimumWidth;
+        /** The minmum image height */
+        uint      minimumHeight;
+        /** The maximum image width */
+        uint      maximumWidth;
+        /** The maximum image height */
+        uint      maximumHeight;
+        /** The maximum size */
+        uint        maxSize;
+        /** data validity */
+        bool        isValid;
+    };
+
+    /**
+     * The Avatar
+     */
+    struct Avatar
+    {
+        /** The avatar data */
+        QByteArray avatar;
+        /** The mimetype of this data */
+        QString    mimeType;
+        /** The id associated with this avatar */
+        QString token;
+    };
+    
+    /**
+     * Validity.
+     * Do not access any methods if the object is invalid!
+     */
+    bool isValid();
+
+    /**
+     * Returns the connection that belongs to this capabilities information.
+     * @return The connection object
+     */
+    TpPrototype::Connection* connection();
+    
+    /**
+     * Set local Avatar.
+     * This function sets the capabilites of the account that belongs to this connection.
+     * @param newValue The new avatar. The content of <i>token</i> is ignored.
+     * @return true if setting was successful
+     */
+    bool setAvatar( const TpPrototype::AvatarManager::Avatar& newValue );
+    
+    /**
+     * Request local Avatar.
+     * Requests the avatar of the account that belongs to this connection.
+     * <b>Info:</b> The signal signalOwnAvatarChanged() is called asynchonously after this call.
+     */
+    void requestAvatar();
+
+    /**
+     * Get the required format of avatars on this connection.
+     * @return The requirements of supported avatars.
+     * @see AvatarRequirements
+     */
+    AvatarRequirements avatarRequirements();
+    
+    /**
+     * Get the avatar for a list of contacts.
+     * The avatars can be requested from the contact object.
+     * <b>Info:</b> The signal signalAvatarChanged() is called asynchonously after this call for every contact in this list.
+     * @param List of contacts to request the avatars from.
+     * @see signalAvatarChanged()
+     */
+    void avatarForContactList( const QList<QPointer<Contact> >& contacts );
+    
+signals:
+    /**
+     * The avatar of a contact was changed. This signal is emitted when any of the known contacts changed its avatar.
+     */
+    void signalAvatarChanged( TpPrototype::Contact* contact );
+
+    /**
+     * My avatar was changed.
+     * This signal is emmitted if the local avatar was changed.
+     */
+    void signalOwnAvatarChanged( TpPrototype::AvatarManager::Avatar avatar );
+ 
+protected:
+    /**
+     * Constructor. The capabilities manager cannot be instantiated directly. Use Connection::AvatarManager() for it!
+     */
+    AvatarManager( TpPrototype::Connection* connection,
+                   Telepathy::Client::ConnectionInterface* interface,
+                   QObject* parent = NULL );
+    ~AvatarManager();
+
+protected slots:
+    void slotAvatarUpdated( uint contact, const QString& newAvatarToken );
+    void slotAvatarRetrieved( uint contact, const QString& token, const QByteArray& avatar, const QString& type );
+ 
+private:
+    void init( TpPrototype::Connection* connection, Telepathy::Client::ConnectionInterface* interface );
+    
+    TpPrototype::AvatarManagerPrivate * const d;
+    friend class Connection;
+    friend class ConnectionPrivate;
+};
+}
+
+Q_DECLARE_METATYPE( TpPrototype::AvatarManager::Avatar );
+Q_DECLARE_METATYPE( TpPrototype::AvatarManager::AvatarRequirements );
+#endif
diff --git a/TelepathyQt4/Prototype/CapabilitiesManager.cpp b/TelepathyQt4/Prototype/CapabilitiesManager.cpp
new file mode 100644
index 0000000..250cd0d
--- /dev/null
+++ b/TelepathyQt4/Prototype/CapabilitiesManager.cpp
@@ -0,0 +1,321 @@
+/*
+ * This file is part of TelepathyQt4
+ *
+ * Copyright (C) 2008 basysKom GmbH
+ * Copyright (C) 2008 Collabora Ltd. <http://www.collabora.co.uk/>
+ * Copyright (C) 2008 Nokia Corporation
+ *
+ * This library is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU Lesser General Public
+ * License as published by the Free Software Foundation; either
+ * version 2.1 of the License, or (at your option) any later version.
+ *
+ * This library is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
+ * Lesser General Public License for more details.
+ *
+ * You should have received a copy of the GNU Lesser General Public
+ * License along with this library; if not, write to the Free Software
+ * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA  02110-1301  USA
+ */
+
+#include "TelepathyQt4/Prototype/CapabilitiesManager.h"
+
+#include <QCoreApplication>
+#include <QDBusObjectPath>
+#include <QDBusPendingReply>
+#include <QDebug>
+#include <QMap>
+#include <QPointer>
+
+#include <TelepathyQt4/Client/Connection>
+
+#include <TelepathyQt4/Prototype/Account.h>
+#include <TelepathyQt4/Prototype/AccountManager.h>
+#include <TelepathyQt4/Prototype/ConnectionFacade.h>
+#include <TelepathyQt4/Prototype/Connection.h>
+#include <TelepathyQt4/Prototype/Contact.h>
+#include <TelepathyQt4/Prototype/ContactManager.h>
+
+// #define ENABLE_DEBUG_OUTPUT_
+
+using namespace TpPrototype;
+
+class TpPrototype::CapabilitiesManagerPrivate
+{
+public:
+    CapabilitiesManagerPrivate()
+    { init(); }
+
+    Telepathy::Client::ConnectionInterface* m_pConnectionInterface;
+    Telepathy::Client::ConnectionInterfaceCapabilitiesInterface* m_pCapabilitiesInterface;
+
+   
+    QPointer<Connection> m_pConnection;
+    
+    bool m_isValid;
+    void init()
+    {
+        m_pConnectionInterface   = NULL;
+        m_pCapabilitiesInterface = NULL;
+        m_pConnection            = NULL;
+        m_isValid                = true;
+    }
+
+};
+
+CapabilitiesManager::CapabilitiesManager( Connection* connection,
+                                  Telepathy::Client::ConnectionInterface* interface,
+                                  QObject* parent ):
+    QObject( parent ),
+    d( new CapabilitiesManagerPrivate )
+{
+    init( connection, interface );
+}
+
+CapabilitiesManager::~CapabilitiesManager()
+{
+#ifdef ENABLE_DEBUG_OUTPUT_
+    qDebug() << "D'tor CapabilitiesManager (" << this << ")";
+#endif
+    delete d;
+}
+
+bool CapabilitiesManager::isValid()
+{
+    return d->m_isValid;
+}
+
+
+
+TpPrototype::Connection* CapabilitiesManager::connection()
+{
+    return d->m_pConnection;
+}
+
+bool CapabilitiesManager::setCapabilities( const Telepathy::CapabilityPairList& capabilities, const QStringList& removedChannels )
+{
+    QDBusPendingReply<Telepathy::CapabilityPairList> advertise_capabilities_reply = d->m_pCapabilitiesInterface->AdvertiseCapabilities( capabilities, removedChannels );
+    advertise_capabilities_reply.waitForFinished();
+    
+    if ( !advertise_capabilities_reply.isValid() )
+    {
+        QDBusError error = advertise_capabilities_reply.error();
+    
+        qWarning() << "CapabilitiesManager::AdvertiseCapabilities: error type:" << error.type()
+                << "error name:" << error.name()
+                << "error message:" << error.message();
+
+        d->m_isValid = false;
+        return false;
+    }
+
+#ifdef ENABLE_DEBUG_OUTPUT_
+    qDebug() << "CapabilitiesManager::setCapabilities: " << capabilities.count();
+    qDebug() << "CapabilitiesManager::setCapabilities: " << advertise_capabilities_reply.value().count();
+#endif    
+    
+    return true;
+}
+
+Telepathy::ContactCapabilityList CapabilitiesManager::capabilities()
+{
+    uint self_handle = TpPrototype::ConnectionFacade::instance()->selfHandleForConnectionInterface( d->m_pConnectionInterface );
+    QList<uint> handle_list;
+    handle_list.append( self_handle );
+    QDBusPendingReply<Telepathy::ContactCapabilityList> capabilities_reply = d->m_pCapabilitiesInterface->GetCapabilities( handle_list );
+    capabilities_reply.waitForFinished();
+
+    if ( !capabilities_reply.isValid() )
+    {
+        QDBusError error = capabilities_reply.error();
+    
+        qWarning() << "CapabilitiesManager::capabilities: error type:" << error.type()
+                << "error name:" << error.name()
+                << "error message:" << error.message();
+
+        d->m_isValid = false;
+        return Telepathy::ContactCapabilityList();
+    }
+  
+    Telepathy::ContactCapabilityList capabilities=capabilities_reply.value();
+
+    return capabilities;
+}
+
+
+void CapabilitiesManager::capabilitiesForContactList( const QList<QPointer<Contact> >& contacts )
+{
+    Q_ASSERT( d->m_pCapabilitiesInterface );
+    Telepathy::UIntList contact_ids;
+    foreach( Contact* contact, contacts )
+    {
+        if ( !contact )
+        { continue; }
+        contact_ids.append( contact->telepathyHandle() );
+    }
+
+    QDBusPendingReply<Telepathy::ContactCapabilityList> capabilities_reply = d->m_pCapabilitiesInterface->GetCapabilities( contact_ids );
+    capabilities_reply.waitForFinished();
+
+    if ( !capabilities_reply.isValid() )
+    {
+        QDBusError error = capabilities_reply.error();
+    
+        qWarning() << "GetInterfaces: error type:" << error.type()
+                << "GetInterfaces: error name:" << error.name()
+                << "error message:" << error.message();
+
+        d->m_isValid = false;
+        return;
+    }
+  
+    Telepathy::ContactCapabilityList capabilities=capabilities_reply.value();
+
+    foreach( Contact* contact, contacts )
+    {
+        Telepathy::ContactCapabilityList contact_capabilities;
+        for ( int i=0; i < capabilities.size(); i++ )
+        {
+            Telepathy::ContactCapability capability = capabilities.value( i );
+            if ( contact && contact->telepathyHandle() == capability.handle )
+            {
+                contact_capabilities.append( capability );
+            }
+        }
+        contact->setCapabilities( contact_capabilities );
+    }
+}
+
+void CapabilitiesManager::slotCapabilitiesChanged( const Telepathy::CapabilityChangeList& capabilities )
+{
+    if ( !d->m_pConnection )
+    {
+        qWarning() << "CapabilitiesManager::slotCapabilitiesChanged(): Received a Capabilities changed signal but no connection object exists!";
+        return;
+    }
+
+    Q_ASSERT( d->m_pCapabilitiesInterface );
+    Q_ASSERT( d->m_pCapabilitiesInterface->isValid() );
+
+    QPointer<TpPrototype::Contact> contact;
+    for (int i=0; i<capabilities.size(); i++)
+    {
+
+        Telepathy::CapabilityChange changed_capability = capabilities.value( i );
+#ifdef ENABLE_DEBUG_OUTPUT_
+            qDebug() << "CapabilityChange "<< i<< "handle" <<changed_capability.handle;
+            qDebug() << "CapabilityChange"<< i << "CannelType" <<changed_capability.channelType;
+            qDebug() << "CapabilityChange "<< i << "Generic Flags" <<changed_capability.oldGenericFlags;
+            qDebug() << "CapabilityChange "<< i << "Generic Flags" <<changed_capability.newGenericFlags;
+            qDebug() << "CapabilityChange "<< i << "Type Specific Flags" <<changed_capability.oldTypeSpecificFlags;
+            qDebug() << "CapabilityChange "<< i << "Type Specific Flags" <<changed_capability.newTypeSpecificFlags;
+#endif
+        
+        if ( !d->m_pConnection->contactManager() )
+        {
+            qWarning() << "CapabilitiesManager::slotCapabilitiesChanged(): Unable to request contact manager!";
+            return;
+        }
+
+        uint self_handle = ConnectionFacade::instance()->selfHandleForConnectionInterface( d->m_pConnectionInterface );
+        foreach( const Telepathy::CapabilityChange& changed_capability, capabilities )
+        {
+            if ( changed_capability.handle == self_handle )
+            {
+                emit signalOwnCapabilityChanged( changed_capability );
+            }
+            else
+            {
+                foreach( Contact* contact, d->m_pConnection->contactManager()->contactList() )
+                {
+                    if ( contact && contact->telepathyHandle() == changed_capability.handle )
+                    {
+                        // Modify stored list of capabilities
+                        Telepathy::ContactCapabilityList contact_capabilities = contact->capabilities();
+                        for ( int i = 0; i < contact_capabilities.size(); ++i )
+                        {
+                            if ( contact_capabilities.at(i).channelType == changed_capability.channelType )
+                            {
+                                contact_capabilities.removeAt( i );
+                            }
+                        }
+
+                        Telepathy::ContactCapability new_capability;
+                        new_capability.handle            = changed_capability.handle;
+                        new_capability.channelType       = changed_capability.channelType;
+                        new_capability.genericFlags      = changed_capability.newGenericFlags;
+                        new_capability.typeSpecificFlags = changed_capability.newTypeSpecificFlags;
+                        contact_capabilities.append( new_capability );
+                        
+                        contact->setCapabilities( contact_capabilities );
+                        emit signalCapabilitiesChanged( contact, changed_capability );
+                    }
+                }
+            }
+        }
+    }
+}
+
+
+void CapabilitiesManager::init( Connection* connection,
+                            Telepathy::Client::ConnectionInterface* interface )
+{
+    Q_ASSERT( interface );
+
+    if ( !interface || !connection )
+    {
+        d->m_isValid = false;
+        return;
+    }
+    
+    Telepathy::registerTypes();
+    d->m_pConnectionInterface = interface;
+    d->m_pConnection          = connection;
+    QDBusPendingReply<QStringList> interfaces_reply = d->m_pConnectionInterface->GetInterfaces(); 
+    interfaces_reply.waitForFinished();
+
+    if ( !interfaces_reply.isValid() )
+    {
+        QDBusError error = interfaces_reply.error();
+    
+        qWarning() << "GetInterfaces: error type:" << error.type()
+                << "error name:" << error.name()
+                << "error message:" << error.message();
+
+        d->m_isValid = false;
+        return;
+    }
+    QString capabilities_interface_name;
+    bool found_capabilities_support = false;
+
+    
+    foreach( const QString& interface, interfaces_reply.value() )
+    {
+        if ( interface.endsWith( ".Capabilities" ) )
+        {
+            found_capabilities_support = true;
+            capabilities_interface_name = interface;
+            break;
+        }     
+    }
+    if ( !found_capabilities_support )
+    {
+        d->m_isValid = false;
+        qWarning( "CapabilitiesManager::init(): Connection Manager does not support the Interface \"Capabilities\". Other interfaces are not supported!" );
+        return;
+    }
+
+#ifdef ENABLE_DEBUG_OUTPUT_
+    //qDebug() << "Connection interface :" << d->m_pConnectionInterface->connection().interface()->path();
+    qDebug() << "Interface Name: " << capabilities_interface_name;
+#endif
+    d->m_pCapabilitiesInterface = new Telepathy::Client::ConnectionInterfaceCapabilitiesInterface(d->m_pConnectionInterface->service(),d->m_pConnectionInterface->path(),this );
+    
+    connect( d->m_pCapabilitiesInterface, SIGNAL( CapabilitiesChanged( const Telepathy::CapabilityChangeList& ) ),
+             this, SLOT( slotCapabilitiesChanged( const Telepathy::CapabilityChangeList& ) ) );
+   
+}
+            
+
diff --git a/TelepathyQt4/Prototype/CapabilitiesManager.h b/TelepathyQt4/Prototype/CapabilitiesManager.h
new file mode 100644
index 0000000..a92f460
--- /dev/null
+++ b/TelepathyQt4/Prototype/CapabilitiesManager.h
@@ -0,0 +1,129 @@
+/*
+ * This file is part of TelepathyQt4
+ *
+ * Copyright (C) 2008 basysKom GmbH
+ * Copyright (C) 2008 Collabora Ltd. <http://www.collabora.co.uk/>
+ * Copyright (C) 2008 Nokia Corporation
+ *
+ * This library is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU Lesser General Public
+ * License as published by the Free Software Foundation; either
+ * version 2.1 of the License, or (at your option) any later version.
+ *
+ * This library is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
+ * Lesser General Public License for more details.
+ *
+ * You should have received a copy of the GNU Lesser General Public
+ * License along with this library; if not, write to the Free Software
+ * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA  02110-1301  USA
+ */
+
+#ifndef TelepathyQt4_Prototype_CapabilitiesManager_H_
+#define TelepathyQt4_Prototype_CapabilitiesManager_H_
+
+#include <QDBusObjectPath>
+#include <QObject>
+#include <QPointer>
+
+#include <TelepathyQt4/Types>
+
+namespace Telepathy
+{
+    namespace Client
+    {
+        class ConnectionInterface;
+    }
+}
+
+namespace TpPrototype {
+
+class CapabilitiesManagerPrivate;
+class Connection;
+class Contact;
+class Account;
+
+/**
+ * @ingroup qt_connection
+ * This class manages capabilities information for one connection.
+ * Setting the right capability decide whether it is possible to handle incoming or outgoing VoIP or Video over IP channels!
+ * Whenever a contact capability changes, the signal signalCapabilitiesChanged() is emitted. This signal provides the related contact object
+ * obtained from the ContactManager.
+ * In order to keep the contacts updated, you just have to instantiate this class (by requesting the object with Connection::capabilitiesManager())
+ * and initialize the list of contacts once (by calling capabilitiesForContactList() ). After this point, the capabilty information of the contact
+ * is updated automatically if a change is signalled by the backend.
+ * @see Connection
+ * @see StreamedMediaChannel
+ */
+class CapabilitiesManager : public QObject
+{
+    Q_OBJECT
+public:
+    /**
+     * Validity.
+     * Do not access any methods if the object is invalid!
+     */
+    bool isValid();
+
+    /**
+     * Returns the connection that belongs to this capabilities information.
+     * @return The connection object
+     */
+    TpPrototype::Connection* connection();
+    
+    /**
+     * Set the capabilities.
+     * This function sets the capabilites of the account that belongs to this connection.
+     * @param capabilities List of capabilities for a specific channel. See Telepathy D-Bus spec section "Channel_Media_Capabilities"
+     * @param removedChanels List of channels that are removed.
+     * @return true if setting was successful
+     */
+    bool setCapabilities( const Telepathy::CapabilityPairList& capabilities, const QStringList& removedChannels = QStringList() );
+    
+    /**
+     * Request capabilites.
+     * Returns the capabilites of the account that belongs to this connection.
+     * @return List of capabilities
+     */
+    Telepathy::ContactCapabilityList capabilities();
+    
+    /**
+     * Gets the capabilities for a list of contacts and provides them to to specific contacts.
+     * The capabilities can be requested from the contact object.
+     */
+    void capabilitiesForContactList( const QList<QPointer<Contact> >& contacts );
+    
+signals:
+    /**
+     * The capability of a contact has changed. This signal is emitted when any of the known contacts changed its capability.
+     */
+    void signalCapabilitiesChanged( TpPrototype::Contact* contact, const Telepathy::CapabilityChange& changedCapability );
+
+    /**
+     * My capability was changed. This signal is emmitted if the capability of one of my channes was changed.
+     */
+    void signalOwnCapabilityChanged( const Telepathy::CapabilityChange& changedCapability );
+ 
+protected:
+    /**
+     * Constructor. The capabilities manager cannot be instantiated directly. Use Connection::CapabilitiesManager() for it!
+     */
+    CapabilitiesManager( TpPrototype::Connection* connection,
+                     Telepathy::Client::ConnectionInterface* interface,
+                     QObject* parent = NULL );
+    ~CapabilitiesManager();
+
+protected slots:
+    void slotCapabilitiesChanged( const Telepathy::CapabilityChangeList& capabilities );
+ 
+private:
+    void init( TpPrototype::Connection* connection, Telepathy::Client::ConnectionInterface* interface );
+    
+    TpPrototype::CapabilitiesManagerPrivate * const d;
+    friend class Connection;
+    friend class ConnectionPrivate;
+};
+}
+
+#endif
diff --git a/TelepathyQt4/Prototype/ChatChannel.cpp b/TelepathyQt4/Prototype/ChatChannel.cpp
new file mode 100644
index 0000000..f02916b
--- /dev/null
+++ b/TelepathyQt4/Prototype/ChatChannel.cpp
@@ -0,0 +1,223 @@
+/*
+ * This file is part of TelepathyQt4
+ *
+ * Copyright (C) 2008 basysKom GmbH
+ * Copyright (C) 2008 Collabora Ltd. <http://www.collabora.co.uk/>
+ * Copyright (C) 2008 Nokia Corporation
+ *
+ * This library is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU Lesser General Public
+ * License as published by the Free Software Foundation; either
+ * version 2.1 of the License, or (at your option) any later version.
+ *
+ * This library is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
+ * Lesser General Public License for more details.
+ *
+ * You should have received a copy of the GNU Lesser General Public
+ * License along with this library; if not, write to the Free Software
+ * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA  02110-1301  USA
+ */
+
+#include "TelepathyQt4/Prototype/ChatChannel.h"
+
+#include <QDebug>
+#include <QMetaProperty>
+
+#include <TelepathyQt4/Constants>
+#include <TelepathyQt4/Client/Connection>
+#include <TelepathyQt4/Client/Channel>
+
+#include <TelepathyQt4/Prototype/Contact.h>
+
+using namespace TpPrototype;
+
+class TpPrototype::ChatChannelPrivate
+{
+public:
+    ChatChannelPrivate()
+    { init(); }
+    
+    QPointer<TpPrototype::Contact>                          m_pContact;
+    Telepathy::Client::ChannelTypeTextInterface*          m_pTextChannel;
+    QPointer<Telepathy::Client::ConnectionInterface>      m_pConnectionInterface;
+
+    bool m_isValid;
+    bool m_areSignalsConnected;
+
+private:
+    void init()
+    {
+        m_pContact              = NULL;
+        m_pConnectionInterface  = NULL;
+        m_pTextChannel          = NULL;
+        m_isValid               = true;
+        m_areSignalsConnected   = false;
+    }
+};
+
+ChatChannel::ChatChannel( Contact* contact, Telepathy::Client::ConnectionInterface* connectionInterface, QObject* parent ):
+        QObject( parent ),
+        d(new ChatChannelPrivate())
+{
+    Telepathy::registerTypes();
+
+    d->m_pContact = contact;
+    d->m_pConnectionInterface = connectionInterface;
+
+    requestTextChannel( d->m_pContact->telepathyHandle() );
+}
+
+ChatChannel::~ChatChannel()
+        { delete d; }
+
+bool ChatChannel::isValid() const
+{ return d->m_isValid; }
+
+
+void ChatChannel::sendTextMessage( const QString& text )
+{
+
+    if ( d->m_pTextChannel == NULL )
+    {
+        requestTextChannel( d->m_pContact->telepathyHandle() );
+    }
+
+    Q_ASSERT( d->m_pTextChannel );
+    if ( !d->m_pTextChannel )
+    {
+        qWarning() << "ChatChannel::sendTextMessage: Action ignored due to missing text channel!";
+    }
+         
+    d->m_pTextChannel->Send( 0, text ); // TODO: Remove this magic number!
+
+}
+
+void ChatChannel::pendingTextMessages()
+{
+    if ( d->m_pTextChannel == NULL )
+    {
+        requestTextChannel( d->m_pContact->telepathyHandle() );
+    }
+
+    Q_ASSERT( d->m_pTextChannel );
+    if ( !d->m_pTextChannel )
+    {
+        qWarning() << "ChatChannel::pendingTextMessages: Action ignored due to missing text channel!";
+    }
+    
+    QDBusPendingReply<Telepathy::PendingTextMessageList> reply= d->m_pTextChannel->ListPendingMessages( true );
+    const Telepathy::PendingTextMessageList chatMessages = reply.value();
+    Telepathy::PendingTextMessage messageshandle;
+    for ( int i=0; i < chatMessages.size(); i++ )
+    {
+        messageshandle = chatMessages.at(i);
+        slotReceivedText( messageshandle.identifier,
+                          messageshandle.unixTimestamp,
+                          messageshandle.sender,
+                          messageshandle.messageType,
+                          messageshandle.flags,
+                          messageshandle.text );
+    }
+}
+
+// Called if a new text channel shall be established.
+void ChatChannel::requestTextChannel( uint handle )
+{
+    QDBusPendingReply<QDBusObjectPath> reply0 =
+            d->m_pConnectionInterface->RequestChannel( "org.freedesktop.Telepathy.Channel.Type.Text",
+                                             Telepathy::HandleTypeContact, handle, true );
+    reply0.waitForFinished();
+    if (!reply0.isValid())
+    {
+        QDBusError error = reply0.error();
+        qWarning() << "Get ContactListChannel: error type:" << error.type()
+                   << "error name:" << error.name()
+                   << "error message:" << error.message();
+        d->m_isValid = false;
+        return;
+    }
+
+    QDBusObjectPath channel_path=reply0.value();
+    openTextChannel( handle, 1,channel_path.path(), "org.freedesktop.Telepathy.Channel.Type.Text" ); // TODO: Remove magic number
+}
+
+// Called if a new text channel was notified by the connection channel
+void ChatChannel::openTextChannel(uint handle, uint handleType, const QString& channel_path, const QString& channelType)
+{
+    QString channel_service_name = d->m_pConnectionInterface->service();
+    qDebug() << "ContactManager Channel Services Name" << channel_service_name;
+    qDebug() << "ContactManager Channel Path" << channel_path;
+    // This channel may never be closed!
+    d->m_pTextChannel = new Telepathy::Client::ChannelTypeTextInterface( channel_service_name,
+                                                                     channel_path,
+                                                                     this );
+    if (!d->m_pTextChannel->isValid())
+    {
+        qDebug() << "Failed to connect channel interface class to D-Bus object.";
+        delete d->m_pTextChannel;
+        d->m_pTextChannel = NULL;
+        d->m_isValid = false;
+        return;
+    }
+    else
+    {
+        if ( d->m_areSignalsConnected )
+        { return; }
+         
+        d->m_areSignalsConnected = true;
+        
+        qDebug() << "Success WE got a valid Text channel";
+        //ChatChannel * pChatChannel=new ChatChannel();
+        //pChatChannel->setChannel(d->m_groupTextChannel);
+        //pChatChannel->setContact(channel_contact);
+        QString messagesender;
+        messagesender = d->m_pContact->name();
+
+        qDebug() << "*************************************";
+        
+        connect(d->m_pTextChannel, SIGNAL(Received(uint , uint , uint , uint , uint , const QString& )),
+                this, SLOT(slotReceivedText(uint , uint , uint , uint , uint , const QString& )));
+        connect(d->m_pTextChannel, SIGNAL(Sent(uint , uint , const QString& )),
+                this, SLOT(slotSentText(uint , uint , const QString& )));
+        connect(d->m_pTextChannel, SIGNAL(LostMessage()),
+                this, SLOT(slotLostMessage()));
+        connect(d->m_pTextChannel, SIGNAL(SendError(uint , uint , uint , const QString& )),
+                this, SLOT(slotSendError(uint , uint , uint , const QString& )));
+
+    /*  QDBusPendingReply<Telepathy::PendingTextMessageList>  reply= d->m_groupTextChannel->ListPendingMessages(false);
+                                const Telepathy::PendingTextMessageList chatMessages=reply.value();
+                                Telepathy::PendingTextMessage messageshandle;
+                                for (int i=0; i<chatMessages.size(); i++)
+                                {
+                                messageshandle= chatMessages.at(i);
+                                pChatChannel->slotReceivedText( messageshandle.identifier, messageshandle.unixTimestamp, messageshandle.sender, messageshandle.messageType, messageshandle.flags, messageshandle.text);
+
+                }     */
+    }
+}
+
+
+void ChatChannel::slotReceivedText( uint id, uint timestamp, uint sender, uint type, uint flags, const QString& text )
+{
+    qDebug() << "ChatChannel: Reveived text:" << text;
+    QList<uint> message_ids;
+    message_ids.append( id );
+    d->m_pTextChannel->AcknowledgePendingMessages( message_ids );
+    emit signalTextMessageReceived( this , timestamp, type, flags, text );
+}
+
+void ChatChannel::slotSentText(uint timestamp, uint type, const QString& text )
+{
+    qDebug() << "ChatChannel: Sent text:" << text;
+    emit signalTextMessageSent( this, timestamp, type, text );
+}
+
+void ChatChannel::slotLostMessage()
+{
+}
+
+void ChatChannel::slotSendError(uint error, uint timestamp, uint type, const QString& text )
+{
+}
diff --git a/TelepathyQt4/Prototype/ChatChannel.h b/TelepathyQt4/Prototype/ChatChannel.h
new file mode 100644
index 0000000..14d05b6
--- /dev/null
+++ b/TelepathyQt4/Prototype/ChatChannel.h
@@ -0,0 +1,119 @@
+/*
+ * This file is part of TelepathyQt4
+ *
+ * Copyright (C) 2008 basysKom GmbH
+ * Copyright (C) 2008 Collabora Ltd. <http://www.collabora.co.uk/>
+ * Copyright (C) 2008 Nokia Corporation
+ *
+ * This library is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU Lesser General Public
+ * License as published by the Free Software Foundation; either
+ * version 2.1 of the License, or (at your option) any later version.
+ *
+ * This library is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
+ * Lesser General Public License for more details.
+ *
+ * You should have received a copy of the GNU Lesser General Public
+ * License along with this library; if not, write to the Free Software
+ * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA  02110-1301  USA
+ */
+
+#ifndef TelepathyQt4_Prototype_ChatChannel_H_
+#define TelepathyQt4_Prototype_ChatChannel_H_
+
+#include <QObject>
+#include <QPointer>
+#include <QVariantMap>
+
+#ifdef DEPRECATED_ENABLED__
+#define ATTRIBUTE_DEPRECATED __attribute__((deprecated))
+#else
+#define ATTRIBUTE_DEPRECATED
+#endif
+
+namespace Telepathy {
+namespace Client{
+    class ConnectionInterface;
+}
+}
+
+namespace TpPrototype {
+
+class ChatChannelPrivate;
+class Contact;
+class Account;
+
+/**
+ * @ingroup qt_connection
+ * Chat Channel.
+ * This class provides the interface to send or receive text messages.
+ */
+class ChatChannel : public QObject
+{
+    Q_OBJECT
+public:
+    /**
+     * Validity check.
+     * Do not access any functions if this account is invalid.
+     */
+    bool isValid() const;
+    
+    /**
+     * Send a text message.
+     * This function sends a text message to the contact that belongs to this channel.
+     */
+    void sendTextMessage( const QString& text );
+
+    /**
+     * Fetch pending text messages.
+     * Force to refetch all messages that were sent while the account was offline.
+     * A signal signalTextMessageReceived() will be emitted for every message.
+     * @see signalTextMessageReceived()
+     */
+    void pendingTextMessages();
+        
+    /**
+     * Destructor.
+     * Deleting this object forces to drop all channels.
+     */
+    ~ChatChannel();
+
+signals:
+    /**
+     * A new text message was received.
+     * This signal is emmitted right after receiving a new test message.
+     */
+    void signalTextMessageReceived( TpPrototype::ChatChannel* chatchannel, uint timestamp, uint type, uint flags, const QString& text );
+    
+    /**
+     * A text message was sent.
+     * This signal is emmitted right after test message was delivered.
+     */
+    void signalTextMessageSent( TpPrototype::ChatChannel* chatchannel, uint timestamp, uint type, const QString& text );
+
+protected:
+   /**
+    * Constructor.
+    * Use Contact::chatChannel() to obtain an object of ChatChannel.
+    */
+    ChatChannel( Contact* contact, Telepathy::Client::ConnectionInterface* connectionInterface , QObject* parent = NULL );
+    
+    void requestTextChannel(uint handle);
+    void openTextChannel(uint handle, uint handleType, const QString& channelPath, const QString& channelType );
+
+protected slots:
+        void slotSentText(uint timestamp, uint type, const QString& text );
+        void slotLostMessage();
+        void slotSendError(uint error, uint timestamp, uint type, const QString& text );
+        void slotReceivedText(uint ID, uint timestamp, uint sender, uint type, uint flags, const QString& text);
+private:
+    ChatChannelPrivate * const d;
+    friend class ContactManager;
+    friend class Contact;
+};
+
+} // namespace
+
+#endif // Header guard
diff --git a/TelepathyQt4/Prototype/Client/ChannelHandler b/TelepathyQt4/Prototype/Client/ChannelHandler
new file mode 100644
index 0000000..142eada
--- /dev/null
+++ b/TelepathyQt4/Prototype/Client/ChannelHandler
@@ -0,0 +1,6 @@
+#ifndef _TelepathyQt4_Prototype_Client_ChannelHandler_HEADER_GUARD_
+#define _TelepathyQt4_Prototype_Client_ChannelHandler_HEADER_GUARD_
+
+#include <TelepathyQt4/Prototype/_gen/cli-channel-handler.h>
+
+#endif
diff --git a/TelepathyQt4/Prototype/Connection.cpp b/TelepathyQt4/Prototype/Connection.cpp
new file mode 100644
index 0000000..9a9ca06
--- /dev/null
+++ b/TelepathyQt4/Prototype/Connection.cpp
@@ -0,0 +1,434 @@
+/*
+ * This file is part of TelepathyQt4
+ *
+ * Copyright (C) 2008 basysKom GmbH
+ * Copyright (C) 2008 Collabora Ltd. <http://www.collabora.co.uk/>
+ * Copyright (C) 2008 Nokia Corporation
+ *
+ * This library is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU Lesser General Public
+ * License as published by the Free Software Foundation; either
+ * version 2.1 of the License, or (at your option) any later version.
+ *
+ * This library is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
+ * Lesser General Public License for more details.
+ *
+ * You should have received a copy of the GNU Lesser General Public
+ * License along with this library; if not, write to the Free Software
+ * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA  02110-1301  USA
+ */
+
+#include "TelepathyQt4/Prototype/Connection.h"
+
+#include <QDebug>
+#include <QMetaProperty>
+
+#include <TelepathyQt4/Client/Connection>
+#include <TelepathyQt4/Client/ConnectionManager>
+
+#include <TelepathyQt4/Prototype/Account.h>
+#include <TelepathyQt4/Prototype/AvatarManager.h>
+#include <TelepathyQt4/Prototype/CapabilitiesManager.h>
+#include <TelepathyQt4/Prototype/ContactManager.h>
+#include <TelepathyQt4/Prototype/PresenceManager.h>
+
+// #define ENABLE_DEBUG_OUTPUT_
+
+namespace TpPrototype {
+
+class ConnectionPrivate
+{
+public:
+    ConnectionPrivate()
+    { init(); }
+    
+    QString                                 m_serviceName;
+    QString                                 m_objectPath;
+    bool                                    m_isValid;
+    Telepathy::ConnectionStatus             m_status;
+    Telepathy::ConnectionStatusReason       m_reason;
+    Telepathy::Client::ConnectionInterface* m_pInterface;
+    QPointer<ContactManager>                m_pContactManager;
+    QPointer<PresenceManager>               m_pPresenceManager;
+    QPointer<CapabilitiesManager>           m_pCapabilitiesManager;
+    QPointer<AvatarManager>                 m_pAvatarManager;
+    QPointer<Account>                       m_pAccount;
+    QString                                 m_connectionManager;
+    QString                                 m_protocol;
+    void init()
+    {
+        m_isValid              = false; // Will be set on true after initial initialization.
+        m_status               = Telepathy::ConnectionStatusDisconnected;
+        m_reason               = Telepathy::ConnectionStatusReasonNoneSpecified;
+        m_pInterface           = NULL;
+        m_pContactManager      = NULL;
+        m_pPresenceManager     = NULL;
+        m_pCapabilitiesManager = NULL;
+        m_pAvatarManager       = NULL;
+        m_pAccount             = NULL;
+    }
+
+    void cleanup()
+    {
+        m_isValid              = true;
+        m_status               = Telepathy::ConnectionStatusDisconnected;
+        m_reason               = Telepathy::ConnectionStatusReasonNoneSpecified;
+        delete m_pInterface;
+        m_pInterface           = NULL;
+        delete m_pContactManager;
+        m_pContactManager      = NULL;
+        delete m_pPresenceManager;
+        m_pPresenceManager     = NULL;
+        delete m_pCapabilitiesManager;
+        m_pCapabilitiesManager = NULL;
+        delete m_pAvatarManager;
+        m_pAvatarManager       = NULL;
+    }
+
+    void initConnectionDBUSService()
+    {
+        cleanup();
+        
+        Q_ASSERT( m_pAccount );
+        Q_ASSERT( !m_pInterface ); // needs to be removed. Otherwise all following will fail
+        Q_ASSERT( !m_connectionManager.isEmpty() );
+        Q_ASSERT( !m_protocol.isEmpty() );
+        
+        Telepathy::Client::ConnectionManagerInterface cm_interface( "org.freedesktop.Telepathy.ConnectionManager." + m_connectionManager,
+                                                                    "/org/freedesktop/Telepathy/ConnectionManager/" +  m_connectionManager,
+                                                                    NULL );
+
+
+        QVariantMap parameter_map = m_pAccount->parameters();
+
+        // 2. Request a connection to the server
+
+#ifdef ENABLE_DEBUG_OUTPUT_
+        qDebug() << "Protocol: " << m_protocol;
+        qDebug() << "Params  : " << parameter_map;
+#endif
+
+        QDBusPendingReply<QString, QDBusObjectPath> reply = cm_interface.RequestConnection( m_protocol, parameter_map );
+        reply.waitForFinished();
+
+        if ( !reply.isValid() )
+        {
+            QDBusError error = reply.error();
+#ifdef ENABLE_DEBUG_OUTPUT_
+            qDebug() << "initConnectionDBUSService: error type:" << error.type()
+                    << " error name:" << error.name();
+#endif
+            m_isValid = false;
+            return /*NULL*/;
+        }
+
+        QString connection_service_name = reply.argumentAt<0>();
+        QDBusObjectPath connection_object_path = reply.argumentAt<1>();
+#ifdef ENABLE_DEBUG_OUTPUT_
+        qDebug() << "Service Name: " << connection_service_name;
+        qDebug() << "Object Path : " << connection_object_path.path();
+#endif
+        m_serviceName = connection_service_name;
+        m_objectPath  = connection_object_path.path();
+        
+        m_pInterface  = new Telepathy::Client::ConnectionInterface( m_serviceName,
+                                                                    m_objectPath,
+                                                                    NULL );
+
+    }
+};
+};
+
+TpPrototype::Connection::Connection( TpPrototype::Account* account, QObject* parent ):
+    QObject( parent ),
+    d( new ConnectionPrivate )
+{
+
+    if ( !account )
+    { return; }
+    
+    init( account );
+}
+
+using namespace TpPrototype;
+Connection::~Connection()
+{
+#ifdef ENABLE_DEBUG_OUTPUT_
+    qDebug() << "D'tor Connection:" << this;
+#endif
+    if ( Telepathy::ConnectionStatusDisconnected != d->m_status )
+    { requestDisconnect(); }
+    delete d;
+}
+
+
+bool Connection::isValid()
+{
+    return d->m_isValid;
+}
+
+Telepathy::ConnectionStatus Connection::status()
+{
+    return d->m_status;
+}
+
+Telepathy::ConnectionStatusReason Connection::reason()
+{
+    return d->m_reason;
+}
+
+bool Connection::requestConnect()
+{
+    if ( ( Telepathy::ConnectionStatusConnecting == d->m_status )
+           || ( Telepathy::ConnectionStatusConnected == d->m_status ) )
+    { return false; }
+
+    startupInit();
+
+    if ( !d->m_pInterface )
+    { return false; }
+    
+    d->m_status = Telepathy::ConnectionStatusConnecting;
+    QDBusPendingReply<> connection_connect_reply = d->m_pInterface->Connect();
+    connection_connect_reply.waitForFinished();
+   
+    if ( !connection_connect_reply.isValid() )
+    {
+        QDBusError error = connection_connect_reply.error();
+    
+        qWarning() << "Connect: error type:" << error.type()
+                << "Connect: error name:" << error.name()
+                << "error message:" << error.message();
+        
+        d->m_status      = Telepathy::ConnectionStatusDisconnected;
+        d->m_isValid     = false;
+
+        return false;
+    }
+
+    d->m_isValid = true;
+    return true;
+}
+
+bool Connection::requestDisconnect()
+{
+    if ( ! d->m_pInterface || ! isValid() || ( Telepathy::ConnectionStatusDisconnected == d->m_status ) )
+    { return false; }
+    
+    QDBusPendingReply<> connection_disconnect_reply = d->m_pInterface->Disconnect();
+    connection_disconnect_reply.waitForFinished();
+
+    if ( !connection_disconnect_reply.isValid() )
+    {
+        QDBusError error = connection_disconnect_reply.error();
+
+        qWarning() << "Connect: error type:" << error.type()
+                << "Connect: error name:" << error.name()
+                << "error message:" << error.message();
+    }
+
+    // Always expect that we are disconnected after this point!
+    d->m_status = Telepathy::ConnectionStatusDisconnected;
+
+    // Get rid of the contact and presence manager
+    delete d->m_pContactManager;
+    d->m_pContactManager = NULL;
+    delete d->m_pPresenceManager;
+    d->m_pPresenceManager = NULL;
+
+    return d->m_status;
+}
+
+ContactManager* Connection::contactManager()
+{
+    if ( Telepathy::ConnectionStatusConnected != d->m_status )
+    { return NULL; }
+    if ( !d->m_pContactManager )
+    { d->m_pContactManager = new ContactManager( d->m_pInterface, this ); }
+    return d->m_pContactManager;
+}
+
+PresenceManager* Connection::presenceManager()
+{
+    return createManager<PresenceManager>( d->m_pPresenceManager, "Presence" );
+}
+
+CapabilitiesManager* Connection::capabilitiesManager()
+{
+    return createManager<CapabilitiesManager>(d->m_pCapabilitiesManager, "Capabilities" );
+}
+
+AvatarManager* Connection::avatarManager()
+{
+    return createManager<AvatarManager>( d->m_pAvatarManager, "Avatars" );
+}
+
+
+Account* Connection::account() const
+{
+    if ( !d->m_pAccount
+        || !d->m_pAccount->isValid() )
+    { return NULL; }
+    
+    return d->m_pAccount;
+}        
+
+QString Connection::handle() const
+{
+    return d->m_objectPath;
+}
+
+Telepathy::Client::ConnectionInterface* Connection::interface()
+{
+    return d->m_pInterface;
+}
+
+void Connection::slotStatusChanged( uint status, uint reason )
+{
+#ifdef ENABLE_DEBUG_OUTPUT_
+    qDebug() << "Connection::slotStatusChanged() Status:" << status;
+#endif
+    Telepathy::ConnectionStatus old_status = d->m_status;
+    d->m_status = static_cast<Telepathy::ConnectionStatus>( status );
+    d->m_reason = static_cast<Telepathy::ConnectionStatusReason>( reason );
+
+    emit signalStatusChanged( this, d->m_status, old_status );
+
+    if ( account() && account()->parameters().value( "register") == true )
+    {
+        QVariantMap parameter_map;
+        parameter_map.insert( "register", false );
+        account()->setParameters( parameter_map );
+    }
+}
+
+void Connection::slotNewChannel(const QDBusObjectPath& objectPath, const QString& channelType, uint handleType, uint handle, bool suppressHandler)
+{
+    Q_UNUSED( suppressHandler );
+
+    QString tmp_objectpath=objectPath.path();
+#ifdef ENABLE_DEBUG_OUTPUT_
+    qDebug() << "Connection:: slotNewChannel";
+    qDebug() << "Connection:: slotNewChannel ObjectPath"<< tmp_objectpath;
+    qDebug() << "Connection:: slotNewChannel ChannelType"<< channelType;
+    qDebug() << "Connection:: slotNewChannel handleType"<< handleType <<"handle"<<handle;
+#endif
+
+    // Ignore signals if no contact manager is available..
+    if ( !contactManager() )
+    {
+        // Q_ASSERT( contactManager() ); //FIXME: We have to understand why this can happen and how to avoid it!
+        qWarning() << "Connection::slotNewChannel: Receiving signals but don't get a contact manager!";
+        return;
+    }
+    
+    if ( handleType == Telepathy::HandleTypeContact )
+    {
+        contactManager()->openTextChannel(handle,handleType,objectPath.path(),channelType);
+    }
+  
+    if (channelType==QString("org.freedesktop.Telepathy.Channel.Type.ContactList"))
+    {
+        if (tmp_objectpath.contains("/subscribe"))
+        { 
+            contactManager()->openSubscribedContactsChannel(handle,objectPath,channelType);
+        }
+    }
+    
+    if (channelType==QString("org.freedesktop.Telepathy.Channel.Type.ContactList"))
+    {
+      if (tmp_objectpath.contains("/known"))
+      {         
+          contactManager()->openKnownContactsChannel(handle,objectPath,channelType);
+      }
+    }
+    if (channelType==QString("org.freedesktop.Telepathy.Channel.Type.ContactList"))
+    {
+        if (tmp_objectpath.contains("/publish"))
+        {
+            contactManager()->openPublishContactsChannel(handle,objectPath,channelType);
+        }
+    }
+
+    if (channelType==QString("org.freedesktop.Telepathy.Channel.Type.ContactList"))
+    {
+        if (tmp_objectpath.contains("/deny"))
+        { 
+            contactManager()->openDenyContactsChannel(handle,objectPath,channelType);
+        }
+    }
+
+    if (channelType==QString("org.freedesktop.Telepathy.Channel.Type.StreamedMedia"))
+    {
+#ifdef ENABLE_DEBUG_OUTPUT_
+        qDebug() << "Connection::slotNewChannel(): Stream media channel opened!!";
+#endif
+        contactManager()->openStreamedMediaChannel( handle, handleType, objectPath.path(), channelType );
+    }
+}
+
+QList<uint> Connection::RequestHandles( Telepathy::HandleType handletype, QStringList& handlestrings)
+{
+    Telepathy::registerTypes();
+    return d->m_pInterface->RequestHandles( handletype,handlestrings);
+}
+
+
+bool Connection::managerSupported( const QString& managerName )
+{
+    QDBusPendingReply<QStringList> interfaces_reply = interface()->GetInterfaces();
+    interfaces_reply.waitForFinished();
+
+    if ( !interfaces_reply.isValid() )
+    {
+        QDBusError error = interfaces_reply.error();
+        
+        qWarning() << "Connection::GetInterfaces: error type:" << error.type()
+                << "error name:" << error.name()
+                << "error message:" << error.message();
+
+        return false;
+    }
+
+    foreach( const QString& interface, interfaces_reply.value() )
+    {
+        if ( interface.endsWith( managerName ) )
+        {
+            return true;
+        }
+    }
+    return false;
+}
+
+void Connection::init( TpPrototype::Account* account )
+{
+    Telepathy::registerTypes();
+
+    if ( !account )
+    { return; }
+
+    d->m_pAccount          = account;
+    d->m_connectionManager = account->connectionManagerName();
+    d->m_protocol          = account->protocolName();
+
+    d->m_isValid = true;
+}
+
+// Called immediately before connection attempts
+void Connection::startupInit()
+{
+    d->initConnectionDBUSService();
+
+    if ( !d->m_isValid )
+    { return; }
+    
+    Q_ASSERT( d->m_pInterface );
+
+
+    connect( d->m_pInterface, SIGNAL( NewChannel( const QDBusObjectPath&, const QString&, uint, uint, bool ) ),
+             this, SLOT( slotNewChannel( const QDBusObjectPath&, const QString&, uint, uint, bool ) ) );
+    connect( d->m_pInterface, SIGNAL( StatusChanged( uint, uint ) ),
+             this, SLOT( slotStatusChanged( uint, uint ) ) );
+}
diff --git a/TelepathyQt4/Prototype/Connection.h b/TelepathyQt4/Prototype/Connection.h
new file mode 100644
index 0000000..34e4904
--- /dev/null
+++ b/TelepathyQt4/Prototype/Connection.h
@@ -0,0 +1,256 @@
+/*
+ * This file is part of TelepathyQt4
+ *
+ * Copyright (C) 2008 basysKom GmbH
+ * Copyright (C) 2008 Collabora Ltd. <http://www.collabora.co.uk/>
+ * Copyright (C) 2008 Nokia Corporation
+ *
+ * This library is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU Lesser General Public
+ * License as published by the Free Software Foundation; either
+ * version 2.1 of the License, or (at your option) any later version.
+ *
+ * This library is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
+ * Lesser General Public License for more details.
+ *
+ * You should have received a copy of the GNU Lesser General Public
+ * License along with this library; if not, write to the Free Software
+ * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA  02110-1301  USA
+ */
+#ifndef TelepathyQt4_Prototype_Connection_H_
+#define TelepathyQt4_Prototype_Connection_H_
+
+#include <QDBusObjectPath>
+#include <QDBusPendingReply>
+#include <QObject>
+#include <QPointer>
+#include <QVariantMap>
+
+#include <TelepathyQt4/Constants>
+
+#ifdef DEPRECATED_ENABLED__
+#define ATTRIBUTE_DEPRECATED __attribute__((deprecated))
+#else
+#define ATTRIBUTE_DEPRECATED
+#endif
+
+namespace Telepathy
+{ 
+    namespace Client
+    {
+        class ConnectionInterface;
+    }
+}
+
+/**
+ * @defgroup qt_connection Connection Management
+ * @ingroup qt_style_api
+ * Classes that provide functions to handle connections and additional optional interfaces related to a connection.
+ */
+
+
+
+namespace TpPrototype {
+
+class ConnectionPrivate;
+class ContactManager;
+class PresenceManager;
+class CapabilitiesManager;
+class AvatarManager;
+class Account;
+/**
+ * @ingroup qt_connection
+ * This class manages a connection.
+ * The connection object provides access to optional interfaces that are related to the connection using contactManager(),
+ * capabilitiesManager(), presenceManager(), avatarManager().
+ * @todo In order to allow custom extensions, we need a support for register proxies in the Account object
+ */
+class Connection : public QObject
+{
+    Q_OBJECT
+    Q_PROPERTY( bool valid READ isValid )
+public:
+
+    ~Connection();
+
+    /**
+     * Validity check.
+     * Do not access any functions if this account is invalid.
+     */
+    bool isValid();
+
+    /**
+     * Connection Status.
+     * @return The current connection status.
+     * @see Telepathy::ConnectionStatus defined in constants.h
+     */
+    Telepathy::ConnectionStatus status();
+
+    /**
+     * Reason for last state change.
+     * @return The reason.
+     * @see Telepathy::ConnectionStatusReason defined in constants.h
+     */
+    Telepathy::ConnectionStatusReason reason();
+
+   /**
+    * Connect to server.
+    * This call is asynchrous. Wait until signalStatusChanged() was emitted and the connection state is Telepathy::ConnectionStatusConnected
+    * before calling contactManager() or presenceManager() will succeed.
+    * @see signalStatusChanged()
+    */
+    bool requestConnect();
+
+   /**
+    * Disconnect. Disconnects from the server.
+    */
+    bool requestDisconnect();
+
+    /**
+     * Returns the contact list manager.
+     * The contact list manager contains the list of contacts and provides functions like add and remove.<br>
+     * <b>Note:</b> You have to request a connection with requestConnect() before a contact manager can be returned. If the connection disconnects the ContactManager will be invalid!
+     * @return Pointer to the contact manager or NULL if something went wrong.
+     * @see requestConnect()
+     */
+    ContactManager* contactManager();
+
+    /**
+     * Returns the presence manager.
+     * The presence manager handles your presence state for this connection.<br>
+     * <br>
+     * <b>Note:</b>
+     * <ul><li>You have to request a connection with requestConnect() before a presence manager can be returned.</li>
+     *     <li>You have to call this function in order to get your contacts updated automatically.</li>
+     * </ul>
+     * @return Pointer to the presence manager or NULL if no presence handling is supported or no connection was requested.
+     * @see requestConnect()
+     */
+    PresenceManager* presenceManager(); 
+ 
+    /**
+     * Returns the capabilities manager.
+     * The capabilities manager handles your capabilities state for this connection.<br>
+     * <br>
+     * <b>Note:</b>
+     * <ul><li>You have to request a connection with requestConnect() before a capability manager can be returned.</li>
+     *     <li>You have to call this function in order to get your contacts updated automatically.</li>
+     * </ul>
+     * @return Pointer to the capabilities manager or NULL if no capabilities handling is supported or no connection was requested.
+     * @see requestConnect()
+     */
+    CapabilitiesManager* capabilitiesManager();
+
+    /**
+     * Returns the avatar manager.
+     * The avatar manager provides you information about the avatars of the connection.<br>
+     * <br>
+     * <b>Note:</b>
+     * <ul><li>You have to request a connection with requestConnect() before an avatar manager can be returned.</li>
+     *     <li>You have to call this function in order to get your contacts updated automatically.</li>
+     * </ul>
+     * @return Pointer to the avatar manager or NULL if no avatar support is available or no connection was requested.
+     * @see requestConnect()
+     */
+    AvatarManager* avatarManager();
+   
+    /**
+     * Returns the account for this connection.
+     * Every connection belongs to an account that is returned with this call.
+     * @return The account for this connection or NULL if no valid account exists.
+     */
+    Account* account() const;
+
+signals:
+    /**
+     * Connection status changed.
+     * This signal is emitted if the status of the connection was changed
+     * @param connection The connection which changes its status.
+     * @param newStatus The new status that is valid now.
+     * @param oldStatus The old status that was valid before.
+     * @see Telepathy::ConnectionStatus
+     */
+    void signalStatusChanged( TpPrototype::Connection* connection,
+                              Telepathy::ConnectionStatus newStatus,
+                              Telepathy::ConnectionStatus oldStatus );
+
+protected slots:
+    void slotStatusChanged( uint status, uint reason );
+    void slotNewChannel( const QDBusObjectPath& objectPath, const QString& channelType, uint handleType, uint handle, bool suppressHandler );
+
+protected:
+   /**
+    * Constructor.
+    * The connection cannot be instantiated directly. Use Account::connection() to receive a valid connection object.
+    * @param account Account to create connection with.
+    */
+    Connection( TpPrototype::Account* account, QObject* parent );
+
+    /**
+     * Returns the handle.
+     * The handle is an internal representation to access the real data. Its format should
+     * not be interpreted.
+     */
+    QString handle() const;
+
+    /**
+     * D-BUS interface.
+     * This protected access to the D-BUS interface can be used to extend this class with special features.
+     */
+    Telepathy::Client::ConnectionInterface* interface();
+
+    /**
+     * Provides a generic handle.
+     * @param handleType The type of handle required.
+     * @param handlestrings An array of names of entities to request handles for
+     * @return An array of integer handle numbers in the same order as the given strings
+     */
+    QList<uint> RequestHandles( Telepathy::HandleType handletype, QStringList& handlestrings);
+
+    /**
+     * Check if manager is supported.
+    */
+    bool managerSupported( const QString& managerName );
+
+    template <class Manager>
+            inline Manager* createManager( QPointer<Manager>& pManager, const QString& managerName )
+    {
+        if ( pManager && pManager->isValid() )
+        { return pManager; }
+
+        // Force to reinitialize an invalid manager
+        if ( pManager && !pManager->isValid() )
+        {
+            delete pManager;
+            pManager = NULL;
+        }
+
+        if ( status() != Telepathy::ConnectionStatusConnected )
+        { return NULL; }
+
+        pManager = new Manager( this, interface(), this );
+        Q_ASSERT( pManager );
+        
+        if ( pManager->isValid() )
+        { return pManager; }
+            
+        // Fall through: Cleanup if manager is not valid.
+        delete pManager;
+        pManager = NULL;
+        return NULL;
+    }
+
+
+private:
+    void init( TpPrototype::Account* account );
+    void startupInit();
+    ConnectionPrivate * const d;
+
+    friend class Account;
+};
+
+} // namespace
+
+#endif
diff --git a/TelepathyQt4/Prototype/ConnectionFacade.cpp b/TelepathyQt4/Prototype/ConnectionFacade.cpp
new file mode 100644
index 0000000..d4b8af0
--- /dev/null
+++ b/TelepathyQt4/Prototype/ConnectionFacade.cpp
@@ -0,0 +1,265 @@
+/*
+ * This file is part of TelepathyQt4
+ *
+ * Copyright (C) 2008 basysKom GmbH
+ * Copyright (C) 2008 Collabora Ltd. <http://www.collabora.co.uk/>
+ * Copyright (C) 2008 Nokia Corporation
+ *
+ * This library is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU Lesser General Public
+ * License as published by the Free Software Foundation; either
+ * version 2.1 of the License, or (at your option) any later version.
+ *
+ * This library is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
+ * Lesser General Public License for more details.
+ *
+ * You should have received a copy of the GNU Lesser General Public
+ * License along with this library; if not, write to the Free Software
+ * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA  02110-1301  USA
+ */
+
+#include "TelepathyQt4/Prototype/ConnectionFacade.h"
+
+#include <QCoreApplication>
+#include <QDebug>
+#include <QPointer>
+
+#include <TelepathyQt4/Client/Connection>
+#include <TelepathyQt4/Client/ConnectionManager>
+
+#include <TelepathyQt4/Prototype/Account.h>
+#include <TelepathyQt4/Prototype/AccountManager.h>
+#include <TelepathyQt4/Prototype/Connection.h>
+#include <TelepathyQt4/Prototype/DBusInterface.h>
+
+using namespace TpPrototype;
+
+ConnectionFacade* ConnectionFacade::m_instance = NULL;
+
+enum {
+    mgr_Param_Flag_Required = 1,
+    mgr_Param_Flag_Register = 2,
+    mgr_Param_Flag_Has_Default = 4,
+    mgr_Param_Flag_Secret = 8
+};
+    
+
+class TpPrototype::ConnectionFacadePrivate
+{
+public:
+};
+
+ConnectionFacade* ConnectionFacade::instance()
+{
+    if ( NULL == m_instance )
+    {
+        m_instance = new ConnectionFacade( QCoreApplication::instance() );
+    }
+
+    return m_instance;
+}
+
+ConnectionFacade::ConnectionFacade( QObject* parent ):
+    QObject( parent ),
+    d( new ConnectionFacadePrivate )
+{
+}
+
+ConnectionFacade::~ConnectionFacade()
+{
+    delete d;
+}
+
+QStringList ConnectionFacade::listOfConnectionManagers()
+{
+    Telepathy::registerTypes();
+
+    QStringList ret_list;
+    
+    DBusInterface* interface = new DBusInterface( NULL );
+    
+    QDBusReply<QStringList> reply = interface->listActivatableNames();
+    
+    delete interface;
+    
+    if ( !reply.isValid() )
+    {
+        QDBusError error = reply.error();
+    
+        qWarning() << "Disconnect: error type:" << error.type()
+                << "error name:" << error.name()
+                << "error message:" << error.message();
+                   
+        return ret_list; // returns empty list
+    }
+    
+    
+    foreach( const QString& name, reply.value() )
+    {
+        // qDebug() << "+++Name: " << name;
+        if ( !name.startsWith( "org.freedesktop.Telepathy.ConnectionManager" ) 
+             || name.isEmpty() )
+        { continue; }
+        
+        QString cm_name;
+        int pos_of_last_dot = name.lastIndexOf( "." );
+        Q_ASSERT( pos_of_last_dot >= 0 );
+        cm_name = name.right( name.length() - ( pos_of_last_dot + 1 ) );
+        ret_list << cm_name;
+    }
+        
+    // qDebug() << "+++Names found: " << ret_list;
+    return ret_list;
+}
+
+QStringList ConnectionFacade::listOfProtocolsForConnectionManager( const QString& connectionManager )
+{
+    Telepathy::registerTypes();
+
+    QStringList empty_list;
+
+    QStringList list_of_connection_managers = listOfConnectionManagers();
+    if ( !list_of_connection_managers.contains( connectionManager ) )
+    { return empty_list; } // return empty list
+
+    Telepathy::Client::ConnectionManagerInterface connection_manager_interface( "org.freedesktop.Telepathy.ConnectionManager." + connectionManager,
+                                                                                "/org/freedesktop/Telepathy/ConnectionManager/" + connectionManager );
+    
+    QDBusPendingReply<QStringList> list_protocols_reply = connection_manager_interface.ListProtocols();
+    list_protocols_reply.waitForFinished();
+
+    if ( !list_protocols_reply.isValid() )
+    {
+        QDBusError error = list_protocols_reply.error();
+    
+        qWarning() << "ListProtocols: error type:" << error.type()
+                << "error name:" << error.name()
+                << "error message:" << error.message();
+                   
+        return empty_list; // returns empty list
+    }
+   
+    return list_protocols_reply.value(); 
+}
+
+// TODO: Return the parameter list with all flags as we receive it from telepathy. This solution hides the flags and is unable
+//       to handle all required types..
+Telepathy::ParamSpecList ConnectionFacade::paramSpecListForConnectionManagerAndProtocol( const QString& connectionManager, const QString& protocol )
+{
+    Telepathy::registerTypes();
+
+    Telepathy::Client::ConnectionManagerInterface connection_manager_interface( "org.freedesktop.Telepathy.ConnectionManager." + connectionManager,
+                                                                                "/org/freedesktop/Telepathy/ConnectionManager/" + connectionManager );
+    
+    QDBusPendingReply<Telepathy::ParamSpecList> get_parameters_reply = connection_manager_interface.GetParameters( protocol );
+    get_parameters_reply.waitForFinished();
+
+    if ( !get_parameters_reply.isValid() )
+    {
+        QDBusError error = get_parameters_reply.error();
+    
+        qWarning() << "ListProtocols: error type:" << error.type()
+                << "error name:" << error.name()
+                << "error message:" << error.message();
+                   
+        return Telepathy::ParamSpecList() ; // returns empty list
+    }
+
+    Telepathy::ParamSpecList param_spec_list = get_parameters_reply.value();
+
+    return param_spec_list;
+}
+
+QVariantMap ConnectionFacade::parameterListForConnectionManagerAndProtocol( const QString& connectionManager, const QString& protocol )
+{
+    QVariantMap ret_map;
+            
+    foreach( const Telepathy::ParamSpec& item, paramSpecListForConnectionManagerAndProtocol(connectionManager, protocol)  )
+    {
+        ret_map.insert( item.name, item.defaultValue.variant() );
+#ifdef ENABLE_DEBUG_OUTPUT_
+        qDebug() << "item: " << item.name << "flag:" << item.flags;
+#endif
+        if ( ( item.flags & ( mgr_Param_Flag_Required | mgr_Param_Flag_Register ) )
+               && item.defaultValue.variant().toString().isEmpty() )
+        {
+
+            if ( item.defaultValue.variant().type() == QVariant::String )
+            {
+                ret_map.insert( item.name, QVariant("required") );
+            }
+        }
+    }
+
+    return ret_map;
+}
+
+QVariantMap ConnectionFacade::parameterListForProtocol( const QString& protocol, int account_number ) 
+{
+    Telepathy::registerTypes();
+
+    QVariantMap ret_map;
+    
+    if (account_number==1)
+    {
+        ret_map.insert( "account", "basyskom at localhost" );
+    }
+    else  if (account_number==2)
+    {
+        ret_map.insert( "account", "test at localhost" );
+    }
+    ret_map.insert( "password", "basyskom" );
+    ret_map.insert( "server", "localhost" );
+    ret_map.insert( "resource", "Telepathy" );
+    ret_map.insert( "port", static_cast<uint>(5222) );    
+    return ret_map;
+}
+
+// account_number is used for test purposes only we have to delte this later
+TpPrototype::Connection* ConnectionFacade::connectionWithAccount( Account* account, int account_number )
+{
+    Telepathy::registerTypes();
+
+    if ( !account )
+    { return NULL; }
+
+    account->setParameters( parameterListForProtocol( "jabber", account_number  ) );
+    
+    // Get the default connection manager. "Default" is currently only the first one in the list of possible connection managers
+    QStringList connection_managers = listOfConnectionManagers();
+    Q_ASSERT( connection_managers.count() );
+    if ( !connection_managers.count() )
+    { return NULL; }
+    
+    return account->connection();
+}
+
+int ConnectionFacade::selfHandleForConnectionInterface( Telepathy::Client::ConnectionInterface* connectionInterface )
+{
+    if ( !connectionInterface )
+    {
+        return -1;
+    }
+
+    QDBusPendingReply<uint> local_handle_reply = connectionInterface->GetSelfHandle();
+    local_handle_reply.waitForFinished();
+
+    if ( !local_handle_reply.isValid() )
+    {
+        QDBusError error = local_handle_reply.error();
+
+        qWarning() << "GetSelfHandle: error type:" << error.type()
+                << "error name:" << error.name()
+                << "error message:" << error.message();
+
+        return -1;
+    }
+#ifdef ENABLE_DEBUG_OUTPUT_
+    qDebug() << "****Self handle:" << local_handle_reply.value();
+#endif
+    
+    return local_handle_reply.value();
+}
+
diff --git a/TelepathyQt4/Prototype/ConnectionFacade.h b/TelepathyQt4/Prototype/ConnectionFacade.h
new file mode 100644
index 0000000..4dbf1ed
--- /dev/null
+++ b/TelepathyQt4/Prototype/ConnectionFacade.h
@@ -0,0 +1,137 @@
+/*
+ * This file is part of TelepathyQt4
+ *
+ * Copyright (C) 2008 basysKom GmbH
+ * Copyright (C) 2008 Collabora Ltd. <http://www.collabora.co.uk/>
+ * Copyright (C) 2008 Nokia Corporation
+ *
+ * This library is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU Lesser General Public
+ * License as published by the Free Software Foundation; either
+ * version 2.1 of the License, or (at your option) any later version.
+ *
+ * This library is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
+ * Lesser General Public License for more details.
+ *
+ * You should have received a copy of the GNU Lesser General Public
+ * License along with this library; if not, write to the Free Software
+ * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA  02110-1301  USA
+ */
+#ifndef ConnectionFacade_H_
+#define ConnectionFacade_H_
+
+#include <QObject>
+#include <QStringList>
+#include <QVariantMap>
+
+#include <TelepathyQt4/Types>
+
+#ifdef DEPRECATED_ENABLED__
+#define ATTRIBUTE_DEPRECATED __attribute__((deprecated))
+#else
+#define ATTRIBUTE_DEPRECATED
+#endif
+
+namespace Telepathy
+{
+    namespace Client
+    {
+        class ConnectionInterface;
+    }
+}
+
+namespace TpPrototype
+{
+
+/**
+ * @defgroup qt_style_api Qt-Style Client API
+ * This API provides a high level client side API that enables developer to access to Telepathy on a high level of abstraction.
+ * These classes encapsulate all the D-Bus communication, error handling and Telepathy-Channel handling.
+ */
+
+/**
+ * @defgroup qt_convenience Convenience Classes
+ * @ingroup qt_style_api
+ * Classes that provide functions that are needed for various tasks.
+ */
+
+class ConnectionFacadePrivate;
+class Connection;
+class Account;
+
+/**
+ * @ingroup qt_convenience
+ * Class to access to Telepathy and Mission control services. This class is used to encapsulate the low level D-BUS Interface
+ * to Telepathy and MissionControl. It provides a series of helper functions.<br>
+ * This class follows the <i>facade</i> pattern.
+ * @todo Move as much functions as possible into adequate classes.
+ */
+class ConnectionFacade: public QObject
+{
+    Q_OBJECT
+public:
+    static ConnectionFacade* instance();
+    /**
+     * Returns a list of all connection managers registered.
+     * @return List of connection manager names.
+     */
+    QStringList listOfConnectionManagers();
+
+    /**
+     * Returns a list of supported protocols of a connection manager.
+     * @return List of supported protocols.
+     */
+    QStringList listOfProtocolsForConnectionManager( const QString& connectionManager );
+
+    /**
+     * Returns a Telepathy::ParamSpecList from the given protocol an connection manager.
+     * @param connectionManager The connection manager for the protocol.
+     * @param protocol Name of the protocol that is supported by the connection manager.
+     * @return A map with all supported parameters with default values. 
+     */
+    Telepathy::ParamSpecList paramSpecListForConnectionManagerAndProtocol( const QString& connectionManager, const QString& protocol );
+    
+    /**
+     * Returns a list of parameters for the given protocol and connection manager.
+     * @param connectionManager The connection manager for the protocol.
+     * @param protocol Name of the protocol that is supported by the connection manager.
+     * @return A map with all supported parameters with default values.
+     */
+    QVariantMap parameterListForConnectionManagerAndProtocol( const QString& connectionManager, const QString& protocol );
+
+    /**
+     * Returns a list of parameters for the given protocol.
+     * @deprecated Use parameterListForConnectionManagerAndProtocol() instead!
+     * @param protocol Name of the protocol.
+     * @return A map with all supported parameters with default values.
+     */
+    QVariantMap parameterListForProtocol( const QString& protocol, int account_number=1 ) ATTRIBUTE_DEPRECATED;
+
+    /**
+     * Connects to account. Connects an account to a service using the default connection manager.
+     * @deprecated Use <i>Account::connection()</i> instead!
+     * @param account The account to use.
+     * @return A connection. A null pointer is returned if the connection was <i>not</i> successful.
+     */
+    TpPrototype::Connection* connectionWithAccount( Account* account, int account_number=1 ) ATTRIBUTE_DEPRECATED;
+
+    /**
+     *  Returns the self handle. The self handle is needed by various interfaces to request information about myself
+     *  @todo: This is more or less a local function and should not be part of a public API. But I don't have a better place right now!
+     *  @return The local handle is usually 1 but may change on demand. -1 is returned on error.
+     */
+    int selfHandleForConnectionInterface( Telepathy::Client::ConnectionInterface* connectionInterface );
+
+private:
+    ConnectionFacade( QObject* parent );
+    ~ConnectionFacade();
+
+    ConnectionFacadePrivate * const d;
+    static ConnectionFacade* m_instance;
+};
+
+}
+#endif // ConnectionFacade_H_
+
diff --git a/TelepathyQt4/Prototype/Constants b/TelepathyQt4/Prototype/Constants
new file mode 100644
index 0000000..3cc33f9
--- /dev/null
+++ b/TelepathyQt4/Prototype/Constants
@@ -0,0 +1,6 @@
+#ifndef _TelepathyQt4_Prototype_Constants_HEADER_GUARD_
+#define _TelepathyQt4_Prototype_Constants_HEADER_GUARD_
+
+#include <TelepathyQt4/Prototype/constants.h>
+
+#endif
diff --git a/TelepathyQt4/Prototype/Contact.cpp b/TelepathyQt4/Prototype/Contact.cpp
new file mode 100644
index 0000000..c1ec2b8
--- /dev/null
+++ b/TelepathyQt4/Prototype/Contact.cpp
@@ -0,0 +1,189 @@
+/*
+ * This file is part of TelepathyQt4
+ *
+ * Copyright (C) 2008 basysKom GmbH
+ * Copyright (C) 2008 Collabora Ltd. <http://www.collabora.co.uk/>
+ * Copyright (C) 2008 Nokia Corporation
+ *
+ * This library is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU Lesser General Public
+ * License as published by the Free Software Foundation; either
+ * version 2.1 of the License, or (at your option) any later version.
+ *
+ * This library is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
+ * Lesser General Public License for more details.
+ *
+ * You should have received a copy of the GNU Lesser General Public
+ * License along with this library; if not, write to the Free Software
+ * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA  02110-1301  USA
+ */
+
+#include "TelepathyQt4/Prototype/Contact.h"
+
+#include <QDebug>
+#include <QMetaProperty>
+
+#include <TelepathyQt4/Client/Channel>
+#include <TelepathyQt4/Constants>
+
+#include <TelepathyQt4/Prototype/ChatChannel.h>
+#include <TelepathyQt4/Prototype/ContactManager.h>
+#include <TelepathyQt4/Prototype/StreamedMediaChannel.h>
+
+using namespace TpPrototype;
+
+class TpPrototype::ContactPrivate
+{
+public:
+    ContactPrivate( const uint & handle, const QString & name, Contact::ContactTypes type,
+                    Telepathy::Client::ConnectionInterface* connectionInterface, TpPrototype::ContactManager* contactManager )
+    { init(handle, name, type, connectionInterface, contactManager); }
+    ~ContactPrivate()
+    {}
+    uint                                      m_handle;
+    bool                                      m_isValid;
+    bool                                      m_isPresenceInitialized;
+    Contact::ContactTypes                     m_type;
+    QString                                   m_name;
+    uint                                      m_presenceType;
+    QString                                   m_presenceStatus;
+    QString                                   m_presenceMessage;
+    Telepathy::ContactCapabilityList          m_capabilityList;
+    TpPrototype::AvatarManager::Avatar          m_avatar;
+    Telepathy::Client::ConnectionInterface*   m_pConnectionInterface;
+    QPointer<TpPrototype::ChatChannel>          m_pChatChannel;
+    QPointer<TpPrototype::StreamedMediaChannel> m_pStreamedMediaChannel;
+    QPointer<TpPrototype::ContactManager>       m_pContactManager;
+    
+private:
+    void init( uint handle, const QString & name, Contact::ContactTypes type,
+               Telepathy::Client::ConnectionInterface* connectionInterface, TpPrototype::ContactManager* contactManager )
+    {
+        Q_ASSERT( connectionInterface );
+        Q_ASSERT( contactManager );
+        
+        m_handle                  = handle;
+        m_name                    = name;
+        m_type                    = type;
+        m_presenceType            = 0;
+        m_presenceStatus          = "unknown";
+        m_presenceMessage         = "";
+        m_pChatChannel            = NULL;
+        m_pStreamedMediaChannel   = NULL;
+        m_pConnectionInterface    = connectionInterface;
+        m_pContactManager         = contactManager;
+        m_isPresenceInitialized   = false;
+        
+        if ( 0 == m_handle )
+            m_isValid = false;
+        else
+            m_isValid = true;
+    }
+};
+
+uint Contact::telepathyHandle() const
+{ return d->m_handle; }
+
+uint Contact::telepathyHandleType() const
+{ return Telepathy::HandleTypeContact; }
+
+QString Contact::name() const
+{ return d->m_name; }
+
+Contact::ContactTypes Contact::type() const
+{ return d->m_type; }
+
+void Contact::setType( ContactTypes type )
+{
+    d->m_type = type;
+}
+
+bool Contact::isValid() const
+{ return d->m_isValid; }
+
+void Contact::setPresenceType( uint _presenceType)
+{ d->m_presenceType=_presenceType; }
+
+uint Contact::presenceType()
+{
+    d->m_isPresenceInitialized = true;
+    return d->m_presenceType;
+}
+
+void Contact::setPresenceStatus( QString _presenceStatus)
+{
+    d->m_isPresenceInitialized = true;
+    d->m_presenceStatus=_presenceStatus;
+}
+
+QString Contact::presenceStatus()
+{ return d->m_presenceStatus; }
+
+bool Contact::isPresenceStateAvailable()
+{ return d->m_isPresenceInitialized; }
+
+void Contact::setPresenceMessage( QString _presenceMessage)
+{ d->m_presenceMessage=_presenceMessage; }
+
+QString Contact::presenceMessage()
+{ return d->m_presenceMessage; }
+
+void Contact::setCapabilities( const Telepathy::ContactCapabilityList& capabilityList )
+{ d->m_capabilityList = capabilityList; }
+
+Telepathy::ContactCapabilityList Contact::capabilities() const
+{ return d->m_capabilityList; }
+
+void Contact::setAvatar( const TpPrototype::AvatarManager::Avatar& avatar )
+{
+    d->m_avatar = avatar;
+}
+
+Telepathy::Client::ConnectionInterface* Contact::interface()
+{
+    return d->m_pConnectionInterface;
+}
+
+TpPrototype::AvatarManager::Avatar Contact::avatar() const
+{
+    return d->m_avatar;
+}
+
+ChatChannel* Contact::chatChannel()
+{
+    if ( !d->m_pChatChannel )
+    {
+        d->m_pChatChannel = new ChatChannel( this, d->m_pConnectionInterface, this );
+        Q_ASSERT( d->m_pChatChannel->isValid() );
+    }
+    return d->m_pChatChannel;
+}
+
+TpPrototype::StreamedMediaChannel* Contact::streamedMediaChannel()
+{
+    if ( !d->m_pStreamedMediaChannel )
+    {
+        d->m_pStreamedMediaChannel = new StreamedMediaChannel( this, d->m_pConnectionInterface, this );
+        Q_ASSERT( d->m_pStreamedMediaChannel->isValid() );
+    }
+    return d->m_pStreamedMediaChannel;
+    
+}
+
+TpPrototype::ContactManager* Contact::contactManager()
+{
+    return d->m_pContactManager;
+}
+
+
+Contact::Contact( const uint & handle, const QString & url, ContactTypes type,
+                  Telepathy::Client::ConnectionInterface* connectionInterface, TpPrototype::ContactManager* contactManager ) :
+    QObject( contactManager ),
+    d( new ContactPrivate( handle, url, type, connectionInterface, contactManager ) )
+{   
+}
+
+Contact::~Contact()
+{ delete d; }
diff --git a/TelepathyQt4/Prototype/Contact.h b/TelepathyQt4/Prototype/Contact.h
new file mode 100644
index 0000000..3dc9bab
--- /dev/null
+++ b/TelepathyQt4/Prototype/Contact.h
@@ -0,0 +1,247 @@
+/*
+ * This file is part of TelepathyQt4
+ *
+ * Copyright (C) 2008 basysKom GmbH
+ * Copyright (C) 2008 Collabora Ltd. <http://www.collabora.co.uk/>
+ * Copyright (C) 2008 Nokia Corporation
+ *
+ * This library is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU Lesser General Public
+ * License as published by the Free Software Foundation; either
+ * version 2.1 of the License, or (at your option) any later version.
+ *
+ * This library is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
+ * Lesser General Public License for more details.
+ *
+ * You should have received a copy of the GNU Lesser General Public
+ * License along with this library; if not, write to the Free Software
+ * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA  02110-1301  USA
+ */
+
+#ifndef TelepathyQt4_Prototype_Contact_H_
+#define TelepathyQt4_Prototype_Contact_H_
+
+#include <QObject>
+#include <QPointer>
+#include <QVariantMap>
+
+#include <TelepathyQt4/Client/Channel>
+
+#include <TelepathyQt4/Prototype/AvatarManager.h>
+
+#ifdef DEPRECATED_ENABLED__
+#define ATTRIBUTE_DEPRECATED __attribute__((deprecated))
+#else
+#define ATTRIBUTE_DEPRECATED
+#endif
+
+namespace Telepathy
+{
+    namespace Client
+    {
+        class ConnectionInterface;
+    }
+}
+
+namespace TpPrototype {
+
+class ContactPrivate;
+class ContactManager;
+class ChatChannel;
+class StreamedMediaChannel;
+
+/**
+ * This class handles information related to a contact.
+ * Contact objects are always owned by ContactManager. Therefore, there is no way to create or remove a contact without using the ContactManager object.<br>
+ * Other Managers (like PresenceManager, AvatarManager) are accessing the contacts inside of the contact manager to update its information.
+ * Whether a contact was updated is signalled by the Managers but the new information is stored in the contact object and can be retrieved from it.
+ * @ingroup qt_connection
+ * @ingroup qt_contact
+ * @todo Do not provide a function for every presence parameter. Use SimplePresence instead.
+ * @todo Use implicit sharing instead of expolicit sharig!
+ * @see CapabilitiesManager, AvatarManager, PresenceManager
+ */
+class Contact : public QObject
+{
+    Q_OBJECT
+public:
+    enum ContactTypes
+    {
+        CT_Subscribed = 0,
+        CT_LocalPending,
+        CT_RemotePending,
+        CT_Removed,
+        CT_Known,
+        CT_Blocked
+    };
+
+    /**
+     * Validity.
+     * Do not access any method if this function returns false. 
+     */
+    bool isValid() const;
+    
+    /**
+     * Returns the contact type.
+     * @return The contact type.
+     */
+    ContactTypes type() const;
+
+    /**
+     * Set type.
+     * @param type The new type
+     * @see ContactTypes
+     */
+    void setType( ContactTypes type );
+    
+    /**
+     * Returns the telepathy internal handle.
+     * @return The telepathy internal handle.
+     */
+    uint telepathyHandle() const;
+    
+    /**
+     * Returns the telepathy internal handle type.
+     * @return The telepathy internal handle type.
+     */
+    uint telepathyHandleType() const;
+
+    /**
+     * Returns the name of the contact.
+     * @return The name of the contact as it is used by protocol  (E.g. user at jabber.org).
+     * @todo Make this private. We need an encapsulation for </i>PresenceManager::presencesForContacts()</i> first. (ses)
+     *       THUN: Stefan, this is not possible as this information is required to work with all telepathy classes
+     *       unknown to this lib.
+     */
+    QString name() const;
+
+    /**
+     * Returns the presence information of this contact.
+     * This presence information is automatically updated after the presence information was requested for the first time (PresenceManager::presencesForContacts()).<br>
+     * <b>Note:</b> Use <i>isPresenceStateAvailable()</i> to check whether the returned presence is valid!
+     * @todo Implement this!
+     * @see PresenceManager
+     */
+    Telepathy::SimplePresence presence() { return Telepathy::SimplePresence(); /* TODO: Implement me ! */ };
+    
+    /**
+     * @todo: Add Doc and get/setr in presence manager
+     * @deprecated Use <i>presence()</i> instead.
+     *
+     */
+    uint presenceType() ATTRIBUTE_DEPRECATED; 
+
+    /**
+     * @todo: Add Doc and get/setr in presence manager
+     * @deprecated Use <i>presence()</i> instead.
+     *
+     */
+    QString presenceStatus() ATTRIBUTE_DEPRECATED;
+
+    /**
+     * Returns whether there is any presence information available.
+     * This functionreturns <i>false</i> if there is no valid presence information available.
+     * @return <i>true</i> if valid resence information is available. Otherwise <i>false</i> is returned.
+     */
+    bool isPresenceStateAvailable();
+
+    /**
+     * @todo: Add Doc and get/setr in presence manager
+     * @deprecated Use <i>presence()</i> instead.
+     *
+     */
+    QString presenceMessage() ATTRIBUTE_DEPRECATED; 
+
+    /**
+     * @todo: Add Doc and get/setr in presence manager
+     *
+     */
+    Telepathy::ContactCapabilityList capabilities() const;
+            
+
+    /**
+     * Get Avatar for this contact.
+     * This function does not return valid information after the avatar was not requested by avatarForContactList()
+     * @see AvatarManager
+     */ 
+    TpPrototype::AvatarManager::Avatar avatar() const;
+    
+    /**
+     * Get chat channel for this contact.
+     * This function provides the chat channel object for this contact. It contains all information to do a text chat
+     * @return The channel object.
+     */
+    TpPrototype::ChatChannel* chatChannel();
+
+    /**
+     * Get channel for media streaming.
+     * This function returns the media streaming object for this contact. It contains all information and functions for VoIP and Video Over IP communication.
+     */
+    TpPrototype::StreamedMediaChannel* streamedMediaChannel();
+
+    /**
+     * Get the contact manager where this object is stored.
+     * @return The contact manager that owns this object.
+     */
+     TpPrototype::ContactManager* contactManager();
+
+protected:
+    /**
+     * Contstuctor.
+     * This object is never created directly. Use ContactManager to create or request a contact.
+     * @see ContactManager
+     */
+    Contact( const uint & handle, const QString & name, ContactTypes type, Telepathy::Client::ConnectionInterface* connectionInterface, TpPrototype::ContactManager* contactManager );
+
+    ~Contact();
+
+     /**
+      * @todo: Add Doc and get/setr in presence manager
+      */
+    void setPresenceType( uint _presenceType);
+    
+    /**
+     * @todo: Add Doc and get/setr in presence manager
+     */
+    void setPresenceStatus( QString _presenceStatus);
+
+    /**
+     * @todo: Add Doc and get/setr in presence manager
+     */
+    void setPresenceMessage( QString _presenceMessage);
+
+    /**
+     * @todo: Add Doc and get/setr in presence manager
+     */
+    void setCapabilities( const Telepathy::ContactCapabilityList& capabilityList );
+
+    /**
+     * Set the avatar.
+     * This avatar is set by the AvatarManager.
+     *
+     */
+    void setAvatar( const TpPrototype::AvatarManager::Avatar& avatar );
+
+    /**
+     * D-BUS interface.
+     * This protected access to the D-BUS interface can be used to extend this class with special features.
+     */
+    Telepathy::Client::ConnectionInterface* interface();
+
+
+private:
+    ContactPrivate * const d;
+
+    friend class ContactManager;
+    friend class AvatarManager;
+    friend class PresenceManager;
+    friend class CapabilitiesManager;
+};
+
+} // namespace
+
+// Q_DECLARE_METATYPE( TpPrototype::Contact )
+
+#endif // Header guard
diff --git a/TelepathyQt4/Prototype/ContactManager.cpp b/TelepathyQt4/Prototype/ContactManager.cpp
new file mode 100644
index 0000000..61f76f3
--- /dev/null
+++ b/TelepathyQt4/Prototype/ContactManager.cpp
@@ -0,0 +1,965 @@
+/*
+ * This file is part of TelepathyQt4
+ *
+ * Copyright (C) 2008 basysKom GmbH
+ * Copyright (C) 2008 Collabora Ltd. <http://www.collabora.co.uk/>
+ * Copyright (C) 2008 Nokia Corporation
+ *
+ * This library is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU Lesser General Public
+ * License as published by the Free Software Foundation; either
+ * version 2.1 of the License, or (at your option) any later version.
+ *
+ * This library is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
+ * Lesser General Public License for more details.
+ *
+ * You should have received a copy of the GNU Lesser General Public
+ * License along with this library; if not, write to the Free Software
+ * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA  02110-1301  USA
+ */
+
+#include "TelepathyQt4/Prototype/ContactManager.h"
+
+#include <time.h>
+
+#include <QCoreApplication>
+#include <QDBusPendingReply>
+#include <QDBusObjectPath>
+#include <QDebug>
+#include <QHash>
+#include <QPointer>
+#include <QString>
+
+#include <TelepathyQt4/Client/Channel>
+
+#include <TelepathyQt4/Prototype/ChatChannel.h>
+#include <TelepathyQt4/Prototype/ConnectionFacade.h>
+#include <TelepathyQt4/Prototype/Contact.h>
+#include <TelepathyQt4/Prototype/StreamedMediaChannel.h>
+
+//#define ENABLE_DEBUG_OUTPUT_
+
+using namespace TpPrototype;
+
+class TpPrototype::ContactManagerPrivate
+{
+public:
+    ContactManagerPrivate()
+    { init(); }
+
+    ~ContactManagerPrivate()
+    { }
+
+    Telepathy::Client::ConnectionInterface* m_pInterface;
+    Telepathy::Client::ChannelInterfaceGroupInterface*  m_groupSubscribedChannel;
+    Telepathy::Client::ChannelInterfaceGroupInterface*  m_groupKnownChannel;
+    Telepathy::Client::ChannelInterfaceGroupInterface*  m_groupPublishedChannel;
+    Telepathy::Client::ChannelTypeTextInterface*  m_groupTextChannel;
+
+    QHash<uint, QPointer<Contact> > m_members;
+    QHash<uint, QPointer<Contact> > m_subscribed;
+    QHash<uint, QPointer<Contact> > m_localPending;
+    QHash<uint, QPointer<Contact> > m_remotePending;
+    QHash<uint, QPointer<Contact> > m_known;
+
+    bool m_isValid;
+
+    void init()
+    {
+        m_pInterface = NULL;
+        m_groupSubscribedChannel = NULL;
+        m_groupKnownChannel = NULL;
+        m_groupPublishedChannel = NULL;
+        m_groupTextChannel = NULL; //leave this temporaryly here push it later to contact
+        m_isValid    = false;
+    }
+
+    QList<uint> SubscribedHandlesToLookUp(const Telepathy::UIntList& handles)
+    {
+        QList<uint> subscribed_to_look_up;
+        foreach(uint handle, handles)
+        {
+            if (!m_subscribed.contains(handle) )
+                subscribed_to_look_up.append(handle);
+        }
+        return subscribed_to_look_up;
+    }
+    
+    QList<uint> KnownHandlesToLookUp(const Telepathy::UIntList& handles)
+    {
+        QList<uint> known_to_look_up;
+        foreach(uint handle, handles)
+        {
+            if (!m_members.contains(handle) )
+                known_to_look_up.append(handle);
+        }
+        return known_to_look_up;
+    }    
+    QList<uint> RemovedHandlesToLookUp(const Telepathy::UIntList& handles)
+    {
+        QList<uint> removed_to_look_up;
+        foreach(uint handle, handles)
+        {
+            if (m_members.contains(handle) )
+                removed_to_look_up.append(handle);
+        }
+        return removed_to_look_up;
+    }
+
+    QList<uint> LocalPendingHandlesToLookUp(const Telepathy::UIntList& handles)
+    {
+        QList<uint> localpending_to_look_up;
+        foreach(uint handle, handles)
+        {
+            if (!m_localPending.contains(handle))
+                localpending_to_look_up.append(handle);
+        }
+        return localpending_to_look_up;
+    }
+    
+    QList<uint> RemotePendingHandlesToLookUp(const Telepathy::UIntList& handles)
+    {
+        QList<uint> remotepending_to_look_up;
+        foreach(uint handle, handles)
+        {
+            if (!m_remotePending.contains(handle))
+                remotepending_to_look_up.append(handle); 
+            
+        }
+        return remotepending_to_look_up;
+    }
+
+    QList<QPointer<TpPrototype::Contact> > mapHashToList( QHash<uint, QPointer<Contact> > hash )
+    {
+        QList<QPointer<TpPrototype::Contact> > ret_list;
+
+        foreach( const QPointer<TpPrototype::Contact>& contact, hash )
+        {
+            // Filter possilble null pointers
+            if ( NULL == contact )
+            { continue; }
+
+            ret_list.append( contact );
+        }
+
+        return ret_list;
+    }
+
+};
+
+ContactManager::ContactManager( Telepathy::Client::ConnectionInterface* connection,
+                                QObject* parent ):
+    QObject( parent ),
+    d( new ContactManagerPrivate )
+{
+    init( connection );
+}
+
+ContactManager::~ContactManager()
+{
+    // Delete this here as we are a friend of contact.
+    foreach (QPointer<Contact> current_contact, d->m_members)
+    { delete current_contact; }    
+    foreach (QPointer<Contact> current_contact, d->m_subscribed)
+    { delete current_contact; }
+    foreach (QPointer<Contact> current_contact, d->m_localPending)
+    { delete current_contact; }
+    foreach (QPointer<Contact> current_contact, d->m_remotePending)
+    { delete current_contact; }
+
+    delete d;
+}
+
+int ContactManager::count()
+{ return d->m_members.size(); }
+
+bool ContactManager::isValid()
+{ return d->m_isValid; }
+
+QList<QPointer<Contact> > ContactManager::contactList()
+{ return d->m_members.values(); }
+
+QList<QPointer<Contact> > ContactManager::toAuthorizeList()
+{ return d->m_localPending.values();}
+
+QList<QPointer<Contact> > ContactManager::remoteAuthorizationPendingList()
+{ return d->m_remotePending.values();}
+
+
+void ContactManager::init( Telepathy::Client::ConnectionInterface* connection )
+{
+    Q_ASSERT(0 != connection);
+    Telepathy::registerTypes();
+    d->m_pInterface = connection;
+#ifdef ENABLE_DEBUG_OUTPUT_
+    qDebug() << "ContactManager up and running... waiting for signals.";
+#endif//
+    d->m_isValid = true;
+}
+
+bool ContactManager::requestContact( const QString& id )
+{
+    QStringList contact_ids;
+    contact_ids.append(id);
+    
+    QList<uint> contact_handles=d->m_pInterface->RequestHandles( Telepathy::HandleTypeContact,contact_ids);
+    if (!contact_handles.empty())
+    {
+        if ( d->m_groupSubscribedChannel)
+            d->m_groupSubscribedChannel->AddMembers(contact_handles,"Contact Request");
+        return true;
+    }
+    return false;
+}
+
+bool ContactManager::authorizeContact( const Contact* contact )
+{
+    if ( !contact )
+    { return false; }
+
+#ifdef ENABLE_DEBUG_OUTPUT_
+    qDebug() << "ContactManager Try to authorize a contact";
+#endif
+    QList<uint> toauthorizelist;
+    toauthorizelist.append(contact->telepathyHandle());
+    if ( d->m_groupPublishedChannel)
+        d->m_groupPublishedChannel->AddMembers(toauthorizelist,"Add");
+    return true;
+}
+
+
+bool ContactManager::removeContact( const Contact* contact_toremove )
+{
+    if ( !contact_toremove )
+    { return false; }
+
+#ifdef ENABLE_DEBUG_OUTPUT_
+    qDebug() << "ContactManager Try to remove a contact";
+#endif    
+    QList<uint> toremovelist;
+    toremovelist.append(contact_toremove->telepathyHandle());
+    d->m_members.remove(contact_toremove->telepathyHandle());
+    d->m_subscribed.remove(contact_toremove->telepathyHandle());
+    d->m_remotePending.remove(contact_toremove->telepathyHandle());
+    d->m_localPending.remove(contact_toremove->telepathyHandle());
+    d->m_known.remove(contact_toremove->telepathyHandle());
+    if ( d->m_groupSubscribedChannel)
+        d->m_groupSubscribedChannel->RemoveMembers(toremovelist,"Remove");
+    if ( d->m_groupPublishedChannel)
+        d->m_groupPublishedChannel->RemoveMembers(toremovelist,"Remove");
+    if ( d->m_groupKnownChannel)
+        d->m_groupKnownChannel->RemoveMembers(toremovelist,"Remove");
+
+    delete contact_toremove;
+
+    return true;
+}
+
+QPointer<TpPrototype::Contact> ContactManager::contactForHandle( uint handle )
+{
+    return d->m_members.value( handle );
+}
+
+uint ContactManager::localHandle()
+{
+    return ConnectionFacade::instance()->selfHandleForConnectionInterface( d->m_pInterface );
+}
+
+
+/*
+    inline QDBusPendingReply<> AcknowledgePendingMessages(const Telepathy::UIntList& IDs)
+{
+    QList<QVariant> argumentList;
+    argumentList << QVariant::fromValue(IDs);
+    return asyncCallWithArgumentList(QLatin1String("AcknowledgePendingMessages"), argumentList);
+}
+
+    inline QDBusPendingReply<Telepathy::UIntList> GetMessageTypes()
+{
+    return asyncCall(QLatin1String("GetMessageTypes"));
+}
+
+*/
+
+
+void ContactManager::openSubscribedContactsChannel(uint handle, const QDBusObjectPath& channelPath, const QString& channelType)
+{
+    Telepathy::registerTypes();
+
+    QString channel_service_name(d->m_pInterface->service());
+#ifdef ENABLE_DEBUG_OUTPUT_
+    qDebug() << "ContactManager Channel Services Name" << channel_service_name;
+    qDebug() << "ContactManager Channel Path" << channelPath.path();
+#endif        
+    // This channel may never be closed!
+    d->m_groupSubscribedChannel = new Telepathy::Client::ChannelInterfaceGroupInterface(channel_service_name,channelPath.path(),
+            this);
+    if (!d->m_groupSubscribedChannel->isValid())
+    {
+#ifdef ENABLE_DEBUG_OUTPUT_
+        qDebug() << "Failed to connect Group channel interface class to D-Bus object.";
+#endif
+        delete d->m_groupSubscribedChannel;
+        d->m_groupSubscribedChannel = 0;
+        return;
+    }
+    QDBusPendingReply<Telepathy::UIntList, Telepathy::UIntList, Telepathy::UIntList> reply2=d->m_groupSubscribedChannel->GetAllMembers();
+    reply2.waitForFinished();
+
+    const Telepathy::UIntList mlist1= QList< quint32 > (reply2.argumentAt<0>());
+    const Telepathy::UIntList mlist2;
+    const Telepathy::UIntList mlist3= QList< quint32 > (reply2.argumentAt<1>());
+    const Telepathy::UIntList mlist4= QList< quint32 > (reply2.argumentAt<2>());
+#ifdef ENABLE_DEBUG_OUTPUT_    
+    qDebug() << "Number of current members" << mlist1.size();
+    qDebug() << "Number of local pending members" << mlist2.size();
+    qDebug() << "Number of remote pending members" << mlist3.size();
+#endif      
+    if (( mlist1.size()>0) || ( mlist3.size()>0) || ( mlist4.size()>0))   
+        slotSubscribedMembersChanged("",
+                        mlist1,
+                        mlist2,
+                        mlist3,
+                        mlist4,
+                        0, 0);
+
+    // All lists are empty when the channel is created, so it suffices to connect
+    // the MembersChanged signal.
+    connect(d->m_groupSubscribedChannel, SIGNAL(MembersChanged(const QString&,
+            const Telepathy::UIntList&, // added to members list
+            const Telepathy::UIntList&, // removed from members list
+            const Telepathy::UIntList&, // local pending list
+            const Telepathy::UIntList&, // remote pending list
+            uint, uint)),
+            this, SLOT(slotSubscribedMembersChanged(const QString&,
+                       const Telepathy::UIntList&,
+                       const Telepathy::UIntList&,
+                       const Telepathy::UIntList&,
+                       const Telepathy::UIntList&,
+                       uint, uint)));
+   
+}
+
+void ContactManager::openKnownContactsChannel(uint handle, const QDBusObjectPath& channelPath, const QString& channelType)
+{
+    Telepathy::registerTypes();
+
+    QString channel_service_name(d->m_pInterface->service());
+#ifdef ENABLE_DEBUG_OUTPUT_   
+    qDebug() << "ContactManager Channel Services Name" << channel_service_name;
+    qDebug() << "ContactManager Channel Path" << channelPath.path();
+#endif         
+    // This channel may never be closed!
+    d->m_groupKnownChannel = new Telepathy::Client::ChannelInterfaceGroupInterface(channel_service_name,channelPath.path(),
+                               this);
+    if (!d->m_groupKnownChannel->isValid())
+    {
+#ifdef ENABLE_DEBUG_OUTPUT_
+        qDebug() << "Failed to connect Group channel interface class to D-Bus object.";
+#endif
+        delete d->m_groupKnownChannel;
+        d->m_groupKnownChannel = 0;
+        return;
+    }
+    QDBusPendingReply<Telepathy::UIntList, Telepathy::UIntList, Telepathy::UIntList> reply2=d->m_groupKnownChannel->GetAllMembers();
+    reply2.waitForFinished();
+
+    const Telepathy::UIntList mlist1= QList< quint32 > (reply2.argumentAt<0>());
+    const Telepathy::UIntList mlist2;
+    const Telepathy::UIntList mlist3= QList< quint32 > (reply2.argumentAt<1>());
+    const Telepathy::UIntList mlist4= QList< quint32 > (reply2.argumentAt<2>());
+#ifdef ENABLE_DEBUG_OUTPUT_    
+    qDebug() << "Number of current members" << mlist1.size();
+    qDebug() << "Number of local pending members" << mlist2.size();
+    qDebug() << "Number of remote pending members" << mlist3.size();
+#endif     
+    if (( mlist1.size()>0) || ( mlist3.size()>0) || ( mlist4.size()>0))
+        slotKnownMembersChanged("",
+                        mlist1,
+                        mlist2,
+                        mlist3,
+                        mlist4,
+                        0, 0);
+    
+   // qDebug() << "Number of current members" << mlist1.size();
+   // qDebug() << "Number of local pending members" << mlist2.size();
+   // qDebug() << "Number of remote pending members" << mlist3.size();
+    
+    // All lists are empty when the channel is created, so it suffices to connect
+    // the MembersChanged signal.
+    connect(d->m_groupKnownChannel, SIGNAL(MembersChanged(const QString&,
+            const Telepathy::UIntList&, // added to members list
+            const Telepathy::UIntList&, // removed from members list
+            const Telepathy::UIntList&, // local pending list
+            const Telepathy::UIntList&, // remote pending list
+            uint, uint)),
+            this, SLOT(slotKnownMembersChanged(const QString&,
+                       const Telepathy::UIntList&,
+                       const Telepathy::UIntList&,
+                       const Telepathy::UIntList&,
+                       const Telepathy::UIntList&,
+                       uint, uint)));
+
+}
+
+void ContactManager::openTextChannel( uint handle, uint handleType, const QString& channelPath, const QString& channelTyp )
+{
+    Contact* contact = d->m_members.value( handle );
+
+    if ( !contact )
+    {
+        qWarning() << "ContactManager::openTextChannel: Tried to open a text channel but there was no receiving contact found!";
+        return;
+    }
+    if ( !contact->chatChannel() )
+    {
+        qWarning() << "ContactManager::openTextChannel: Requesting a valid text channel object failed!";
+        return;
+    }
+    
+    if ( contact && contact->chatChannel() )
+    {
+        contact->chatChannel()->openTextChannel( handle, handleType, channelPath, channelTyp );
+        emit signalTextChannelOpenedForContact( contact );
+    }
+}
+
+void ContactManager::openStreamedMediaChannel( uint handle, uint handleType, const QString& channelPath, const QString& channelType )
+{
+#ifdef ENABLE_DEBUG_OUTPUT_
+    qDebug() << "ContactManager::openStreamedMediaChannel handle: " << handle
+             << "handleType:" << handleType
+             << "channelPath: " << channelPath
+             << "channelType: " << channelType;
+#endif
+
+    // Outbound calls have no handle and don't need to be handled here.
+    if ( handle == 0 )
+    { return; }
+
+    
+    Contact* contact = d->m_members.value( handle );
+
+    if ( !contact )
+    {
+        qWarning() << "ContactManager::openStreamedMediaChannel: Tried to open a media stream channel but there was no receiving contact found!";
+        return;
+    }
+    if ( !contact->streamedMediaChannel() )
+    {
+        qWarning() << "ContactManager::openStreamedMediaChannel: Requesting a valid streamed media channel object failed!";
+        return;
+    }
+
+    if ( contact && contact->streamedMediaChannel() )
+    {
+        disconnect( contact->streamedMediaChannel(), SIGNAL( signalIncomingChannel( TpPrototype::Contact* ) ), this, 0 );
+        connect( contact->streamedMediaChannel(), SIGNAL( signalIncomingChannel( TpPrototype::Contact* ) ),
+                 this, SIGNAL( signalStreamedMediaChannelOpenedForContact( TpPrototype::Contact* ) ) );
+        contact->streamedMediaChannel()->openStreamedMediaChannel( handle, handleType, channelPath, channelType );
+    }
+}
+
+void ContactManager::openPublishContactsChannel(uint handle, const QDBusObjectPath& channelPath, const QString& channelType)
+{
+    Telepathy::registerTypes();
+
+    QString channel_service_name(d->m_pInterface->service());
+#ifdef ENABLE_DEBUG_OUTPUT_    
+    qDebug() << "ContactManager Channel Services Name" << channel_service_name;
+    qDebug() << "ContactManager Channel Path" << channelPath.path();
+#endif        
+    // This channel may never be closed!
+    d->m_groupPublishedChannel = new Telepathy::Client::ChannelInterfaceGroupInterface(channel_service_name,channelPath.path(),
+            this);
+    if (!d->m_groupPublishedChannel->isValid())
+    {
+#ifdef ENABLE_DEBUG_OUTPUT_
+        qDebug() << "Failed to connect Group channel interface class to D-Bus object.";
+#endif
+        delete d->m_groupPublishedChannel;
+        d->m_groupPublishedChannel = 0;
+        return;
+    }
+    QDBusPendingReply<Telepathy::UIntList, Telepathy::UIntList, Telepathy::UIntList> reply2=d->m_groupPublishedChannel->GetAllMembers();
+    reply2.waitForFinished();
+
+    const Telepathy::UIntList mlist1= QList< quint32 > (reply2.argumentAt<0>());
+    const Telepathy::UIntList mlist2;
+    const Telepathy::UIntList mlist3= QList< quint32 > (reply2.argumentAt<1>());
+    const Telepathy::UIntList mlist4= QList< quint32 > (reply2.argumentAt<2>());
+#ifdef ENABLE_DEBUG_OUTPUT_
+    qDebug() << "Number of current members" << mlist1.size();
+    qDebug() << "Number of local pending members" << mlist2.size();
+    qDebug() << "Number of remote pending members" << mlist3.size();
+#endif    
+    if (( mlist1.size()>0) || ( mlist3.size()>0) || ( mlist4.size()>0))
+        slotPublishedMembersChanged("",
+                        mlist1,
+                        mlist2,
+                        mlist3,
+                        mlist4,
+                        0, 0);
+   // qDebug() << "Number of current members" << mlist1.size();
+   // qDebug() << "Number of local pending members" << mlist2.size();
+   // qDebug() << "Number of remote pending members" << mlist3.size();
+    
+    // All lists are empty when the channel is created, so it suffices to connect
+    // the MembersChanged signal.
+    connect(d->m_groupPublishedChannel, SIGNAL(MembersChanged(const QString&,
+            const Telepathy::UIntList&, // added to members list
+            const Telepathy::UIntList&, // removed from members list
+            const Telepathy::UIntList&, // local pending list
+            const Telepathy::UIntList&, // remote pending list
+            uint, uint)),
+            this, SLOT(slotPublishedMembersChanged(const QString&,
+                       const Telepathy::UIntList&,
+                       const Telepathy::UIntList&,
+                       const Telepathy::UIntList&,
+                       const Telepathy::UIntList&,
+                       uint, uint)));
+
+}
+  
+
+
+void ContactManager::slotKnownMembersChanged(const QString& message,
+                                        const Telepathy::UIntList& members_added,
+                                        const Telepathy::UIntList& members_removed,
+                                        const Telepathy::UIntList& local_pending,
+                                        const Telepathy::UIntList& remote_pending,
+                                        uint actor, uint reason)
+{
+    slotMembersChanged("Known",
+                       members_added,
+                       members_removed,
+                       local_pending,
+                       remote_pending,
+                       actor, reason);
+}
+void ContactManager::slotPublishedMembersChanged(const QString& message,
+                                             const Telepathy::UIntList& members_added,
+                                             const Telepathy::UIntList& members_removed,
+                                             const Telepathy::UIntList& local_pending,
+                                             const Telepathy::UIntList& remote_pending,
+                                             uint actor, uint reason)
+{
+    slotMembersChanged("Published",
+                       members_added,
+                       members_removed,
+                       local_pending,
+                       remote_pending,
+                       actor, reason);
+}
+
+void ContactManager::slotSubscribedMembersChanged(const QString& message,
+                                             const Telepathy::UIntList& members_added,
+                                             const Telepathy::UIntList& members_removed,
+                                             const Telepathy::UIntList& local_pending,
+                                             const Telepathy::UIntList& remote_pending,
+                                             uint actor, uint reason)
+{
+    slotMembersChanged("Subscribed",
+                       members_added,
+                       members_removed,
+                       local_pending,
+                       remote_pending,
+                       actor, reason);
+}
+
+// TODO: This function is a real beast. It should be split into separate functions. Rething whether it is a good idea
+//       to map all slots to this functions!?
+void ContactManager::slotMembersChanged(const QString& message,
+                                        const Telepathy::UIntList& members_added,
+                                        const Telepathy::UIntList& members_removed,
+                                        const Telepathy::UIntList& local_pending,
+                                        const Telepathy::UIntList& remote_pending,
+                                        uint actor, uint reason)
+{
+    Q_UNUSED(actor);
+    Q_UNUSED(reason);
+//    Q_UNUSED(message);
+
+//    qDebug() << "Members Changed" << message << "Actor" << actor << "Reason" <<reason;
+//    qDebug() << "Members Added" << members_added.size();
+//    qDebug() << "Members Removed" << members_removed.size();
+//    qDebug() << "Members Local Pending" << local_pending.size();
+//    qDebug() << "Members Remote Pending" << remote_pending.size();
+    // Figure out handles that we need to look up.
+    // Batch them up to minimize roundtrips.
+    
+
+
+    
+    if (members_added.size()!=0)
+    {
+        if (message==QString("Known"))
+        {        
+            QList<uint> known_to_look_up(d->KnownHandlesToLookUp(members_added));
+        // look up 'missing' handles:
+            QDBusPendingReply<QStringList> handle_names =
+                    d->m_pInterface->InspectHandles(Telepathy::HandleTypeContact, known_to_look_up);
+            handle_names.waitForFinished();
+            if (!handle_names.isValid())
+            {
+                QDBusError error = handle_names.error();
+
+                qWarning() << "InspectHandles: error type:" << error.type()
+                           << "error name:" << error.name();
+                return;
+            }
+            Q_ASSERT(handle_names.value().size() == known_to_look_up.size());
+#ifdef ENABLE_DEBUG_OUTPUT_            
+            qDebug() << "Known Handle" << handle_names.value().size() <<"Look Up Size" << known_to_look_up.size();
+#endif            
+        // Create Contacts for the looked up handles:
+            QHash<uint, QPointer<Contact> > tmp_list;
+            for (int i = 0; i < known_to_look_up.size(); ++i)
+            {
+                
+
+                QPointer<Contact> contact = new Contact(known_to_look_up.at(i), handle_names.value().at(i), Contact::CT_Known, d->m_pInterface, this );
+#ifdef ENABLE_DEBUG_OUTPUT_                
+                qDebug() << "Known Handle" << handle_names.value().at(i);
+#endif                
+                Q_ASSERT(contact->isValid());
+                tmp_list.insert(known_to_look_up.at(i), contact);
+
+            }
+            known_to_look_up.clear();
+            if (tmp_list.size()>0)
+            {
+                foreach (uint handle, members_added)
+                {
+                //Q_ASSERT(!d->m_subscribed.contains(handle)); // We do not yet know that handle.
+                // FIXME: Check where the handle comes from to figure out whether it was
+                //        Getting authorized, etc.
+                    QPointer<Contact> current_contact = tmp_list.value(handle);
+                // Detect mixups when writing into the hash.
+                    if (current_contact)
+                    {
+                        Q_ASSERT(current_contact->telepathyHandle() == handle);
+                        tmp_list.remove(handle);
+                        if (!d->m_subscribed.contains(handle))
+                        {
+#ifdef ENABLE_DEBUG_OUTPUT_                            
+                            qDebug() << "Added Handle to Known List";
+#endif                            
+                        }
+                        else
+                        {
+#ifdef ENABLE_DEBUG_OUTPUT_
+                            qDebug() << "Known Contact already in contactlist";
+#endif                            
+                            d->m_members.remove(handle);
+                            d->m_subscribed.remove(handle);
+                        }
+                        d->m_members.insert(handle, current_contact);
+                        d->m_known.insert(handle, current_contact);
+                        emit signalContactKnown( this, current_contact );
+                    }
+                }
+            }
+        }
+        else //message!="Known"
+        {
+           
+            QList<uint> subscribed_to_look_up(d->SubscribedHandlesToLookUp(members_added));
+    
+        // look up 'missing' handles:
+            QDBusPendingReply<QStringList> handle_names =
+                    d->m_pInterface->InspectHandles(Telepathy::HandleTypeContact, subscribed_to_look_up);
+            handle_names.waitForFinished();
+            if (!handle_names.isValid())
+            {
+                QDBusError error = handle_names.error();
+
+                qWarning() << "InspectHandles: error type:" << error.type()
+                           << "error name:" << error.name();
+                return;
+            }
+            Q_ASSERT(handle_names.value().size() == subscribed_to_look_up.size());
+#ifdef ENABLE_DEBUG_OUTPUT_
+            qDebug() << "Subscribed  Handle" << handle_names.value().size() <<"Look Up Size" << subscribed_to_look_up.size()<< "Mmebers Added Size "<< members_added.size();
+#endif            
+        // Create Contacts for the looked up handles:
+            QHash<uint, QPointer<Contact> > tmp_list;
+            for (int i = 0; i < subscribed_to_look_up.size(); ++i)
+            {
+                
+                QPointer<Contact> contact = new Contact(subscribed_to_look_up.at(i), handle_names.value().at(i), Contact::CT_Subscribed, d->m_pInterface, this );
+#ifdef ENABLE_DEBUG_OUTPUT_
+                qDebug() << "Subscribed Handle" << handle_names.value().at(i);
+#endif                
+                Q_ASSERT(contact->isValid());
+                tmp_list.insert(subscribed_to_look_up.at(i), contact);
+            }
+            if (tmp_list.size()>0)
+            {
+                QPointer<Contact> current_contact;
+                foreach (uint handle, members_added)
+                {
+                //Q_ASSERT(!d->m_subscribed.contains(handle)); // We do not yet know that handle.
+                // FIXME: Check where the handle comes from to figure out whether it was
+                //        Getting authorized, etc.
+                    current_contact = tmp_list.value(handle);
+
+                    if (current_contact)
+                    {
+                    // Detect mixups when writing into the hash.
+                        Q_ASSERT(current_contact->telepathyHandle() == handle);
+                    
+                        tmp_list.remove(handle);
+                        if (!d->m_members.contains(handle))
+                        {
+#ifdef ENABLE_DEBUG_OUTPUT_                      
+                            qDebug() << "Added Handle to Subscribed List"<< handle;
+#endif
+                            d->m_members.insert(handle, current_contact);
+                            //d->m_subscribed.insert(handle, current_contact);
+                        }
+                        else
+                        {
+#ifdef ENABLE_DEBUG_OUTPUT_                            
+                            qDebug() << "Subscribed Contact already in contactlist"<< handle;
+#endif
+
+                            if (d->m_members[handle]->type()==Contact::CT_LocalPending)
+                            {
+#ifdef ENABLE_DEBUG_OUTPUT_
+                                qDebug() << "Changed Subscribed Contact to local pending"<< handle;
+#endif
+                                d->m_members[handle]->setType(Contact::CT_LocalPending);
+                            }
+                            else
+                            {
+                                d->m_members[handle]->setType(Contact::CT_Subscribed);
+                                if (d->m_remotePending.contains(handle))
+                                    d->m_remotePending.remove(handle);
+                                if (d->m_localPending.contains(handle))
+                                    d->m_localPending.remove(handle);
+                                  
+                            }
+                            delete current_contact;
+                        }
+
+                        emit signalContactSubscribed( this,  d->m_members[handle] );
+                        emit signalForModelContactSubscribed( this,  d->m_members[handle] );
+                    }   
+                }
+            }
+        }
+    }
+    if (local_pending.size()!=0)
+    {
+        QList<uint> localPending_to_look_up(d->LocalPendingHandlesToLookUp(local_pending));
+    // look up 'missing' handles:
+        QDBusPendingReply<QStringList> handle_names =
+                d->m_pInterface->InspectHandles(Telepathy::HandleTypeContact, localPending_to_look_up);
+        handle_names.waitForFinished();
+        if (!handle_names.isValid())
+        {
+            QDBusError error = handle_names.error();
+#ifdef ENABLE_DEBUG_OUTPUT_
+            qDebug() << "InspectHandles: error type:" << error.type()
+                    << "error name:" << error.name();
+#endif
+            return;
+        }
+        Q_ASSERT(handle_names.value().size() == localPending_to_look_up.size());
+#ifdef ENABLE_DEBUG_OUTPUT_
+        qDebug() << "Local Pending Size" << handle_names.value().size() <<"Look Up Size" << localPending_to_look_up.size();
+#endif
+        
+    // Create Contacts for the looked up handles:
+        QHash<uint, QPointer<Contact> > tmp_list;
+        for (int i = 0; i < localPending_to_look_up.size(); ++i)
+        {
+            QPointer<Contact> contact = new Contact(localPending_to_look_up.at(i), handle_names.value().at(i), Contact::CT_LocalPending, d->m_pInterface, this );
+#ifdef ENABLE_DEBUG_OUTPUT_
+            qDebug() << "Local Pending Handle" << handle_names.value().at(i);
+#endif
+            Q_ASSERT(contact->isValid());
+            tmp_list.insert(localPending_to_look_up.at(i), contact);
+        }
+        if (tmp_list.size()>0)
+        {
+            foreach (uint handle, local_pending)
+            {
+                QPointer<Contact> current_contact = tmp_list.value(handle);
+                if (current_contact)
+                {
+                    Q_ASSERT(current_contact->telepathyHandle() == handle);
+                
+                    tmp_list.remove(handle);
+                    if (!d->m_members.contains(handle))
+                    {
+#ifdef ENABLE_DEBUG_OUTPUT_                        
+                        qDebug() << "Added Handle to Local Pending List";
+#endif
+                        d->m_members.insert(handle, current_contact);
+                        d->m_localPending.insert(handle, current_contact);
+                    }
+                    else
+                    {
+#ifdef ENABLE_DEBUG_OUTPUT_
+                        qDebug() << "Local Pending Contact already in contactlist";
+#endif
+                        d->m_members[handle]->setType(Contact::CT_LocalPending);
+                        if (d->m_remotePending.contains(handle))
+                            d->m_remotePending.remove(handle);
+                        delete current_contact;
+                    }
+
+                    emit signalContactLocalPending( this,  d->m_members[handle] );
+                }            
+                               
+            }
+        }
+    }
+        
+    if (remote_pending.size()!=0)
+    {
+        QList<uint> remotePending_to_look_up(d->RemotePendingHandlesToLookUp(remote_pending));
+
+    // look up 'missing' handles:
+        QDBusPendingReply<QStringList> handle_names =
+                d->m_pInterface->InspectHandles(Telepathy::HandleTypeContact, remotePending_to_look_up);
+        handle_names.waitForFinished();
+
+        if (!handle_names.isValid())
+        {
+            QDBusError error = handle_names.error();
+#ifdef ENABLE_DEBUG_OUTPUT_
+            qDebug() << "InspectHandles: error type:" << error.type()
+                    << "error name:" << error.name();
+#endif
+            return;
+        }
+        Q_ASSERT(handle_names.value().size() == remotePending_to_look_up.size());
+#ifdef ENABLE_DEBUG_OUTPUT_
+        qDebug() << "Remote Pending Handle Size" << handle_names.value().size() <<"Look Up Size" << remotePending_to_look_up.size();
+#endif
+   // Create Contacts for the looked up handles:
+        QHash<uint, QPointer<Contact> > tmp_list;
+        for (int i = 0; i < remotePending_to_look_up.size(); ++i)
+        {
+            QPointer<Contact> contact = new Contact(remotePending_to_look_up.at(i), handle_names.value().at(i), Contact::CT_RemotePending, d->m_pInterface, this );
+#ifdef ENABLE_DEBUG_OUTPUT_
+            qDebug() << "Remote Pending Handle " << handle_names.value().at(i);
+#endif
+            Q_ASSERT(contact->isValid());
+            tmp_list.insert(remotePending_to_look_up.at(i), contact);
+        }
+        if (tmp_list.size()>0)
+        {
+            foreach (uint handle, remote_pending)
+            {
+
+                QPointer<Contact> current_contact = tmp_list.value(handle);
+                if (current_contact)
+                {
+                // Detect mixups when writing into the hash.
+                    Q_ASSERT(current_contact->telepathyHandle() == handle);
+                    tmp_list.remove(handle);
+                    if (!d->m_members.contains(handle))
+                    {
+#ifdef ENABLE_DEBUG_OUTPUT_
+                        qDebug() << "Added Handle to Remote Pending List";
+#endif
+                        d->m_remotePending.insert(handle, current_contact);
+                        d->m_members.insert(handle, current_contact);
+                    }
+                    else
+                    {
+#ifdef ENABLE_DEBUG_OUTPUT_
+                        qDebug() << "Remote Pending Contact already in contactlist";
+#endif                        
+                        d->m_members[handle]->setType(Contact::CT_RemotePending);
+
+                        if (d->m_localPending.contains(handle))
+                            d->m_localPending.remove(handle);
+                        
+                        delete current_contact;
+                    }
+
+                    emit signalContactRemotePending( this,  d->m_members[handle] );
+                }
+                                           
+            }
+        }
+    }
+    
+    if (members_removed.size()!=0)
+    {
+#ifdef ENABLE_DEBUG_OUTPUT_
+        qDebug() << "SlotMembers Changed Removed Called";
+#endif
+        QList<uint> removed_to_look_up(d->RemovedHandlesToLookUp(members_removed));
+    // look up 'missing' handles:
+        QDBusPendingReply<QStringList> handle_names =
+                d->m_pInterface->InspectHandles(Telepathy::HandleTypeContact, removed_to_look_up);
+        handle_names.waitForFinished();
+        if (!handle_names.isValid())
+        {
+            QDBusError error = handle_names.error();
+            qWarning() << "InspectHandles: error type:" << error.type()
+                       << "error name:" << error.name();
+            return;
+        }
+        Q_ASSERT(handle_names.value().size() == removed_to_look_up.size());
+    // Create Contacts for the looked up handles:
+        QHash<uint, QPointer<Contact> > tmp_list;
+        for (int i = 0; i < removed_to_look_up.size(); ++i)
+        {
+            QPointer<Contact> contact = new Contact(removed_to_look_up.at(i), handle_names.value().at(i), Contact::CT_Known, d->m_pInterface, this );
+            Q_ASSERT(contact->isValid());
+            tmp_list.insert(removed_to_look_up.at(i), contact);
+        }
+              
+        if (tmp_list.size()>0)
+        {
+            foreach (uint handle, members_removed)
+            {
+
+                QPointer<Contact> current_contact = tmp_list.value(handle);
+                if (current_contact)
+                {
+                // Detect mixups when writing into the hash.
+                    Q_ASSERT(current_contact->telepathyHandle() == handle);
+                
+                    tmp_list.remove(handle);
+                    if (d->m_members.contains(handle))
+                    {
+#ifdef ENABLE_DEBUG_OUTPUT_
+                        qDebug() << "Remove Contact";
+#endif                        
+                        d->m_members.remove(handle);
+                        d->m_subscribed.remove(handle);
+                        d->m_remotePending.remove(handle);
+                        d->m_localPending.remove(handle);
+                        d->m_known.remove(handle);
+                        emit signalContactRemoved( this, current_contact );
+                        delete current_contact;
+                    }
+                    else
+                    {                 
+#ifdef ENABLE_DEBUG_OUTPUT_
+                        qDebug() << "Removed Contact not in contactlist";
+#endif
+                        delete current_contact;
+                    }
+                }
+            }
+        }
+    }
+    emit signalMembersChanged( this,
+                               message,
+                               d->mapHashToList( d->m_members ),
+                               d->mapHashToList( d->m_localPending ),
+                               d->mapHashToList( d->m_remotePending ),
+                               contactForHandle( actor ),
+                               static_cast<Telepathy::ChannelGroupChangeReason>( reason ) );
+}
diff --git a/TelepathyQt4/Prototype/ContactManager.h b/TelepathyQt4/Prototype/ContactManager.h
new file mode 100644
index 0000000..f396985
--- /dev/null
+++ b/TelepathyQt4/Prototype/ContactManager.h
@@ -0,0 +1,304 @@
+/*
+ * This file is part of TelepathyQt4
+ *
+ * Copyright (C) 2008 basysKom GmbH
+ * Copyright (C) 2008 Collabora Ltd. <http://www.collabora.co.uk/>
+ * Copyright (C) 2008 Nokia Corporation
+ *
+ * This library is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU Lesser General Public
+ * License as published by the Free Software Foundation; either
+ * version 2.1 of the License, or (at your option) any later version.
+ *
+ * This library is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
+ * Lesser General Public License for more details.
+ *
+ * You should have received a copy of the GNU Lesser General Public
+ * License along with this library; if not, write to the Free Software
+ * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA  02110-1301  USA
+ */
+
+#ifndef TelepathyQt4_Prototype_ContactManager_H_
+#define TelepathyQt4_Prototype_ContactManager_H_
+
+#include <TelepathyQt4/Types>
+#include <TelepathyQt4/Constants>
+
+#include <QObject>
+#include <QDBusObjectPath>
+#include <QPointer>
+
+#ifdef DEPRECATED_ENABLED__
+#define ATTRIBUTE_DEPRECATED __attribute__((deprecated))
+#else
+#define ATTRIBUTE_DEPRECATED
+#endif
+
+/**
+ * @defgroup qt_contact Contact Management
+ * @ingroup qt_style_api
+ * Classes that provide functions to handle contacts.
+ */
+
+
+
+namespace Telepathy
+{
+    namespace Client
+    {
+        class ConnectionInterface;
+        class ChannelInterfaceGroupInterface;
+
+    }
+}
+
+namespace TpPrototype {
+
+class ContactManagerPrivate;
+class Contact;
+class Connection;
+class ChatChannel;
+class StreamedMediaChannel;
+
+/**
+ * @ingroup qt_connection
+ * @ingroup qt_contact
+ * This class manages all contacts.
+ * This class provides the list of contacts associated with an account. It is possible to register new contacts by requestContact(), or remove contacts
+ * by removeContact(). Signals providing information whether any contact changes or wether a communication channel is opened.
+ * @todo We need a ContactGroup that contains the Contacts instead use QList< QPointer<> >. If a contact is removed we get a NULL element in the list instead to remove one element from the list (seil)
+ */
+class ContactManager : public QObject
+{
+    Q_OBJECT
+public:
+    /**
+     * Validity of this class.
+     * Do not access any methods if this object is invalid.
+     */
+    bool isValid();
+
+    /**
+     * Number of Contacts. Returns how many contacts are available.
+     * @return Number of contacts available.
+     */
+    int count();
+
+     /**
+      * List of contacts. The contact pointer is stored in a QPointer. If the contact is removed it is deleted
+      * by the contact manager. Thus, the pointer is set to 0.
+     * @todo: Return ContactGroup here, instead a list of a pointer.
+      */
+     QList<QPointer<TpPrototype ::Contact> > contactList();
+
+     /**
+      * List of contacts that have requested authorization from us.
+      *
+      * The contact pointer is stored in a QPointer. If the contact is removed it is deleted
+      * by the contact manager. Thus, the pointer is set to 0.
+      * @todo: Return ContactGroup here, instead a list of a pointer.
+      */
+      QList<QPointer<TpPrototype ::Contact> > toAuthorizeList();
+
+     /**
+      * List of contacts <i>we</i> asked to authorize us to see their presence state.
+      *
+      * The contact pointer is stored in a QPointer. If the contact is removed it is deleted
+      * by the contact manager. Thus, the pointer is set to 0.
+      * @todo: Return ContactGroup here, instead of a list of pointer.
+      */
+     QList<QPointer<TpPrototype ::Contact> > remoteAuthorizationPendingList();
+     
+     /**
+      * Request a contact.
+      * A remote contact should be added to the list of known contacts.
+      * @param id The id identifies the contact (protocol specific)
+      * @return true if the handle was found else false.
+      */
+     bool requestContact( const QString& id );
+
+     /**
+      * Authorize contact.
+      * A remote contact should be authorized.
+      * @param contact The contact to autorize.
+      * @return true if ...
+      */
+     bool authorizeContact( const Contact* contact );
+
+     /**
+      * Remove a contact.
+      * The contact should be removed.
+      * @param contactToRemove The contact that should be removed. Do not use this pointer after this call!
+      */
+     bool removeContact( const TpPrototype ::Contact* contactToRemove );
+
+     /**
+      * Returns a contact pointer for handle id.
+      * This function provides a fast lookup of a contact if a valid handle is provided.
+      * @return The contact that corresponds to the handle or NULL if the handle is unknown.
+      */
+     QPointer<TpPrototype ::Contact> contactForHandle( uint handle );
+
+     /**
+      * The local use handle.
+      * The local user has a handle that is returned by this function. The local handle cannot be used to get
+      * a valid contact with contactForHandle()!
+      */
+      uint localHandle();
+
+signals:
+    /**
+     * A text channel was opened.
+     * This signal is emitted when a text channel was opened for a contact. This usually means that you received a text message.<br>
+     * The chat channel object can be retrieved from the contact.
+     * @param contact The contact that received the text message and contains the text channel object.
+     */
+    void signalTextChannelOpenedForContact( TpPrototype ::Contact* contact );
+
+    /**
+     * A streamed media channel was opened.
+     * This signal is emitted when a streamed media channel was opened for a contact and all interfaces were established successfully.
+     * This usually means that you received a call.<br>
+     * The StreamedMedia channel object can be retrieved from the contact. Use acceptIncomingStream() or rejectIncomingStream() to accept or reject.
+     * @param contact The contact that received the text message and contains the StreamedMediaChannel object.
+     * @see StreamMediaChannel
+     */
+    void signalStreamedMediaChannelOpenedForContact( TpPrototype ::Contact* contact );
+
+    /**
+     * A Contact was added.
+     * A new remote Contact was added but needs to be accepted remotely.
+     * @see signalContactRemotePending()
+     */
+    void signalContactAdded( TpPrototype ::ContactManager* contactManager, TpPrototype ::Contact* contact );
+    
+    /**
+     * A Contact is pending locally.
+     * A Contact that is local pending have requested membership of the channel, but the local user of the framework must
+     * accept their request before they may join.
+     */
+    void signalContactLocalPending( TpPrototype ::ContactManager* contactManager, TpPrototype ::Contact* contact );
+    
+    /**
+     * A Contact is pending remotely.
+     * A Contact that is remote pending list have been invited to the channel, but the remote user has not
+     * accepted the invitation.
+     */
+    void signalContactRemotePending( TpPrototype ::ContactManager* contactManager, TpPrototype ::Contact* contact );
+    
+    /**
+     * A Contact was subscribed.
+     * This signal is emitted if a new contact was subscribed.
+     */
+    void signalContactSubscribed( TpPrototype ::ContactManager* contactManager, TpPrototype ::Contact* contact );
+    
+    /**
+     * A Contact was removed.    
+     * This signal is emitted if a new contact was removed.
+     */
+    void signalContactRemoved( TpPrototype ::ContactManager* contactManager, TpPrototype ::Contact* contact );
+    
+    /**
+     * @todo: Add doc! (seil)
+     */
+    void signalContactKnown( TpPrototype ::ContactManager* contactManager, TpPrototype ::Contact* contact );
+    
+    /**
+     * @todo: Add doc! (seil)
+     */
+    void signalForModelContactSubscribed( TpPrototype ::ContactManager* contactManager, TpPrototype ::Contact* contact );
+    
+    /**
+     * @todo: Add doc! (seil)
+     */
+    void signalForModelContactRemoved( TpPrototype ::ContactManager* contactManager, TpPrototype ::Contact* contact );
+
+    /**
+     * Members changed.
+     * This signal is emitted whenever one of the internal lists of contacts (member, local pending, remote pending) changes.
+     * @param contactManager The contact manager that handles the contacts.
+     * @param message A string message from the server, or blank if not
+     * @param members List of contacts currently listed as members.
+     * @param localPending Contacts that are waiting for a local approval.
+     * @param remotePending Contacs that are waiting for a remote approval.
+     * @param actor The contact that causes the change. May be NULL if unkown.
+     * @param reason The reason of the change.
+     */
+    void signalMembersChanged( TpPrototype ::ContactManager* contactManager,
+                               const QString& message,
+                               QList<QPointer<TpPrototype ::Contact> > members,
+                               QList<QPointer<TpPrototype ::Contact> > localPending,
+                               QList<QPointer<TpPrototype ::Contact> > remotePending,
+                               TpPrototype ::Contact* actor,
+                               Telepathy::ChannelGroupChangeReason reason );
+
+protected:
+    /**
+     * Constructor. The contact manager cannot be instantiated directly. Use Connection::contactManager() for it!
+     */
+    ContactManager( Telepathy::Client::ConnectionInterface* connection,
+                    QObject* parent = NULL );
+    ~ContactManager();
+
+    
+    void openSubscribedContactsChannel(uint handle, const QDBusObjectPath& objectPath, const QString& channelType);
+
+     /**
+     * ..
+      */
+    void openPublishContactsChannel(uint handle, const QDBusObjectPath& objectPath, const QString& channelType);
+     
+     /**
+     * ..
+      */
+    void openKnownContactsChannel(uint handle, const QDBusObjectPath& objectPath, const QString& channelType);
+
+     /**
+     * ..
+      */
+    void openDenyContactsChannel(uint handle, const QDBusObjectPath& objectPath, const QString& channelType);
+
+    void openTextChannel( uint handle, uint handleType, const QString& channelPath, const QString& channelType );
+
+    void openStreamedMediaChannel( uint handle, uint handleType, const QString& channelPath, const QString& channelType );
+
+protected slots:
+
+    void slotMembersChanged(const QString& message,
+                            const Telepathy::UIntList& members_added,
+                            const Telepathy::UIntList& members_removed,
+                            const Telepathy::UIntList& local_pending,
+                            const Telepathy::UIntList& remote_pending,
+                            uint actor, uint reason);
+    void slotKnownMembersChanged(const QString& message,
+                            const Telepathy::UIntList& members_added,
+                            const Telepathy::UIntList& members_removed,
+                            const Telepathy::UIntList& local_pending,
+                            const Telepathy::UIntList& remote_pending,
+                            uint actor, uint reason);
+    void slotPublishedMembersChanged(const QString& message,
+                                 const Telepathy::UIntList& members_added,
+                                 const Telepathy::UIntList& members_removed,
+                                 const Telepathy::UIntList& local_pending,
+                                 const Telepathy::UIntList& remote_pending,
+                                 uint actor, uint reason);
+    void slotSubscribedMembersChanged(const QString& message,
+                                     const Telepathy::UIntList& members_added,
+                                     const Telepathy::UIntList& members_removed,
+                                     const Telepathy::UIntList& local_pending,
+                                     const Telepathy::UIntList& remote_pending,
+                                     uint actor, uint reason);       
+private:
+    void init( Telepathy::Client::ConnectionInterface* connection );
+
+    ContactManagerPrivate * const d;
+    friend class Connection;
+    friend class ConnectionPrivate;
+    friend class Contact;
+};
+
+}
+
+#endif
diff --git a/TelepathyQt4/Prototype/DBusInterface.cpp b/TelepathyQt4/Prototype/DBusInterface.cpp
new file mode 100644
index 0000000..fd0f5c8
--- /dev/null
+++ b/TelepathyQt4/Prototype/DBusInterface.cpp
@@ -0,0 +1,47 @@
+/*
+ * This file is part of TelepathyQt4
+ *
+ * Copyright (C) 2008 basysKom GmbH
+ * Copyright (C) 2008 Collabora Ltd. <http://www.collabora.co.uk/>
+ * Copyright (C) 2008 Nokia Corporation
+ *
+ * This library is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU Lesser General Public
+ * License as published by the Free Software Foundation; either
+ * version 2.1 of the License, or (at your option) any later version.
+ *
+ * This library is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
+ * Lesser General Public License for more details.
+ *
+ * You should have received a copy of the GNU Lesser General Public
+ * License along with this library; if not, write to the Free Software
+ * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA  02110-1301  USA
+ */
+
+#include "TelepathyQt4/Prototype/DBusInterface.h"
+
+namespace
+{
+    const char* g_serviceName   = "org.freedesktop.DBus";
+    const char* g_objectPath    = "/";
+    const char* g_interfaceName = "org.freedesktop.DBus";
+}
+
+using namespace TpPrototype;
+
+DBusInterface::DBusInterface( QObject* parent ): 
+QDBusAbstractInterface( g_serviceName, 
+                        g_objectPath, 
+                        g_interfaceName, 
+                        QDBusConnection::sessionBus(), 
+                        parent )
+{
+}
+
+QDBusReply<QStringList> DBusInterface::listActivatableNames()
+{
+    Q_ASSERT( isValid() );
+    return call( QLatin1String("ListActivatableNames")  );
+}
diff --git a/TelepathyQt4/Prototype/DBusInterface.h b/TelepathyQt4/Prototype/DBusInterface.h
new file mode 100644
index 0000000..e786ff1
--- /dev/null
+++ b/TelepathyQt4/Prototype/DBusInterface.h
@@ -0,0 +1,51 @@
+/*
+ * This file is part of TelepathyQt4
+ *
+ * Copyright (C) 2008 basysKom GmbH
+ * Copyright (C) 2008 Collabora Ltd. <http://www.collabora.co.uk/>
+ * Copyright (C) 2008 Nokia Corporation
+ *
+ * This library is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU Lesser General Public
+ * License as published by the Free Software Foundation; either
+ * version 2.1 of the License, or (at your option) any later version.
+ *
+ * This library is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
+ * Lesser General Public License for more details.
+ *
+ * You should have received a copy of the GNU Lesser General Public
+ * License along with this library; if not, write to the Free Software
+ * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA  02110-1301  USA
+ */
+#ifndef TelepathyQt4_Prototype_DBusInterface_h_
+#define TelepathyQt4_Prototype_DBusInterface_h_
+
+#include <QDBusAbstractInterface>
+#include <QDBusReply>
+#include <QStringList>
+
+namespace TpPrototype
+{
+
+/**
+ * Class to access function provided by dbus daemon.
+ */
+class DBusInterface : public QDBusAbstractInterface
+{
+    Q_OBJECT
+public:
+    DBusInterface( QObject* parent = NULL );
+
+    /**
+     * Return a list of all registered service names. These names can be activated by calling the service.
+     * @return List of service names.
+     */
+    QDBusReply<QStringList> listActivatableNames();
+    
+};
+
+}
+#endif
+
diff --git a/TelepathyQt4/Prototype/Makefile.am b/TelepathyQt4/Prototype/Makefile.am
new file mode 100644
index 0000000..15fb7af
--- /dev/null
+++ b/TelepathyQt4/Prototype/Makefile.am
@@ -0,0 +1,161 @@
+protoincludedir=$(includedir)/tpqt4-prototype/TelepathyQt4/Prototype
+protoclientincludedir=$(protoincludedir)/Client
+genincludedir=$(protoincludedir)/_gen
+
+pkgconfigdir = ${libdir}/pkgconfig
+pkgconfig_DATA = TpQt4Prototype.pc
+
+EXTRA_DIST = \
+    all.xml \
+    channel-handler.xml
+
+lib_LTLIBRARIES = libtpqt4-prototype.la
+
+# The quoting here is unnecessary but harmless, and has the useful side-effect
+# that vim quickfix mode (:make) doesn't interpret the libtool --mode=link
+# command as an error message in a bizarrely named file
+libtpqt4_prototype_la_LDFLAGS = \
+    -version-info "$(LT_CURRENT)":"$(LT_REVISION)":"$(LT_AGE)" -static
+libtpqt4_prototype_la_LIBADD = $(ALL_LIBS)
+libtpqt4_prototype_la_DEPENDENCIES = Makefile.am
+
+libtpqt4_prototype_la_SOURCES = \
+    Account.cpp \
+    AccountManager.cpp \
+    AvatarManager.cpp \
+    CapabilitiesManager.cpp \
+    ChatChannel.cpp \
+    Connection.cpp \
+    ConnectionFacade.cpp \
+    DBusInterface.cpp \
+    PresenceManager.cpp \
+    StreamedMediaChannel.cpp \
+    types.cpp
+
+nodist_libtpqt4_prototype_la_SOURCES = \
+    _gen/cli-channel-handler-body.hpp \
+    _gen/types-body.hpp
+
+protoinclude_HEADERS = \
+    Account.h \
+    AccountManager.h \
+    AvatarManager.h \
+    CapabilitiesManager.h \
+    ChatChannel.h \
+    Connection.h \
+    ConnectionFacade.h \
+    Constants \
+    Contact.h \
+    DBusInterface.h \
+    PresenceManager.h \
+    StreamedMediaChannel.h \
+    Types \
+    constants.h \
+    types.h
+
+nodist_geninclude_HEADERS = \
+    _gen/cli-channel-handler.h \
+    _gen/constants.h \
+    _gen/types.h
+
+BUILT_SOURCES = \
+    $(nodist_libtpqt4_prototype_la_SOURCES) \
+    $(nodist_geninclude_HEADERS) \
+    _gen/stable-spec.xml \
+    _gen/spec-stamp \
+    _gen/stable-stamp
+
+CLEANFILES = \
+    $(BUILT_SOURCES)
+
+distclean-local:
+	rm -rf _gen
+
+include $(top_srcdir)/tools/check-coding-style.mk
+check-local: check-coding-style
+
+AM_CXXFLAGS = \
+    $(ERROR_CXXFLAGS) \
+    @QTCORE_CFLAGS@ \
+    @QTDBUS_CFLAGS@ \
+    -I$(top_builddir) \
+    -I$(top_srcdir)
+
+ALL_LIBS = \
+    @QTCORE_LIBS@ \
+    @QTDBUS_LIBS@
+
+# Generated stuff
+
+# Bootstrapping
+
+_gen/spec-stamp: $(wildcard $(top_srcdir)/spec/*.xml)
+	$(mkdir_p) _gen
+	touch $@
+
+_gen/stable-stamp: $(wildcard *.xml) _gen/spec-stamp
+	touch $@
+
+_gen/stable-spec.xml: all.xml _gen/stable-stamp \
+	$(top_srcdir)/tools/xincludator.py \
+	Makefile.am
+	$(PYTHON) $(top_srcdir)/tools/xincludator.py \
+		$< > $@
+
+# Things generated from the whole spec at once
+
+_gen/constants.h: _gen/stable-spec.xml \
+		$(top_srcdir)/tools/qt4-constants-gen.py \
+		Makefile.am
+	$(PYTHON) $(top_srcdir)/tools/qt4-constants-gen.py \
+		--namespace='TpPrototype' \
+		--str-constant-prefix='TP_PROTOTYPE_' \
+		--specxml=$< \
+		> $@.tmp && mv $@.tmp $@
+
+_gen/types.h _gen/types-body.hpp: _gen/stable-spec.xml \
+		$(top_srcdir)/tools/qt4-types-gen.py \
+		Makefile.am
+	$(PYTHON) $(top_srcdir)/tools/qt4-types-gen.py \
+		--namespace='TpPrototype' \
+		--declfile='_gen/types.h' \
+		--implfile='_gen/types-body.hpp' \
+		--realinclude='TelepathyQt4/Prototype/types.h' \
+		--prettyinclude='TelepathyQt4/Prototype/Types' \
+		--specxml=$<
+
+# Things generated per interface group
+
+_gen/spec-%.xml: %.xml $(top_srcdir)/tools/xincludator.py _gen/spec-stamp
+	$(PYTHON) $(top_srcdir)/tools/xincludator.py \
+		$< > $@
+
+_gen/cli-%.h _gen/cli-%-body.hpp: _gen/spec-%.xml \
+		_gen/stable-spec.xml \
+		$(top_srcdir)/tools/qt4-client-gen.py \
+		Makefile.am
+	set -e; \
+	namespace='TpPrototype::Client'; \
+	group= ; \
+	prettyinclude= ; \
+	mainiface= ; \
+	case $* in \
+		channel-handler) \
+			group='clientchannelhandler'; \
+			prettyinclude='ChannelHandler';; \
+	esac; \
+	$(PYTHON) $(top_srcdir)/tools/qt4-client-gen.py \
+		--group=$$group \
+		--namespace=$$namespace \
+		--typesnamespace='Telepathy' \
+		--headerfile=_gen/cli-$*.h \
+		--implfile=_gen/cli-$*-body.hpp \
+		--realinclude='TelepathyQt4/Prototype/cli-$*.h' \
+		--prettyinclude='TelepathyQt4/Prototype/Client/'$$prettyinclude \
+		--specxml=_gen/stable-spec.xml \
+		--ifacexml=$< \
+		--extraincludes='<TelepathyQt4/Types>,<TelepathyQt4/Prototype/Types>' \
+		$$mainiface
+
+%.moc.hpp: %.h _gen/constants.h _gen/types.h
+	$(MOC) @QTCORE_CFLAGS@ @QTDBUS_CFLAGS@ -I$(top_builddir) -I$(top_srcdir) -i $< -o $@
diff --git a/TelepathyQt4/Prototype/PresenceManager.cpp b/TelepathyQt4/Prototype/PresenceManager.cpp
new file mode 100644
index 0000000..caaa18d
--- /dev/null
+++ b/TelepathyQt4/Prototype/PresenceManager.cpp
@@ -0,0 +1,620 @@
+/*
+ * This file is part of TelepathyQt4
+ *
+ * Copyright (C) 2008 basysKom GmbH
+ * Copyright (C) 2008 Collabora Ltd. <http://www.collabora.co.uk/>
+ * Copyright (C) 2008 Nokia Corporation
+ *
+ * This library is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU Lesser General Public
+ * License as published by the Free Software Foundation; either
+ * version 2.1 of the License, or (at your option) any later version.
+ *
+ * This library is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
+ * Lesser General Public License for more details.
+ *
+ * You should have received a copy of the GNU Lesser General Public
+ * License along with this library; if not, write to the Free Software
+ * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA  02110-1301  USA
+ */
+
+#include "TelepathyQt4/Prototype/PresenceManager.h"
+
+#include <QCoreApplication>
+#include <QDBusObjectPath>
+#include <QDBusPendingReply>
+#include <QDebug>
+#include <QMap>
+#include <QPointer>
+
+#include <TelepathyQt4/Client/Connection>
+
+#include <TelepathyQt4/Prototype/Account.h>
+#include <TelepathyQt4/Prototype/AccountManager.h>
+#include <TelepathyQt4/Prototype/ConnectionFacade.h>
+#include <TelepathyQt4/Prototype/Connection.h>
+#include <TelepathyQt4/Prototype/Contact.h>
+#include <TelepathyQt4/Prototype/ContactManager.h>
+
+// #define ENABLE_DEBUG_OUTPUT_
+
+namespace
+{
+    const char* g_offlineStatusString      = "offline";
+    const char* g_statusParamMessageString = "message";
+}
+
+using namespace TpPrototype;
+
+class TpPrototype::PresenceManagerPrivate
+{
+public:
+    PresenceManagerPrivate( Connection* connection,
+                            Telepathy::Client::ConnectionInterface* interface )
+    { init( connection, interface ); }
+
+    Telepathy::Client::ConnectionInterface* m_pConnectionInterface;
+    Telepathy::Client::ConnectionInterfaceSimplePresenceInterface* m_pSimplePresenceInterface;
+    Telepathy::Client::ConnectionInterfacePresenceInterface* m_pPresenceInterface;
+    QPointer<Connection> m_pConnection;
+    bool m_isValid;
+    QMap<QString,int> m_mapStatusStringToType;
+    
+    void init( Connection* connection,
+               Telepathy::Client::ConnectionInterface* interface )
+    {
+        m_pConnectionInterface     = interface;
+        m_pConnection              = connection;
+        m_pSimplePresenceInterface = NULL;
+        m_pPresenceInterface       = NULL;        
+        m_isValid                  = true;
+
+        m_mapStatusStringToType.insert( "offline"  , 1 /*Connection_Presence_Type_Offline*/ ); //TODO: Why is there no enum for these types?
+        m_mapStatusStringToType.insert( "available", 2 /*Connection_Presence_Type_Available*/ );
+        m_mapStatusStringToType.insert( "away"     , 3 /*Connection_Presence_Type_Away*/ );
+        m_mapStatusStringToType.insert( "brb"      , 3 /*Connection_Presence_Type_Away*/  );
+        m_mapStatusStringToType.insert( "xa"       , 4 /*Connection_Presence_Type_Extended_Away*/ );
+        m_mapStatusStringToType.insert( "hidden"   , 5 /*Connection_Presence_Type_Busy*/ );
+        m_mapStatusStringToType.insert( "busy"     , 6 /*Connection_Presence_Type_Busy*/  );
+        m_mapStatusStringToType.insert( "dnd"      , 6 /*Connection_Presence_Type_Busy*/ );
+        m_mapStatusStringToType.insert( "unknown"  , 7 /*Connection_Presence_Type_Unknown*/ );
+        m_mapStatusStringToType.insert( "error"    , 8 /*Connection_Presence_Type_Error*/ );
+        
+    }
+    
+    uint localHandle()
+    {
+        uint self_handle = ConnectionFacade::instance()->selfHandleForConnectionInterface( m_pConnectionInterface );
+        if ( self_handle < 0 )
+        { m_isValid = false; }
+    
+        return self_handle;
+    }
+
+// Protected functions
+
+    uint mapStatusStringToType( const QString& status ) const
+    {
+        return m_mapStatusStringToType.value( status );
+    }
+
+    Telepathy::SimplePresence convertToSimplePresence( const Telepathy::LastActivityAndStatuses& status ) const
+    {
+        Telepathy::SimplePresence simple_presence;
+
+        QStringList status_list = status.statuses.keys();
+
+        Q_ASSERT( status_list.count() == 1 );
+        if ( status_list.count() < 1 )
+        { return simple_presence; }
+
+        simple_presence.type          = mapStatusStringToType( status_list.at( 0 ) );
+        simple_presence.status        = status_list.at( 0 );
+        simple_presence.statusMessage = status.statuses.value( status_list.at( 0 ) ).value( g_statusParamMessageString ).toString();
+    
+        return simple_presence;
+    }
+
+    Telepathy::SimpleContactPresences convertToSimplePresences( const Telepathy::ContactPresences& presences ) const
+    {
+        Telepathy::SimpleContactPresences contact_presences;
+
+        QList<uint> keys = presences.keys();
+        foreach( uint key, keys )
+        {
+            contact_presences.insert( key, convertToSimplePresence( presences.value( key ) ) );
+        }
+    
+        return contact_presences;
+    }
+
+    Telepathy::MultipleStatusMap convertToMultipleStatusMap( const QString& status, const QString& statusMessage ) const
+    {
+        Telepathy::MultipleStatusMap status_map;
+
+        QVariantMap protocol_specif_parameters;
+        if ( !statusMessage.isEmpty() )
+        { protocol_specif_parameters.insert( g_statusParamMessageString, statusMessage ); }
+        
+        status_map.insert( status, protocol_specif_parameters ); 
+
+        return status_map;
+    }
+};
+
+PresenceManager::PresenceManager( Connection* connection,
+                                  Telepathy::Client::ConnectionInterface* interface,
+                                  QObject* parent ):
+    QObject( parent ),
+    d( new PresenceManagerPrivate( connection, interface ) )
+{
+    init();
+}
+
+PresenceManager::~PresenceManager()
+{
+#ifdef ENABLE_DEBUG_OUTPUT_
+    qDebug() << "D'tor PresenceManager (" << this << ")";
+#endif
+    delete d;
+}
+
+bool PresenceManager::isValid()
+{
+    return d->m_isValid;
+}
+
+Telepathy::SimpleStatusSpecMap PresenceManager::statuses()
+{
+    Q_ASSERT( d->m_pSimplePresenceInterface || d->m_pPresenceInterface );
+
+    if ( d->m_pSimplePresenceInterface )
+    { return d->m_pSimplePresenceInterface->Statuses(); }
+
+    if ( d->m_pPresenceInterface )
+    {
+        // We return a minimum set of states that should be provided by every contact manager and protocol
+        Telepathy::SimpleStatusSpecMap ret_status;
+        Telepathy::SimpleStatusSpec available = { 2, 2, true };
+        ret_status.insert( "available", available );
+        Telepathy::SimpleStatusSpec away = { 3, 3, true };
+        ret_status.insert( "away", away );
+        Telepathy::SimpleStatusSpec offline = { 1, 1, true };
+        ret_status.insert( "offline", offline );
+        
+        return ret_status;
+    } 
+
+    return Telepathy::SimpleStatusSpecMap();
+}
+
+bool PresenceManager::setPresence( const QString& status, const QString& statusMessage )
+{
+    Q_ASSERT( d->m_pSimplePresenceInterface || d->m_pPresenceInterface );
+
+    if ( !d->m_pSimplePresenceInterface && !d->m_pPresenceInterface )
+    { return false; }
+    
+    // The state "offline" is presented as possible state with statuses(). Due to unknown reasons it is not
+    // a valid name for setPresence(). Thus, we handle it on this layer..
+    if ( status == g_offlineStatusString )
+    {
+        Q_ASSERT( d->m_pConnection );
+
+        // TODO: Think whether sending this signal here manually (and before disconnecting) is really a good idea!
+        const Telepathy::SimplePresence new_presence = { d->mapStatusStringToType( "offline" ), status, statusMessage };
+        emit signalOwnPresenceUpdated( d->m_pConnection->account(), new_presence );
+        
+        d->m_pConnection->requestDisconnect();
+        return true;
+    }
+    
+    if ( d->m_pSimplePresenceInterface )
+    {
+        QDBusPendingReply<> set_presence_reply = d->m_pSimplePresenceInterface->SetPresence( status, statusMessage );
+        set_presence_reply.waitForFinished();
+
+        if ( !set_presence_reply.isValid() )
+        {
+            QDBusError error = set_presence_reply.error();
+        
+            qWarning() << "SetPresence: error type:" << error.type()
+                    << "error name:" << error.name()
+                    << "error message:" << error.message();
+            
+            d->m_isValid = false;
+            return false;
+        }
+        return true;
+    }
+    
+    if ( d->m_pPresenceInterface )
+    {
+        QDBusPendingReply<> set_status_reply = d->m_pPresenceInterface->SetStatus( d->convertToMultipleStatusMap( status, statusMessage ) );
+        set_status_reply.waitForFinished();
+        if ( !set_status_reply.isValid() )
+        {
+            QDBusError error = set_status_reply.error();
+        
+            qWarning() << "SetStatus: error type:" << error.type()
+                    << "error name:" << error.name()
+                    << "error message:" << error.message();
+
+            d->m_isValid = false;
+            return false;
+        }
+
+#if 0 // TODO: Exame further: At some point I received the signal. Don't know why..
+        // The simple presence interface is emitting a signal if I changed the local presence here but the presence interface does not!
+        // We simulate this behavior here..
+        const Telepathy::SimplePresence new_presence = { d->mapStatusStringToType( status ), status, statusMessage };
+        emit signalOwnPresenceUpdated( d->m_pConnection->account(), new_presence );
+#endif   
+        return true;
+    }
+
+    // Fall through..
+    return false;
+}
+
+// TODO: This function is doing the same as presencesForContacts() but just for one contact! Merge both functions to remove code duplication!
+Telepathy::SimplePresence PresenceManager::currentPresence()
+{
+    Q_ASSERT( d->m_pSimplePresenceInterface || d->m_pPresenceInterface );
+
+    if ( !d->m_pConnection || ( !d->m_pSimplePresenceInterface && !d->m_pPresenceInterface ) )
+    {
+        return Telepathy::SimplePresence();
+    }
+
+    Telepathy::UIntList uid_list;
+    uid_list << d->localHandle();
+
+    if ( d->m_pSimplePresenceInterface )
+    {
+        QDBusPendingReply<Telepathy::SimpleContactPresences> get_presence_reply = d->m_pSimplePresenceInterface->GetPresences( uid_list );
+        get_presence_reply.waitForFinished();
+        
+        if ( !get_presence_reply.isValid() )
+        {
+            QDBusError error = get_presence_reply.error();
+        
+            qWarning() << "GetPresences: error type:" << error.type()
+                    << "error name:" << error.name()
+                    << "error message:" << error.message();
+
+            d->m_isValid = false;
+            return Telepathy::SimplePresence();
+        }
+
+        Telepathy::SimpleContactPresences presence_list = get_presence_reply.value();
+        QList<Telepathy::SimplePresence> value_list = presence_list.values();
+        
+        if ( value_list.count() == 0 )
+        { return Telepathy::SimplePresence(); }
+
+        return value_list.at( 0 );
+    }
+
+    if ( d->m_pPresenceInterface )
+    {
+        QDBusPendingReply<Telepathy::ContactPresences> get_presence_reply = d->m_pPresenceInterface->GetPresence( uid_list );
+        get_presence_reply.waitForFinished();
+        
+        if ( !get_presence_reply.isValid() )
+        {
+            QDBusError error = get_presence_reply.error();
+        
+            qWarning() << "GetPresence: error type:" << error.type()
+                    << "error name:" << error.name()
+                    << "error message:" << error.message();
+
+            d->m_isValid = false;
+            return Telepathy::SimplePresence();
+        }
+
+        Telepathy::ContactPresences presence_list = get_presence_reply.value();
+        QList<Telepathy::LastActivityAndStatuses> value_list = presence_list.values();
+        
+        if ( value_list.count() == 0 )
+        { return Telepathy::SimplePresence(); }
+
+        return d->convertToSimplePresence( value_list.at( 0 ) );
+    }
+
+    // Fall through..
+    return Telepathy::SimplePresence();
+}
+
+// TODO: See comment for currentPresence! Merge both to remove code duplication
+Telepathy::SimpleContactPresences PresenceManager::presencesForContacts( const QList<QPointer<Contact> >& contacts )
+{
+    Q_ASSERT( d->m_pSimplePresenceInterface || d->m_pPresenceInterface );
+
+    if ( !d->m_pConnection || ( !d->m_pSimplePresenceInterface && !d->m_pPresenceInterface ) )
+    { return Telepathy::SimpleContactPresences(); }
+    
+    Telepathy::UIntList contact_ids;
+    foreach( Contact* contact, contacts )
+    {
+        if ( !contact )
+        { continue; }
+        contact_ids.append( contact->telepathyHandle() );
+    }
+
+    if ( d->m_pSimplePresenceInterface )
+    {
+        QDBusPendingReply<Telepathy::SimpleContactPresences> get_presence_reply = d->m_pSimplePresenceInterface->GetPresences( contact_ids );
+        get_presence_reply.waitForFinished();
+
+        if ( !get_presence_reply.isValid() )
+        {
+            QDBusError error = get_presence_reply.error();
+        
+            qWarning() << "GetPresences: error type:" << error.type()
+                    << "error name:" << error.name()
+                    << "error message:" << error.message();
+
+            return Telepathy::SimpleContactPresences();
+        }
+    
+        Telepathy::SimpleContactPresences presences=get_presence_reply.value();
+        QList<uint> keys = presences.keys();
+        QPointer<TpPrototype::Contact> contact;
+        foreach( uint key, keys )
+        {
+#ifdef ENABLE_DEBUG_OUTPUT_
+            qDebug() << "presencesForContacts Key"<<key;
+#endif
+            for (int i=0; i<contacts.size(); i++)
+            {
+
+                contact=contacts.at( i);
+#ifdef ENABLE_DEBUG_OUTPUT_
+                qDebug() << "Contact "<< key << "Status" <<presences.value( key ).status << "Message:" << presences.value( key ).statusMessage;
+#endif
+                if (contact->telepathyHandle()==key)
+                {
+                    contact->setPresenceType(presences.value( key ).type);
+                    contact->setPresenceStatus(presences.value( key ).status);
+                    contact->setPresenceMessage(presences.value( key ).statusMessage);
+                }
+            }
+        }
+        
+        return get_presence_reply.value();
+    }
+    
+    if ( d->m_pPresenceInterface )
+    {
+        QDBusPendingReply<Telepathy::ContactPresences> get_presence_reply = d->m_pPresenceInterface->GetPresence( contact_ids );
+        get_presence_reply.waitForFinished();
+        
+        if ( !get_presence_reply.isValid() )
+        {
+            QDBusError error = get_presence_reply.error();
+        
+            qWarning() << "GetPresence: error type:" << error.type()
+                    << "error name:" << error.name()
+                    << "error message:" << error.message();
+
+            d->m_isValid = false;
+            return Telepathy::SimpleContactPresences();
+        }
+
+        Telepathy::ContactPresences presences = get_presence_reply.value();
+        QList<uint> keys = presences.keys();
+        QPointer<TpPrototype::Contact> contact;
+        foreach( uint key, keys )
+        {
+            //qDebug() << "presencesForContacts Key"<<key;
+            for ( int i=0; i<contacts.size(); i++ )
+            {
+                contact=contacts.at( i);
+                //qDebug() << "Contact "<< key << "Status" <<presences.value( key ).status;            
+                if (contact->telepathyHandle()==key)
+                {
+                    Telepathy::SimplePresence simple_presence = d->convertToSimplePresence( presences.value( key ) );
+                    contact->setPresenceType( simple_presence.type );
+                    contact->setPresenceStatus( simple_presence.status );
+                    contact->setPresenceMessage( simple_presence.statusMessage );
+                }
+            }
+        }
+        
+        return d->convertToSimplePresences( presences );
+    }
+
+    // Fall through..
+    return Telepathy::SimpleContactPresences();
+}
+
+// Protected slots
+    
+// Called by the _simple_ presence interface if presence were updated
+void PresenceManager::slotPresencesChanged( const Telepathy::SimpleContactPresences& presences )
+{
+    if ( !d->m_pConnection )
+    {
+        qWarning() << "PresenceManager::slotPresencesChanged(): Received a presence changed signal but no connection object exists!";
+        return;
+    }
+        
+    QList<uint> keys = presences.keys();
+    foreach( uint key, keys )
+    {
+        Telepathy::SimplePresence changed_presence = presences.value( key );
+#ifdef ENABLE_DEBUG_OUTPUT_
+        qDebug() << "Contact ID: "  << key
+                 << "Type: "        << changed_presence.type
+                 << "Status:"       << changed_presence.status
+                 << "StatusMessage:"<< changed_presence.statusMessage;
+#endif
+        
+        if ( d->localHandle() == key )
+        {
+            if ( !d->m_pConnection->account() )
+            {
+                qWarning() << "PresenceManager::slotPresencesChanged(): Connection without account!";
+                return;
+            }
+#ifdef ENABLE_DEBUG_OUTPUT_
+            qDebug() << "PresenceManager::slotPresencesChanged() -> signalOwnPresenceUpdated";
+#endif
+            emit signalOwnPresenceUpdated( d->m_pConnection->account(), changed_presence );
+        } 
+        else
+        {
+            if ( !d->m_pConnection->contactManager() )
+            {
+                qWarning() << "PresenceManager::slotPresencesChanged(): Unable to request contact manager!";
+                return;
+            }
+
+            Contact* found_contact = NULL;
+            foreach( Contact* contact, d->m_pConnection->contactManager()->contactList() )
+            {
+                if ( contact && contact->telepathyHandle() == key )
+                { found_contact = contact; }
+            }
+            if ( found_contact )
+            {
+                found_contact->setPresenceType(changed_presence.type);
+                found_contact->setPresenceStatus(changed_presence.status);
+                found_contact->setPresenceMessage(changed_presence.statusMessage);
+
+#ifdef ENABLE_DEBUG_OUTPUT_
+                qDebug() << "PresenceManager::slotPresencesChanged() -> signalRemotePresencesUpdated";
+#endif
+                emit signalRemotePresencesUpdated( found_contact, changed_presence );
+            }
+            else
+            {
+                qWarning() << "PresenceManager::slotPresencesChanged: Received a signal that a non existing contact changed its presence!";
+            }
+        }
+    }
+}
+
+// Called by the presence interface (that one without "simple" prefix) if any presences were updated
+void PresenceManager::slotPresencesUpdate( const Telepathy::ContactPresences& presences )
+{
+#ifdef ENABLE_DEBUG_OUTPUT_
+    qDebug() << "PresenceManager::slotPresencesUpdate()";
+    QList<uint> keys = presences.keys();
+    foreach( uint key, keys )
+    {
+        qDebug() << "Contact ID  : "  << key
+                 << "LastActivity: "  << presences.value( key ).lastActivity;
+        Telepathy::MultipleStatusMap statuses = presences.value( key ).statuses; // QMap<QString, QVariantMap>
+        QList<QString> status_keys = statuses.keys();
+        foreach( QString status_key, status_keys )
+        {
+            qDebug() << "Status:" << status_key << "Map:" << statuses.value( status_key );
+        }
+   }
+#endif
+   slotPresencesChanged( d->convertToSimplePresences( presences ) );
+}
+
+TpPrototype::Connection * PresenceManager::connection()
+{
+    return d->m_pConnection;
+}
+
+void PresenceManager::init()
+{
+    Q_ASSERT( d->m_pConnectionInterface );
+
+    if ( !d->m_pConnectionInterface || !d->m_pConnection )
+    {
+        d->m_isValid = false;
+        return;
+    }
+    
+    Telepathy::registerTypes();
+    QDBusPendingReply<QStringList> interfaces_reply = d->m_pConnectionInterface->GetInterfaces();
+    interfaces_reply.waitForFinished();
+
+    if ( !interfaces_reply.isValid() )
+    {
+        QDBusError error = interfaces_reply.error();
+    
+        qWarning() << "GetInterfaces: error type:" << error.type()
+                   << "GetInterfaces: error name:" << error.name();
+
+        d->m_isValid = false;
+        return;
+    }
+    
+    QString simplepresence_interface_name;
+    bool found_simple_presence_support = false;
+    QString presence_interface_name;
+    bool found_presence_support = false;
+    
+    foreach( const QString& interface, interfaces_reply.value() )
+    {
+        if ( interface.endsWith( ".SimplePresence" ) )
+        {
+            found_simple_presence_support = true;
+            simplepresence_interface_name = interface;
+        }
+        if ( interface.endsWith( ".Presence" ) )
+        {
+            found_presence_support = true;
+            presence_interface_name = interface;
+        }
+    }
+    
+#ifdef ENABLE_DEBUG_OUTPUT_
+    qDebug() << "Simple Presence Interface Name: " << simplepresence_interface_name;
+    qDebug() << "Presence Interface Name       : " << presence_interface_name;
+#endif
+
+    // FIXME: The following line shound be commented out!!
+    // found_simple_presence_support = false; // Override to test the (not simple) presence interface implementation
+    
+    if ( found_simple_presence_support )
+    {
+#ifdef ENABLE_DEBUG_OUTPUT_
+        qDebug( "PresenceManager::init(): Connection Manager provides the Interface \"SimplePresence\". I will use this one!" );
+#endif
+        d->m_pSimplePresenceInterface = new Telepathy::Client::ConnectionInterfaceSimplePresenceInterface( d->m_pConnectionInterface->service(),
+                                                                                                           d->m_pConnectionInterface->path(),
+                                                                                                           this );
+        Q_ASSERT( d->m_pSimplePresenceInterface );
+        Q_ASSERT( d->m_pSimplePresenceInterface->isValid() );
+
+        connect( d->m_pSimplePresenceInterface, SIGNAL( PresencesChanged( const Telepathy::SimpleContactPresences& ) ),
+                 this, SLOT( slotPresencesChanged( const Telepathy::SimpleContactPresences& ) ) );
+
+        return;
+    }
+    
+    if ( found_presence_support )
+    {
+#ifdef ENABLE_DEBUG_OUTPUT_
+        qDebug( "PresenceManager::init(): Connection Manager provides the Interface \"Presence\". I will use this one!" );
+#endif
+        d->m_pPresenceInterface = new Telepathy::Client::ConnectionInterfacePresenceInterface( d->m_pConnectionInterface->service(),
+                                                                                               d->m_pConnectionInterface->path(),
+                                                                                               this );
+        Q_ASSERT( d->m_pPresenceInterface );
+        Q_ASSERT( d->m_pPresenceInterface->isValid() );
+
+        connect( d->m_pPresenceInterface, SIGNAL( PresenceUpdate(const Telepathy::ContactPresences& ) ),
+                 this, SLOT( slotPresencesUpdate( const Telepathy::ContactPresences& ) ) );
+
+        return;
+
+    }
+    
+    // Fall through: No valid presence interface was found..
+    d->m_isValid = false;
+    qWarning( "PresenceManager::init(): Connection Manager neither supports the Interface \"Presence\" nor the Interface \"SimplePresence\". Other interfaces are not supported!" );
+    return;
+}
+            
+
diff --git a/TelepathyQt4/Prototype/PresenceManager.h b/TelepathyQt4/Prototype/PresenceManager.h
new file mode 100644
index 0000000..1a9c8cd
--- /dev/null
+++ b/TelepathyQt4/Prototype/PresenceManager.h
@@ -0,0 +1,151 @@
+/*
+ * This file is part of TelepathyQt4
+ *
+ * Copyright (C) 2008 basysKom GmbH
+ * Copyright (C) 2008 Collabora Ltd. <http://www.collabora.co.uk/>
+ * Copyright (C) 2008 Nokia Corporation
+ *
+ * This library is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU Lesser General Public
+ * License as published by the Free Software Foundation; either
+ * version 2.1 of the License, or (at your option) any later version.
+ *
+ * This library is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
+ * Lesser General Public License for more details.
+ *
+ * You should have received a copy of the GNU Lesser General Public
+ * License along with this library; if not, write to the Free Software
+ * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA  02110-1301  USA
+ */
+#ifndef TelepathyQt4_Prototype_PresenceManager_H_
+#define TelepathyQt4_Prototype_PresenceManager_H_
+
+#include <QDBusObjectPath>
+#include <QObject>
+#include <QPointer>
+
+#include <TelepathyQt4/Types>
+
+namespace Telepathy
+{
+    namespace Client
+    {
+        class ConnectionInterface;
+    }
+}
+
+namespace TpPrototype {
+
+class PresenceManagerPrivate;
+class Connection;
+class Contact;
+class Account;
+
+/**
+ * @ingroup qt_connection
+ * This class manages presence information for one connection.
+ * Whenever a contact presence changes, the signal signalRemotePresencesUpdated() is emitted. This signal provides the related contact object
+ * obtained from the ContactManager.
+ * In order to keep the contacts updated, you just have to instantiate this class (by requesting the object with Connection::presenceManager())
+ * and initialize the list of contacts once (by calling presencesForContacts() ). After this point, the presence information of the contact
+ * is updated automatically if a change is signalled by the backend.<br>
+ * <br>
+ * <b>Info:</b> The deprecated interface "org.freedesktop.Telepathy.Channel.Interface.Presence" is used as fallback, if the interface
+ * "org.freedesktop.Telepathy.Channel.Interface.SimplePresence" is not supported by the connection manager. Thus, a wide range of
+ * connection managers should work with this class.
+
+ * @see Connection
+ */
+class PresenceManager : public QObject
+{
+    Q_OBJECT
+public:
+    /**
+     * Validity.
+     * Do not access any methods if the object is invalid!
+     */
+    bool isValid();
+
+    /**
+     * Supported statuses.
+     * Returns the list of supported status states. The list may change if the status of the connection changes from <i>disconnected</i> to <i>connected</i>. 
+     * @return The list of supported statuses.
+     * @see connection::status();
+     */
+     Telepathy::SimpleStatusSpecMap statuses();
+
+    /**
+    * Set Presence.
+    * Request that the presence status and status message are published for the connection.  Changes will be indicated by
+    * signal signalOwnPresenceUpdated().
+    * @param status The state to set the presence to as returned by statuses().
+    * @see signalOwnPresenceUpdated().;
+    */
+    bool setPresence( const QString& status, const QString& statusMessage );
+
+    /**
+     * Gets local presence.
+     * The local presence is returned for the connection.
+     * @return Returns my current local presence or an empty item on error.
+     */
+    Telepathy::SimplePresence currentPresence();
+
+    /**
+     * Request presences.
+     * Requests a list of presences for the given list of contacts.
+     * @param contacts List of contacts.
+     * @return List of presence information for contacts as <i>QMap<int,SimplePresence> </i>. The <i>int</i> represents the
+     * identifier of the contact as returned by Contact::identifier(), An empty list is returned on error.
+     * @todo Future: Use QList<Contact> instead QList<QPointer<Contact> > or introduce a class <i>ContactGroup</i> that handles all internally.
+     * @todo Future: Telepathy::SimpleContactPresences relies of an handle (the <i>int</i>). This should be encapsulated.
+     */
+    Telepathy::SimpleContactPresences presencesForContacts( const QList<QPointer<TpPrototype::Contact> >& contacts );
+
+    /**
+     * Returns the connection that belongs to this presence information.
+     * @return The connection object
+     */
+    TpPrototype::Connection* connection();
+
+signals:
+    /**
+     * Presences of remote contacts are changed.
+     * This signal is emitted when the presence state of a remote contact is changed.
+     * @param contact The contact that changes.
+     * @param presence The presence information.
+     */
+    void signalRemotePresencesUpdated( TpPrototype::Contact* contact, const Telepathy::SimplePresence& presence );
+
+    /**
+     * Local presence changed.
+     * This signal is emitted when the local presence state was changed.
+     * @param account The account that changes.
+     * @param presence The presence information.
+     */
+    void signalOwnPresenceUpdated( const TpPrototype::Account* account, const Telepathy::SimplePresence& presence );
+    
+protected:
+    /**
+     * Constructor. The presence manager cannot be instantiated directly. Use Connection::presenceManager() for it!
+     */
+    PresenceManager( TpPrototype::Connection* connection,
+                     Telepathy::Client::ConnectionInterface* interface,
+                     QObject* parent = NULL );
+    ~PresenceManager();
+
+protected slots:
+    void slotPresencesChanged( const Telepathy::SimpleContactPresences& presences );
+    void slotPresencesUpdate( const Telepathy::ContactPresences& presences );
+private:
+    void init();
+    
+    TpPrototype::PresenceManagerPrivate * const d;
+    friend class Connection;
+    friend class ConnectionPrivate;
+};
+}
+
+
+#endif
diff --git a/TelepathyQt4/Prototype/StreamedMediaChannel.cpp b/TelepathyQt4/Prototype/StreamedMediaChannel.cpp
new file mode 100644
index 0000000..a4724cb
--- /dev/null
+++ b/TelepathyQt4/Prototype/StreamedMediaChannel.cpp
@@ -0,0 +1,578 @@
+/*
+ * This file is part of TelepathyQt4
+ *
+ * Copyright (C) 2008 basysKom GmbH
+ * Copyright (C) 2008 Collabora Ltd. <http://www.collabora.co.uk/>
+ * Copyright (C) 2008 Nokia Corporation
+ *
+ * This library is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU Lesser General Public
+ * License as published by the Free Software Foundation; either
+ * version 2.1 of the License, or (at your option) any later version.
+ *
+ * This library is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
+ * Lesser General Public License for more details.
+ *
+ * You should have received a copy of the GNU Lesser General Public
+ * License along with this library; if not, write to the Free Software
+ * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA  02110-1301  USA
+ */
+
+#include "TelepathyQt4/Prototype/StreamedMediaChannel.h"
+
+#include <QDebug>
+#include <QMetaProperty>
+
+#include <TelepathyQt4/Constants>
+#include <TelepathyQt4/Client/Connection>
+#include <TelepathyQt4/Client/Channel>
+
+#include <TelepathyQt4/Prototype/Client/ChannelHandler>
+#include <TelepathyQt4/Prototype/ConnectionFacade.h>
+#include <TelepathyQt4/Prototype/Contact.h>
+#include <TelepathyQt4/Prototype/ContactManager.h>
+
+#define ENABLE_DEBUG_OUTPUT_
+
+using namespace TpPrototype;
+
+class TpPrototype::StreamedMediaChannelPrivate
+{
+public:
+    StreamedMediaChannelPrivate()
+    { init(); }
+    
+    QPointer<TpPrototype::Contact>                                 m_pContact;
+    QPointer<Telepathy::Client::ConnectionInterface>             m_pConnectionInterface;
+    Telepathy::Client::ChannelTypeStreamedMediaInterface*        m_pStreamedMediaInterface;
+    Telepathy::Client::ChannelInterfaceGroupInterface*           m_pGroupInterface;
+    Telepathy::Client::ChannelInterfaceMediaSignallingInterface* m_pMediaSignallingInterface;
+    Telepathy::Client::ChannelInterfaceCallStateInterface*       m_pCallStateInterface;
+    TpPrototype::Client::ChannelHandlerInterface*                  m_pStreamEngineHandlerInterface;
+    
+    bool m_isValid;
+
+    uint localHandle()
+    {
+        int self_handle = ConnectionFacade::instance()->selfHandleForConnectionInterface( m_pConnectionInterface );
+        Q_ASSERT( self_handle >= 0 );
+        return (uint) self_handle;
+    }
+    
+private:
+    void init()
+    {
+        m_pContact                      = NULL;
+        m_pConnectionInterface          = NULL;
+        m_pStreamedMediaInterface       = NULL;
+        m_pCallStateInterface           = NULL;
+        m_pMediaSignallingInterface     = NULL;
+        m_pStreamEngineHandlerInterface = NULL;
+        m_pGroupInterface               = NULL;
+        m_isValid                       = true;
+    }
+};
+
+StreamedMediaChannel::StreamedMediaChannel( Contact* contact, Telepathy::Client::ConnectionInterface* connectionInterface, QObject* parent ):
+        QObject( parent ),
+        d(new StreamedMediaChannelPrivate())
+{
+    Telepathy::registerTypes();
+
+    d->m_pContact = contact;
+    d->m_pConnectionInterface = connectionInterface;
+
+    //requestTextChannel( d->m_pContact->telepathyHandle() );
+}
+
+StreamedMediaChannel::~StreamedMediaChannel()
+        { delete d; }
+
+bool StreamedMediaChannel::isValid() const
+{ return d->m_isValid; }
+
+// This functions adds the local handle from the group of local pending members into the group of members.
+bool StreamedMediaChannel::acceptIncomingStream()
+{
+    QList<uint> accept_handles;
+    accept_handles << d->localHandle();
+
+    return addMembers( accept_handles );
+}
+
+bool StreamedMediaChannel::rejectIncomingStream()
+{
+    QList<uint> reject_handles;
+    reject_handles << d->localHandle();
+
+    return removeMembers( reject_handles );
+}
+
+bool StreamedMediaChannel::requestChannel( QList<Telepathy::MediaStreamType> types )
+{
+    Q_ASSERT( d->m_pConnectionInterface );
+    Q_ASSERT( d->m_pContact );
+    if ( !d->m_pConnectionInterface
+          || !d->m_pContact )
+    {
+        return false;
+    }
+
+    QDBusPendingReply<QDBusObjectPath> request_channel_reply = d->m_pConnectionInterface->RequestChannel( Telepathy::Client::ChannelTypeStreamedMediaInterface::staticInterfaceName(),
+            Telepathy::HandleTypeNone,
+            0,
+            true );
+    request_channel_reply.waitForFinished();
+
+    if ( !request_channel_reply.isValid() )
+    {
+        QDBusError error = request_channel_reply.error();
+
+        qWarning() << "RequestChannel: error type:" << error.type()
+                   << "error name:" << error.name()
+                   << "error message:" << error.message();
+
+        return false;
+    }
+
+
+    requestStreamedMediaChannel( d->m_pContact->telepathyHandle() );
+    
+    //Q_ASSERT( d->m_pStreamedMediaInterface );
+    if ( !d->m_pStreamedMediaInterface )
+    {
+        return false;
+    }
+
+    
+    QList<uint> stream_types;
+    foreach( uint type, types )
+    {
+        stream_types << type;
+    }
+
+    
+    QDBusPendingReply<Telepathy::MediaStreamInfoList> request_streams_reply = d->m_pStreamedMediaInterface->RequestStreams( d->m_pContact->telepathyHandle(),
+            stream_types );
+    request_streams_reply.waitForFinished();
+
+    if ( !request_streams_reply.isValid() )
+    {
+        QDBusError error = request_streams_reply.error();
+
+        qWarning() << "RequestStreams: error type:" << error.type()
+                << "error name:" << error.name()
+                << "error message:" << error.message();
+
+        return false;
+    }
+    
+    // Fall through..
+    return true;
+}
+
+bool StreamedMediaChannel::addContactsToGroup( QList<QPointer<TpPrototype::Contact> > contacts )
+{
+    QList<uint> handle_list;
+
+    foreach( TpPrototype::Contact* contact, contacts )
+    {
+        if ( !contact )
+        { continue; }
+        
+        handle_list.append( contact->telepathyHandle() );
+    }
+
+    return addMembers( handle_list );
+}
+
+QList<QPointer<TpPrototype::Contact> > StreamedMediaChannel::localPendingContacts()
+{
+    QList<QPointer<TpPrototype::Contact> > local_pending_members;
+#ifdef ENABLE_DEBUG_OUTPUT_
+    qDebug() << "Local Pending members : ";
+#endif
+    foreach( Telepathy::LocalPendingInfo local_pending_info, d->m_pGroupInterface->LocalPendingMembers() )
+    {
+#ifdef ENABLE_DEBUG_OUTPUT_
+        qDebug() << "To be added: " << local_pending_info.toBeAdded;
+        qDebug() << "Actor      : " << local_pending_info.actor;
+        qDebug() << "Reason     : " << local_pending_info.reason;
+        qDebug() << "Message    : " << local_pending_info.message;
+#endif
+        local_pending_members.append( d->m_pContact->contactManager()->contactForHandle( local_pending_info.toBeAdded ) );
+    }
+    return local_pending_members;  
+}
+
+QList<QPointer<TpPrototype::Contact> > StreamedMediaChannel::members()
+{
+    Telepathy::UIntList member_handles = d->m_pGroupInterface->Members();
+
+    QList<QPointer<TpPrototype::Contact> > member_list;
+
+    foreach( uint member_handle, member_handles )
+    {
+        member_list.append( d->m_pContact->contactManager()->contactForHandle( member_handle ) );
+    }
+    
+    return member_list;
+}
+
+
+// Protected functions
+
+// Called if a new media channel shall be established.
+void StreamedMediaChannel::requestStreamedMediaChannel( uint handle )
+{
+    // Ignore this call if the media channel is already available
+    if ( d->m_pStreamedMediaInterface )
+    {
+        delete d->m_pStreamedMediaInterface;
+        d->m_pStreamedMediaInterface = NULL;
+    }
+    
+    QDBusPendingReply<QDBusObjectPath> reply0 = d->m_pConnectionInterface->RequestChannel( "org.freedesktop.Telepathy.Channel.Type.StreamedMedia",
+                                                                                           Telepathy::HandleTypeContact,
+                                                                                           handle,
+                                                                                           true );
+    reply0.waitForFinished();
+    if (!reply0.isValid())
+    {
+        QDBusError error = reply0.error();
+        qWarning() << "RequestChannel (Type: StreamedMedia): error type:" << error.type()
+                                                                          << "error name:" << error.name()
+                                                                          << "error message:" << error.message();
+        d->m_isValid = false;
+        return;
+    }
+    QDBusObjectPath channel_path=reply0.value();
+    d->m_pStreamedMediaInterface = new Telepathy::Client::ChannelTypeStreamedMediaInterface( d->m_pConnectionInterface->service(), channel_path.path(), this );
+    connectSignals();
+}
+
+
+// Called if a new streamed media channel was notified by the connection
+void StreamedMediaChannel::openStreamedMediaChannel( uint handle, uint handleType, const QString& channelPath, const QString& channelType )
+{
+    Q_ASSERT( d->m_pConnectionInterface );
+    
+#ifdef ENABLE_DEBUG_OUTPUT_
+    qDebug() << "StreamedMediaChannel::openStreamedMediaChannel(): handle:" << handle
+             << "handleType:"    << handleType
+             << "channel path: " << channelPath
+             << "Channel Type:"  << channelType;
+#endif
+
+    QString channel_service_name = d->m_pConnectionInterface->service();
+
+    if ( !d->m_pStreamedMediaInterface )
+    {
+#ifdef ENABLE_DEBUG_OUTPUT_
+        qDebug() << "Create new ChannelTypeStreamedMediaInterface";
+#endif
+        d->m_pStreamedMediaInterface = new Telepathy::Client::ChannelTypeStreamedMediaInterface( channel_service_name, channelPath, this );
+        connectSignals();
+    }
+    if (!d->m_pStreamedMediaInterface->isValid())
+    {
+        qWarning() << "Failed to connect streamed media interface class to D-Bus object.";
+        delete d->m_pStreamedMediaInterface;
+        d->m_pStreamedMediaInterface = NULL;
+        d->m_isValid = false;
+        return;
+    }
+    else
+    {
+        // Obtain the group and callstate interfaces.
+        QString streamed_media_service_name = d->m_pStreamedMediaInterface->service();
+
+        // I don't know why, but I have to reinitialize the group channel every time..
+        if ( d->m_pGroupInterface )
+        {
+            delete d->m_pGroupInterface;
+            d->m_pGroupInterface = NULL;
+        }
+    
+        if ( !d->m_pGroupInterface )
+        {
+#ifdef ENABLE_DEBUG_OUTPUT_
+            qDebug() << "Initialize ChannelInterfaceGroupInterface..";
+#endif
+            d->m_pGroupInterface = new Telepathy::Client::ChannelInterfaceGroupInterface( streamed_media_service_name,
+                                                                                          channelPath );
+
+            connect( d->m_pGroupInterface, SIGNAL( MembersChanged(const QString& ,
+                                                                  const Telepathy::UIntList& ,
+                                                                  const Telepathy::UIntList& ,
+                                                                  const Telepathy::UIntList& ,
+                                                                  const Telepathy::UIntList& ,
+                                                                  uint ,
+                                                                  uint )
+                                                 ),
+                     this, SLOT( slotMembersChanged(const QString& ,
+                                 const Telepathy::UIntList& ,
+                                 const Telepathy::UIntList& ,
+                                 const Telepathy::UIntList& ,
+                                 const Telepathy::UIntList& ,
+                                 uint ,
+                                 uint )
+                               )
+                   );                       
+                                                                          
+
+        }
+        
+        if ( !d->m_pCallStateInterface )
+        {
+#ifdef ENABLE_DEBUG_OUTPUT_
+            qDebug() << "Initialize ChannelInterfaceCallStateInterface..";
+#endif
+            d->m_pCallStateInterface = new Telepathy::Client::ChannelInterfaceCallStateInterface( streamed_media_service_name,
+                                                                                                  channelPath );
+        }
+
+        if ( !d->m_pMediaSignallingInterface )
+        {
+#ifdef ENABLE_DEBUG_OUTPUT_
+            qDebug() << "Initialize ChannelInterfaceMediaSignallingInterface..";
+#endif
+            d->m_pMediaSignallingInterface = new Telepathy::Client::ChannelInterfaceMediaSignallingInterface( streamed_media_service_name, channelPath );
+        }
+        
+        if ( !d->m_pStreamEngineHandlerInterface )
+        {
+#ifdef ENABLE_DEBUG_OUTPUT_
+            qDebug() << "Initialize ChannelHandlerInterface..";
+#endif
+            d->m_pStreamEngineHandlerInterface = new TpPrototype::Client::ChannelHandlerInterface( "org.freedesktop.Telepathy.StreamEngine",
+                                                                                                 "/org/freedesktop/Telepathy/StreamEngine",
+                                                                                                 this );
+        }
+
+        Q_ASSERT( d->m_pCallStateInterface->isValid() );
+        // Q_ASSERT( d->m_pGroupInterface->isValid() );
+        Q_ASSERT( d->m_pMediaSignallingInterface->isValid() );
+        Q_ASSERT( d->m_pStreamEngineHandlerInterface->isValid() );
+
+        // Cleanup if we were unable to establish interfaces..
+        if ( d->m_pGroupInterface && !d->m_pGroupInterface->isValid() )
+        {
+            qWarning() << "Could not establish interface:" << Telepathy::Client::ChannelInterfaceGroupInterface::staticInterfaceName();
+            delete d->m_pGroupInterface;
+            d->m_pGroupInterface = NULL;
+        }
+
+        if ( d->m_pCallStateInterface && !d->m_pCallStateInterface->isValid() )
+        {
+            qWarning() << "Could not establish interface:" << Telepathy::Client::ChannelInterfaceCallStateInterface::staticInterfaceName();
+            delete d->m_pCallStateInterface;
+            d->m_pCallStateInterface = NULL;
+        }
+
+        if ( d->m_pMediaSignallingInterface && !d->m_pMediaSignallingInterface->isValid() )
+        {
+            qWarning() << "Could not establish interface:" << Telepathy::Client::ChannelInterfaceMediaSignallingInterface::staticInterfaceName();
+            delete d->m_pMediaSignallingInterface;
+            d->m_pMediaSignallingInterface = NULL;
+        }
+
+        // Now use the streaming engine to handle this media channel
+        if ( d->m_pStreamEngineHandlerInterface && !d->m_pStreamEngineHandlerInterface->isValid() )
+        {
+            qWarning() << "Could not establish interface:" << TpPrototype::Client::ChannelHandlerInterface::staticInterfaceName();
+            delete d->m_pStreamEngineHandlerInterface;
+            d->m_pStreamEngineHandlerInterface = NULL;
+
+            // This is fatal, cause we need this interface
+            d->m_isValid = false;
+            qWarning() << "The interface:" << TpPrototype::Client::ChannelHandlerInterface::staticInterfaceName() << "is required! We will be unable to handle this call!";
+        }
+        else
+        {
+#ifdef ENABLE_DEBUG_OUTPUT_
+            qDebug() << "Now delegate stream to stream-engine by calling HandleChannel()";
+#endif
+            QDBusPendingReply<> handle_channel_reply = d->m_pStreamEngineHandlerInterface->HandleChannel( d->m_pConnectionInterface->service(),
+                                                                                                          QDBusObjectPath( d->m_pConnectionInterface->path() ),
+                                                                                                          channelType,
+                                                                                                          QDBusObjectPath( channelPath ),
+                                                                                                          handleType,
+                                                                                                          handle );
+
+            handle_channel_reply.waitForFinished();
+
+            if ( !handle_channel_reply.isValid() )
+            {
+                QDBusError error = handle_channel_reply.error();
+
+                qWarning() << "HandleChannel: error type:" << error.type()
+                           << "error name:" << error.name()
+                           << "error message:" << error.message();
+
+                d->m_isValid = false;
+                return ;
+            }
+        }
+        
+    }
+
+#ifdef ENABLE_DEBUG_OUTPUT_
+    qDebug() << "Telling the world about new channel (signalIncomingChannel())";
+#endif
+    emit signalIncomingChannel( d->m_pContact );
+
+}
+
+void StreamedMediaChannel::connectSignals()
+{
+    connect( d->m_pStreamedMediaInterface, SIGNAL( StreamAdded(uint , uint , uint ) ),
+             this, SLOT( slotStreamAdded(uint , uint , uint ) ) ); 
+    connect( d->m_pStreamedMediaInterface, SIGNAL( StreamDirectionChanged(uint , uint , uint ) ),
+             this, SLOT( slotStreamDirectionChanged(uint , uint , uint ) ) );
+    connect( d->m_pStreamedMediaInterface, SIGNAL( StreamError(uint , uint , const QString& ) ),
+             this, SLOT( slotStreamError(uint , uint , const QString& ) ) );
+    connect( d->m_pStreamedMediaInterface, SIGNAL( StreamRemoved(uint) ),
+             this, SLOT( slotStreamRemoved(uint) ) );
+    connect( d->m_pStreamedMediaInterface, SIGNAL( StreamStateChanged(uint , uint ) ),
+             this, SLOT( slotStreamStateChanged(uint , uint ) ) );
+}
+
+bool StreamedMediaChannel::addMembers( QList<uint> handles )
+{
+    if ( !d->m_pGroupInterface )
+    {
+        qWarning() << "StreamedMediaChannel::addMembers: No group channel found. Ignore call ..";
+        return false;
+    }
+
+    QDBusPendingReply<> add_members_reply = d->m_pGroupInterface->AddMembers( handles, "Welcome!" );
+    add_members_reply.waitForFinished();
+
+    if ( !add_members_reply.isValid() )
+    {
+        QDBusError error = add_members_reply.error();
+
+        qWarning() << "AddMembers: error type:" << error.type()
+                   << "error name:" << error.name()
+                   << "error message:" << error.message();
+
+        return false;
+    }
+    return true;
+}
+
+bool StreamedMediaChannel::removeMembers( QList<uint> handles )
+{
+    if ( !d->m_pGroupInterface )
+    {
+        qWarning() << "StreamedMediaChannel::removeMembers: No group channel found. Ignore call ..";
+        return false;
+    }
+
+    QDBusPendingReply<> remove_members_reply = d->m_pGroupInterface->RemoveMembers( handles, "Bye-bye!!" );
+    remove_members_reply.waitForFinished();
+
+    if ( !remove_members_reply.isValid() )
+    {
+        QDBusError error = remove_members_reply.error();
+
+        qWarning() << "RemoveMembers: error type:" << error.type()
+                   << "error name:" << error.name()
+                   << "error message:" << error.message();
+
+        return false;
+    }
+    return true;
+}
+
+
+void StreamedMediaChannel::slotStreamAdded(uint streamID, uint contactHandle, uint streamType)
+{
+#ifdef ENABLE_DEBUG_OUTPUT_
+    qDebug() << __PRETTY_FUNCTION__ << "streamID:" << streamID << "contactHandle: " << contactHandle << "streamType:" << streamType;
+#endif
+    emit signalStreamAdded( d->m_pContact->contactManager()->contactForHandle( contactHandle ), streamID, static_cast<Telepathy::MediaStreamType>(streamType) );
+}
+
+void StreamedMediaChannel::slotStreamDirectionChanged(uint streamID, uint streamDirection, uint pendingFlags)
+{
+#ifdef ENABLE_DEBUG_OUTPUT_
+    qDebug() << __PRETTY_FUNCTION__ << "streamID:" << streamID << "streamDirection: " << streamDirection << "pendingFlags:" << pendingFlags;
+#endif
+}
+
+void StreamedMediaChannel::slotStreamError(uint streamID, uint errorCode, const QString& message)
+{
+#ifdef ENABLE_DEBUG_OUTPUT_
+    qDebug() << __PRETTY_FUNCTION__ << "streamID:" << streamID << "errorCode: " << errorCode << "message:" << message;
+#endif
+}
+
+void StreamedMediaChannel::slotStreamRemoved(uint streamID)
+{
+#ifdef ENABLE_DEBUG_OUTPUT_
+    qDebug() << __PRETTY_FUNCTION__ << "streamID:" << streamID;
+#endif
+    emit signalStreamRemoved( streamID );
+}
+
+void StreamedMediaChannel::slotStreamStateChanged(uint streamID, uint streamState)
+{
+#ifdef ENABLE_DEBUG_OUTPUT_
+    qDebug() << __PRETTY_FUNCTION__ << "streamID:" << streamID << "streamState: " << streamState;
+#endif
+}
+
+void StreamedMediaChannel::slotMembersChanged( const QString& message,
+                                               const Telepathy::UIntList& added,
+                                               const Telepathy::UIntList& removed,
+                                               const Telepathy::UIntList& localPending,
+                                               const Telepathy::UIntList& remotePending,
+                                               uint actor,
+                                               uint reason )
+{
+#ifdef ENABLE_DEBUG_OUTPUT_
+    qDebug() << __PRETTY_FUNCTION__
+             << "message:" << message
+             << "added:" << added
+             << "removed:" << removed
+             << "localPending:" << localPending
+             << "remotePending:" << remotePending
+             << "actor:" << actor
+             << "reason:" << reason;
+#endif
+    uint local_handle = d->localHandle();
+#ifdef ENABLE_DEBUG_OUTPUT_
+    qDebug() << "local handle: " << local_handle;
+#endif    
+    if ( !added.isEmpty() )
+    {
+        foreach ( uint handle, added )
+        {
+            if ( handle == local_handle )
+            { continue; }
+            emit signalContactAdded( d->m_pContact->contactManager()->contactForHandle( handle ) );
+#ifdef ENABLE_DEBUG_OUTPUT_
+            qDebug() << "signalContactAdded: " << handle;
+#endif
+        }
+    }
+
+    if ( !removed.isEmpty() )
+    {
+        foreach ( uint handle, removed )
+        {
+            if ( handle == local_handle )
+            { continue; }
+            emit signalContactRemoved( d->m_pContact->contactManager()->contactForHandle( handle ) );
+#ifdef ENABLE_DEBUG_OUTPUT_
+            qDebug() << "signalContactRemoved: " << handle;
+#endif
+        }
+    }
+}
+
+
diff --git a/TelepathyQt4/Prototype/StreamedMediaChannel.h b/TelepathyQt4/Prototype/StreamedMediaChannel.h
new file mode 100644
index 0000000..daf68f3
--- /dev/null
+++ b/TelepathyQt4/Prototype/StreamedMediaChannel.h
@@ -0,0 +1,229 @@
+/*
+ * This file is part of TelepathyQt4
+ *
+ * Copyright (C) 2008 basysKom GmbH
+ * Copyright (C) 2008 Collabora Ltd. <http://www.collabora.co.uk/>
+ * Copyright (C) 2008 Nokia Corporation
+ *
+ * This library is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU Lesser General Public
+ * License as published by the Free Software Foundation; either
+ * version 2.1 of the License, or (at your option) any later version.
+ *
+ * This library is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
+ * Lesser General Public License for more details.
+ *
+ * You should have received a copy of the GNU Lesser General Public
+ * License along with this library; if not, write to the Free Software
+ * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA  02110-1301  USA
+ */
+
+#ifndef TelepathyQt4_Prototype_StreamedMediaChannel_H_
+#define TelepathyQt4_Prototype_StreamedMediaChannel_H_
+
+#include <TelepathyQt4/Client/Connection>
+#include <TelepathyQt4/Client/Channel>
+
+#include <QObject>
+#include <QVariantMap>
+#include <QPointer>
+
+#ifdef DEPRECATED_ENABLED__
+#define ATTRIBUTE_DEPRECATED __attribute__((deprecated))
+#else
+#define ATTRIBUTE_DEPRECATED
+#endif
+
+
+namespace TpPrototype {
+
+class StreamedMediaChannelPrivate;
+class Contact;
+class Account;
+
+/**
+ * @ingroup qt_connection
+ * StreamedMedia Channel for VoIP and Video Over IP.
+ * <b>Hint:</b> You have to set the right capabilities with CapabilitiesManager::setCapabilities() before VoIP or Video over IP will work!
+ * @see CapabiltiesManager
+ */
+class StreamedMediaChannel : public QObject
+{
+    Q_OBJECT
+public:
+    /**
+     * Validity check.
+     * Do not access any functions if this account is invalid.
+     */
+    bool isValid() const;
+    
+    /**
+     * Destructor.
+     * Deleting this object forces to drop all channels.
+     */
+    ~StreamedMediaChannel();
+
+    /**
+     * Accept the incoming media stream (call).
+     * This function must be called to accept the incoming media stream.
+     * @return Returns true if command was successful.
+     */
+    bool acceptIncomingStream();
+
+    /**
+     * Reject the incoming media stream (call).
+     * This function should be called if an incoming call should be rejected.
+     * @return Returns true if command was successful.
+     */
+    bool rejectIncomingStream();
+
+    /**
+     * Request outgoing media channel (call).
+     * Ask remote contact to start a media channel.
+     * @todo Describe what happens after this call ..
+     * @param types The stream types that should be opened for this channel
+     * @return Returns true if request call was successful.
+     */
+    bool requestChannel( QList<Telepathy::MediaStreamType> types );
+
+    /**
+     * Add contacts to the group.
+     * Multiple contacts may sharing the same stream. Use this function to invite a contact to this group. The contact will
+     * be added to the group after he accepted the invitation.
+     * @return Returns true if command was successful.
+     */
+    bool addContactsToGroup( QList<QPointer<TpPrototype::Contact> > contacts );
+
+    /**
+     * Returns a list of contacts that are waiting locally for accaptance.
+     * A Contact that is local pending has requested membership of the channel, but the local user of the framework must
+     * accept their request before they may join.
+     * @return Returns the list of contacts that are waiting for acceptance.
+     */
+    QList<QPointer<TpPrototype::Contact> > localPendingContacts();
+
+    /**
+     * Returns the list of members in the group.
+     * The StreamedMediaChannel contains a group of members that currently part of the group.
+     * @return Returns the list of contacts that are currently group members.
+     */
+    QList<QPointer<TpPrototype::Contact> > members();
+
+signals:
+    /**
+     * Incoming channel detected.
+     * This signal is emitted when a valid incoming channel was detected and all needed interfaces were established successfully.
+     * Usually it does not make sense to connect to this signal, because this object might be created or removed without any prior notification. Thus,
+     * there is no chance to connect before this signal is emitted.<br>
+     * Use ContactManager::signalStreamedMediaChannelOpenedForContact() instead to get informed about new channels!
+     * @param contact The contact that contains this StreamedMediaChannel object.
+     * @see ContactManager
+     */
+    void signalIncomingChannel( TpPrototype::Contact* contact );
+
+    /**
+     * A stream was added.
+     * If a new stream was added to this media channel.
+     * @param contact The contact that belongs to this media channel
+     * @param streamId The id of the stream.
+     * @param streamType The type of the stream.
+     */
+    void signalStreamAdded( TpPrototype::Contact* contact, uint streamId, Telepathy::MediaStreamType streamType );
+    
+    /**
+     * Stream was removed.
+     * This signal is emmitted when a media stream was removed. This may happen on network errors, if the remote contact
+     * rejected the call or if the established connection was closed.
+     * @param streamId The id of the stream.
+     */
+    void signalStreamRemoved( uint streamId );
+
+    /**
+     * A remove contact was added.
+     * This signal has different meaning with regard to the context:
+     * <ul><li>Outgoing call: The remote contact accapted the call</li>
+     *     <li><i>Please add further situations</i></li>
+     * </ul>
+     */
+    void signalContactAdded( TpPrototype::Contact* acceptingContact );
+
+    /**
+     * Call was canceled by remote contact.
+     * This signal has different meaning with regard to the context:
+     * <ul><li>Ongoing chat: The remote contact disconnected</li>
+     *     <li><i>Please add further situations</i></li>
+     * </ul>
+     */
+    void signalContactRemoved( TpPrototype::Contact* rejectingContact );
+protected:
+    /**
+     * Constructor.
+     * Use Contact::streamedMediaChannel() to obtain an object of StreamedMediaChannel.
+     */
+    StreamedMediaChannel( Contact* contact, Telepathy::Client::ConnectionInterface* connectionInterface , QObject* parent = NULL );
+
+    /**
+     * Request a new streamed media channel.
+     * This functions needs to be called if a new streamed media channel D-BUS object should be established.
+     */
+    void requestStreamedMediaChannel( uint handle );
+    
+    /**
+     * Called internally to notify that a new media channel object was stablished on D-BUS.
+     */
+    void openStreamedMediaChannel( uint handle, uint handleType, const QString& channelPath, const QString& channelType );
+
+    /** Connect slots to channel signals */
+    void connectSignals();
+
+    bool addMembers( QList<uint> handles );
+    
+    bool removeMembers( QList<uint> handles );
+
+protected slots:
+    /**
+     *  Represents the signal "slotStreamAdded" on the remote object.
+     */
+    void slotStreamAdded(uint streamID, uint contactHandle, uint streamType);
+
+    /**
+     * Represents the signal "StreamDirectionChanged" on the remote object.
+     */
+    void slotStreamDirectionChanged(uint streamID, uint streamDirection, uint pendingFlags);
+
+    /**
+     * Represents the signal "StreamError" on the remote object.
+     */
+    void slotStreamError(uint streamID, uint errorCode, const QString& message);
+
+    /**
+     * Represents the signal "StreamRemoved" on the remote object.
+     */
+    void slotStreamRemoved(uint streamID);
+
+    /**
+     * Represents the signal "StreamStateChanged" on the remote object.
+     */
+    void slotStreamStateChanged(uint streamID, uint streamState);
+
+    /**
+     * Represents the signal "MembersChanged" on the remote object.
+     */
+    void slotMembersChanged(const QString& message,
+                            const Telepathy::UIntList& added,
+                            const Telepathy::UIntList& removed,
+                            const Telepathy::UIntList& localPending,
+                            const Telepathy::UIntList& remotePending,
+                            uint actor,
+                            uint reason);
+private:
+    StreamedMediaChannelPrivate * const d;
+    friend class ContactManager;
+    friend class Contact;
+};
+
+} // namespace
+
+#endif // Header guard
diff --git a/TelepathyQt4/Prototype/TpQt4Prototype.pc.in b/TelepathyQt4/Prototype/TpQt4Prototype.pc.in
new file mode 100644
index 0000000..e62070d
--- /dev/null
+++ b/TelepathyQt4/Prototype/TpQt4Prototype.pc.in
@@ -0,0 +1,11 @@
+prefix=@prefix@
+exec_prefix=@exec_prefix@
+libdir=@libdir@
+includedir=@includedir@
+
+Name: TpQt4Prototype
+Description: Transitional Qt4 utility library for the Telepathy framework
+Version: @VERSION@
+Requires.private: QtCore >= 4.5, QtDBus >= 4.5, TelepathyQt4 >= @VERSION@
+Libs: -L${libdir} -ltpqt4-prototype
+Cflags: -I${includedir}/tpqt4-prototype
diff --git a/TelepathyQt4/Prototype/Types b/TelepathyQt4/Prototype/Types
new file mode 100644
index 0000000..59ee649
--- /dev/null
+++ b/TelepathyQt4/Prototype/Types
@@ -0,0 +1,6 @@
+#ifndef _TelepathyQt4_Prototype_Types_HEADER_GUARD_
+#define _TelepathyQt4_Prototype_Types_HEADER_GUARD_
+
+#include <TelepathyQt4/Prototype/types.h>
+
+#endif
diff --git a/TelepathyQt4/Prototype/all.xml b/TelepathyQt4/Prototype/all.xml
new file mode 100644
index 0000000..011e479
--- /dev/null
+++ b/TelepathyQt4/Prototype/all.xml
@@ -0,0 +1,9 @@
+<tp:spec
+  xmlns:tp="http://telepathy.freedesktop.org/wiki/DbusSpec#extensions-v0"
+  xmlns:xi="http://www.w3.org/2001/XInclude">
+
+  <tp:title>Prototype/transitional spec extensions</tp:title>
+
+<xi:include href="channel-handler.xml"/>
+
+</tp:spec>
diff --git a/TelepathyQt4/Prototype/channel-handler.xml b/TelepathyQt4/Prototype/channel-handler.xml
new file mode 100644
index 0000000..71c9c7e
--- /dev/null
+++ b/TelepathyQt4/Prototype/channel-handler.xml
@@ -0,0 +1,9 @@
+<tp:spec
+  xmlns:tp="http://telepathy.freedesktop.org/wiki/DbusSpec#extensions-v0"
+  xmlns:xi="http://www.w3.org/2001/XInclude">
+
+<tp:title>Old ChannelHandler interface</tp:title>
+
+<xi:include href="../../spec/Channel_Handler.xml"/>
+
+</tp:spec>
diff --git a/TelepathyQt4/Prototype/constants.h b/TelepathyQt4/Prototype/constants.h
new file mode 100644
index 0000000..79fd647
--- /dev/null
+++ b/TelepathyQt4/Prototype/constants.h
@@ -0,0 +1,27 @@
+/*
+ * This file is part of TelepathyQt4
+ *
+ * Copyright (C) 2008 Collabora Ltd. <http://www.collabora.co.uk/>
+ * Copyright (C) 2008 Nokia Corporation
+ *
+ * This library is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU Lesser General Public
+ * License as published by the Free Software Foundation; either
+ * version 2.1 of the License, or (at your option) any later version.
+ *
+ * This library is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
+ * Lesser General Public License for more details.
+ *
+ * You should have received a copy of the GNU Lesser General Public
+ * License along with this library; if not, write to the Free Software
+ * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA  02110-1301  USA
+ */
+
+#ifndef _TelepathyQt4_Prototype_constants_h_HEADER_GUARD_
+#define _TelepathyQt4_Prototype_constants_h_HEADER_GUARD_
+
+#include <TelepathyQt4/Prototype/_gen/constants.h>
+
+#endif
diff --git a/TelepathyQt4/Prototype/types.cpp b/TelepathyQt4/Prototype/types.cpp
new file mode 100644
index 0000000..12aeb7c
--- /dev/null
+++ b/TelepathyQt4/Prototype/types.cpp
@@ -0,0 +1,22 @@
+/*
+ * This file is part of TelepathyQt4
+ *
+ * Copyright (C) 2008 Collabora Ltd. <http://www.collabora.co.uk/>
+ * Copyright (C) 2008 Nokia Corporation
+ *
+ * This library is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU Lesser General Public
+ * License as published by the Free Software Foundation; either
+ * version 2.1 of the License, or (at your option) any later version.
+ *
+ * This library is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
+ * Lesser General Public License for more details.
+ *
+ * You should have received a copy of the GNU Lesser General Public
+ * License along with this library; if not, write to the Free Software
+ * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA  02110-1301  USA
+ */
+
+#include "_gen/types-body.hpp"
diff --git a/TelepathyQt4/Prototype/types.h b/TelepathyQt4/Prototype/types.h
new file mode 100644
index 0000000..d94e621
--- /dev/null
+++ b/TelepathyQt4/Prototype/types.h
@@ -0,0 +1,27 @@
+/*
+ * This file is part of TelepathyQt4
+ *
+ * Copyright (C) 2008 Collabora Ltd. <http://www.collabora.co.uk/>
+ * Copyright (C) 2008 Nokia Corporation
+ *
+ * This library is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU Lesser General Public
+ * License as published by the Free Software Foundation; either
+ * version 2.1 of the License, or (at your option) any later version.
+ *
+ * This library is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
+ * Lesser General Public License for more details.
+ *
+ * You should have received a copy of the GNU Lesser General Public
+ * License along with this library; if not, write to the Free Software
+ * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA  02110-1301  USA
+ */
+
+#ifndef _TelepathyQt4_Prototype_types_h_HEADER_GUARD_
+#define _TelepathyQt4_Prototype_types_h_HEADER_GUARD_
+
+#include <TelepathyQt4/Prototype/_gen/types.h>
+
+#endif
diff --git a/configure.ac b/configure.ac
index 92f283b..c29af6e 100644
--- a/configure.ac
+++ b/configure.ac
@@ -159,6 +159,8 @@ AC_OUTPUT( Makefile \
 	   spec/Makefile \
 	   TelepathyQt4/Makefile \
 	   TelepathyQt4/TelepathyQt4.pc \
+	   TelepathyQt4/Prototype/Makefile \
+	   TelepathyQt4/Prototype/TpQt4Prototype.pc \
 	   tools/Makefile \
 	   m4/Makefile \
 	   examples/Makefile \
-- 
1.5.6.5



More information about the Telepathy-commits mailing list