/**************************************************************
 * 
 * Licensed to the Apache Software Foundation (ASF) under one
 * or more contributor license agreements.  See the NOTICE file
 * distributed with this work for additional information
 * regarding copyright ownership.  The ASF licenses this file
 * to you under the Apache License, Version 2.0 (the
 * "License"); you may not use this file except in compliance
 * with the License.  You may obtain a copy of the License at
 * 
 *   http://www.apache.org/licenses/LICENSE-2.0
 * 
 * Unless required by applicable law or agreed to in writing,
 * software distributed under the License is distributed on an
 * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
 * KIND, either express or implied.  See the License for the
 * specific language governing permissions and limitations
 * under the License.
 * 
 *************************************************************/



// MARKER(update_precomp.py): autogen include statement, do not remove
#include "precompiled_sd.hxx"

#include "TaskPaneShellManager.hxx"

#include "ViewShellManager.hxx"
#include <tools/diagnose_ex.h>
#include <vcl/window.hxx>

#include <algorithm>

namespace sd { namespace toolpanel {

TaskPaneShellManager::TaskPaneShellManager (
    const ::boost::shared_ptr<ViewShellManager>& rpViewShellManager,
    const ViewShell& rViewShell)
    : mpViewShellManager(rpViewShellManager),
      mrViewShell(rViewShell),
      maSubShells()
{
}




TaskPaneShellManager::~TaskPaneShellManager (void)
{
    while ( ! maSubShells.empty())
        RemoveSubShell(maSubShells.begin()->second.mpShell);
}




SfxShell* TaskPaneShellManager::CreateShell( ShellId nId, ::Window* , FrameView* )
{
    SubShells::const_iterator iShell (maSubShells.find(nId));
    if (iShell != maSubShells.end())
        return iShell->second.mpShell;
    else
        return NULL;
}




void TaskPaneShellManager::ReleaseShell (SfxShell* )
{
    // Nothing to do.
}

void TaskPaneShellManager::AddSubShell (
    ShellId nId,
    SfxShell* pShell,
    ::Window* pWindow)
{
    if (pShell != NULL)
    {
        maSubShells[nId] = ShellDescriptor(pShell,pWindow);
        if (pWindow != NULL)
        {
            pWindow->AddEventListener(LINK(this,TaskPaneShellManager,WindowCallback));
            if (pWindow->IsReallyVisible())
                mpViewShellManager->ActivateSubShell(mrViewShell, nId);
        }
        else
            mpViewShellManager->ActivateSubShell(mrViewShell, nId);
    }
}




void TaskPaneShellManager::RemoveSubShell (const ShellId i_nShellId)
{
    SubShells::iterator pos = maSubShells.find( i_nShellId );
    ENSURE_OR_RETURN_VOID( pos != maSubShells.end(), "no shell for this ID" );
    if ( pos->second.mpWindow != NULL )
    {
        pos->second.mpWindow->RemoveEventListener( LINK( this, TaskPaneShellManager, WindowCallback ) );
    }
    mpViewShellManager->DeactivateSubShell( mrViewShell, pos->first );
    maSubShells.erase( pos );
}




void TaskPaneShellManager::RemoveSubShell (const SfxShell* pShell)
{
    if (pShell != NULL)
    {
        SubShells::iterator iShell;
        for (iShell=maSubShells.begin(); iShell!=maSubShells.end(); ++iShell)
            if (iShell->second.mpShell == pShell)
            {
                if (iShell->second.mpWindow != NULL)
                    iShell->second.mpWindow->RemoveEventListener(
                        LINK(this,TaskPaneShellManager,WindowCallback));
                mpViewShellManager->DeactivateSubShell(mrViewShell,iShell->first);
                maSubShells.erase(iShell);
                break;
            }
    }
}




void TaskPaneShellManager::MoveToTop (SfxShell* pShell)
{
    SubShells::const_iterator iShell;
    for (iShell=maSubShells.begin(); iShell!=maSubShells.end(); ++iShell)
        if (iShell->second.mpShell == pShell)
        {
            ViewShellManager::UpdateLock aLocker (mpViewShellManager);
            mpViewShellManager->MoveSubShellToTop(mrViewShell,iShell->first);
            mpViewShellManager->MoveToTop(mrViewShell);
            break;
        }
}




IMPL_LINK(TaskPaneShellManager, WindowCallback, VclWindowEvent*, pEvent)
{
    if (pEvent != NULL)
    {
        SubShells::const_iterator iShell;
        ::Window* pWindow = pEvent->GetWindow();
        for (iShell=maSubShells.begin(); iShell!=maSubShells.end(); ++iShell)
            if (iShell->second.mpWindow == pWindow)
                break;
        if (iShell != maSubShells.end())
            switch (pEvent->GetId())
            {
                case VCLEVENT_WINDOW_SHOW:
                    mpViewShellManager->ActivateSubShell(mrViewShell,iShell->first);
                    break;

                case VCLEVENT_WINDOW_HIDE:
                    // Do not activate the sub shell.  This leads to
                    // problems with shapes currently being in text edit
                    // mode: Deactivating the shell leads to leaving the
                    // text editing mode.
                    // mpViewShellManager->DeactivateSubShell(mrViewShell,iShell->first);
                    break;
            }
    }

    return 0;
}


} } // end of namespace ::sd::toolpanel
