local function ScoreYMultiplier(ypos)
    local Multiplier = 24;
    Multiplier = Multiplier * ypos;
    return Multiplier;
end;

local function ScoreOnCommand(player,order)
    local PlayerPreparation = { "horizalign,left","horizalign,right" };
    local StartStub = cmd(FirstAnimationStub;SecondAnimationStub);
    local FirstAnimationStub = "PlayerPreparation[player];"
    local SecondAnimationStub = "diffusealpha,0;sleep,0.2*order;decelerate,0.5;diffusealpha,1"
    return StartStub;
end;

local function MakeGradeDisplay(state)
    local stub = LoadActor("_grades") .. { InitCommand=cmd(animate,false;setstate,state); };
    return stub;
end;

local function MakeDifficultyLabel(dc)
    local Font = LoadFont("Common") .. { Text=label; InitCommand=cmd(shadowlength,0;settext,dc); };
    return Font;
end;

local function MakeAwardFont(award)
    local Font = LoadFont("System") .. { Text=label; InitCommand=cmd(shadowlength,0;settext,award); };
    return Font;
end;

local Song = GAMESTATE:GetCurrentSong();
local Course = GAMESTATE:GetCurrentCourse();
local Current = GAMESTATE:IsCourseMode() and Course or Song;

local GradeFrames = {
	Grade_Tier01 = 0,
	Grade_Tier02 = 1,
	Grade_Tier03 = 2,
	Grade_Tier04 = 3,
	Grade_Tier05 = 4,
	Grade_Tier06 = 5,
    Grade_Tier07 = 6,
	Grade_Failed = 7,
};

local t = Def.ActorFrame{ };

local Judgments = Def.ActorFrame{ };

local Grades = Def.ActorFrame{ InitCommand=cmd(y,SCREEN_TOP+60+64+8); };

local Awards = Def.ActorFrame{ InitCommand=cmd(y,SCREEN_BOTTOM-60-32;); };

for pn in ivalues(PlayerNumber) do
	local stats = STATSMAN:GetCurStageStats():GetPlayerStageStats(pn);
	
	--judgment
	function MakeJudgmentsFont(value)
--~         local JudgeColor = JudgeColor(value)
        local t = Def.ActorFrame {
            LoadActor("judgment line") .. {
                InitCommand=cmd(x,-148);
            };
            LoadFont("Common") .. { 
                Text=value; 
                InitCommand=cmd(shadowlength,0;horizalign,right); 
            };
        };
        return t;
    end
    
	local judgmentstats = Def.ActorFrame{
		InitCommand=function(self)
			local xpos = (pn == PLAYER_1) and SCREEN_CENTER_X*0.5+32 or SCREEN_CENTER_X*1.5-32
            self:y(SCREEN_TOP+60);
			self:x(xpos);
		end;
	};
    
--[[ 	local judgmentlabels = Def.ActorFrame {
		InitCommand=function(self)
            self:x(SCREEN_CENTER_X);
            self:y(SCREEN_TOP+60);
        end;
		MakeJudgmentsFont("Marvelous") .. { InitCommand=cmd(y,ScoreYMultiplier(1)); };
		MakeJudgmentsFont("Perfect") .. { InitCommand=cmd(y,ScoreYMultiplier(2)); };
		MakeJudgmentsFont("Great") .. { InitCommand=cmd(y,ScoreYMultiplier(3)); };
		MakeJudgmentsFont("Good") .. { InitCommand=cmd(y,ScoreYMultiplier(4)); };
		MakeJudgmentsFont("Bad") .. { InitCommand=cmd(y,ScoreYMultiplier(5)); };
		MakeJudgmentsFont("Miss") .. { InitCommand=cmd(y,ScoreYMultiplier(6)); };
		MakeJudgmentsFont("O.K.") .. { InitCommand=cmd(y,ScoreYMultiplier(8)); };
		MakeJudgmentsFont("N.G.") .. { InitCommand=cmd(y,ScoreYMultiplier(9)); };
		MakeJudgmentsFont("Max Combo") .. { InitCommand=cmd(y,ScoreYMultiplier(10.25)); };
	}; --]]
	local comboalign = (pn == PLAYER_1) and "left" or "right";
	local combox = (pn == PLAYER_1) and -20 or 20;
	function GetTNS(tns,stats)
		local value = stats:GetTapNoteScores(tns);
		value = string.format("%04i", value);
		return value;
	end;
	function GetHNS(hns,stats)
		local value = stats:GetHoldNoteScores(hns);
		value = string.format("%04i", value);
		return value;
	end;
	if GAMESTATE:IsHumanPlayer(pn) then
		judgmentstats[#judgmentstats+1] = MakeJudgmentsFont(GetTNS("TapNoteScore_W1",stats)) .. { InitCommand=cmd(y,ScoreYMultiplier(1)); };
		judgmentstats[#judgmentstats+1] = MakeJudgmentsFont(GetTNS("TapNoteScore_W2",stats)) .. { InitCommand=cmd(y,ScoreYMultiplier(2)); };
		judgmentstats[#judgmentstats+1] = MakeJudgmentsFont(GetTNS("TapNoteScore_W3",stats)) .. { InitCommand=cmd(y,ScoreYMultiplier(3)); };
		judgmentstats[#judgmentstats+1] = MakeJudgmentsFont(GetTNS("TapNoteScore_W4",stats)) .. { InitCommand=cmd(y,ScoreYMultiplier(4)); };
		judgmentstats[#judgmentstats+1] = MakeJudgmentsFont(GetTNS("TapNoteScore_W5",stats)) .. { InitCommand=cmd(y,ScoreYMultiplier(5)); };
		judgmentstats[#judgmentstats+1] = MakeJudgmentsFont(GetTNS("TapNoteScore_Miss",stats)) .. { InitCommand=cmd(y,ScoreYMultiplier(6)); };
		judgmentstats[#judgmentstats+1] = MakeJudgmentsFont(GetHNS("HoldNoteScore_Held",stats)) .. { InitCommand=cmd(y,ScoreYMultiplier(8)); };
		judgmentstats[#judgmentstats+1] = MakeJudgmentsFont(GetHNS("HoldNoteScore_LetGo",stats)) .. { InitCommand=cmd(y,ScoreYMultiplier(9)); };
		judgmentstats[#judgmentstats+1] = MakeJudgmentsFont(stats:MaxCombo()) .. { InitCommand=cmd(y,ScoreYMultiplier(10.25);horizalign,comboalign;x,combox); };
	end
	
	if pn == PLAYER_1 then --do once
		Judgments[#Judgments+1] = judgmentlabels;
	end
	Judgments[#Judgments+1] = judgmentstats;
	
	--awards
	function MakeRewardFont(label)
		local Font = LoadFont("System") .. { Text=label; InitCommand=cmd(shadowlength,0;settext,label); };
		return Font;
	end;
    local awardalign = (pn == PLAYER_1) and SCREEN_CENTER_X-128-16 or SCREEN_CENTER_X+128+16;
    local awardhoriz = (pn == PLAYER_1) and 1 or 0;
	Awards[#Awards+1] = MakeRewardFont("It's a New Record!") .. {
		InitCommand=function(self)
            self:x(awardalign);
			self:y(16);
            self:halign(awardhoriz);
			self:diffuseshift();
			self:effectcolor1(color("#00aeef"));
			self:visible(stats:GetMachineHighScoreIndex() == 0);
            end;
	    };
    Awards[#Awards+1] = MakeRewardFont("New Personal Record") .. {
		InitCommand=function(self)
            self:x(awardalign);
			self:y(32);
            self:halign(awardhoriz);
			self:diffuseshift();
			self:effectcolor1(1,1,0,1);
			self:visible(stats:GetPersonalHighScoreIndex() == 0);
		end;
	};
    local Frame = Def.ActorFrame { };
    Frame[#Frame+1] = Grades;
    Frame[#Frame+1] = Judgments;
    Frame[#Frame+1] = Awards;
    t[#t+1] = Frame;
end;

t[#t+1] = Def.ActorFrame { InitCommand=cmd(x,SCREEN_CENTER_X;y,SCREEN_BOTTOM-60-32);
	Def.Sprite {
		InitCommand=cmd();
		BeginCommand=function(self)
			local banner = Current:GetBannerPath();
			if banner == nil then
				self:LoadBanner( THEME:GetPathG("Common","fallback banner") );
			else
				self:LoadBanner( banner );
			end
			self:scaletoclipped(256, 80);
		end;
	};
	LoadActor( "_banner frame" ) .. {};
	LoadFont("System") .. {
		InitCommand=cmd(shadowlength,0;y,-40-16);
		BeginCommand=function(self)
			local text = Current:GetDisplayFullTitle();
			self:settext(text);
		end;
	};
};


return t;
--~ local Top = Def.ActorFrame {
--~     Def.ActorFrame { InitCommand=cmd(y,SCREEN_TOP+60+64+8);
--~         -- Include Rewards
--~         Def.ActorFrame { InitCommand=cmd(x,SCREEN_LEFT+96;y,64+8); 
--~             MakeAwardFont("100 Combo!") .. { InitCommand=cmd(y,ScoreYMultiplier(0)); };
--~             MakeAwardFont("200 Combo!") .. { InitCommand=cmd(y,ScoreYMultiplier(1)); };
--~             MakeAwardFont("300 Combo!") .. { InitCommand=cmd(y,ScoreYMultiplier(2)); };
--~             MakeAwardFont("400 Combo!") .. { InitCommand=cmd(y,ScoreYMultiplier(3)); };
--~         };
--~     };
--~     -- Graphs
--~     Def.ActorFrame { InitCommand=cmd(y,SCREEN_BOTTOM-60-32;x,SCREEN_LEFT+80+16);
--~         LifeGraph();
--~         --MakeRewardFont("It's a New Record!") .. { InitCommand=cmd(y,32;diffuseshift;effectcolor1,color("#00aeef")); };
--~         --MakeRewardFont("New Personal Record") .. { InitCommand=cmd(y,32+16;diffuseshift;effectcolor1,1,1,0,1); };
--~         MakeDifficultyLabel("10 Oni") .. { InitCommand=cmd(y,-32); };
--~     };
--~ };

--~ return Top;