void CMountedGunController::OnEnter(EntityId mountedGunId)
{
    CRY_ASSERT_MESSAGE(m_pControlledPlayer, "Controlled player not initialized");

    ICharacterInstance* pCharacter = m_pControlledPlayer->IsThirdPerson() ? m_pControlledPlayer->GetEntity()->GetCharacter(0) : m_pControlledPlayer->GetShadowCharacter();
    if (pCharacter)
        {
            CItem* pWeapon = static_cast<CItem*>(g_pGame->GetIGameFramework()->GetIItemSystem()->GetItem(mountedGunId));
            assert(pWeapon);

            IActionController* pActionController = m_pControlledPlayer->GetAnimatedCharacter()->GetActionController();
            if (pActionController && m_pMannequinParams)
                {
                    SAFE_RELEASE(m_pMovementAction);

                    m_pMovementAction = new TPlayerAction(PP_PlayerAction, m_pMannequinParams->fragmentIDs.MotionMounted);
                    m_pMovementAction->AddRef();
                    pActionController->Queue(m_pMovementAction);
                }

            //////////////////////////////////////////////////////////////////////////
            // NOTE: This should go through mannequin
            CRecordingSystem* pRecordingSystem = g_pGame->GetRecordingSystem();
            if (pRecordingSystem)
                {
                    const SParams& pWeaponParams = pWeapon->GetParams();

                    IAnimationSet* pAnimationSet = pCharacter->GetIAnimationSet();
                    const int upAnimId = pAnimationSet->GetAnimIDByName(pWeaponParams.mountedTPAimAnims[MountedTPAimAnim::Up].c_str());
                    const int downAnimId = pAnimationSet->GetAnimIDByName(pWeaponParams.mountedTPAimAnims[MountedTPAimAnim::Down].c_str());

                    pRecordingSystem->OnMountedGunEnter(m_pControlledPlayer, upAnimId, downAnimId);
                }

            //////////////////////////////////////////////////////////////////////////

            IAnimatedCharacter* pAnimatedCharacter = m_pControlledPlayer->GetAnimatedCharacter();
            CRY_ASSERT(pAnimatedCharacter);

            pAnimatedCharacter->RequestPhysicalColliderMode(eColliderMode_Disabled, eColliderModeLayer_Game, "CMountedGunController::OnEnter");
            pAnimatedCharacter->SetNoMovementOverride(true);

            if (gEnv->bMultiplayer)
                pAnimatedCharacter->EnableRigidCollider(0.5f);
            else if (m_pControlledPlayer->IsPlayer())
                pAnimatedCharacter->EnableRigidCollider(1.5f);

            pAnimatedCharacter->GetGroundAlignmentParams().SetFlag(eGA_AllowWithNoCollision, true);

            BATTLECHATTER(BC_WatchMyBack, m_pControlledPlayer->GetEntityId());
        }
}
void CAnimationProxyDualCharacterBase::Generate1P3PPairFile()
{
    const int MAX_MODELS = 128;
    ICharacterModel *pCharacterModels[MAX_MODELS];
    int numModels;
    gEnv->pCharacterManager->GetLoadedModels(NULL, numModels);
    numModels = min(numModels, MAX_MODELS);

    gEnv->pCharacterManager->GetLoadedModels(pCharacterModels, numModels);

    s_animCrCHashMap.clear();

    for (uint32 i=0; i<numModels; ++i)
        {
            if (pCharacterModels[i]->GetNumInstances() > 0)
                {
                    IAnimationSet *animSet = pCharacterModels[i]->GetICharInstanceFromModel(0)->GetIAnimationSet();
                    uint32 numAnims = animSet->GetAnimationCount();

                    for (uint32 anm = 0; anm < numAnims; anm++)
                        {
                            uint32 animCRC = animSet->GetCRCByAnimID(anm);
                            if (s_animCrCHashMap.find(animCRC) == s_animCrCHashMap.end())
                                {
                                    int animID3P = -1;
                                    const char *name = animSet->GetNameByAnimID(anm);
                                    if (strlen(name) >= 255)
                                        {
                                            CRY_ASSERT_MESSAGE(0, string().Format("[CAnimationProxyDualCharacterBase::Generate1P3PPairFiles] Animname %s overruns buffer", name));
                                            CryLogAlways("[CAnimationProxyDualCharacterBase::Generate1P3PPairFiles] Animname %s overruns buffer", name);
                                            continue;
                                        }
                                    const char *pos = CryStringUtils::stristr(name, "_1p");
                                    if (pos)
                                        {
                                            char name3P[256];
                                            strcpy(name3P, name);
                                            name3P[(int)(TRUNCATE_PTR)pos + 1 - (int)(TRUNCATE_PTR)name] = '3';
                                            animID3P = animSet->GetAnimIDByName(name3P);

                                            if (animID3P >= 0)
                                                {
                                                    uint32 animCRCTP = animSet->GetCRCByAnimID(animID3P);
                                                    s_animCrCHashMap[animCRC] = animCRCTP;
                                                }
                                        }
                                }
                        }
                }
        }


    //--- Save the file
    CryFixedStringT<256> animCrC;
    XmlNodeRef nodePairList	= gEnv->pSystem->CreateXmlNode( "Pairs" );
    for (NameHashMap::iterator iter = s_animCrCHashMap.begin(); iter != s_animCrCHashMap.end(); ++iter)
        {
            XmlNodeRef nodePair = nodePairList->newChild( "Pair" );
            animCrC.Format("%u", iter->first);
            nodePair->setAttr( "FP", animCrC.c_str());
            animCrC.Format("%u", iter->second);
            nodePair->setAttr( "TP", animCrC.c_str());
        }
    nodePairList->saveToFile(ANIMPAIR_PATHNAME);

    s_animCrCHashMap.clear();
    Load1P3PPairFile();
}