%%-----------------------------------------------------------------------------
%% @Module  :       lib_custom_act_slices
%% @Author  :       zmh
%% @Created :       20201123
%% @Description:	积分拼图
%%-----------------------------------------------------------------------------
-module (lib_custom_act_slices).

-compile(export_all).
-include("custom_act.hrl").
-include("common.hrl").
-include("server.hrl").
-include("errcode.hrl").
-include("figure.hrl").
-include("def_goods.hrl").
-include("def_module.hrl").
-include("goods.hrl").
-include("predefine.hrl").
-include("def_event.hrl").
-include("rec_event.hrl").
-include("dungeon.hrl").

-export([
    task_event/3
    , send_slice_info/2
    , check/1
]).

% %%积分拼图
% -record(custom_act_slices, {
%     grades = [],
%     tasks = []    %[{行,列,num,0/1/2}]
% }).

-define(STATE_DOING, 0).
-define(STATE_DONE,  1).
-define(STATE_OVER,  2).

%%奖励领取
fetch_slice_award(RoleID,SubType,Grade)->
    {ActSlice,CustomActData} = get_act_slice_data(SubType),
    #custom_act_slices{
        grades = Grades,
        tasks  = Tasks
    }=ActSlice,
    CKList = [
        {check_open,SubType},
        {check_repeate,Grade,Grades},
        {check_cfg,SubType,Grade,Tasks}
    ],
    case util:check_lists(?MODULE,CKList) of
        {ok,{NTasks,Awards}}->
            NGrades = [Grade|Grades],
            NActSlice = ActSlice#custom_act_slices{grades=NGrades,tasks=NTasks},
            send_slice_info(RoleID,SubType,NActSlice),
            lib_custom_act_data:save_custom_data(RoleID, CustomActData#custom_act_data{act_data = [NActSlice]}),
            Produce = #produce{type=act_slices,reward=Awards},
            lib_goods_api:send_reward_with_mail(RoleID, Produce, ?MOD_AC_CUSTOM),
            Res = ?SUCCESS;
        {false,Res}->
            skip
    end,
    {ok,Bin} = pt_331:write(33154,[Res,SubType,Grade]),
    lib_server_send:send_to_uid(RoleID,Bin),
    ok.



check({check_open,SubType})->
    case lib_custom_act_api:is_open_act(?CUSTOM_ACT_TYPE_SLICES,SubType) of
        true->
            true;
        _->
            {false,?ERRCODE(err331_act_closed)}
    end;
check({check_repeate,Grade,Grades})->
    case lists:member(Grade,Grades) of
        false->
            true;
        _->
            {false,?ERRCODE(err331_already_get_reward)}
    end;
check({check_cfg,SubType,Grade,Tasks})->
    case lib_custom_act_util:get_act_reward_cfg_info(?CUSTOM_ACT_TYPE_SLICES,SubType,Grade) of
        #custom_act_reward_cfg{condition=Cons,reward=Awards}->
            case do_check(Cons,Tasks,false) of
                {ok,NTasks}->
                     {ok,{NTasks,Awards}};
                _->
                    {false,?ERRCODE(err331_act_can_not_get)}
            end;
        _->
            {false,?ERRCODE(err331_can_not_pick_up)}
    end.


do_check([],_Task,IsFin)->
    IsFin;
do_check([{row,Row}|T],Tasks,IsFin)->
    FinTasks = [1||{R,_,_,S}<-Tasks,R=:=Row,S>=?STATE_DONE],
    case length(FinTasks)>= 3 of
        true->
            {ok,Tasks};
        _->
            do_check(T,Tasks,IsFin)
    end;
do_check([{column,Colu}|T],Tasks,IsFin)->
    FinTasks = [1||{_,C,_,S}<-Tasks,C=:=Colu,S>=?STATE_DONE],
    case length(FinTasks)>= 3 of
        true->
            {ok,Tasks};
        _->
            do_check(T,Tasks,IsFin)
    end;
do_check([{count,Count}|T],Tasks,IsFin)->
    FinTasks = [1||{_,_,_,S}<-Tasks,S>=?STATE_DONE],
    case length(FinTasks)>= Count of
        true->
            {ok,Tasks};
        _->
            do_check(T,Tasks,IsFin)
    end;
do_check([{order,Row,Colu}|T],Tasks,IsFin)->
    FinTasks = [1||{R,C,_,S}<-Tasks,R=:=Row,C=:=Colu,S=:=?STATE_DONE],
    case length(FinTasks)>= 1 of
        true->
            NTasks = change_state(Tasks,Row,Colu,[]),
            {ok,NTasks};
        _->
            do_check(T,Tasks,IsFin)
    end.

change_state([],_,_,Tasks)->
    Tasks;
change_state([{R,C,N,S}|T],Row,Colu,Tasks)->
    case R =:= Row andalso C =:= Colu of
        true->
            T++[{R,C,N,?STATE_OVER}|Tasks];
        _->
            change_state(T,Row,Colu,[{R,C,N,S}|Tasks])
    end.


finish_dungeon(RoleID,DunType)->
    case DunType of
        ?DUNGEON_TYPE_MATERIAL->
            task_event(RoleID,?MOD_DUNGEON,?DUNGEON_TYPE_MATERIAL);
        ?DUNGEON_TYPE_PET->
            task_event(RoleID,?MOD_DUNGEON,?DUNGEON_TYPE_PET);
        _->
            skip
    end.

finish_dungeon(RoleId,DunType,Num)->
    case Num>0 of
        true->
            finish_dungeon(RoleId,DunType),
            finish_dungeon(RoleId,DunType,Num-1);
        _->
            skip
    end.

enter_dungeon(RoleID,DunType)->
    case DunType of
        ?DUNGEON_TYPE_PET->
            task_event(RoleID,?MOD_DUNGEON,?DUNGEON_TYPE_PET);
        _->
            skip
    end.


%%触发事件
task_event(RoleID,Mod,Sub) when is_integer(RoleID)->
    lib_player:apply_cast(RoleID, ?APPLY_CAST_STATUS, ?MODULE, task_event, [Mod,Sub]);
task_event(Status,Mod,Sub)->
    SubTypes = lib_custom_act_api:get_open_subtype_ids(?CUSTOM_ACT_TYPE_SLICES),
    task_event(Status,SubTypes,Mod,Sub).
task_event(Status,[],_Mod,_Sub)->
    {ok,Status};
task_event(Status,[H|T],Mod,Sub)->
    #player_status{id=RoleID}=Status,
    {ActSlice,CustomActData} = get_act_slice_data(H),
    #custom_act_slices{tasks=Tasks}=ActSlice,
    #custom_act_cfg{
        condition=Cons
    } = lib_custom_act_util:get_act_cfg_info(?CUSTOM_ACT_TYPE_SLICES,H),
    case lists:keyfind(suit,1,Cons) of
        {_,Suit}->
            skip;
        _->
            Suit = 1
    end,
    {IsUpdate,NTasks} = update_task_event(Tasks,Suit,Mod,Sub,[],false),
    case IsUpdate of
        true->
            NActSlice = ActSlice#custom_act_slices{tasks=NTasks},
            send_slice_info(RoleID,H,NActSlice),
            lib_custom_act_data:save_custom_data(RoleID, CustomActData#custom_act_data{act_data = [NActSlice]});
        _->
            skip
    end,
    task_event(Status,T,Mod,Sub).

update_task_event([],_Suit,_Mod,_Sub,Tasks,IsUpdate)->
    {IsUpdate,Tasks};
update_task_event([{Row,Col,CurN,CurS}|T],Suit,Mod,Sub,Tasks,IsUpdate)->
    #slice_task{times=Max,mod=M,sub=S}=data_custom_act:get_slice_task(Suit,Row,Col),
    case CurS >= ?STATE_DONE of
        true->
            update_task_event(T,Suit,Mod,Sub,[{Row,Col,Max,CurS}|Tasks],IsUpdate);
        _->
            case M =:= Mod andalso S =:= Sub of
                true->
                    NewS = case CurN+1>=Max of
                        true->
                            ?STATE_DONE;
                        _->
                            ?STATE_DOING
                    end,
                    update_task_event(T,Suit,Mod,Sub,[{Row,Col,CurN+1,NewS}|Tasks],true);
                _->
                    update_task_event(T,Suit,Mod,Sub,[{Row,Col,CurN,CurS}|Tasks],IsUpdate)
            end
    end.

send_slice_info(RoleID,SubType)->
    {ActSlice,_CustomActData} = get_act_slice_data(SubType),
    send_slice_info(RoleID,SubType,ActSlice).

send_slice_info(RoleID,H,ActSlice)->
    #custom_act_slices{
        grades = Grades,
        tasks = Tasks    %[{行,列,num,0/1/2}]
    }=ActSlice,
    {ok,Bin} = pt_331:write(33153,[H,Grades,Tasks]),
    lib_server_send:send_to_uid(RoleID,Bin),
    ok.


get_act_slice_data(SubType)->
    CustomActData = lib_custom_act_data:custom_act_data(?CUSTOM_ACT_TYPE_SLICES, SubType),
    #custom_act_data{act_data = ActData} = CustomActData,
    case ActData of
        [ActSlice]->
            ActSlice;
        _->
            ActSlice = init_slices(SubType)
    end,
    {ActSlice,CustomActData}.


init_slices(SubType)->
    #custom_act_cfg{
        condition=Cons
    } = lib_custom_act_util:get_act_cfg_info(?CUSTOM_ACT_TYPE_SLICES,SubType),
    case lists:keyfind(suit,1,Cons) of
        {_,Key}->
            skip;
        _->
            Key = 1
    end,
    Tasks = data_custom_act:get_all_slice_task(Key),
    InitTasks = [{Row,Col,0,?STATE_DOING}||{Row,Col}<-Tasks],
    #custom_act_slices{tasks=InitTasks}.



