432 lines
13 KiB
Plaintext
Executable File
432 lines
13 KiB
Plaintext
Executable File
--
|
|
-- Object Link manager
|
|
-- @Author Gunnar Droege
|
|
-- @Description An interface to the dotnet library to manage externally defined global linking
|
|
--
|
|
|
|
global gRsLinkMgr
|
|
|
|
global useMetaLinks = false
|
|
|
|
struct sLinkState
|
|
(
|
|
name,
|
|
guid,
|
|
asset,
|
|
target,
|
|
linkState,
|
|
linkChannel = -1,
|
|
sceneState = #unresolved, -- #resolved #resolvedByName #notSerialised
|
|
|
|
fn ResolveInScene linkObj =
|
|
(
|
|
name = linkObj.name
|
|
guid = linkObj.guid.toString()
|
|
asset = linkObj.ContentNode
|
|
linkState = linkObj.StatusFlags
|
|
target = ::RsGuidTools.GetObjByGuid guid
|
|
if undefined!=target then
|
|
(
|
|
sceneState = #resolved
|
|
)
|
|
else
|
|
(
|
|
-- optional name fallback
|
|
local nameMatches = getNodeByName name all:true
|
|
if nameMatches.count>0 then
|
|
(
|
|
sceneState = #resolvedByName
|
|
target = nameMatches[1]
|
|
)
|
|
)
|
|
)
|
|
)
|
|
|
|
struct sObjChannelLinkStates
|
|
(
|
|
linkChannel = -1,
|
|
parent,
|
|
children = #()
|
|
)
|
|
|
|
struct RsObjLinkMgr
|
|
(
|
|
dotnetMgr,
|
|
|
|
---------------------------------
|
|
|
|
fn ResolveContainer obj =
|
|
(
|
|
local map = RsMapObjectGetMapContainerFor obj
|
|
if undefined==map then
|
|
map = RsMapContainer name:"none" filename:(maxfilePath+maxFileName)
|
|
return map
|
|
),
|
|
|
|
public
|
|
---------------------------------
|
|
|
|
fn SetContentTreeHelper CTreeHelper =
|
|
(
|
|
print "setting contenttreehelper"
|
|
dotnetMgr.CTreeHelper = CTreeHelper
|
|
),
|
|
fn SetLog ulog =
|
|
(
|
|
print "setting ulog"
|
|
dotnetMgr.Log = ulog
|
|
),
|
|
fn SetBranch branch =
|
|
(
|
|
print ("setting branch to "+branch.Project.name as string+"|"+branch.name as string)
|
|
dotnetMgr.Branch = branch
|
|
),
|
|
|
|
fn printBranch =
|
|
(
|
|
local branch = dotnetMgr.Branch
|
|
print ("branch "+branch.Project.name as string+"|"+branch.name as string)
|
|
),
|
|
|
|
-------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------
|
|
-- Reset .Net cache
|
|
-------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------
|
|
fn FlushCache deleteSceneLinks:true =
|
|
(
|
|
if not useMetaLinks then
|
|
return true
|
|
print "Resetting link cache"
|
|
local serialisedGuids = dotnetMgr.FlushEditedNodes()
|
|
if deleteSceneLinks then
|
|
(
|
|
progressstart "Deleting links' scene representation"
|
|
local i=1
|
|
for guid in serialisedGuids while (RsMapProgress i serialisedGuids.count) do
|
|
(
|
|
local sceneObj = ::RsGuidTools.GetObjByGuid (guid.toString())
|
|
if undefined!=sceneObj then
|
|
(
|
|
RsSceneLink.RemoveContainer ::LinkType_ANY sceneObj
|
|
)
|
|
i+=1
|
|
)
|
|
progressend()
|
|
)
|
|
),
|
|
|
|
-------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------
|
|
-- forget viewport links
|
|
-------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------
|
|
fn RemoveRsSceneLinks =
|
|
(
|
|
local openContainers = RsMapGetMapContainers()
|
|
for map in openContainers do
|
|
(
|
|
editingNamespace = map.name
|
|
print ("Deleting RsScene links on map \""+editingNamespace+"\"")
|
|
progressStart ("Map \""+editingNamespace+"\" link deletion.")
|
|
local objIndex = 1
|
|
for obj in map.objects while (RsMapProgress objIndex map.objects.count) do
|
|
(
|
|
RsSceneLink.RemoveContainer ::LinkType_ANY obj
|
|
objIndex += 1
|
|
)
|
|
progressEnd()
|
|
)
|
|
),
|
|
|
|
fn GetLinkFile obj =
|
|
(
|
|
local objGuid = RsGuidMgr.GetGuid obj
|
|
if undefined!=objGuid then
|
|
(
|
|
return (dotnetClass "RSG.ObjectLinks.MetaAssetResolver").GetMetaFilePath gRsBranch (::RsObjLinkFuncs.MakeGuid objGuid) ((dotnetclass "RSG.ObjectLinks.MetaTypes").MetaTypeLinks)
|
|
)
|
|
return ""
|
|
),
|
|
|
|
-------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------
|
|
-- Save link from scene into meta files
|
|
-------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------
|
|
fn SaveObjLinks obj map: =
|
|
(
|
|
if not isValidnode obj then
|
|
return false
|
|
if map==unsupplied then
|
|
map = ResolveContainer obj
|
|
|
|
-- save out legacy scene stored linking
|
|
for parentLinkType in RsSceneLink.GetNodeParentLinkTypes obj do
|
|
(
|
|
local target = RsSceneLink.GetParent parentLinkType obj
|
|
if undefined!=target then
|
|
this.SetParent parentLinkType obj target sourcemap:map
|
|
else
|
|
RsSceneLink.RemoveContainer parentLinkType obj
|
|
)
|
|
for childLinkType in RsSceneLink.GetNodeChildLinkTypes obj do
|
|
(
|
|
local children = #()
|
|
RsSceneLink.GetChildren childLinkType obj &children
|
|
for child in children do
|
|
(
|
|
if undefined!=child then
|
|
this.SetParent childLinkType child obj targetmap:map
|
|
)
|
|
)
|
|
),
|
|
|
|
-------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------
|
|
-- Save all scene links from scene into meta files and delete .Net cache
|
|
-------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------
|
|
fn SaveSceneLinks =
|
|
(
|
|
-- Touching nodes
|
|
print "Saving out links"
|
|
local openContainers = RsMapGetMapContainers()
|
|
local sceneObjs = objects as array
|
|
for map in openContainers do
|
|
(
|
|
editingNamespace = map.name
|
|
progressStart ("Saving out links for map \""+editingNamespace as string+"\"")
|
|
local objIndex = 0
|
|
for obj in map.objects while (RsMapProgress objIndex map.objects.count) do
|
|
(
|
|
local kids = #()
|
|
::RsCollectChildren obj kids
|
|
for k in kids do
|
|
(
|
|
SaveObjLinks k map:map
|
|
|
|
local sceneObjIndex = findItem sceneObjs k
|
|
deleteItem sceneObjs sceneObjIndex
|
|
)
|
|
|
|
objIndex += 1
|
|
)
|
|
progressEnd()
|
|
)
|
|
|
|
-- we need to save out SOME sort of asset information. we can't resolve any objects in DCC if no assetpath is given and it's unlikely to be exported, too.
|
|
if maxFilename!="" then
|
|
(
|
|
progressStart ("Saving out mapless links")
|
|
objIndex = 0
|
|
local maplessContainer = RsMapContainer \
|
|
name:(getFilenameFile maxFilename) \
|
|
filename:(maxFilePath + maxFilename) \
|
|
objects:sceneObjs
|
|
for obj in sceneObjs where isValidNode obj while (RsMapProgress objIndex sceneObjs.count) do
|
|
(
|
|
SaveObjLinks obj map:maplessContainer
|
|
objIndex += 1
|
|
)
|
|
progressEnd()
|
|
)
|
|
-- triggerng serialiation and cache reset
|
|
FlushCache()
|
|
gRsUlog.Validate()
|
|
),
|
|
|
|
fn ResolveChannelObjStates obj channelObj =
|
|
(
|
|
local channelStates = sObjChannelLinkStates linkChannel:channelObj.Channel.value__
|
|
|
|
local linkParent = channelObj.Parent
|
|
if undefined!=linkParent then
|
|
(
|
|
channelStates.parent = sLinkState linkChannel:channelObj.Channel.value__
|
|
channelStates.parent.ResolveInScene linkParent
|
|
if channelStates.parent.sceneState != #unresolved then
|
|
(
|
|
local res = RsSceneLink.Setparent channelStates.parent.linkChannel obj channelStates.parent.target
|
|
)
|
|
)
|
|
|
|
local linkChildren = channelObj.Children
|
|
local childEnum = linkChildren.GetEnumerator()
|
|
while childEnum.MoveNext() do
|
|
(
|
|
linkChild = childEnum.Current
|
|
local linkState = sLinkState linkChannel:channelObj.Channel.value__
|
|
linkState.ResolveInScene linkChild
|
|
if linkState.sceneState != #unresolved then
|
|
(
|
|
local res = RsSceneLink.Setparent linkState.linkChannel linkState.target obj
|
|
)
|
|
append channelStates.children linkState
|
|
)
|
|
|
|
return channelStates
|
|
),
|
|
|
|
-------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------
|
|
-- Save scenes from scene into meta files and delete .Net cache
|
|
-------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------
|
|
fn LoadObjLinks obj =
|
|
(
|
|
local objectChannelStates = #()
|
|
-- local now = (dotnetclass "DateTime").now
|
|
|
|
local objGuid = RsGuidMgr.GetGuid obj
|
|
if undefined==objGuid then
|
|
return objectChannelStates
|
|
|
|
-- now = (dotnetclass "DateTime").now
|
|
local linkObj = dotnetMgr.Resolve (::RsObjLinkFuncs.MakeGuid objGuid)
|
|
-- print ("Time for "+obj.name+" Container resolve: "+ ((dotnetclass "DateTime").now.subtract now).tostring())
|
|
-- now = (dotnetclass "DateTime").now
|
|
|
|
if undefined!=linkObj then
|
|
(
|
|
local chEnum = linkObj.Channels.GetEnumerator()
|
|
while chEnum.MoveNext() do
|
|
(
|
|
append objectChannelStates (ResolveChannelObjStates obj chEnum.Current)
|
|
)
|
|
)
|
|
|
|
-- print ("loading time: "+ ((dotnetclass "DateTime").now.subtract now).tostring())
|
|
|
|
objectChannelStates
|
|
),
|
|
|
|
-------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------
|
|
-- load all links from meta files into scene cache
|
|
-------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------
|
|
fn LoadSceneLinks conts:(RsMapGetMapContainers()) =
|
|
(
|
|
progressStart ("Loading links for map...")
|
|
local objIndex = 0
|
|
for obj in objects while (RsMapProgress objIndex objects.count) do
|
|
(
|
|
LoadObjLinks obj
|
|
objIndex += 1
|
|
)
|
|
progressEnd()
|
|
FlushCache deleteSceneLinks:false
|
|
gRsUlog.Validate()
|
|
),
|
|
|
|
fn SaveCallback =
|
|
(
|
|
if not useMetaLinks then
|
|
return true
|
|
|
|
if (RsQueryBoxTimeOut "Save out ALL SceneLinks to metadata? This will delete all local links in max to avoid ambiguity on next load." timeout:10 defaultBtn:2) then
|
|
(
|
|
SaveSceneLinks()
|
|
)
|
|
else
|
|
(
|
|
FlushCache()
|
|
)
|
|
),
|
|
|
|
-------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------
|
|
-- accessors
|
|
-------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------
|
|
fn SetParent linkChannel source target sourcemap: targetmap: =
|
|
(
|
|
if not isValidNode source or not isValidNode target then
|
|
(
|
|
print ("Either of the nodes is not a valid node to link: "+source as string+", "+target as string)
|
|
return false
|
|
)
|
|
|
|
if not RsSceneLink.SetParent linkChannel source target then
|
|
(
|
|
print ("Linking failed for nodes "+source as string+" and "+target as string+" for channel "+linkChannel as string)
|
|
return false
|
|
)
|
|
|
|
if sourcemap==unsupplied then
|
|
sourcemap = ResolveContainer source
|
|
if targetmap==unsupplied then
|
|
targetmap = ResolveContainer target
|
|
|
|
-- we need all f these to link:
|
|
if undefined == sourcemap or
|
|
#none == sourcemap or
|
|
undefined == sourcemap.filename or
|
|
"" == sourcemap.filename or
|
|
undefined == targetmap or
|
|
#none == targetmap or
|
|
undefined == targetmap.filename or
|
|
"" == targetmap.filename then
|
|
(
|
|
gRsUlog.LogWarning ("Didn't (re)link "+source as string+" and "+target as string+" due to missing map information.") context:#(source, target)
|
|
return false
|
|
)
|
|
|
|
local sourceGuid = (RsGuidMgr.GetGuid source)
|
|
local targetGuid = (RsGuidMgr.GetGuid target)
|
|
|
|
local sourceContentNode = (RsContentTree.getContentNode sourcemap.filename)
|
|
local targetContentNode = (RsContentTree.getContentNode targetmap.filename)
|
|
|
|
dotnetMgr.CTreeHelper = RsContentTree.ContentTreeHelper
|
|
|
|
-- print ("Linking "+target as string+" to "+source as string+" on channel "+linkChannel as string+" with map "+map as string)
|
|
|
|
dotnetMgr.Link \
|
|
linkChannel \
|
|
sourceContentNode sourceGuid (source.name) \
|
|
targetContentNode targetGuid (target.name)
|
|
),
|
|
|
|
fn Unlink linkChannel source target:unsupplied map: =
|
|
(
|
|
if map==unsupplied then
|
|
map = ResolveContainer source
|
|
|
|
local filename = map.filename
|
|
local srcGuidStr = (RsGuidMgr.GetGuid source)
|
|
|
|
RsSceneLink.RemoveContainer linkChannel source
|
|
|
|
local trgGuidStr = ""
|
|
if unsupplied!=target then
|
|
(
|
|
trgGuidStr = (RsGuidMgr.GetGuid target)
|
|
)
|
|
|
|
dotnetMgr.Unlink linkChannel srcGuidStr trgGuidStr
|
|
|
|
return false
|
|
),
|
|
|
|
fn GetChildren ch obj kids update:true =
|
|
(
|
|
if useMetaLinks and update then
|
|
LoadObjLinks obj
|
|
RsSceneLink.GetChildren ch obj kids
|
|
),
|
|
fn GetParents ch obj kids update:true =
|
|
(
|
|
if useMetaLinks and update then
|
|
LoadObjLinks obj
|
|
RsSceneLink.GetParents ch obj kids
|
|
),
|
|
fn GetParent ch obj update:true =
|
|
(
|
|
if useMetaLinks and update then
|
|
LoadObjLinks obj
|
|
RsSceneLink.GetParent ch obj
|
|
),
|
|
fn GetNodeChildLinkTypes obj update:true =
|
|
(
|
|
if useMetaLinks and update then
|
|
LoadObjLinks obj
|
|
RsSceneLink.GetNodeChildLinkTypes obj
|
|
),
|
|
fn GetNodeParentLinkTypes obj update:true =
|
|
(
|
|
if useMetaLinks and update then
|
|
LoadObjLinks obj
|
|
RsSceneLink.GetNodeParentLinkTypes obj
|
|
),
|
|
getChannelName = RsSceneLink.getChannelName
|
|
)
|
|
|
|
filein "ObjectLink_funcs.ms" |