
-- Gestion des liste d'objets à trouver -> ce n'est pas l'inventaire donc !

.namespace ObjectManager

TEXTPOSNORMAL = {x =97,y =362}
TEXTPOSCOLOR = {x =97,y =362}

TEXTPOSENUMERATE = {x =97,y =362}
TEXTPOSPIECE = { x = 97,y = 362}

NBSHAPEBYCOLLUMN = 3 --nombre d'ombre par colonne
SHAPECASESIZE = 85

BARTEXTPOS = {x = -60,y = 10}

SHAPEFADELENGTH = 1 --temps de fade poour les ombres

g_lasttimepickedobject = 0

TEXTCOLORSEARCH = --correspondance textes
{
	Orange = "obj_search_color_orange",
	Rouge = "obj_search_color_red",
	Bleu = "obj_search_color_blue",
	Vert = "obj_search_color_green",
	Gris = "obj_search_color_grey",
}

COLORVALUE = --correspondance textes
{
	Orange = {r=212,b=10,g = 103},
	Rouge = {r=150,b=29,g=42},
	Bleu = {r=0,b=255,g=0},
	Vert = {r=0,b=0,g=255},
	Gris = {r=128,b=128,g=128},
}

COLORTEXTSTARTX = 40
COLORTEXTSTARTSECONDX = COLORTEXTSTARTX + 60 
COLORTEXTINTERLIGNE = 30
COLORMIDDLETEXTPOSY = 530


g_curpagetext = 0 --indique si on est sur la seconde page pour les noms

NBTEXTTODISPLAY = 9 -- on fait par vague de NBTEXTTODISPLAY pour les recherches par nom

--ces objets sont prioritaires pour le tuto
PRIORITYOBJECT = {"obj_01_couteau","obj_01_bougie"}

HARDTOFINDSPRITE = "media/common/graph/interface/InGame/RightwingInterface/int_hardtofind.png"
HARDTOFINDSPRITETUTO = "media/common/graph/interface/InGame/RightwingInterface/int_hardtofind_highlight.png"

SHIFTXSPRITEHARDTOFINDFROMTEXT = -25
SHIFTYSPRITEHARDTOFINDFROMTEXT = 11

NBCOLORTEXTBYCOLLUMN = 8

g_objcurrentlypicked = {} -- objets dont les particules sont en train de tourner
g_objectsearchlist = {} -- 0 = trouvé, 1 ou n = n objets encore à trouver, nil objets par dans la liste 


g_needcloseupconsigne = false -- indique si on est mode closeup avec un seul type d'objet ou en mode liste
g_uniquetextcreated = "" -- indique si on est en recherche closeups avec un seul type d'élément

TUTOTEXT = 
{
	[1] = "msg_ig_tuto21",
	[2] = "msg_ig_tuto20",
	[3] = "msg_ig_tuto19",
	[4] = "msg_ig_tuto18",
}

function OnEnable()
	--.member test = "toto"
	--test = "toto"
	--OPLog.Log(test)
	self.todelete = {}
	
	AssertPopup( ObjectData ~= nil, "prob  : confobject.lua est corrompu !!!")
	
	-- SearchInterface_Compteur.Flags_Visible = false
	-- Search_Interface_CompteurOmbre.Flags_Visible = false
end

function BuildObjects(name,parents)


	local name = string.lower(name)
	
	--on reset la liste pour les indices
	g_objectsearchlist = {}
	
	local isacloseup =  string.find(name,"_cup") 
	

	
	OPLog.Log("build object "..name)
	
	local nbobject = 0
	for objname ,tab in pairs(ObjectData) do
		if not SampleLevel.IsRegistered(objname.."_picked") then --on rajoute ces variables dans la datarray du level en cours
			--OPLog.Log("register de "..objname.."_picked")
			SampleLevel.RegisterValue(objname.."_picked",false)
		end
		
		--on crée l'unit même si elle a déjà été prise, par contre on la désactive
		if tab.screen == name then
			--on vérifie qu'une unit du même nom n'existe pas déjà
			AssertPopup( unit(objname) == nil , "erreur "..objname.. " est déjà crée !" )
		
			local ut
			if isacloseup then
				-- ut = OPUnitFactory.CreateUnit("CloseupObject")
				ut = OPUnitFactory.CreateUnit("Object")
				-- ut.Image = "media/graph/world/"..string.sub(name,1,3).."/"..name.."/"..tab.image
				ut.Image = "media/graph/world/"..string.sub(name,1,3).."/"..tab.image
			else
				ut = OPUnitFactory.CreateUnit("Object")
				ut.Image = "media/graph/world/"..name.."/"..tab.image
			end
			
			if SampleLevel.IsEqual(objname.."_picked",true) then
				ut.Enabled = false
			end
			
			ut.Position_X = tab.positionx
			ut.Position_Y = tab.positiony
			ut.Name = objname
			ut.IsDifficult = tab.difficult
			ut.TypeObj = tab.typeobj
			ut.IdText = tab.idtext
			
			if tab.refpointx ~= 0 or tab.refpointy ~= 0 then
				ut.refpointx = tab.refpointx
				ut.refpointy = tab.refpointy
			end
			
			if parents ~= nil then
				AssertPopup(parents[tab.layer] ~= nil , "prob sur le layer de l'objet ! "..objname)
			
				ut.Parent = parents[tab.layer]
				
				--if string.find(ut.Parent.Name,"foreground") then
				ut.Position_Y = ut.Position_Y - ut.Parent.InitPosY
				ut.Position_X = ut.Position_X - ut.Parent.InitPosX
				--end
			end
			
			nbobject = nbobject +1
			
			--OPLog.Log("création de l'unit "..ut.Name.." "..ut.Image)
		end
	end
	
	g_curcolor = nil
	SearchInfo.Flags_Visible = false
	
	
	return nbobject
end

function CleanOldUnit()

	SpriteFader.StopAll()
	if self.todelete ~= nil then
		for u,ut in pairs(self.todelete) do
				OPUnitFactory.CloseUnit(ut)
		end
	end
		
	self.todelete = {}
	
	SearchInfo.Flags_Visible = false
	
	g_objectsearchlist = {}
	

end


--code de recherche - à mettre dans une autre unit peut être ?
function LaunchNewResearch(screenname, typesearch)

	
	if SearchActivated() then
		AssertPopup(false , "recherche déjà lancé automatiquement, appel spécifique à virer !")
	end



	screenname = string.lower(screenname)
	if (typesearch == nil) then
		g_cursearch = math.random(4)
	else
		g_cursearch = typesearch
		AssertPopup(type(typesearch) == "number" ,"prob pas de paramétres de type de recherche ")	
	end
	
	OPLog.Log("cursearch "..g_cursearch)
	
	AssertPopup(type(screenname) == "string" ,"prob pas de paramétres d'écran ")	
	
	--g_cursearch = SEARCHBYPIECES
	g_totalobjnb = 0
	g_foundobject = 0
	g_lastscreenname = screenname --pour relancer une autre liste, temporaire !!
	g_needcloseupconsigne = false 

	CleanOldUnit()

	--on calcule la liste des objets à chercher
	
	
	
	if g_cursearch == SEARCHBYCOLOR then
		for name,tab in pairs(ObjectData) do
			if tab.screen == screenname then
				if tab.typeobj == "Couleur" and (tab.couleur == g_curcolor or g_curcolor == nil) then
					if (g_curcolor == nil) then
						g_curcolor = tab.couleur
					end					
					g_objectsearchlist[name] = 1
					g_totalobjnb = g_totalobjnb + 1
				end
			end
		end
				
		CreateColorTexts()
	
	elseif g_cursearch == SEARCHBYNAME or g_cursearch == SEARCHINCLOSEUPBYNAME then
		local displaytext = false
		g_uniquetextcreated = ""
		g_needcloseupconsigne = true
		for name,tab in pairs(ObjectData) do
			local curfirstobj = "zzzz"
			
			if tab.screen == screenname then
				--on différencie les noms dans liste nom et les noms dans les liste closeups
				if (tab.typeobj == "Nom" and g_cursearch == SEARCHBYNAME) or (tab.typeobj == "NomCloseup" and g_cursearch == SEARCHINCLOSEUPBYNAME)  
				or tab.typeobj == "Enum" or (tab.typeobj == "Closeup" and g_cursearch == SEARCHINCLOSEUPBYNAME) then
			
					if g_objectsearchlist[name] == nil then
						g_objectsearchlist[name] = 1
					end
						
					--attention on n'affiche les noms pour le type closeup (comme avant pour la lettre par ex)	
					if tab.typeobj == "Nom" or tab.typeobj == "NomCloseup"  or tab.typeobj == "Enum" then
						displaytext = true
						OPLog.Log("hello: "..tab.idtext)
						CreateTextObject(tab,name) --on envoie name pour les deux car il faut bien différencier l'idtext et le unit objet qui a son nom propre
						g_needcloseupconsigne = false -- c'est donc une liste, pas de consigne en haut
					end
					
					--dernier modif : on affiche juste le nom dans la liste SANS le chiffre entre parenthéses
					if tab.typeobj == "Closeup" and g_uniquetextcreated == "" then
						curfirstobj = name
						local idmsg = "msg_ig_inventaire_"..CURRENTCHAPTER.."_"..string.gsub(GetSearchName(),"_Closeup_search_5","")
						OPLog.Log("idmsg "..idmsg)
						tab.idtext = idmsg
						CreateTextObject(tab,name)
						g_uniquetextcreated = name
						displaytext = true
					end
				
					g_totalobjnb = g_totalobjnb + 1

				end
			end
		end
		
		if displaytext then --on affiche le texte que si on a du enum ou du nom
			g_curpagetext = 0
			UpdateTexts(0)
		end
	
	elseif g_cursearch == SEARCHBYSHAPE then
		g_activeshapelist = {}
		for name,tab in pairs(ObjectData) do
			if tab.screen == screenname then
				if tab.typeobj == "Ombre" then
					g_objectsearchlist[name] = 1
					g_totalobjnb = g_totalobjnb + 1
					CreateShapeSprite(tab,name)
				end
			end
		end
		
		UpdateShapePositions(true)
	
	elseif g_cursearch == SEARCHBYPIECES or g_cursearch == SEARCHINCLOSEUPBYPIECES then --gérer le cas plusieurs blocs avec morceaux dans une piéce ?
		local firstobject = true
		for name,tab in pairs(ObjectData) do
			if tab.screen == screenname then
				if tab.typeobj == "Decoupe" or tab.typeobj == "DecoupeCloseup" then
					if firstobject then
						firstobject = false
						
					end
					g_objectsearchlist[name] = 1
					g_totalobjnb = g_totalobjnb + 1
				end
			end
			
			
		end
		
		CreateCompleteSprites() --crée les sprite de recherche à partir de la recherche en cours
	else 
		AssertPopup(false,"prob random cursearch "..tostring(g_cursearch))	
	end
	
	AssertPopup(g_totalobjnb >0,"prob liste d'objet vide !! " ..screenname.." type recherche : "..g_cursearch)	
	
	ShowInstructions( true)
		
	UpdateInterface()
		
	SampleLevel.Set(GetSearchName(),"started")
	-- if SampleLevel.IsEqual(GetSearchName(),"started") then
		-- OPLog.Log("GOOD "..GetSearchName())
	-- end
	
		--on vire les objets déjà trouvé
	for name,val in pairs(g_objectsearchlist) do
		OPLog.Log(name)
		if SampleLevel.IsEqual(name.."_picked",true) then
			OPLog.Log(name.." a déjà été fait, on le biffe ")
			OnMoveEndParticules(name) -- on relance tout le process, c'est plus simple
		end
	end

		
	return g_needcloseupconsigne
end

function ShowInstructions( firstcall)
	 if SearchActivated() and IsEqualVariables("CurrentGamePhase","SearchSite") then

	 --pour le tuto on lance la phrase correcte
		if g_cursearch == SEARCHBYCOLOR then
			--DisplaySimpleText(TEXTCOLORSEARCH[g_curcolor],6)		
		elseif g_cursearch <= 4 then
			--cas particulier (jeff)
			if firstcall == true and g_cursearch == 3 and not IsEqualVariables("currentNavManager","s01_SearchSite") then-- silhouette
				local i  = 0 -- rien
			elseif firstcall == true and g_cursearch == 1 then
				local i = 0
			else
				--DisplaySimpleText(TUTOTEXT[g_cursearch],6)
				if g_cursearch == 4 and  UserData.IsEqual("displayTutorial", true) then
						NewTutorialManager.OpenPopupTuto(TUTOTEXT[4],nil,180,394,"waitforanyclic")
						popups_tuto.SetFrame(1)
				end
			end
			
		end
		
		--on met la vignette du journal
		-- OPLog.Log("vignette "..g_cursearch.." "..GetCurrentManager().ClassName)		
		-- if g_cursearch ~= SEARCHBYPIECES and (g_cursearch ~= SEARCHINCLOSEUPBYNAME) then 
			-- -- Search_Polaroid.SetFrame(3)
		-- end
	 end
end

--renvoit l'unit objet poour l'aide
function GetNextObject()

	GetObjectCurrentlyPicked()
	
	for name,val in pairs(g_objectsearchlist) do
		if g_objectsearchlist[name] == 1 and CheckPickableObjetAndGetPosForParticules(name) ~= nil and g_objcurrentlypicked[name] == nil then
			return unit(name) 
		end
	end
	
	return nil
end

function GetObjectCurrentlyPicked()
	g_objcurrentlypicked = {}
	ApplyToClass("TakeObjectEffect",CheckParticules)
	
	OPLog.Log(" g_objcurrentlypicked "..GlobalFunctions.Display(g_objcurrentlypicked))
end

function CheckParticules(ut)
	if ut.objectattached ~= nil then
		g_objcurrentlypicked[ut.objectattached] = true
	end
end

--appeler onmovened particules plutot
function PickObject(objname)

		--rajout d'un callback
		--On verifie que l'objet n'a pas déjà été trouvé pour eviter la répétition des dialogues/popups
	g_lasttimepickedobject = OPTime.GetTime()
	SampleLevel.Set(objname.."_picked",true)
	
	local posres={}
	
	AssertPopup(g_objectsearchlist[objname] == 1, "prob objet déjà trouvé !! "..objname)
	OPLog.Log("blabla: "..g_foundobject)
	if g_objectsearchlist[objname] > 0 then
		g_objectsearchlist[objname] = g_objectsearchlist[objname] - 1
		g_foundobject = g_foundobject + 1
		
		g_lastobjfound = objname --pour mettre à jour à la fin des particules
		

		
		--cas particulier tuto
		-- if IsEqualVariables("CurrentGamePhase","Tutorial") then
			-- TutorialManager.OnPickListObject()
		-- end
		
	
	end
	SaveManager.saveGame("Profil"..ProfilConfig.Get("CurrentProfil"))
	return true
end

--renvoit la position pour le mouvement de particules et indique en même temps si l'unit est cliquable
function CheckPickableObjetAndGetPosForParticules(objname)
	local text
	
	if g_objectsearchlist[objname] == nil then
		return nil
	end
	
	--cas particulier ombre, si on le voit pas dans la liste -> on invalide le click
	if g_cursearch == SEARCHBYSHAPE and unit(objname.."_ombre").Flags_Visible == false then
		return nil
	end
	
	--on vérifie dans le cas recherche par texte que le nom est bien affiché
	 if g_cursearch == SEARCHBYNAME then
		text = Load(objname.."_text","TTFText")
		if unit(objname).TypeObj == "Enum" then
			text = Load(unit(objname).IdText.."_text","TTFText")
		end	 
		if text.Flags_Visible == false then
			return nil
		end
	end
	
	
	

	local posres={}
	
	AssertPopup(g_objectsearchlist[objname] == 1, "prob objet déjà trouvé !! "..objname)

	if g_cursearch == SEARCHBYSHAPE then
		local shape = Load(objname.."_ombre","Sprite")
		posres = GetCenter(shape)
	elseif g_cursearch == SEARCHBYNAME or g_cursearch == SEARCHBYCOLOR then
		
		
		posres.x = text.Position_X
		posres.y = text.Position_Y
	elseif g_cursearch == SEARCHBYPIECES then
		local ut = Load(objname.."_int","Sprite")
		posres = GetCenter(ut)
	else
		posres.x = 97 --par défaut, à régler
		posres.y = 388
	end
	
	return posres
end

--on met à jour l'interface quand la trainée de particules a fini
--TODO : bizarre de séparer interfacelist et le text , à revoir ??
	function OnMoveEndParticules(obj)
	AssertPopup(type(obj) == "string" , "prob param")
	
	OPLog.Log("Tried to get"..obj.." in "..GetCurrentManager().Name)
	
	if GetVariables("CurrentGamePhase") == "Transition" then
		OPLog.Log("OnMoveEnd started in transition phase; ignoring")
		return
	end
	
	PickObject(obj)
	
	UpdateInterfaceList(g_lastobjfound)
	
	UpdateInterface()
	
	if unit(obj).IsDifficult then
		OPLog.Log("special effet objet difficile !")
		--TODO à faire
	end
	
	if g_foundobject == g_totalobjnb then
		--FIN DE LA RECHERCHE
		DisplayTextEndSearch()	
		return
	end
	if GetCurrentManager().OnPickObject ~= nil then
		GetCurrentManager().OnPickObject(obj)
	end	
end

function DisplayTextEndSearch()

	g_curcolor = nil
	
	local keyword = ConvertToEndKeyword(GetSearchName())
	
	--il y a un stop allfade dans le cleanoldunit, donc il faut le faire AVANT la popup
	CleanOldUnit()
	if keyword ~= nil then
		SubtitlesDisplay.Enabled = true
		--on lance la popup NON c'est lancé dans inventorymanager finalement
		--PopupManager.OpenPopup(keyword,self)
	end
	
	SampleLevel.Set(GetSearchName(),"finished") --dataarray à mettre en param peut être ?
	SearchInfo.Flags_Visible = false

	self.sentenceobjecttoplay = keyword
	
	
	OPUnitFactory.GetUnit(GetVariables("currentNavManager")).OnSearchEnd(g_cursearch)
	PlaySoundEffect("gmp_finishlist")
	-- if g_cursearch == SEARCHBYSHAPE or g_cursearch == SEARCHBYNAME or g_cursearch == SEARCHBYCOLOR or g_cursearch == SEARCHBYPIECES then
		-- PlaySoundEffect("int_liste02")
	-- else
		-- --son fin de close up 
	-- end
end


function GetRemainingEnumObject(objut)
	local res = 0
	
	for name,val in pairs(g_objectsearchlist) do
		if unit(name).IdText == objut.IdText and val > 0  then
			res = res + 1
		end		
	end

	return res
end


--raye un nom ou vire un shape, pour l'objet donné
function UpdateInterfaceList(objname)
	if g_cursearch == SEARCHBYSHAPE then
		local shape = Load(objname.."_ombre","Sprite")
		SpriteFader.Fade(shape,false,SHAPEFADELENGTH,self)
	elseif g_cursearch == SEARCHBYNAME or g_cursearch == SEARCHINCLOSEUPBYNAME then
		local text	
		if unit(objname).TypeObj == "Closeup" then
			return
		end
		
		if unit(objname).TypeObj == "Enum" then
			local nbobj = GetRemainingEnumObject(unit(objname))
			text = Load(unit(objname).IdText.."_text","TTFText")
			
			--on met à jour
			text.Text = GlobalFunctions.GetText(unit(objname).IdText).." ("..nbobj..")"
			
			if nbobj > 0 then --s'il reste des objets on barre pas
				return
			end
		else
			text = Load(objname.."_text","TTFText")
		end
		
		local bar = OPUnitFactory.CreateUnit("Sprite")
		bar.Parent = text
		bar.Image = "media/common/graph/interface/InGame/LeftInterface/liste_rayure.png"
		bar.Position_X = BARTEXTPOS.x
		bar.Position_Y = BARTEXTPOS.y
		SpriteFader.Fade(bar,true,SHAPEFADELENGTH,self)
		--on l'ajoute pas à todelete car leur parent est dynamique donc ils seront supprimé avec
		--table.insert(self.todelete,bar)
	elseif g_cursearch == SEARCHBYPIECES or g_cursearch == SEARCHINCLOSEUPBYPIECES then
		local piece = Load(objname.."_int","Sprite")
		SpriteFader.Fade(piece,true,SHAPEFADELENGTH)
	elseif g_cursearch == SEARCHBYCOLOR then
		local textnb = Load(objname.."_text","TTFText")
		SpriteFader.Fade(textnb,false,SHAPEFADELENGTH)
	end	
end

--fin du fade poour les ombres
--on refraichit l'interface de recherche
function OnFaderEnd(ut)
	if g_cursearch == SEARCHBYSHAPE then
		UpdateShapePositions(false)
		ut.Enabled = false
	elseif g_cursearch == SEARCHBYNAME then
		UpdateTexts(0)
	end
end

NBSHAPESLOT = 6

function UpdateShapePositions(firstime)
	local curshapecolx = 0
	
	local alreadyfound = {}
		
	--on met à jour la shapeactivelist et alreadyfound pour que ce soit bien visible
	for i = 1,NBSHAPESLOT do
		if g_activeshapelist[i] ~= nil then
			alreadyfound[g_activeshapelist[i]] = true
		end
	
		if g_activeshapelist[i] ~= nil and g_objectsearchlist[g_activeshapelist[i]] == 0 then
			g_activeshapelist[i] = nil
		end
	end
	

	

	for i = 1 , NBSHAPESLOT do
		if g_activeshapelist[i] == nil then
			for objname,state in pairs(g_objectsearchlist) do
				local ut = Load(objname.."_ombre","Sprite")
				if (state > 0 and alreadyfound[objname] == nil) then
					ut.Position_Y = AREASHAPE.ymin 
					ut.Position_X = MARGIN
					SpriteMover.Move(ut,Vector:new(MARGIN + math.floor((i-1)/NBSHAPEBYCOLLUMN) * COLSHAPEWIDTH + ut.shiftx,
					AREASHAPE.ymin + math.mod((i-1),NBSHAPEBYCOLLUMN) * SHAPECASESIZE + ut.shifty),MOVESHAPESPEED)

					g_activeshapelist[i] = objname --on met le nom au slot numéro 6
					ut.Flags_Visible = true
					alreadyfound[objname] = true
					break
				end
			end
		end
	end
	
	--on les autres ts par défaut
	for objname,state in pairs(g_objectsearchlist) do
		if alreadyfound[objname] == nil then
			local ut = Load(objname.."_ombre","Sprite")
			ut.Flags_Visible = false
		end
	end
	
	
	--OPLog.Log("curshapecolx en sortie "..curshapecolx)
end

--met à jour les positions des textes et leur états

INTERLIGNEMAX = 35 -- quand on a 5 lignes seulement
INTERLIGNEMIN = 20
STARTEXTX = 30
MIDDLETEXTPOSY = 545

--prend en compte les enum
function GetRealTotalNbObject()
	local res = 0
	local tab = {}
	for name,val in pairs(g_objectsearchlist) do
		if unit(name).TypeObj == "Enum" then
			if tab[unit(name).IdText] == nil then
				res = res + 1
				tab[unit(name).IdText] = true
			end
		else
			res = res + 1
		end
	end
	
	OPLog.Log("GetRealTotalNbObject nb obj "..res)
	
	return res
end

STARTYKARIM = 399
INTERLIGNEKARIM = 24.5

function UpdateTexts(nb)
	if nb > 10 then
		AssertPopup(false, "erreur appel recursif sur UpdateTexts")
	end

	local compteur = 0
	local compteurfound = 0
	local needtoloopagain = false
	local tabsorted = {}
	local currenttextbypages = 0
	
	local nbtotalpage = 1
	
	local totalnbobj = GetRealTotalNbObject()
	
	while totalnbobj > (nbtotalpage * NBTEXTTODISPLAY) do
		nbtotalpage = nbtotalpage + 1
	end
	
	currenttextbypages = math.floor(totalnbobj / nbtotalpage)
	
	if (totalnbobj / nbtotalpage) > math.floor(totalnbobj / nbtotalpage) then --on arrondit à l'unité supérieur
		currenttextbypages = currenttextbypages +1
	end
	
	--OPLog.Log("currenttextbypages totalnbobj g_curpagetext"..currenttextbypages.." "..totalnbobj.." "..g_curpagetext)
	
	local interligne = currenttextbypages / NBTEXTTODISPLAY * INTERLIGNEMIN + (1 - currenttextbypages / NBTEXTTODISPLAY ) * INTERLIGNEMAX
	local starty = math.floor(MIDDLETEXTPOSY - (currenttextbypages * interligne)/2 )
	
	
	--OPLog.Log(" starty "..starty.." interligne "..interligne)
	--premier parcours pour trier les textes par nom
	local tabenum = {}
	
	for objname,state in pairs(g_objectsearchlist) do --on ne prend en compte l'enum qu'une seule fois
		if unit(objname).TypeObj == "Enum" then
			if tabenum[unit(objname).IdText] == nil then
				table.insert(tabsorted,objname)
				tabenum[unit(objname).IdText] = true
			end
		else
			table.insert(tabsorted,objname)
		end
	end
	
	--OPLog.Log(GlobalFunctions.Display(tabsorted))
	table.sort(tabsorted,SortObject)
	--OPLog.Log(GlobalFunctions.Display(tabsorted))
	
	for ind,objname in pairs(tabsorted) do
		local ut
		
		--cas ultra particluer closeup avec une seule liste
		--on a un seul identifiant text donc on sort sinon
		if g_uniquetextcreated ~= "" then
			objname = g_uniquetextcreated 
		end
		
		if unit(objname).TypeObj == "Enum" then	
			ut = Load(unit(objname).IdText.."_text","TTFText")
		else
			ut = Load(objname.."_text","TTFText")
		end
		
		if ut == nil then
			AssertPopup( false, "prob sur les id text !!!")
			return
		end
		
		local state = g_objectsearchlist[objname]
		
		ut.Position_X = STARTEXTX
		ut.Position_Y = (compteur - (currenttextbypages*g_curpagetext))*interligne + starty	
		
		if state > 0 then						
			compteurfound = compteurfound + 1
			--OPLog.Log(objname.." pas encore trouvé")
		end
		
		-- on met -1 pour les erreurs d'arrondies
		ut.Flags_Visible = (nbtotalpage == 1) or ((ut.Position_Y >= starty) and ut.Position_Y < (starty + currenttextbypages*interligne - 1))
		
		
		compteur = compteur + 1
		
		--OPLog.Log("compteurfound | compteur | palier "..compteurfound.." "..compteur.." "..(currenttextbypages-1) * (g_curpagetext+1))
		if (compteurfound == 0 and compteur >= (currenttextbypages) * (g_curpagetext+1)) then--si on a pas trouvé d'élément on passe à la page suivante
			needtoloopagain = true
			g_curpagetext = g_curpagetext + 1
			--OPLog.Log("changement de page"..g_curpagetext)
		end
		
		if g_uniquetextcreated ~= "" then --on a un seul élément dans ce mode on quitte direct
			--on surchager la position du texte
			ut.Position_Y = 418
			ut.Position_X = 16
			break		
		end
	end
	
	if needtoloopagain then
		UpdateTexts(nb+1)
	end
end

function SortObject(obj1,obj2)
	
	if IsIn(PRIORITYOBJECT,obj2) then
		return false
	end
	
	if IsIn(PRIORITYOBJECT,obj1) then
		return true
	end
	
	return obj1 < obj2
end

--nous donne le mot clé de la phase de fin de recherche
function ConvertToEndKeyword( name)
	local s = "liste_"..CURRENTCHAPTER.."_"..name
	s = string.gsub(s,"_1","_nom")
	s = string.gsub(s,"_2","_couleur")
	s = string.gsub(s,"_3","_ombre")
	s = string.gsub(s,"_4","_portions")
	s = string.gsub(s,"_5","_closeup")
	s = string.gsub(s,"_search","")
	
	--cas particulier closeup
	s = string.gsub(s,"Closeup_","")
	
	if TextData['fre'][s] == nil then
		s = string.gsub(s,"cup%d%d_","")
	end

	
	if TextData['fre'][s] == nil then
		OPLog.Log("attention pas de texte pour cette recherche !!!" .. s)
		return nil
	end
	
	return s
end

function GetSearchName() --renvoit le nom de lentrée dans le dataarray correspondant
	return string.gsub(GetCurrentManager().Name.."_search_"..g_cursearch,"SearchSite_","")
end


-- POSCOMPLETEPIECE = {y=426}

PIECESCOMPLETESHIFTY = 421
HEIGHTPAPER = 295
WIDTHPAPER = 194

--on utilise le suffixe _int pour indique que c'est le sprite complet
function CreateCompleteSprites()
	--création du sprite noir et blanc
	--path = "media/graph/world/"..g_lastscreenname.."/"..string.gsub(tab.image,"decoupe_%d%d","decoupe")
	
	--en x on positionne au milieu de la feuille	
	
	local xpiece, ypiece
	local firstname = true
	local path
	for objname,state in pairs(g_objectsearchlist) do
		if firstname then
			firstname = false
			local ut = OPUnitFactory.CreateUnit("Sprite")
			-- path = "media/graph/world/"..g_lastscreenname.."/"..string.gsub(objname,"_portions%d%d","_NB")..".png"
			path = "media/graph/world/"..string.sub(g_lastscreenname,0,3).."/"..string.gsub(objname,"(_p%a*%d+)","_NB")..".png"
			ut.Image = path
			ut.Name = objname.."_NB"
			--ut.Parent = SearchInterface
			if DebugOptions.interfaceVersion == 2 then
				ut.Parent = LeftInterface_bg
			else
				ut.Parent = SearchInterface
			end
			xpiece = WIDTHPAPER/2 - ut.Dimension_Width/2 
			ut.Position_X = xpiece
			-- ut.Position_Y = POSCOMPLETEPIECE.y
			ypiece = HEIGHTPAPER/2 - ut.Dimension_Height/2 + PIECESCOMPLETESHIFTY
			ut.Position_Y = ypiece
			table.insert(self.todelete,ut)
		end
		
		local ut = OPUnitFactory.CreateUnit("Sprite")
		ut.Position_X = xpiece
		-- ut.Position_Y = POSCOMPLETEPIECE.y
		ut.Position_Y = ypiece
		path = "media/graph/world/"..string.sub(g_lastscreenname,0,3).."/"..objname.."_int.png"
		ut.Image = path
		ut.Name = objname.."_int"
			if DebugOptions.interfaceVersion == 2 then
				ut.Parent = LeftInterface_bg
			else
				ut.Parent = SearchInterface
			end
		ut.Color.a = 0
		table.insert(self.todelete,ut)
	end
	

end


AREASHAPE = {ymin = 402, ymax = 709}
COLSHAPEWIDTH = 95
MARGIN = 6
MOVESHAPESPEED = 8



-- cette fonction sert à créer les sprites d'ombre et à les mettre à jour aussi
function CreateShapeSprite(tab,objname)
	local ut
		
	if tab ~= nil then
		ut = OPUnitFactory.CreateUnit("Sprite")
		local path
		path = "media/graph/world/"..g_lastscreenname.."/"..tab.image
		path = string.gsub(path,".tga","_ombre.tga")
		path = string.gsub(path,".png","_ombre.png")
		ut.Image = path
		ut.Name = objname.."_ombre"
		ut.Color.a = 95
			if DebugOptions.interfaceVersion == 2 then
				ut.Parent = LeftInterface_bg
			else
				ut.Parent = SearchInterface
			end
		
		--on s'assure que la taille ne dépasse pas 100
		local maxside = math.max(ut.Dimension_Width,ut.Dimension_Height)
		if (maxside > SHAPECASESIZE) then
			local newscale = SHAPECASESIZE / maxside
			ut.Scale_X = newscale
			ut.Scale_Y = newscale
		end
		
		--pour placer l'objet au centre de la case
		ut.shiftx = (SHAPECASESIZE/2) - (ut.Dimension_Width/2)*ut.Scale_X
		ut.shifty = (SHAPECASESIZE/2) - (ut.Dimension_Height/2)*ut.Scale_Y
		
		--création pastille rouge
		if unit(objname).IsDifficult then
			local pastille = OPUnitFactory.CreateUnit("Sprite")
			pastille.Parent = ut
			pastille.Image = HARDTOFINDSPRITE
			SetCenter(pastille, Vector:new((ut.Dimension_Width/2)*ut.Scale_X ,(ut.Dimension_Height)*ut.Scale_Y - (pastille.Dimension_Height/2)) )
			
		end
		
	end
	
	

	table.insert(self.todelete,ut)	
	
end




function CreateColorTexts()
	local compteur = 1

	local starty = COLORMIDDLETEXTPOSY - ((g_totalobjnb/2) * COLORTEXTINTERLIGNE)/2 
	
	for name,state in pairs(g_objectsearchlist) do
		local ut = OPUnitFactory.CreateUnit("TTFText")
		local path
		ut.Font = "media/common/graph/fonts/amrtypen.ttf"
		ut.Text = compteur
		ut.Name = name.."_text"
		ut.Color.r = 76
		ut.Color.g = 26
		ut.Color.b = 12
			if DebugOptions.interfaceVersion == 2 then
				ut.Parent = LeftInterface_bg
			else
				ut.Parent = SearchInterface
			end
		ut.Color.r = COLORVALUE[g_curcolor].r
		ut.Color.g = COLORVALUE[g_curcolor].g
		ut.Color.b = COLORVALUE[g_curcolor].b 
		
		ut.Position_X = COLORTEXTSTARTX + math.mod(compteur-1,2)*COLORTEXTSTARTSECONDX
		ut.Position_Y = (math.floor((compteur-1)/2))*COLORTEXTINTERLIGNE + starty
		
		
		if unit(name).IsDifficult then
			local pastille = OPUnitFactory.CreateUnit("Sprite")
			pastille.Parent = ut
			pastille.Image = HARDTOFINDSPRITE
			pastille.Position_X = SHIFTXSPRITEHARDTOFINDFROMTEXT
			pastille.Position_Y = 24
			
		end
	
		table.insert(self.todelete,ut)

		compteur = compteur +1		
	end
end

function CreateTextObject(tab,objname)
	if tab.typeobj == "Enum" then --on utilise l'idtexte pour le référencer
		local nameunit = tab.idtext.."_text"
		if unit(nameunit) ~= nil then
			UpdateInterfaceList(objname)
			return
		else
			OPLog.Log(nameunit.." manquant")
		end
		
	end

	local ut = OPUnitFactory.CreateUnit("TTFText")
	local path
	ut.Font = "media/common/graph/fonts/amrtypen.ttf"
	ut.Text = string.gsub(GlobalFunctions.GetText(tab.idtext),":","")
	ut.Color.r = 76
	ut.Color.g = 26
	ut.Color.b = 12
	ut.Alignment = 1
	
	if tab.typeobj == "Enum" then --on utilise l'idtexte pour le référencer
		ut.Name = tab.idtext.."_text"
	else
		ut.Name = objname.."_text"
	end
			if DebugOptions.interfaceVersion == 2 then
				ut.Parent = LeftInterface_bg
			else
				ut.Parent = SearchInterface
			end

	--ut.Rotation = math.rad(-1.5)
	
	if unit(objname).IsDifficult then
		local pastille = OPUnitFactory.CreateUnit("PastilleHardToFind")
		pastille.Parent = ut
		pastille.Image = HARDTOFINDSPRITE
		pastille.Position_X = SHIFTXSPRITEHARDTOFINDFROMTEXT
		pastille.Position_Y = SHIFTYSPRITEHARDTOFINDFROMTEXT
	end
	
	table.insert(self.todelete,ut)	
end

--c'est pour du débug
function Cheat_FinishCurrentSearch()
	for objname,val in pairs(g_objectsearchlist) do
		if val > 0 then
			g_objectsearchlist[objname] = 1
			OnMoveEndParticules(objname)
			unit(objname).Enabled = false
		end
	end

end

--nous dit si une recherche est en cours
function SearchActivated()
	for name,b in pairs (g_objectsearchlist) do
		return true
	end
	
	return false
end

function UpdateInterface()
	--on calcule la liste des objets à chercher
	local s = ""
	s = GlobalFunctions.GetText("int_objcount_prefix")
	SearchInfo.Color.r = 255
	SearchInfo.Color.g = 255
	SearchInfo.Color.b = 255
	-- SearchInfo.AutoDimension_Y = true		
	if g_cursearch == SEARCHBYCOLOR then
		if TEXTCOLORSEARCH[g_curcolor] ~= nil then
			--s = GlobalFunctions.GetText(TEXTCOLORSEARCH[g_curcolor]).."\r" 
			s = s.." "..g_foundobject.." / " .. g_totalobjnb
			SearchInfo.Flags_Visible = true
			SearchInfo.Text = s
			SearchInfo.Position_X = TEXTPOSCOLOR.x
			SearchInfo.Position_Y = TEXTPOSCOLOR.y
			SearchInfo.Color.r = COLORVALUE[g_curcolor].r
			SearchInfo.Color.g = COLORVALUE[g_curcolor].g
			SearchInfo.Color.b = COLORVALUE[g_curcolor].b
		end

	

			
	elseif g_cursearch == SEARCHBYNAME then

		s = s.." "..g_foundobject.." / " .. g_totalobjnb
		SearchInfo.Flags_Visible = true
		SearchInfo.Text = s
		SearchInfo.Position_X = TEXTPOSNORMAL.x
		SearchInfo.Position_Y = TEXTPOSNORMAL.y
	elseif g_cursearch == SEARCHBYSHAPE then
		s = s.." "..g_foundobject.." / " .. g_totalobjnb
		SearchInfo.Flags_Visible = true
		SearchInfo.Text = s
		SearchInfo.Position_X = TEXTPOSNORMAL.x
		SearchInfo.Position_Y = TEXTPOSNORMAL.y

	elseif g_cursearch == SEARCHBYPIECES or g_cursearch == SEARCHINCLOSEUPBYPIECES then --gérer le cas plusieurs blocs avec morceaux dans une piéce ?
		
		s = s.." "..g_foundobject.." / " .. g_totalobjnb
		SearchInfo.Flags_Visible = true
		SearchInfo.Text = s
		SearchInfo.Position_X = TEXTPOSPIECE.x
		SearchInfo.Position_Y = TEXTPOSPIECE.y
		
	elseif g_cursearch == SEARCHINCLOSEUPBYNAME then 
		--on affiche en continu
		-- if IsEqualVariables("CurrentGamePhase","Closeup") and g_needcloseupconsigne then
			-- OPLog.Log("msg_ig_inventaire_"..CURRENTCHAPTER.."_"..string.gsub(GetSearchName(),"_Closeup_search_5",""))
			
			-- -- on met le texte spécifique pour chaque objets
			-- local idmsg = "msg_ig_inventaire_"..CURRENTCHAPTER.."_"..string.gsub(GetSearchName(),"_Closeup_search_5","")
			-- --DisplaySimpleText(idmsg,-1)
			-- Search_Polaroid.SetFrame(3)
			-- -- --DisplaySimpleText("msg_ig_inventaire01",-1)
			-- -- pas trop propre mais bon .... (todo à revoir ?)
			-- SubtitlesText.Text = SubtitlesText.Text.." "..g_foundobject.." / " .. g_totalobjnb
		-- end
		
		s = s.." "..g_foundobject .. " / " .. g_totalobjnb
		SearchInfo.Flags_Visible = true
		SearchInfo.Text = s
		SearchInfo.Position_X = TEXTPOSENUMERATE.x
		SearchInfo.Position_Y = TEXTPOSENUMERATE.y
	else 
		AssertPopup(false,"prob random cursearch")	
	end
	

end