-- -- File:: rockstar/helpers/collset.ms -- Description:: Rockstar Collision Set -- Utility for setting collision attributes by the collision type -- Rockstar North -- 13/10/2006 -- by Greg Smith ----------------------------------------------------------------------------- -- HISTORY -- -- 01/06/2010 -- by Luke Openshaw -- Rewrite: Added ability to set RexBounds flags. -- -- 19/01/2010 -- by Marissa Warner-Wu -- Added ability to set RexBounds flags. -- -- by Luke Openshaw -- Changed backend to XML and added support for randomised second surface baking -- -- 15/01/2007 -- by Neal D Corbett (R* Leeds) -- - Assigning collision for multiple-selected objects now works. -- - Full-size texture-preview (double-click texture-name) will now show different textures -- without having to manually close the preview-dialog. -- - Tool no longer dies when you hit "Cancel" after clicking "Get Tex List From Folder" -- -- 10/06/2010 -- GunnarD -- - Ripping out terrain shader helper functions for usage in other tool. ----------------------------------------------------------------------------- ----------------------------------------------------------------------------- -- Uses ----------------------------------------------------------------------------- filein "rockstar/util/material.ms" filein "pipeline/util/file.ms" filein "pipeline/util/string.ms" filein "rockstar/export/settings.ms" filein "rockstar/util/terrain.ms" filein "rockstar/helpers/terrain_helperFunctions.ms" ----------------------------------------------------------------------------- -- Global ----------------------------------------------------------------------------- rootDir = RsConfigGetNetworkDir() + "tex2col/" -- MARK FOR DELETE rootDirXml = RsConfigGetNetworkStreamDir() + "texture_metadata/" testDir = "c:/tex2col/" RsBlankCollName = "_BLANK" RsMakeSurePathExists rootDir -- MARK FOR DELETE RsMakeSurePathExists rootDirXml localdataname = "unknown" if maxfilename != "" then ( localdataname = RsLowercase (RsRemoveExtension maxfilename) if localdataname == "global" then ( localdataname = "unknown" ) ) m_filelocal = "" m_fileglobal = "" m_path = "" m_pathglobal = "" m_pathXml = "" m_pathglobalXml = "" m_fixFile = "" ----------------------------------------------------------------------------- -- Functions ----------------------------------------------------------------------------- fn RsSetupPaths = ( m_filelocal = localdataname + ".ini" -- MARK FOR DELETE m_fileglobal = "global.ini" -- MARK FOR DELETE m_filelocalXml = localdataname + ".xml" m_fileglobalXml = "global.xml" m_path = rootDir + m_filelocal -- MARK FOR DELETE m_pathglobal = rootDir + m_fileglobal -- MARK FOR DELETE m_pathXml = rootDirXml + m_filelocalXml m_pathglobalXml = rootDirXml + m_fileglobalXml m_fixFile = testDir + m_filelocal ) RsSetupPaths() if (rootDir != testDir) and ((getfiles m_fixFile).count > 0) then ( fixOpen = openfile m_fixFile if fixOpen != undefined then ( while eof fixOpen == false do ( fixLine = readline fixOpen fixTokens = filterstring fixLine "=" if fixTokens.count == 2 then ( setinisetting m_path "match" fixTokens[1] fixTokens[2] ) ) close fixOpen deletefile m_fixFile ) ) m_globalappend = " (Global)" CollNames = #() TexMapNames = #() TexMapsBmps = #() TexMapNamesOut = #() TexMapsBmpsOut = #() RsTexTypes = #("bmp","tga","dds") ----------------------------------------------------------------------------- -- Rollout ----------------------------------------------------------------------------- rollout CollisionTypeRoll "Select Texture and Surface Type" ( --//////////////////////////////////////////////////////////// -- interface --//////////////////////////////////////////////////////////// local FLAG_STAIRS = (bit.shift 1 0) local FLAG_NON_CLIMB = (bit.shift 1 1) local FLAG_SEE_THROUGH = (bit.shift 1 2) local FLAG_SHOOT_THROUGH = (bit.shift 1 3) local FLAG_NO_COVER = (bit.shift 1 4) local FLAG_PATH = (bit.shift 1 5) local FLAG_NO_CAMCOLL = (bit.shift 1 6) local FLAG_PED_POP = (bit.shift 1 7) local img local SECOND_SURFACE_CHANNEL = 10 local TERRAIN_PAINT_CHANNEL = 9 hyperlink lnkHelp "Help?" address:"https://devstar.rockstargames.com/wiki/index.php/Collision_Set" align:#right color:(color 0 0 255) hoverColor:(color 0 0 255) visitedColor:(color 0 0 255) listbox lstMaterials pos:[10,25] width:200 height:20 align:#center listbox lstAttr pos:[220,25] width:200 height:20 align:#center checkbox chkUnset "Display Unset Textures Only" pos:[10,295] spinner spnMinSS "Min SS depth" pos:[250,295] width:50 range:[0,1,0] spinner spnMaxSS "Max SS depth" pos:[370,295] width:50 range:[0,1,0] button btnAssignMat "Assign All" pos:[185,320] width:220 enabled:true align:#center button btnCreateMat "Create All" pos:[185,345] width:220 enabled:true align:#center button btnGetFolder "Get Tex List From Folder" pos:[185,370] width:220 enabled:true align:#center button btnToggle "Toggle Global" pos:[185,395] width:220 enabled:true align:#center button btnSnapPivot "Snap Pivots of Selected to Parent" pos:[185,420] width:220 enabled:true align:#center bitmap bmpUi pos:[18,325] width:140 height:117 -- Use the tooltip as an associated name string groupBox grpFlags "RexBounds Flags" pos:[18, 450] width:400 height:85 checkbox chkStairs "Stairs" pos:[25, 470] tooltip:"Stairs" checkbox chkClimable "Non Climable" pos:[125, 470] tooltip:"Non Climable" checkbox chkSeeThrough "See Through" pos:[225, 470] tooltip:"See Through" checkbox chkShootThrough "Shoot Through" pos:[25, 490] tooltip:"Shoot Through" checkbox chkPath "Path" pos:[125, 490] tooltip:"Path" checkbox chkSetPedPop "Set Ped Density" pos:[225, 490] tooltip:"Ped population" --enabled:false spinner spnPedDensity range:[0,7,0] pos:[330, 490] width:50 type:#integer --enabled:false checkbox chkCover "Doesn't Provide Cover" pos:[225, 510] tooltip:"Doesn't Prov Cover" checkbox chkCamera "Non Camera Collidable" pos:[25, 510] tooltip:"Non Camera Collide" local FlagControls = #(chkStairs, chkClimable, chkSeeThrough, chkShootThrough, chkPath, chkCover, chkCamera, chkSetPedPop) struct TextureElement (name, material, min_ss, max_ss, flags, matid, pedPop) --//////////////////////////////////////////////////////////// -- methods --//////////////////////////////////////////////////////////// fn GetFlagsUI = ( flags = 0 if chkStairs.checked == true then flags = bit.or flags FLAG_STAIRS if chkClimable.checked == true then flags = bit.or flags FLAG_NON_CLIMB if chkSeeThrough.checked == true then flags = bit.or flags FLAG_SEE_THROUGH if chkShootThrough.checked == true then flags = bit.or flags FLAG_SHOOT_THROUGH if chkPath.checked == true then flags = bit.or flags FLAG_PATH if chkCover.checked == true then flags = bit.or flags FLAG_NO_COVER if chkCamera.checked == true then flags = bit.or flags FLAG_NO_CAMCOLL if chkSetPedPop.checked == true then flags = bit.or flags FLAG_PED_POP print "gettign flags" print flags return flags ) fn SetFlagsUI flags = ( print "Setting flags" print flags if bit.and flags FLAG_STAIRS == FLAG_STAIRS then chkStairs.checked = true else chkStairs.checked = false if bit.and flags FLAG_NON_CLIMB == FLAG_NON_CLIMB then chkClimable.checked = true else chkClimable.checked = false if bit.and flags FLAG_SEE_THROUGH == FLAG_SEE_THROUGH then chkSeeThrough.checked = true else chkSeeThrough.checked = false if bit.and flags FLAG_SHOOT_THROUGH == FLAG_SHOOT_THROUGH then chkShootThrough.checked = true else chkShootThrough.checked = false if bit.and flags FLAG_NO_COVER == FLAG_NO_COVER then chkCover.checked = true else chkCover.checked = false if bit.and flags FLAG_PATH == FLAG_PATH then chkPath.checked = true else chkPath.checked = false if bit.and flags FLAG_NO_CAMCOLL == FLAG_NO_CAMCOLL then chkCamera.checked = true else chkCamera.checked = false if bit.and flags FLAG_PED_POP == FLAG_PED_POP then chkSetPedPop.checked = true else chkSetPedPop.checked = false ) -- XML Replacement for ini files -------------------------------------------------------------- -- -------------------------------------------------------------- fn PopulateTextureElement elem = ( texNameAttr = elem.Attributes.ItemOf( "name" ) materialAttr = elem.Attributes.ItemOf( "material" ) minSSAttr = elem.Attributes.ItemOf( "min_ss" ) maxSSAttr = elem.Attributes.ItemOf( "max_ss" ) flagsAttr = elem.Attributes.ItemOf( "flags_unfucked" ) pedPopAttr = elem.Attributes.ItemOf( "pedPop" ) local pedPop = -1 local flags = 0 if undefined!=pedPopAttr then pedPop = (pedPopAttr.value as Number) if undefined!=flagsAttr then flags = (flagsAttr.value as integer) texElem = TextureElement texNameAttr.value materialAttr.value (minSSAttr.value as float) (maxSSAttr.value as float) flags pedPop:pedPop texElem ) -------------------------------------------------------------- -- -------------------------------------------------------------- fn GetTextureElement texName filename = ( if RsFileExist filename then ( collMapDoc = XmlDocument() collMapDoc.init() collMapDoc.load filename rootElem = collMapDoc.document.DocumentElement childNodeList = rootElem.ChildNodes for i = 0 to ( childNodeList.Count - 1 ) do ( texElem = PopulateTextureElement (childNodeList.ItemOf(i)) if texElem.name == texName then return texElem ) ) return undefined ) -------------------------------------------------------------- -- -------------------------------------------------------------- fn IsDataSetXML texName = ( if GetTextureElement texName m_pathglobalXml != undefined then return true if GetTextureElement texName m_pathXml != undefined then return true xmlFiles = getfiles (rootDirXml + "*.xml") for file in xmlFiles do ( if GetTextureElement texName file != undefined then return true ) false ) -------------------------------------------------------------- -- -------------------------------------------------------------- fn GetDataSettingXML texName = ( texElem = GetTextureElement texName m_pathglobalXml if texElem != undefined then return texElem texElem = GetTextureElement texName m_pathXml if texElem != undefined then return texElem xmlFiles = getfiles (rootDirXml + "*.xml") for file in xmlFiles do ( texElem = GetTextureElement texName file if texElem != undefined then return texElem ) undefined ) -------------------------------------------------------------- -- -------------------------------------------------------------- fn SetDataSettingXML texElemIn isglobal:false = ( pathXml = "" if isglobal == false then pathXml = m_pathXml else pathXml = m_pathglobalXml collMapDoc = XmlDocument() collMapDoc.init() if RsFileExist pathXml then collMapDoc.load pathXml else ( collMapXmlRoot = collMapDoc.createelement("textures") collMapDoc.document.AppendChild collMapXmlRoot ) rootElem = collMapDoc.document.DocumentElement childNodeList = rootElem.ChildNodes exists = false for i = 0 to ( childNodeList.Count - 1 ) do ( texXmlElem = childNodeList.ItemOf(i) texElem = PopulateTextureElement texXmlElem if texElem.name == texElemIn.name then ( materialAttr = texXmlElem.Attributes.ItemOf( "material" ) minSSAttr = texXmlElem.Attributes.ItemOf( "min_ss" ) maxSSAttr = texXmlElem.Attributes.ItemOf( "max_ss" ) flagsAttr = texXmlElem.Attributes.ItemOf( "flags_unfucked" ) pedPopAttr = texXmlElem.Attributes.ItemOf( "pedPop" ) materialAttr.value = texElemIn.material minSSAttr.value = texElemIn.min_ss as string maxSSAttr.value = texElemIn.max_ss as string if flagsAttr != undefined then ( flagsAttr.value = texElemIn.flags as string ) if pedPopAttr != undefined then ( pedPopAttr.value = texElemIn.pedPop as string ) exists = true ) ) if exists == false then ( attributearray = #() newElem = collMapDoc.createelement "texture" append attributearray (Attribute "name" texElemIn.name) append attributearray (Attribute "material" texElemIn.material) append attributearray (Attribute "min_ss" texElemIn.min_ss) append attributearray (Attribute "max_ss" texElemIn.max_ss) append attributearray (Attribute "flags_unfucked" texElemIn.flags) append attributearray (Attribute "pedPop" texElemIn.pedPop) rootElem.AppendChild( RsCreateXmlElement "texture" attributearray collMapDoc ) ) collMapDoc.save pathXml ) -------------------------------------------------------------- -- -------------------------------------------------------------- fn DeleteDataSettingXML filename texName = ( collMapDoc = XmlDocument() collMapDoc.init() collMapDoc.load filename rootElem = collMapDoc.document.DocumentElement childNodeList = rootElem.ChildNodes for i = 0 to ( childNodeList.Count - 1 ) do ( texXmlElem = childNodeList.ItemOf(i) texElem = PopulateTextureElement texXmlElem if texElem.name == texName then ( collMapDoc.removechild rootElem texXmlElem collMapDoc.save filename return true ) ) false ) -------------------------------------------------------------- -- -------------------------------------------------------------- fn IsGlobalDataSettingXML texName = ( if GetTextureElement texName m_pathglobalXml != undefined then return true false ) -------------------------------------------------------------- -- -------------------------------------------------------------- fn ToggleGlobalDataSettingXML texName = ( texElem = undefined if IsGlobalDataSettingXML texName then ( texElem = GetDataSettingXML texName if DeleteDataSettingXML m_pathglobalXml texName == false then print ("Failed to delete global node for " + texName) SetDataSettingXML texElem ) else ( texElem = GetDataSettingXML texName if DeleteDataSettingXML m_pathXml texName == false then print ("Failed to delete local node for " + texName) SetDataSettingXML texElem isglobal:true ) ) -------------------------------------------------------------- -- -------------------------------------------------------------- fn IsDataSet mapName = ( attrName = getinisetting m_pathglobal "match" mapName if attrName == "" then ( attrName = getinisetting m_path "match" mapName ) iniFiles = getfiles (rootDir + "*.ini") for file in iniFiles do ( if attrName == "" and file != m_path and file != m_pathglobal then ( attrName = getinisetting file "match" mapName ) ) retval = true if attrName == "" then ( retval = false ) retval ) -------------------------------------------------------------- -- -------------------------------------------------------------- fn GetDataSetting mapName = ( attrName = getinisetting m_pathglobal "match" mapName if attrName == "" then ( attrName = getinisetting m_path "match" mapName ) iniFiles = getfiles (rootDir + "*.ini") for file in iniFiles do ( if attrName == "" and file != m_path and file != m_pathglobal then ( attrName = getinisetting file "match" mapName ) ) if attrName == "" then ( attrName = "default" ) attrName ) -------------------------------------------------------------- -- -------------------------------------------------------------- fn SetDataSetting mapName surftype isglobal:false = ( if isglobal == false then ( idxFound = getinisetting m_pathglobal "match" mapName ) else ( idxFound = surftype ) if idxFound == "" then ( setinisetting m_path "match" mapName surftype ) else ( setinisetting m_pathglobal "match" mapName surftype ) ) -------------------------------------------------------------- -- -------------------------------------------------------------- fn ToggleGlobalDataSetting mapName = ( collName = getinisetting m_pathglobal "match" mapName if collName == "" then ( collName = getinisetting m_path "match" mapName setinisetting m_pathglobal "match" mapName collName delinisetting m_path "match" mapName ) else ( setinisetting m_path "match" mapName collName delinisetting m_pathglobal "match" mapName ) ) -------------------------------------------------------------- -- -------------------------------------------------------------- fn IsGlobalDataSetting mapName = ( retval = false if (getinisetting m_pathglobal "match" mapName) != "" then retval = true retval ) -------------------------------------------------------------- -- -------------------------------------------------------------- fn GetActualMapName inMapName = ( retVal = inMapName if (inMapName.count > m_globalappend.count) then ( subVal = (substring inMapName (inMapName.count - m_globalappend.count + 1) m_globalappend.count) if subVal == m_globalappend then ( retVal = substring inMapName 1 (inMapName.count - m_globalappend.count) ) ) retVal ) -------------------------------------------------------------- -- -------------------------------------------------------------- fn FindCollTexArray colltexarray finditem = ( for i = 1 to colltexarray.count do ( if colltexarray[i].texname == finditem then ( return i ) ) 0 ) -------------------------------------------------------------- -- -------------------------------------------------------------- fn SetupList = ( sort CollNames insertitem RsBlankCollName CollNames 1 lstAttr.items = CollNames -- Select Default rather than BLANK - GTA5 #5045 idDefault = finditem lstAttr.items "DEFAULT" lstAttr.selection = idDefault ) -------------------------------------------------------------- -- Parse materials.dat file. -------------------------------------------------------------- fn ParseMaterials filename = ( matfile = openfile filename if matfile == undefined then return 0 while eof matfile == false do ( matline = readline matfile if matline.count > 0 and matline[1] != "#" and matline[1] != " " and matline[1] != "\t" then ( mattokens = filterstring matline " \t" append CollNames mattokens[1] ) ) close matfile ) -------------------------------------------------------------- -- -------------------------------------------------------------- fn UpdateTexture = ( if lstMaterials.selection > 0 then ( if TexMapsBmpsOut[lstMaterials.selection] != undefined then ( if classof TexMapsBmpsOut[lstMaterials.selection] == bitmaptexture then ( img = bitmap 140 117 rm = rendermap TexMapsBmpsOut[lstMaterials.selection] into:img size:[100,75] bmpUi.bitmap = img close rm ) else ( local bmpset = bitmaptexture() bmpset.filename = TexMapsBmpsOut[lstMaterials.selection] bmpset.reload() img = bitmap 140 117 rm = rendermap bmpset into:img size:[100,75] bmpUi.bitmap = img close rm ) ) ) ) -------------------------------------------------------------- -- -------------------------------------------------------------- fn UpdateMaterial = ( if lstMaterials.selection > 0 then ( mapName = lstMaterials.items[lstMaterials.selection] texElem = GetDataSettingXml mapName idxFind = 1 if texElem != undefined then ( idxFind = finditem lstAttr.items texElem.material spnMinSS.value = texElem.min_ss spnMaxSS.value = texElem.max_ss spnPedDensity.value = texElem.pedPop SetFlagsUI texElem.flags ) else ( SetFlagsUI 0 spnMinSS.value = 0.0 spnMaxSS.value = 0.0 spnPedDensity.value = 0 ) lstAttr.selection = idxFind ) ) -------------------------------------------------------------- -- -------------------------------------------------------------- fn UpdateTexMapList = ( TexMapNamesOut = #() TexMapsBmpsOut = #() for i = 1 to TexMapNames.count do ( mapName = RsLowercase(TexMapNames[i]) if chkUnset.checked == false or (IsDataSetXml mapName) == false do ( if IsGlobalDataSettingXml mapName then ( mapName = mapName + m_globalappend ) append TexMapNamesOut mapName append TexMapsBmpsOut TexMapsBmps[i] ) ) lstMaterials.items = TexMapNamesOut ) -------------------------------------------------------------- -- -------------------------------------------------------------- fn UpdateSelectionSet = ( TexMapNames = #() TexMapsBmps = #() for obj in selection do ( RsSetMapsFlags false true false false RsGetTexMapsFromObjWithMaps obj TexMapNames TexMapsBmps RsSetMapsFlags true true true true ) UpdateTexMapList() UpdateTexture() UpdateMaterial() ) -------------------------------------------------------------- -- -------------------------------------------------------------- fn UpdateSelectionSetFromFolderRec foldername mapNameList mapBmpList = ( fileList = #() for texType in RsTexTypes do ( fileListNew = getFiles (foldername + "*." + texType) fileList = fileList + fileListNew ) for filename in fileList do ( texName = RsLowercase(RsRemovePathAndExtension(filename)) if finditem mapNameList texName == 0 then ( append mapNameList texName append mapBmpList filename ) ) childDirs = getdirectories (foldername + "*") for dir in childDirs do ( UpdateSelectionSetFromFolderRec dir mapNameList mapBmpList ) ) -------------------------------------------------------------- -- -------------------------------------------------------------- fn UpdateSelectionSetFromFolder = ( rootfoldername = getsavepath() if (rootfoldername != undefined) do ( TexMapNames = #() TexMapsBmps = #() UpdateSelectionSetFromFolderRec rootfoldername TexMapNames TexMapsBmps ) UpdateTexMapList() UpdateTexture() UpdateMaterial() ) -------------------------------------------------------------- -- -------------------------------------------------------------- fn SetMaterial matid = ( if TexMapNames.count > 0 then ( texName = lstMaterials.items[lstMaterials.selection] if lstMaterials.selection > 0 then ( flags = GetFlagsUI() local pedPop = -1 if chkSetPedPop.checked then ( pedPop = spnPedDensity.value ) texElem = (TextureElement texName lstAttr.items[matid] spnMinSS.value spnMaxSS.value flags pedPop:pedPop) SetDataSettingXml texElem ) ) ) -------------------------------------------------------------- -- -------------------------------------------------------------- fn GetTextureElementFromMapID obj matID = ( LocalTexMapNames = #() LocalTexMapsBmps = #() collMaterial = "default" RsSetMapsFlags false true false false RsGetTexMapsFromObjWithMaps obj LocalTexMapNames LocalTexMapsBmps id:matID RsSetMapsFlags true true true true if LocalTexMapNames.count > 0 then ( texElem = GetDataSettingXml(RsLowercase(LocalTexMapNames[1])) local pedPop = -1 if chkSetPedPop.checked then ( pedPop = spnPedDensity.value ) if texElem == undefined then texElem = TextureElement (RsLowercase(LocalTexMapNames[1])) collMaterial 0.0 0.0 0 matID pedPop:pedPop return texElem ) undefined ) -------------------------------------------------------------- -- -------------------------------------------------------------- fn GetCollNameFromMapID obj matID = ( LocalTexMapNames = #() LocalTexMapsBmps = #() collMaterial = "default" RsSetMapsFlags false true false false RsGetTexMapsFromObjWithMaps obj LocalTexMapNames LocalTexMapsBmps id:matID RsSetMapsFlags true true true true if LocalTexMapNames.count > 0 then ( texElem = GetDataSettingXml(RsLowercase(LocalTexMapNames[1])) if texElem != undefined then collMaterial = texElem.material ) collMaterial ) -------------------------------------------------------------- -- -------------------------------------------------------------- fn CreateObjectMat obj = ( idxCollType = getattrindex "Gta Collision" "Coll Type" for childobj in obj.children do ( if getattrclass childobj == "Gta Collision" then delete childobj ) objFaceCollName = #() objFacesCollNameFaces = #() objFacesSSValFaces = #() objFacesFlagsFaces = #() objAllFaces = #() objMatPedPop = #() doConvertToPoly = false select obj if classof obj == Editable_Poly then ( converttomesh obj doConvertToPoly = true ) newFaceIndex = 0 if classof obj == Editable_Mesh then ( select obj subobjectlevel = 3 meshops.unhideall obj subobjectlevel = 0 numFaces = getnumfaces obj matIDList = #() colNameList = #() texElemList = #() for i = 1 to numFaces do ( matID = getfaceMatID obj i idxFound = finditem matIDList matID collName = undefined if idxFound == 0 then ( collName = GetCollNameFromMapID obj matID texElem = GetTextureElementFromMapID obj matID if texElem != undefined then ( append matIDList matID append colNameList collName append texElemList texElem ) ) else ( texElem = texElemList[idxFound] collName = texElem.material ) secondSurfaceValue = 0.0 flags = 0 pedPop = undefined if texElem != undefined then ( collName = texElem.material secondSurfaceValue = (1.0 - (random texElem.min_ss texElem.max_ss)) * 255.0 flags = texElem.flags pedPop = texElem.pedPop ) if collName != RsBlankCollName then ( newFaceIndex = newFaceIndex + 1 append objAllFaces i idxFound = finditem objFaceCollName collName if idxFound == 0 then ( append objFaceCollName collName append objFacesCollNameFaces #(newFaceIndex) append objFacesSSValFaces #(secondSurfaceValue) append objFacesFlagsFaces #(flags) append objMatPedPop pedPop ) else ( append objFacesCollNameFaces[idxFound] newFaceIndex append objFacesSSValFaces[idxFound] secondSurfaceValue append objFacesFlagsFaces[idxFound] flags ) ) ) ) else ( numFaces = polyop.getnumfaces obj for i = 1 to numFaces do ( matID = polyop.getfaceMatID obj i collName = GetCollNameFromMapID obj matID secondSurfaceValue = 0.0 flags = 0 texElem = GetTextureElementFromMapID obj matID if texElem != undefined then ( collName = texElem.material secondSurfaceValue = (random texElem.min_ss texElem.max_ss) * 255.0 flags = texElem.flags ) if collName != RsBlankCollName then ( newFaceIndex = newFaceIndex + 1 append objAllFaces i idxFound = finditem objFaceCollName collName if idxFound == 0 then ( append objFaceCollName collName append objFacesCollNameFaces #(newFaceIndex) append objFacesSSValFaces #(secondSurfaceValue) append objFacesFlagsFaces #(flags) append objMatPedPop undefined ) else ( append objFacesCollNameFaces[idxFound] newFaceIndex append objFacesSSValFaces[idxFound] secondSurfaceValue append objFacesFlagsFaces[idxFound] flags ) ) ) ) if classof obj == Editable_Mesh then ( setfaceselection obj objAllFaces ) else ( polyop.setfaceselection obj objAllFaces ) volcreate = VolumeCreate() addModifier obj volcreate volumecreatemod volcreate deleteModifier obj volcreate subobjectLevel = 0 newobj = undefined for childobj in obj.children do ( if isdeleted childobj then continue if getattrclass childobj != "Gta Collision" then continue if newobj == undefined then ( newobj = childobj ) ) if newobj != undefined then ( savetrans = newobj.transform col2mesh newobj submatlist = #() hasSecondSurface = false for i = 1 to objFaceCollName.count do ( for j = 1 to objFacesSSValFaces[i].count do ( if objFacesSSValFaces[i][j] != 0.0 then ( hasSecondSurface = true break ) ) ) for i = 1 to objFaceCollName.count do ( newsubmat = RexBoundMtl() RexSetCollisionFlags newsubmat objFacesFlagsFaces[i][1] RexSetCollisionName newsubmat objFaceCollName[i] newsubmat.name = objFaceCollName[i] if ( -1 != objMatPedPop[i] ) and ( undefined != objMatPedPop[i] ) then ( RexSetPopDensity newsubmat objMatPedPop[i] ) append submatlist newsubmat if hasSecondSurface == true then ( for j = 1 to objFacesCollNameFaces[i].count do ( setfaceMatID newobj (objFacesCollNameFaces[i][j]) i face = getface newobj.mesh objFacesCollNameFaces[i][j] meshop.setVertColor newobj.mesh SECOND_SURFACE_CHANNEL face[1] (color objFacesSSValFaces[i][j] objFacesSSValFaces[i][j] objFacesSSValFaces[i][j]) meshop.setVertColor newobj.mesh SECOND_SURFACE_CHANNEL face[2] (color objFacesSSValFaces[i][j] objFacesSSValFaces[i][j] objFacesSSValFaces[i][j]) meshop.setVertColor newobj.mesh SECOND_SURFACE_CHANNEL face[3] (color objFacesSSValFaces[i][j] objFacesSSValFaces[i][j] objFacesSSValFaces[i][j]) ) ) ) newobj.showvertexcolors = true newobj.vertexColorType = #map_channel newobj.vertexColorMapChannel = SECOND_SURFACE_CHANNEL newmat = Multimaterial() newmat.numsubs = submatlist.count newmat.materialList = submatlist newobj.material = newmat mesh2col newobj newobj.transform = savetrans ) if doConvertToPoly then ( converttopoly obj ) ) --------------------------------------------------------------- fn GetTextureElementFromMapIDAndColour obj mat matID faceId = ( local highestTexElem = GetDominantTextureFromTerrainFace obj mat matID faceId if highestTexElem != undefined then ( texElem = GetDataSettingXml(RsRemoveExtension(RsLowercase(highestTexElem.name))) ) texElem ) -------------------------------------------------------------- -- -------------------------------------------------------------- fn AssignObjectMat obj = ( idxCollType = getattrindex "Gta Collision" "Coll Type" objFacePos = #() objFaceCollName = #() objFaceSSValue = #() objFaceFlagsValue = #() if classof obj == Editable_Mesh then ( numFaces = getnumfaces obj for i = 1 to numFaces do ( faceVal = getface obj i averageVert = getvert obj faceVal[1] averageVert += getvert obj faceVal[2] averageVert += getvert obj faceVal[3] averageVert /= 3.0 append objFacePos averageVert matID = getfaceMatID obj i collName = "default" secondSurfaceValue = 0.0 flags = #{} texElem = undefined if classof obj.mat == Multimaterial and RsIsTerrainMaterial obj.mat[matID] then ( texElem = GetTextureElementFromMapIDAndColour obj obj.mat[matID] matID i ) else ( if RsIsTerrainMaterial obj.mat then ( texElem = GetTextureElementFromMapIDAndColour obj obj.mat matID i ) else texElem = GetTextureElementFromMapID obj matID ) if texElem != undefined then ( collName = texElem.material secondSurfaceValue = (1.0 - (random texElem.min_ss texElem.max_ss)) * 255.0 flags = texElem.flags ) append objFaceSSValue secondSurfaceValue append objFaceCollName collName append objFaceFlagsValue flags ) ) else if classof obj == Editable_Poly then ( numFaces = polyop.getnumfaces obj for i = 1 to numFaces do ( faceVerts = polyop.getfaceverts obj i averageVert = polyop.getvert obj faceVerts[1] for j = 2 to faceVerts.count do ( averageVert += polyop.getvert obj faceVerts[j] ) averageVert /= faceVerts.count append objFacePos averageVert matID = polyop.getfaceMatID obj i collName = "default" secondSurfaceValue = 0.0 flags = #{} texElem = undefined if classof obj.mat == Multimaterial and RsIsTerrainMaterial obj.mat[matID] then ( texElem = GetTextureElementFromMapIDAndColour obj obj.mat[matID] matID i ) else ( if RsIsTerrainMaterial obj.mat then ( texElem = GetTextureElementFromMapIDAndColour obj obj.mat matID i ) else texElem = GetTextureElementFromMapID obj matID ) if texElem != undefined then ( collName = texElem.material secondSurfaceValue = (1.0 - (random texElem.min_ss texElem.max_ss)) * 255.0 flags = texElem.flags ) append objFaceSSValue secondSurfaceValue append objFaceCollName collName append objFaceFlagsValue flags ) ) else ( return 0 ) if objFacePos.count > 1 then ( for childobj in obj.children do ( if classof childobj == Col_Mesh then ( savetrans = childobj.transform col2mesh childobj numFaces = getnumfaces childobj matchingCollNames = #() matchingCollNamesFaces = #() matchingPerFaceSSValues = #() matchingFlagValues = #() for i = 1 to numFaces do ( faceVal = getface childobj i averageVert = getvert childobj faceVal[1] averageVert += getvert childobj faceVal[2] averageVert += getvert childobj faceVal[3] averageVert /= 3.0 currentDist = distance objFacePos[1] averageVert matchingFace = 1 for j = 2 to objFacePos.count do ( newDist = distance objFacePos[j] averageVert if newDist < currentDist then ( currentDist = newDist matchingFace = j ) ) collName = objFaceCollName[matchingFace] ssValue = objFaceSSValue[matchingFace] flags = objFaceFlagsValue[matchingFace] idxFound = finditem matchingCollNames collName if idxFound == 0 then ( append matchingCollNames collName append matchingCollNamesFaces #(i) append matchingPerFaceSSValues #(ssValue) append matchingFlagValues #(flags) ) else ( append matchingCollNamesFaces[idxFound] i append matchingPerFaceSSValues[idxFound] ssValue append matchingFlagValues[idxFound] flags ) ) submatlist = #() hasSecondSurface = false for i = 1 to matchingCollNames.count do ( for j = 1 to matchingCollNamesFaces[i].count do ( if matchingPerFaceSSValues[i][j] != 0.0 then ( hasSecondSurface = true break ) ) ) for i = 1 to matchingCollNames.count do ( newsubmat = RexBoundMtl() RexSetCollisionFlags newsubmat matchingFlagValues[i] RexSetCollisionName newsubmat matchingCollNames[i] newsubmat.name = matchingCollNames[i] append submatlist newsubmat if hasSecondSurface == true then ( for j = 1 to matchingCollNamesFaces[i].count do ( setfaceMatID childobj (matchingCollNamesFaces[i][j]) i face = getface childobj.mesh matchingCollNamesFaces[i][j] meshop.setVertColor childobj.mesh SECOND_SURFACE_CHANNEL face[1] (color matchingPerFaceSSValues[i][j] matchingPerFaceSSValues[i][j] matchingPerFaceSSValues[i][j]) meshop.setVertColor childobj.mesh SECOND_SURFACE_CHANNEL face[2] (color matchingPerFaceSSValues[i][j] matchingPerFaceSSValues[i][j] matchingPerFaceSSValues[i][j]) meshop.setVertColor childobj.mesh SECOND_SURFACE_CHANNEL face[3] (color matchingPerFaceSSValues[i][j] matchingPerFaceSSValues[i][j] matchingPerFaceSSValues[i][j]) ) ) ) if hasSecondSurface == true then ( childobj.showvertexcolors = true childobj.vertexColorType = #map_channel childobj.vertexColorMapChannel = SECOND_SURFACE_CHANNEL ) newmat = Multimaterial() newmat.numsubs = submatlist.count newmat.materialList = submatlist childobj.material = newmat mesh2col childobj childobj.transform = savetrans ) ) ) ) -------------------------------------------------------------- -- -------------------------------------------------------------- fn AssignObject obj = ( idxCollType = getattrindex "Gta Collision" "Coll Type" objFacePos = #() objFaceMatID = #() if classof obj == Editable_Mesh then ( numFaces = getnumfaces obj for i = 1 to numFaces do ( faceVal = getface obj i averageVert = getvert obj faceVal[1] averageVert += getvert obj faceVal[2] averageVert += getvert obj faceVal[3] averageVert /= 3.0 append objFacePos averageVert append objFaceMatID (getfaceMatID obj i) ) ) else if classof obj == Editable_Poly then ( numFaces = polyop.getnumfaces obj for i = 1 to numFaces do ( faceVerts = polyop.getfaceverts obj i averageVert = polyop.getvert obj faceVerts[1] for j = 2 to faceVerts.count do ( averageVert += polyop.getvert obj faceVerts[j] ) averageVert /= faceVerts.count append objFacePos averageVert append objFaceMatID (polyop.getfaceMatID obj i) ) ) else ( return 0 ) if objFacePos.count > 1 then ( for childobj in obj.children do ( if classof childobj == Col_Mesh then ( savetrans = childobj.transform col2mesh childobj numFaces = getnumfaces childobj matchingFaces = #() for i = 1 to numFaces do ( faceVal = getface childobj i averageVert = getvert childobj faceVal[1] averageVert += getvert childobj faceVal[2] averageVert += getvert childobj faceVal[3] averageVert /= 3.0 currentDist = distance objFacePos[1] averageVert matchingFace = 1 for j = 2 to objFacePos.count do ( newDist = distance objFacePos[j] averageVert if newDist < currentDist then ( currentDist = newDist matchingFace = j ) ) append matchingFaces matchingFace ) -- this bit works for the old style per object collision matIDs = #() matIDCounts = #() for i = 1 to matchingFaces.count do ( matID = objFaceMatID[matchingFaces[i]] idxFound = finditem matIDs matID if idxFound == 0 then ( append matIDs matID append matIDCounts 1 ) else ( matIDCounts[idxFound] = matIDCounts[idxFound] + 1 ) ) currentIDIdx = 1 if matIDs.count > 1 then ( for i = 2 to matIDs.count do ( if matIDCounts[i] > matIDCounts[currentIDIdx] then ( currentIDIdx = i ) ) ) mesh2col childobj childobj.transform = savetrans matID = matIDs[currentIDIdx] collMaterial = GetCollNameFromMapID obj matID setattr childobj idxCollType collMaterial -- end of old style per object collision ) ) ) ) --//////////////////////////////////////////////////////////// -- events --//////////////////////////////////////////////////////////// -------------------------------------------------------------- -- -------------------------------------------------------------- on btnAssignMat pressed do ( for obj in selection do ( if getattrclass obj == "Gta Object" then ( AssignObjectMat obj ) ) ) -------------------------------------------------------------- -- -------------------------------------------------------------- on btnCreateMat pressed do ( currentMode = getCommandPanelTaskMode() setCommandPanelTaskMode #modify idxHandEdited = getattrindex "Gta Object" "Hand edited collision" for obj in (selection as array) do ( if getattrclass obj == "Gta Object" then ( createCol = true if getattr obj idxHandEdited then ( createCol = querybox (obj.name + " has hand edited collision which will be destroyed. Continue?") ) if createCol then ( CreateObjectMat obj ) ) ) setCommandPanelTaskMode currentMode ) -------------------------------------------------------------- -- -------------------------------------------------------------- on btnAssign pressed do ( for obj in selection do ( if getattrclass obj == "Gta Object" then ( AssignObject obj ) ) ) -------------------------------------------------------------- -- -------------------------------------------------------------- on btnToggle pressed do ( if lstMaterials.selection > 0 then ( mapName = lstMaterials.items[lstMaterials.selection] ToggleGlobalDataSettingXml mapName UpdateTexMapList() ) ) -------------------------------------------------------------- -- -------------------------------------------------------------- on btnGetFolder pressed do ( UpdateSelectionSetFromFolder() ) -------------------------------------------------------------- -- -------------------------------------------------------------- on btnSnapPivot pressed do ( -- Iterate through the selected objects, looking for collision sel = selection as array for obj in sel do ( if getattrclass obj == "Gta Collision" then ( objParent = obj.parent obj.pivot = objParent.pivot ) ) ) -------------------------------------------------------------- -- -------------------------------------------------------------- on chkUnset changed newval do ( UpdateTexMapList() UpdateTexture() UpdateMaterial() ) -------------------------------------------------------------- -- -------------------------------------------------------------- on lstMaterials selected idx do ( UpdateTexture() UpdateMaterial() ) -------------------------------------------------------------- -- -------------------------------------------------------------- on lstMaterials doubleClicked idx do ( rollout test_bitmaps "Bitmap" ( bitmap bmpUi on test_bitmaps open do ( if lstMaterials.selection > 0 then ( if TexMapsBmpsOut[lstMaterials.selection] != undefined then ( if classof TexMapsBmpsOut[lstMaterials.selection] == bitmaptexture then ( width = TexMapsBmpsOut[lstMaterials.selection].bitmap.width height = TexMapsBmpsOut[lstMaterials.selection].bitmap.height test_bitmaps.width = width test_bitmaps.height = height img = bitmap width height rm = rendermap TexMapsBmpsOut[lstMaterials.selection] into:img size:[width,height] bmpUi.width = width bmpUi.height = height bmpUi.bitmap = img bmpUi.pos = [0,0] close rm ) else ( local bmpset = bitmaptexture() bmpset.filename = TexMapsBmpsOut[lstMaterials.selection] bmpset.reload() width = bmpset.bitmap.width height = bmpset.bitmap.height test_bitmaps.width = width test_bitmaps.height = height img = bitmap width height rm = rendermap bmpset into:img size:[width,height] bmpUi.width = width bmpUi.height = height bmpUi.bitmap = img bmpUi.pos = [0,0] close rm ) ) ) ) ) DestroyDialog test_bitmaps createDialog test_bitmaps modal:false ) -------------------------------------------------------------- -- -------------------------------------------------------------- on lstAttr selected idx do ( SetMaterial idx ) -------------------------------------------------------------- -- -------------------------------------------------------------- on spnMinSS changed val do ( SetMaterial lstAttr.selection ) -------------------------------------------------------------- -- -------------------------------------------------------------- on spnMaxSS changed val do ( SetMaterial lstAttr.selection ) -------------------------------------------------------------- -- -------------------------------------------------------------- on chkStairs changed val do ( SetMaterial lstAttr.selection ) -------------------------------------------------------------- -- -------------------------------------------------------------- on chkClimable changed val do ( SetMaterial lstAttr.selection ) -------------------------------------------------------------- -- -------------------------------------------------------------- on chkSeeThrough changed val do ( SetMaterial lstAttr.selection ) -------------------------------------------------------------- -- -------------------------------------------------------------- on chkShootThrough changed val do ( SetMaterial lstAttr.selection ) -------------------------------------------------------------- -- -------------------------------------------------------------- on chkPath changed val do ( SetMaterial lstAttr.selection ) -------------------------------------------------------------- -- -------------------------------------------------------------- on chkSetPedPop changed val do ( SetMaterial lstAttr.selection ) -------------------------------------------------------------- -- -------------------------------------------------------------- on spnPedDensity changed val do ( SetMaterial lstAttr.selection ) -------------------------------------------------------------- -- -------------------------------------------------------------- on chkCover changed val do ( SetMaterial lstAttr.selection ) -------------------------------------------------------------- -- -------------------------------------------------------------- on chkCamera changed val do ( SetMaterial lstAttr.selection ) -------------------------------------------------------------- -- -------------------------------------------------------------- on CollisionTypeRoll open do ( CollNames = #() ParseMaterials ( RsConfigGetCommonDir() + "data/materials/materials.dat" ) SetupList() callbacks.addscript #selectionSetChanged "CollisionTypeUtil.rollouts[1].UpdateSelectionSet()" id:#collisionSet UpdateSelectionSet() ) -------------------------------------------------------------- -- -------------------------------------------------------------- on CollisionTypeRoll close do ( callbacks.removescripts id:#collisionSet ) ) try CloseRolloutFloater CollisionTypeUtil catch() CollisionTypeUtil = newRolloutFloater "Collision Set" 450 570 50 126 addRollout CollisionTypeRoll CollisionTypeUtil rolledup:false