package extend.zp;

import java.util.ArrayList;
import java.util.HashSet;
import java.util.List;
import java.util.Map;
import java.util.Map.Entry;
import java.util.Stack;

import com.game.Util;
import com.game.data.Player;
import com.game.data.Room;
import com.game.data.Score;
import com.taurus.core.entity.ITArray;
import com.taurus.core.entity.ITObject;
import com.taurus.core.entity.TArray;
import com.taurus.core.entity.TObject;

import extend.zp.player.rule.RuleChi;
import extend.zp.tip.IRuleBase;
import extend.zp.tip.Tip;
import extend.zp.tip.TipManager;
import extend.zp.uitl.CardUtil;
import extend.zp.uitl.ChowCard;

/**
 * 
 * 
 *
 *         2017��8��30�� EXPlayer.java
 */
public class EXPlayer extends Player {
	// ����
	public List<Integer>	cardInhand;
	// ������
	public List<Integer>	outcardList;
	// ������
	public List<Integer>	outcardExList;

	public ITArray			opCard;

	public int				biCard;

	public List<int[]>		tiGroup;
	public List<int[]>		paoGroup;
	public List<int[]>		kanGroup;
	public List<int[]>		pongGroup;
	public List<int[]>		weiGroup;
	public List<int[]>		chowGroup;
	public List<OpCard>		opCardList;

	public Stack<OpCard>	handCard;
	public List<Integer>	handCardEx;

	public HashSet<Integer>	chouChiSet;
	public HashSet<Integer>	chouChiExSet;
	public HashSet<Integer>	chouPongSet;

	public int				drawCard	= 0;
	public int				winCard		= 0;
	public int				winScore	= 0;
	public int				winFan		= 0;
	public List<MingTang>	mingtangList;

	public int				kongCount	= 0;
	public int				tiCount		= 0;
	// ��Ϣ
	public int				huXi		= 0;
	
	public int				total_huxi	= 0;
	
	public boolean			isTingHu	= true;

	// �Ƿ�����ү
	public boolean			isLaoYe		= false;

	public boolean			isMingTang	= true;

	public TipManager		tipMgr;
	
	public Tip				actionTip;

	public EXPlayer(int playerid, Room table, String session_id) {
		super(playerid, table, session_id);

		cardInhand = new ArrayList<>();
		outcardList = new ArrayList<>();
		outcardExList = new ArrayList<>();

		tiGroup = new ArrayList<>();
		paoGroup = new ArrayList<>();
		kanGroup = new ArrayList<>();
		pongGroup = new ArrayList<>();
		weiGroup = new ArrayList<>();
		chowGroup = new ArrayList<>();
		opCardList = new ArrayList<>();
		mingtangList = new ArrayList<>();

		opCard = new TArray();
		chouChiSet = new HashSet<>();
		chouChiExSet = new HashSet<>();
		chouPongSet = new HashSet<>();

		handCard = new Stack<OpCard>();
		handCardEx = new ArrayList<>();

		tipMgr = new TipManager(this);
	}

	protected Score newScore() {
		return new EXScore(this);
	}

	public void initOpCard(ITArray opcard) {
		this.opCard.clear();
		for (int i = 0; i < opcard.size(); ++i) {
			this.opCard.addInt(opcard.getInt(i));
		}
	}

	public ITObject getReloadInfo(boolean self) {
		ITObject playerData = super.getReloadInfo(self);
		ITArray disCard = Util.toTArray(this.outcardList);
		playerData.putTArray("outcard_list", disCard);
		playerData.putInt("card_count", this.cardInhand.size());
		playerData.putInt("score", this.score.total_score);
		playerData.putInt("hu_xi", this.getShowHuXi(self));
		ITArray opcards = TArray.newInstance();
		for (OpCard opcard : opCardList) {
			ITObject opcardParam = new TObject();
			opcardParam.putInt("type", opcard.type);
			opcardParam.putInt("card1", opcard.card1);
			opcardParam.putInt("card2", opcard.card2);
			opcardParam.putInt("card3", opcard.card3);
			opcards.addTObject(opcardParam);
		}
		playerData.putTArray("opcard", opcards);
		return playerData;
	}

	public int getShowHuXi(boolean self) {
		int huXi = 0;
		for (OpCard opCard : this.opCardList) {
			if (!self) {
				if (opCard.type == RuleWeight.TYPE_KAN || opCard.type == RuleWeight.TYPE_WEI) {
					continue;
				}
			} else {
				if (opCard.type == RuleWeight.TYPE_KAN) {
					continue;
				}
			}
			huXi += opCard.huXi;
		}
		return huXi;
	}

	public void resetHuXi() {
		this.huXi = 0;
		for (OpCard opCard : this.opCardList) {
			this.huXi += opCard.huXi;
		}
	}

	public void clear() {
		this.cardInhand.clear();
		this.winer = 0;
		this.outcardList.clear();
		this.outcardExList.clear();
		this.drawCard = 0;
		this.winScore = 0;
		this.winFan = 0;
		this.kongCount = 0;
		this.tiCount = 0;
		this.huXi = 0;
		this.isTingHu = true;
		this.isLaoYe = false;
		this.isMingTang = true;
		this.tiGroup.clear();
		this.paoGroup.clear();
		this.kanGroup.clear();
		this.pongGroup.clear();
		this.weiGroup.clear();
		this.chowGroup.clear();
		this.opCardList.clear();
		this.chouChiSet.clear();
		this.chouChiExSet.clear();
		this.chouPongSet.clear();
		this.mingtangList.clear();
		this.score.resetRound();
	}

	public EXRoom getRoom() {
		return (EXRoom) room;
	}
	/**
	 * �Զ����ƣ��йܣ�
	 */
	public  Integer autoDiscard(){
		Map<Integer, Integer> cardNum=CardUtil.getCardNumMap(this.cardInhand);
		for (Entry<Integer, Integer> card : cardNum.entrySet()) {
			 if (card.getValue()==1||card.getValue()==2) {
				return card.getKey();
			}
		}
		return 0;
	}
	public boolean chi(int eventCard, IRuleBase rule) {
		EXPlayer activePlayer = (EXPlayer) this.room.playerMapBySeat.get(this.room.activeSeat);
		if (this.cardInhand.size() <= 2) {
			return false;
		}
		if (eventCard == 0) {
			return false;
		}
		if (this.isEntrust()) {
			this.chouChiSet.add(eventCard);
			return false;
		}
		// ����
		if (this.chouChiSet.contains(eventCard)) {
			return false;
		}
		// ����
		if (this.chouChiExSet.contains(eventCard) && this.getRoom().throwCardsSet.contains(eventCard)) {
			return false;
		}
		if (CardUtil.cardNum(eventCard, this.outcardExList) != 0) {
			return false;
		}
		if (activePlayer.nextSeat != this.seat && activePlayer.seat != this.seat) {
			return false;
		}
		if (this.getRoom().checkPao(eventCard, rule  instanceof RuleChi)) {
			return false;
		}
		
		ChowCard chow = new ChowCard(this.cardInhand, eventCard);
		ITArray list = TArray.newInstance();
		boolean isChi = chow.tryChow(list);
		if (isChi) {
			int weight = activePlayer.seat != this.seat ? RuleWeight.CHOW1 : RuleWeight.CHOW2;
			for (int i = 0; i < list.size(); ++i) {
				ITObject obj = list.getTObject(i);
				ITArray opCard = obj.getTArray("opcard");
				Tip tip = new Tip(eventCard, opCard, weight, rule, RuleWeight.TYPE_CHOW);
				tip.bi_list = obj.getTArray("bi_list");
				this.tipMgr.addTip(tip);
			}
		} else {
			this.chouChiExSet.add(eventCard);
		}
		return isChi;
	}

}
