| #!/usr/bin/python  | 
| # -*- coding: GBK -*-  | 
| #  | 
| #  | 
| ##@package PlayerEquipDecompose.py  | 
| #  | 
| # @todo:×°±¸·Ö½â  | 
| #  | 
| # @author xdh  | 
| # @date 2016-08-05  | 
| # @version 1.0  | 
| # @note:  | 
| #------------------------------------------------------------------------------   | 
| #"""Version = 2017-05-24 14:51"""  | 
| #------------------------------------------------------------------------------   | 
| import IpyGameDataPY  | 
| import IPY_GameWorld  | 
| import GameWorld  | 
| import ItemCommon  | 
| import ChPyNetSendPack  | 
| import ShareDefine  | 
| import NetPackCommon  | 
| import PlayerControl  | 
| import ChConfig  | 
| import DataRecordPack  | 
| import PlayerSuccess  | 
| import GameFuncComm  | 
| import PlayerVip  | 
| import ItemControler  | 
| import random  | 
| import json  | 
|   | 
| import math  | 
| #---------------------------------------------------------------------  | 
|   | 
|   | 
| ##µÇ¼´¦Àí  | 
| # @param curPlayer Íæ¼Ò  | 
| # @return None  | 
| def PlayerLogin(curPlayer):  | 
|     Sync_EDLVInfo(curPlayer)  | 
|     return  | 
|   | 
| def DoEquipDecomposeOpen(curPlayer):  | 
|     #¹¦ÄÜ¿ªÆô  | 
|     RefreshEDAttr(curPlayer) # ÊôÐÔˢР | 
|     return  | 
|   | 
| #//A3 2C ×°±¸·Ö½â #tagCMEquipDecompose  | 
| #  | 
| #struct    tagCMEquipDecompose  | 
| #{  | 
| #    tagHead        Head;  | 
| #    BYTE        IndexCount;        //²ÄÁÏËùÔÚ±³°üË÷ÒýµÄÊýÁ¿  | 
| #    BYTE        IndexList[IndexCount];    //²ÄÁÏËùÔÚ±³°üË÷ÒýÁÐ±í  | 
| #};  | 
|   | 
| ## Íæ¼Ò·Ö½â×°±¸·â°ü A5 08  | 
| #  @param playerIndex Íæ¼ÒË÷Òý    | 
| #  @param clientData ¿Í»§¶Ë·â°ü    | 
| #  @param tick Ê±¼ä  | 
| #  @return None  | 
| def OnDoEquipDecompose(index, clientData, tick):  | 
|     curPlayer = GameWorld.GetPlayerManager().GetPlayerByIndex(index)  | 
|       | 
|     eatIndexList = clientData.IndexList  | 
|       | 
|     EatItems(curPlayer, eatIndexList)  | 
|     return  | 
|   | 
| # ÍÌÊÉÎïÆ·, ·µ»Ø±»ÍÌÊýÁ¿  | 
| def EatItems(curPlayer, eatIndexList):  | 
|     drDelItemList, totalAddExp, delAllCnt = __GetCanEatItemInfo(curPlayer, eatIndexList)  | 
|     if not totalAddExp:  | 
|         GameWorld.DebugLog("    ×°±¸ÎüÊՠûÓпÉÍÌÊÉÎïÆ·£¡")  | 
|         return 0, 0  | 
|     LV = curPlayer.NomalDictGetProperty(ChConfig.Def_PDict_EquipDecomposeLV)  | 
|     Exp = curPlayer.NomalDictGetProperty(ChConfig.Def_PDict_EquipDecomposeExp)  | 
|     reduceTotalExp, updLV, updExp = __GetEatItemResult(curPlayer, LV, Exp, totalAddExp)  | 
|      | 
|     PlayerControl.NomalDictSetProperty(curPlayer, ChConfig.Def_PDict_EquipDecomposeExp, updExp)  | 
|     if LV != updLV:  | 
|         PlayerControl.NomalDictSetProperty(curPlayer, ChConfig.Def_PDict_EquipDecomposeLV, updLV)  | 
|           | 
|         #Ë¢ÊôÐÔ  | 
|         RefreshEDAttr(curPlayer) # ÊôÐÔˢР | 
|         PlayerControl.PlayerControl(curPlayer).RefreshPlayerAttrState()  | 
|     #¸øÁ¶µ¤²ÄÁÏ  | 
|     curDecomposeCnt = curPlayer.NomalDictGetProperty(ChConfig.Def_PDict_EquipDecomposeCnt)  | 
|     updDecomposeCnt = curDecomposeCnt + delAllCnt  | 
|     perDecomposeCnt = IpyGameDataPY.GetFuncCfg('EquipDecomposeAward')  | 
|     PlayerControl.NomalDictSetProperty(curPlayer, ChConfig.Def_PDict_EquipDecomposeCnt, updDecomposeCnt%perDecomposeCnt)  | 
|     jsonItemList = []  | 
|     giveCnt = 0  | 
|     if updDecomposeCnt >= perDecomposeCnt:  | 
|         awardList = IpyGameDataPY.GetFuncCfg('EquipDecomposeAward', 2)  | 
|         if not awardList:  | 
|             return len(drDelItemList), giveCnt  | 
|         giveCnt = updDecomposeCnt/perDecomposeCnt  | 
|         giveItemIDDict = {}  | 
|         for _ in xrange(giveCnt):  | 
|             itmeID = random.choice(awardList)  | 
|             giveItemIDDict[itmeID] = giveItemIDDict.get(itmeID, 0) + 1  | 
|         for giveItemID, itemCnt in giveItemIDDict.items():   | 
|             jsonItemList.append(ItemCommon.GetJsonItem([giveItemID,itemCnt,1]))  | 
|         needSpace = len(giveItemIDDict)  | 
|         packSpace = ItemCommon.GetItemPackSpace(curPlayer, IPY_GameWorld.rptItem, needSpace)  | 
|         if packSpace < needSpace:  | 
|             prizeItemList = [[giveItemID, itemCnt, 1] for giveItemID, itemCnt in giveItemIDDict.items()]  | 
|             PlayerControl.SendMailByKey("DefaultLackSpace", [curPlayer.GetPlayerID()], prizeItemList)  | 
|         else:  | 
|             for giveItemID, itemCnt in giveItemIDDict.items():  | 
|                 ItemControler.GivePlayerItem(curPlayer, giveItemID, itemCnt, True, [IPY_GameWorld.rptItem], True)  | 
|       | 
|     #ͬ²½¿Í»§¶Ë  | 
|     Sync_EDLVInfo(curPlayer, jsonItemList)  | 
|     # Á÷Ïò  | 
|     saveDataDict = {"ExpBefore":Exp, "AddTotalExp":reduceTotalExp, "ExpAfter":updExp,  | 
|                     "DelItemList(ItemID,delCnt,baseExp,addExp)":drDelItemList}  | 
|     DataRecordPack.DR_ClassUpSystem(curPlayer, "EquipDecomposeUp", updLV, saveDataDict)  | 
|       | 
|     #EventReport.WriteEvent__lv(curPlayer, LV, updLV, Exp, updExp)  | 
|     return len(drDelItemList), giveCnt  | 
|   | 
| ##»ñÈ¡¿ÉÒÔÍÌÊɵÄÎïÆ·ÐÅÏ¢  | 
| #  @param curPlayer: Íæ¼ÒʵÀý  | 
| #  @return [¿ÉÍÌÊɵÄÎïÆ·Áбí], ×î´ó¿ÉÌṩµÄ¾Ñé  | 
| def __GetCanEatItemInfo(curPlayer, expIndexList):  | 
|     eatItemList = []  | 
|     totalAddExp = 0  | 
|     allitemCnt = 0  | 
|     petEatItemAddExpPer = PlayerVip.GetPrivilegeValue(curPlayer, ChConfig.VIPPrivilege_EatItem)  | 
|     itemPack = curPlayer.GetItemManager().GetPack(IPY_GameWorld.rptItem)  | 
|     for index in expIndexList:  | 
|         eatItem = itemPack.GetAt(index)  | 
|           | 
|         if not eatItem or eatItem.IsEmpty():  | 
|             continue  | 
|   | 
|         eatItemID = eatItem.GetItemTypeID()  | 
|         if eatItem.GetType() == ChConfig.Def_ItemType_EquipDecomposeExp:  | 
|             curEff = eatItem.GetEffectByIndex(0)  | 
|             baseExp = curEff.GetEffectValue(0)  | 
|         else:  | 
|             itemColor = eatItem.GetItemColor()  | 
|             itemClass = eatItem.GetLV()  | 
|             ipyData = IpyGameDataPY.GetIpyGameData("PetEatEquip", itemColor, itemClass)  | 
|             if not ipyData:  | 
|                 GameWorld.DebugLog("    tagPetEatEquip.txt,δÅäÖøÃÎïÆ·£¡ eatItemID=%s, EquipColor=%s,EquipClass=%s" % (eatItemID, itemColor, itemClass))  | 
|                 continue  | 
|             baseExp = ipyData.GetExp()  | 
|           | 
|         itemCnt = eatItem.GetCount() # ×°±¸Ò»°ãĬÈÏ1£¬ÈçÊǾÑéµÀ¾ßÔòÒ»°ã¿Éµþ¼Ó  | 
|         addExp = baseExp * itemCnt  | 
|           | 
|         totalAddExp += addExp  | 
|         allitemCnt += itemCnt  | 
|         ItemCommon.DelItem(curPlayer, eatItem, itemCnt, True, ChConfig.ItemDel_EquipDecompose)  | 
|           | 
|           | 
|         GameWorld.DebugLog("    ÎüÊՠɾ³ýÎïÆ· i=%s,baseExp=%s,itemCnt=%s,addExp=%s,totalAddExp=%s"   | 
|                            % (index, baseExp, itemCnt, addExp, totalAddExp))  | 
|         # ÏȼìË÷¿É³ÔÁÐ±í£¬·ÀÖ¹Éý¼¶¹ý³ÌÖгԵôÔÀ´²»¿É³ÔµÄ[index, ÎïÆ·ÊµÀý, »ù´¡¾Ñé]  | 
|         eatItemList.append([eatItemID, itemCnt, baseExp, addExp])  | 
|     if petEatItemAddExpPer:  | 
|         totalAddExp += totalAddExp * petEatItemAddExpPer / ChConfig.Def_MaxRateValue  | 
|               | 
|     PlayerSuccess.DoAddSuccessProgress(curPlayer, ShareDefine.SuccType_DecomposeEquip, allitemCnt)  | 
|     return eatItemList, totalAddExp, allitemCnt  | 
|   | 
|   | 
| ##»ñÈ¡ÍÌÊɽá¹û  | 
| #  @param curPlayer: Íæ¼ÒʵÀý  | 
| #  @return Êµ¼ÊÐèÒª¿Û³ýµÄ¾Ñé, ×îÖÕÄ¿±êÎïÆ·, ×îÖÕ¾ÑéÖµ  | 
| def __GetEatItemResult(curPlayer, LV, Exp, totalAddExp):  | 
|     remainExp = totalAddExp # Ê£Óà¿ÉÓþÑé  | 
|     reduceTotalExp = 0 # ÕæÕýÐèÒª¿Û³ýµÄ¾Ñé  | 
|     ipyMgr = IpyGameDataPY.IPY_Data()  | 
|     maxLV = ipyMgr.GetEquipDecomposeByIndex(ipyMgr.GetEquipDecomposeCount()-1).GetLV()  | 
|     # ¾Ñé¼ì²é  | 
|     while remainExp > 0:  | 
|         if LV +1 >= maxLV:  | 
|             break  | 
|         maxExp = __GetLvUpNeedExp(LV)  | 
|           | 
|         if not maxExp:  | 
|             break  | 
|           | 
|         needExp = max(0, maxExp - Exp)  | 
|         if remainExp >= needExp:  | 
|             Exp = 0  | 
|             reduceTotalExp += needExp  | 
|             remainExp -= needExp  | 
|             LV += 1  | 
|         else:  | 
|             Exp += remainExp  | 
|             reduceTotalExp += remainExp  | 
|             remainExp = 0  | 
|               | 
|     #µÈ¼¶ÂúºóÒ²¿ÉÒÔ·Ö½â¼Ó¾Ñ飬¹ÊËùÓÐ×°±¸¶¼·Ö½â  | 
|     Exp += remainExp  | 
|     reduceTotalExp = totalAddExp  | 
|     GameWorld.DebugLog("×ܿɼӾÑé=%s,ʵ¼Ê×ܿ۳ý¾Ñé=%s,newLV=%s,×îÖÕ¾Ñé=%s" %   | 
|                        (totalAddExp, reduceTotalExp, LV, Exp))  | 
|     return reduceTotalExp, LV, Exp  | 
|   | 
|   | 
|   | 
| def __GetLvUpNeedExp(lv):  | 
|     """»ñȡװ±¸·Ö½âÉý¼¶ÐèÒª¾Ñé"""  | 
|     #ÅäÖõĵȼ¶´Ó1¿ªÊ¼  | 
|     ipyData = IpyGameDataPY.GetIpyGameData("EquipDecompose", lv+1)  | 
|     if not ipyData:  | 
|         return 0  | 
|     return ipyData.GetUpNeedExp()  | 
|   | 
|   | 
| ## Ë¢ÊôÐÔ  | 
| def RefreshEDAttr(curPlayer):  | 
|     if not GameFuncComm.GetFuncCanUse(curPlayer, ShareDefine.GameFuncID_EquipDecompose):  | 
|         return  | 
|     allAttrList = [{} for _ in range(4)]  | 
|     curLV = curPlayer.NomalDictGetProperty(ChConfig.Def_PDict_EquipDecomposeLV)  | 
|     ipyData = IpyGameDataPY.GetIpyGameData('EquipDecompose', curLV+1)  | 
|     if not ipyData:  | 
|         return  | 
|     for attrID, attrValue in ipyData.GetAttr().items():  | 
|         PlayerControl.CalcAttrDict_Type(int(attrID), attrValue, allAttrList)  | 
|       | 
|           | 
|     # ±£´æ¼ÆËãÖµ  | 
|     PlayerControl.SetCalcAttrListValue(curPlayer, ChConfig.Def_CalcAttrFunc_EquipDecompose, allAttrList)  | 
|     return  | 
|   | 
|   | 
|   | 
| #// A3 2D ×°±¸·Ö½âÉèÖà#tagCMDecomposeSeting  | 
| #  | 
| #struct    tagCMDecomposeSeting  | 
| #{  | 
| #    tagHead        Head;  | 
| #    DWORD        Seting;  | 
| #};  | 
| def OnDecomposeSetingSave(index, clientData, tick):  | 
|     curPlayer = GameWorld.GetPlayerManager().GetPlayerByIndex(index)  | 
|     PlayerControl.NomalDictSetProperty(curPlayer, ChConfig.Def_PDict_EquipDecomposeSeting, clientData.Seting)  | 
|     return  | 
|   | 
| ## ·Ö½âµÈ¼¶Ïà¹ØÐÅÏ¢  | 
| def Sync_EDLVInfo(curPlayer, getItemInfo=[]):  | 
|     getItemInfo = json.dumps(getItemInfo, ensure_ascii=False)  | 
|     PackData = ChPyNetSendPack.tagMCEquipDecomposeInfo()  | 
|     PackData.Clear()  | 
|     PackData.LV = curPlayer.NomalDictGetProperty(ChConfig.Def_PDict_EquipDecomposeLV)  | 
|     PackData.Exp = curPlayer.NomalDictGetProperty(ChConfig.Def_PDict_EquipDecomposeExp)  | 
|     PackData.Seting = curPlayer.NomalDictGetProperty(ChConfig.Def_PDict_EquipDecomposeSeting)  | 
|     PackData.DecomposeCnt = curPlayer.NomalDictGetProperty(ChConfig.Def_PDict_EquipDecomposeCnt)  | 
|     PackData.GetItemData = str(getItemInfo)  | 
|     PackData.GetItemLen = len(PackData.GetItemData)  | 
|     NetPackCommon.SendFakePack(curPlayer, PackData)  | 
|     return  |