mirror of
https://github.com/ynput/ayon-core.git
synced 2025-12-25 21:32:15 +01:00
Merge branch 'develop' into feature/maya_testing
This commit is contained in:
commit
404f4c4f70
135 changed files with 461 additions and 237 deletions
|
|
@ -176,9 +176,9 @@ def run(script):
|
|||
# future versions might remove it.
|
||||
first_arg = sys.argv[0]
|
||||
if is_running_from_build():
|
||||
comp_path = os.path.join(os.environ["AYON_ROOT"], "start.py")
|
||||
else:
|
||||
comp_path = os.getenv("AYON_EXECUTABLE")
|
||||
else:
|
||||
comp_path = os.path.join(os.environ["AYON_ROOT"], "start.py")
|
||||
# Compare paths and remove first argument if it is the same as AYON
|
||||
if Path(first_arg).resolve() == Path(comp_path).resolve():
|
||||
sys.argv.pop(0)
|
||||
|
|
|
|||
|
|
@ -21,7 +21,7 @@ class BackgroundLoader(api.AfterEffectsLoader):
|
|||
"""
|
||||
label = "Load JSON Background"
|
||||
product_types = {"background"}
|
||||
representations = ["json"]
|
||||
representations = {"json"}
|
||||
|
||||
def load(self, context, name=None, namespace=None, data=None):
|
||||
stub = self.get_stub()
|
||||
|
|
|
|||
|
|
@ -20,7 +20,7 @@ class FileLoader(api.AfterEffectsLoader):
|
|||
"review",
|
||||
"audio",
|
||||
}
|
||||
representations = ["*"]
|
||||
representations = {"*"}
|
||||
|
||||
def load(self, context, name=None, namespace=None, data=None):
|
||||
stub = self.get_stub()
|
||||
|
|
|
|||
|
|
@ -43,7 +43,7 @@ class AppendBlendLoader(plugin.AssetLoader):
|
|||
so you could also use it as a new base.
|
||||
"""
|
||||
|
||||
representations = ["blend"]
|
||||
representations = {"blend"}
|
||||
product_types = {"workfile"}
|
||||
|
||||
label = "Append Workfile"
|
||||
|
|
@ -68,7 +68,7 @@ class ImportBlendLoader(plugin.AssetLoader):
|
|||
so you could also use it as a new base.
|
||||
"""
|
||||
|
||||
representations = ["blend"]
|
||||
representations = {"blend"}
|
||||
product_types = {"workfile"}
|
||||
|
||||
label = "Import Workfile"
|
||||
|
|
|
|||
|
|
@ -27,7 +27,7 @@ class CacheModelLoader(plugin.AssetLoader):
|
|||
At least for now it only supports Alembic files.
|
||||
"""
|
||||
product_types = {"model", "pointcache", "animation"}
|
||||
representations = ["abc"]
|
||||
representations = {"abc"}
|
||||
|
||||
label = "Load Alembic"
|
||||
icon = "code-fork"
|
||||
|
|
|
|||
|
|
@ -25,7 +25,7 @@ class BlendActionLoader(plugin.AssetLoader):
|
|||
"""
|
||||
|
||||
product_types = {"action"}
|
||||
representations = ["blend"]
|
||||
representations = {"blend"}
|
||||
|
||||
label = "Link Action"
|
||||
icon = "code-fork"
|
||||
|
|
|
|||
|
|
@ -17,7 +17,7 @@ class BlendAnimationLoader(plugin.AssetLoader):
|
|||
"""
|
||||
|
||||
product_types = {"animation"}
|
||||
representations = ["blend"]
|
||||
representations = {"blend"}
|
||||
|
||||
label = "Link Animation"
|
||||
icon = "code-fork"
|
||||
|
|
|
|||
|
|
@ -21,7 +21,7 @@ class AudioLoader(plugin.AssetLoader):
|
|||
"""Load audio in Blender."""
|
||||
|
||||
product_types = {"audio"}
|
||||
representations = ["wav"]
|
||||
representations = {"wav"}
|
||||
|
||||
label = "Load Audio"
|
||||
icon = "volume-up"
|
||||
|
|
|
|||
|
|
@ -21,7 +21,7 @@ class BlendLoader(plugin.AssetLoader):
|
|||
"""Load assets from a .blend file."""
|
||||
|
||||
product_types = {"model", "rig", "layout", "camera"}
|
||||
representations = ["blend"]
|
||||
representations = {"blend"}
|
||||
|
||||
label = "Append Blend"
|
||||
icon = "code-fork"
|
||||
|
|
|
|||
|
|
@ -19,7 +19,7 @@ class BlendSceneLoader(plugin.AssetLoader):
|
|||
"""Load assets from a .blend file."""
|
||||
|
||||
product_types = {"blendScene"}
|
||||
representations = ["blend"]
|
||||
representations = {"blend"}
|
||||
|
||||
label = "Append Blend"
|
||||
icon = "code-fork"
|
||||
|
|
|
|||
|
|
@ -24,7 +24,7 @@ class AbcCameraLoader(plugin.AssetLoader):
|
|||
"""
|
||||
|
||||
product_types = {"camera"}
|
||||
representations = ["abc"]
|
||||
representations = {"abc"}
|
||||
|
||||
label = "Load Camera (ABC)"
|
||||
icon = "code-fork"
|
||||
|
|
|
|||
|
|
@ -24,7 +24,7 @@ class FbxCameraLoader(plugin.AssetLoader):
|
|||
"""
|
||||
|
||||
product_types = {"camera"}
|
||||
representations = ["fbx"]
|
||||
representations = {"fbx"}
|
||||
|
||||
label = "Load Camera (FBX)"
|
||||
icon = "code-fork"
|
||||
|
|
|
|||
|
|
@ -24,7 +24,7 @@ class FbxModelLoader(plugin.AssetLoader):
|
|||
"""
|
||||
|
||||
product_types = {"model", "rig"}
|
||||
representations = ["fbx"]
|
||||
representations = {"fbx"}
|
||||
|
||||
label = "Load FBX"
|
||||
icon = "code-fork"
|
||||
|
|
|
|||
|
|
@ -27,7 +27,7 @@ class JsonLayoutLoader(plugin.AssetLoader):
|
|||
"""Load layout published from Unreal."""
|
||||
|
||||
product_types = {"layout"}
|
||||
representations = ["json"]
|
||||
representations = {"json"}
|
||||
|
||||
label = "Load Layout"
|
||||
icon = "code-fork"
|
||||
|
|
|
|||
|
|
@ -24,7 +24,7 @@ class BlendLookLoader(plugin.AssetLoader):
|
|||
"""
|
||||
|
||||
product_types = {"look"}
|
||||
representations = ["json"]
|
||||
representations = {"json"}
|
||||
|
||||
label = "Load Look"
|
||||
icon = "code-fork"
|
||||
|
|
|
|||
|
|
@ -18,7 +18,7 @@ class LoadClip(opfapi.ClipLoader):
|
|||
"""
|
||||
|
||||
product_types = {"render2d", "source", "plate", "render", "review"}
|
||||
representations = ["*"]
|
||||
representations = {"*"}
|
||||
extensions = set(
|
||||
ext.lstrip(".") for ext in IMAGE_EXTENSIONS.union(VIDEO_EXTENSIONS)
|
||||
)
|
||||
|
|
|
|||
|
|
@ -17,7 +17,7 @@ class LoadClipBatch(opfapi.ClipLoader):
|
|||
"""
|
||||
|
||||
product_types = {"render2d", "source", "plate", "render", "review"}
|
||||
representations = ["*"]
|
||||
representations = {"*"}
|
||||
extensions = set(
|
||||
ext.lstrip(".") for ext in IMAGE_EXTENSIONS.union(VIDEO_EXTENSIONS)
|
||||
)
|
||||
|
|
|
|||
|
|
@ -17,7 +17,7 @@ class FusionSetFrameRangeLoader(load.LoaderPlugin):
|
|||
"pointcache",
|
||||
"render",
|
||||
}
|
||||
representations = ["*"]
|
||||
representations = {"*"}
|
||||
extensions = {"*"}
|
||||
|
||||
label = "Set frame range"
|
||||
|
|
@ -54,7 +54,7 @@ class FusionSetFrameRangeWithHandlesLoader(load.LoaderPlugin):
|
|||
"pointcache",
|
||||
"render",
|
||||
}
|
||||
representations = ["*"]
|
||||
representations = {"*"}
|
||||
|
||||
label = "Set frame range (with handles)"
|
||||
order = 12
|
||||
|
|
|
|||
|
|
@ -13,7 +13,7 @@ class FusionLoadAlembicMesh(load.LoaderPlugin):
|
|||
"""Load Alembic mesh into Fusion"""
|
||||
|
||||
product_types = {"pointcache", "model"}
|
||||
representations = ["*"]
|
||||
representations = {"*"}
|
||||
extensions = {"abc"}
|
||||
|
||||
label = "Load alembic mesh"
|
||||
|
|
|
|||
|
|
@ -13,7 +13,7 @@ class FusionLoadFBXMesh(load.LoaderPlugin):
|
|||
"""Load FBX mesh into Fusion"""
|
||||
|
||||
product_types = {"*"}
|
||||
representations = ["*"]
|
||||
representations = {"*"}
|
||||
extensions = {
|
||||
"3ds",
|
||||
"amc",
|
||||
|
|
|
|||
|
|
@ -137,7 +137,7 @@ class FusionLoadSequence(load.LoaderPlugin):
|
|||
"image",
|
||||
"online",
|
||||
}
|
||||
representations = ["*"]
|
||||
representations = {"*"}
|
||||
extensions = set(
|
||||
ext.lstrip(".") for ext in IMAGE_EXTENSIONS.union(VIDEO_EXTENSIONS)
|
||||
)
|
||||
|
|
|
|||
|
|
@ -17,7 +17,7 @@ class FusionLoadUSD(load.LoaderPlugin):
|
|||
"""
|
||||
|
||||
product_types = {"*"}
|
||||
representations = ["*"]
|
||||
representations = {"*"}
|
||||
extensions = {"usd", "usda", "usdz"}
|
||||
|
||||
label = "Load USD"
|
||||
|
|
|
|||
|
|
@ -15,7 +15,7 @@ class FusionLoadWorkfile(load.LoaderPlugin):
|
|||
"""Load the content of a workfile into Fusion"""
|
||||
|
||||
product_types = {"workfile"}
|
||||
representations = ["*"]
|
||||
representations = {"*"}
|
||||
extensions = {"comp"}
|
||||
|
||||
label = "Load Workfile"
|
||||
|
|
|
|||
|
|
@ -590,7 +590,7 @@ class ImageSequenceLoader(load.LoaderPlugin):
|
|||
"reference",
|
||||
"review",
|
||||
}
|
||||
representations = ["*"]
|
||||
representations = {"*"}
|
||||
extensions = {"jpeg", "png", "jpg"}
|
||||
|
||||
def load(self, context, name=None, namespace=None, data=None):
|
||||
|
|
|
|||
|
|
@ -36,7 +36,7 @@ class ImportAudioLoader(load.LoaderPlugin):
|
|||
"""Import audio."""
|
||||
|
||||
product_types = {"shot", "audio"}
|
||||
representations = ["wav"]
|
||||
representations = {"wav"}
|
||||
label = "Import Audio"
|
||||
|
||||
def load(self, context, name=None, namespace=None, data=None):
|
||||
|
|
|
|||
|
|
@ -234,7 +234,7 @@ class BackgroundLoader(load.LoaderPlugin):
|
|||
Stores the imported asset in a container named after the asset.
|
||||
"""
|
||||
product_types = {"background"}
|
||||
representations = ["json"]
|
||||
representations = {"json"}
|
||||
|
||||
def load(self, context, name=None, namespace=None, data=None):
|
||||
|
||||
|
|
|
|||
|
|
@ -28,7 +28,7 @@ class ImageSequenceLoader(load.LoaderPlugin):
|
|||
"reference",
|
||||
"review",
|
||||
}
|
||||
representations = ["*"]
|
||||
representations = {"*"}
|
||||
extensions = {"jpeg", "png", "jpg"}
|
||||
|
||||
def load(self, context, name=None, namespace=None, data=None):
|
||||
|
|
|
|||
|
|
@ -12,7 +12,7 @@ class ImportPaletteLoader(load.LoaderPlugin):
|
|||
"""Import palettes."""
|
||||
|
||||
product_types = {"palette", "harmony.palette"}
|
||||
representations = ["plt"]
|
||||
representations = {"plt"}
|
||||
label = "Import Palette"
|
||||
|
||||
def load(self, context, name=None, namespace=None, data=None):
|
||||
|
|
|
|||
|
|
@ -24,7 +24,7 @@ class TemplateLoader(load.LoaderPlugin):
|
|||
"""
|
||||
|
||||
product_types = {"template", "workfile"}
|
||||
representations = ["*"]
|
||||
representations = {"*"}
|
||||
label = "Load Template"
|
||||
icon = "gift"
|
||||
|
||||
|
|
|
|||
|
|
@ -14,7 +14,7 @@ class ImportTemplateLoader(load.LoaderPlugin):
|
|||
"""Import templates."""
|
||||
|
||||
product_types = {"harmony.template", "workfile"}
|
||||
representations = ["*"]
|
||||
representations = {"*"}
|
||||
label = "Import Template"
|
||||
|
||||
def load(self, context, name=None, namespace=None, data=None):
|
||||
|
|
@ -61,5 +61,5 @@ class ImportWorkfileLoader(ImportTemplateLoader):
|
|||
"""Import workfiles."""
|
||||
|
||||
product_types = {"workfile"}
|
||||
representations = ["zip"]
|
||||
representations = {"zip"}
|
||||
label = "Import Workfile"
|
||||
|
|
|
|||
|
|
@ -16,7 +16,7 @@ class LoadClip(phiero.SequenceLoader):
|
|||
"""
|
||||
|
||||
product_types = {"render2d", "source", "plate", "render", "review"}
|
||||
representations = ["*"]
|
||||
representations = {"*"}
|
||||
extensions = set(
|
||||
ext.lstrip(".") for ext in IMAGE_EXTENSIONS.union(VIDEO_EXTENSIONS)
|
||||
)
|
||||
|
|
|
|||
|
|
@ -15,7 +15,7 @@ class LoadEffects(load.LoaderPlugin):
|
|||
"""Loading colorspace soft effect exported from nukestudio"""
|
||||
|
||||
product_types = {"effect"}
|
||||
representations = ["*"]
|
||||
representations = {"*"}
|
||||
extension = {"json"}
|
||||
|
||||
label = "Load Effects"
|
||||
|
|
|
|||
|
|
@ -1001,6 +1001,82 @@ def add_self_publish_button(node):
|
|||
node.setParmTemplateGroup(template)
|
||||
|
||||
|
||||
def get_scene_viewer():
|
||||
"""
|
||||
Return an instance of a visible viewport.
|
||||
|
||||
There may be many, some could be closed, any visible are current
|
||||
|
||||
Returns:
|
||||
Optional[hou.SceneViewer]: A scene viewer, if any.
|
||||
"""
|
||||
panes = hou.ui.paneTabs()
|
||||
panes = [x for x in panes if x.type() == hou.paneTabType.SceneViewer]
|
||||
panes = sorted(panes, key=lambda x: x.isCurrentTab())
|
||||
if panes:
|
||||
return panes[-1]
|
||||
|
||||
return None
|
||||
|
||||
|
||||
def sceneview_snapshot(
|
||||
sceneview,
|
||||
filepath="$HIP/thumbnails/$HIPNAME.$F4.jpg",
|
||||
frame_start=None,
|
||||
frame_end=None):
|
||||
"""Take a snapshot of your scene view.
|
||||
|
||||
It takes snapshot of your scene view for the given frame range.
|
||||
So, it's capable of generating snapshots image sequence.
|
||||
It works in different Houdini context e.g. Objects, Solaris
|
||||
|
||||
Example:
|
||||
This is how the function can be used::
|
||||
|
||||
from ayon_core.hosts.houdini.api import lib
|
||||
sceneview = hou.ui.paneTabOfType(hou.paneTabType.SceneViewer)
|
||||
lib.sceneview_snapshot(sceneview)
|
||||
|
||||
Notes:
|
||||
.png output will render poorly, so use .jpg.
|
||||
|
||||
How it works:
|
||||
Get the current sceneviewer (may be more than one or hidden)
|
||||
and screengrab the perspective viewport to a file in the
|
||||
publish location to be picked up with the publish.
|
||||
|
||||
Credits:
|
||||
https://www.sidefx.com/forum/topic/42808/?page=1#post-354796
|
||||
|
||||
Args:
|
||||
sceneview (hou.SceneViewer): The scene view pane from which you want
|
||||
to take a snapshot.
|
||||
filepath (str): thumbnail filepath. it expects `$F4` token
|
||||
when frame_end is bigger than frame_star other wise
|
||||
each frame will override its predecessor.
|
||||
frame_start (int): the frame at which snapshot starts
|
||||
frame_end (int): the frame at which snapshot ends
|
||||
"""
|
||||
|
||||
if frame_start is None:
|
||||
frame_start = hou.frame()
|
||||
if frame_end is None:
|
||||
frame_end = frame_start
|
||||
|
||||
if not isinstance(sceneview, hou.SceneViewer):
|
||||
log.debug("Wrong Input. {} is not of type hou.SceneViewer."
|
||||
.format(sceneview))
|
||||
return
|
||||
viewport = sceneview.curViewport()
|
||||
|
||||
flip_settings = sceneview.flipbookSettings().stash()
|
||||
flip_settings.frameRange((frame_start, frame_end))
|
||||
flip_settings.output(filepath)
|
||||
flip_settings.outputToMPlay(False)
|
||||
sceneview.flipbook(viewport, flip_settings)
|
||||
log.debug("A snapshot of sceneview has been saved to: {}".format(filepath))
|
||||
|
||||
|
||||
def update_content_on_context_change():
|
||||
"""Update all Creator instances to current asset"""
|
||||
host = registered_host()
|
||||
|
|
|
|||
|
|
@ -15,7 +15,7 @@ class SetFrameRangeLoader(load.LoaderPlugin):
|
|||
"vdbcache",
|
||||
"usd",
|
||||
}
|
||||
representations = ["abc", "vdb", "usd"]
|
||||
representations = {"abc", "vdb", "usd"}
|
||||
|
||||
label = "Set frame range"
|
||||
order = 11
|
||||
|
|
@ -52,7 +52,7 @@ class SetFrameRangeWithHandlesLoader(load.LoaderPlugin):
|
|||
"vdbcache",
|
||||
"usd",
|
||||
}
|
||||
representations = ["abc", "vdb", "usd"]
|
||||
representations = {"abc", "vdb", "usd"}
|
||||
|
||||
label = "Set frame range (with handles)"
|
||||
order = 12
|
||||
|
|
|
|||
|
|
@ -11,7 +11,7 @@ class AbcLoader(load.LoaderPlugin):
|
|||
|
||||
product_types = {"model", "animation", "pointcache", "gpuCache"}
|
||||
label = "Load Alembic"
|
||||
representations = ["*"]
|
||||
representations = {"*"}
|
||||
extensions = {"abc"}
|
||||
order = -10
|
||||
icon = "code-fork"
|
||||
|
|
|
|||
|
|
@ -11,7 +11,7 @@ class AbcArchiveLoader(load.LoaderPlugin):
|
|||
|
||||
product_types = {"model", "animation", "pointcache", "gpuCache"}
|
||||
label = "Load Alembic as Archive"
|
||||
representations = ["*"]
|
||||
representations = {"*"}
|
||||
extensions = {"abc"}
|
||||
order = -5
|
||||
icon = "code-fork"
|
||||
|
|
|
|||
|
|
@ -13,7 +13,7 @@ class AssLoader(load.LoaderPlugin):
|
|||
|
||||
product_types = {"ass"}
|
||||
label = "Load Arnold Procedural"
|
||||
representations = ["ass"]
|
||||
representations = {"ass"}
|
||||
order = -10
|
||||
icon = "code-fork"
|
||||
color = "orange"
|
||||
|
|
|
|||
|
|
@ -14,9 +14,9 @@ class BgeoLoader(load.LoaderPlugin):
|
|||
|
||||
label = "Load bgeo"
|
||||
product_types = {"model", "pointcache", "bgeo"}
|
||||
representations = [
|
||||
representations = {
|
||||
"bgeo", "bgeosc", "bgeogz",
|
||||
"bgeo.sc", "bgeo.gz", "bgeo.lzma", "bgeo.bz2"]
|
||||
"bgeo.sc", "bgeo.gz", "bgeo.lzma", "bgeo.bz2"}
|
||||
order = -10
|
||||
icon = "code-fork"
|
||||
color = "orange"
|
||||
|
|
|
|||
|
|
@ -89,7 +89,7 @@ class CameraLoader(load.LoaderPlugin):
|
|||
|
||||
product_types = {"camera"}
|
||||
label = "Load Camera (abc)"
|
||||
representations = ["abc"]
|
||||
representations = {"abc"}
|
||||
order = -10
|
||||
|
||||
icon = "code-fork"
|
||||
|
|
|
|||
|
|
@ -17,7 +17,7 @@ class FbxLoader(load.LoaderPlugin):
|
|||
order = -10
|
||||
|
||||
product_types = {"*"}
|
||||
representations = ["*"]
|
||||
representations = {"*"}
|
||||
extensions = {"fbx"}
|
||||
|
||||
def load(self, context, name=None, namespace=None, data=None):
|
||||
|
|
|
|||
|
|
@ -22,7 +22,7 @@ class FilePathLoader(load.LoaderPlugin):
|
|||
icon = "link"
|
||||
color = "white"
|
||||
product_types = {"*"}
|
||||
representations = ["*"]
|
||||
representations = {"*"}
|
||||
|
||||
def load(self, context, name=None, namespace=None, data=None):
|
||||
|
||||
|
|
|
|||
|
|
@ -12,7 +12,7 @@ class HdaLoader(load.LoaderPlugin):
|
|||
|
||||
product_types = {"hda"}
|
||||
label = "Load Hda"
|
||||
representations = ["hda"]
|
||||
representations = {"hda"}
|
||||
order = -10
|
||||
icon = "code-fork"
|
||||
color = "orange"
|
||||
|
|
|
|||
|
|
@ -54,7 +54,7 @@ class ImageLoader(load.LoaderPlugin):
|
|||
"online",
|
||||
}
|
||||
label = "Load Image (COP2)"
|
||||
representations = ["*"]
|
||||
representations = {"*"}
|
||||
order = -10
|
||||
|
||||
icon = "code-fork"
|
||||
|
|
|
|||
|
|
@ -15,7 +15,7 @@ class RedshiftProxyLoader(load.LoaderPlugin):
|
|||
|
||||
product_types = {"redshiftproxy"}
|
||||
label = "Load Redshift Proxy"
|
||||
representations = ["rs"]
|
||||
representations = {"rs"}
|
||||
order = -10
|
||||
icon = "code-fork"
|
||||
color = "orange"
|
||||
|
|
|
|||
|
|
@ -14,7 +14,7 @@ class USDSublayerLoader(load.LoaderPlugin):
|
|||
"usdCamera",
|
||||
}
|
||||
label = "Sublayer USD"
|
||||
representations = ["usd", "usda", "usdlc", "usdnc", "abc"]
|
||||
representations = {"usd", "usda", "usdlc", "usdnc", "abc"}
|
||||
order = 1
|
||||
|
||||
icon = "code-fork"
|
||||
|
|
|
|||
|
|
@ -14,7 +14,7 @@ class USDReferenceLoader(load.LoaderPlugin):
|
|||
"usdCamera",
|
||||
}
|
||||
label = "Reference USD"
|
||||
representations = ["usd", "usda", "usdlc", "usdnc", "abc"]
|
||||
representations = {"usd", "usda", "usdlc", "usdnc", "abc"}
|
||||
order = -8
|
||||
|
||||
icon = "code-fork"
|
||||
|
|
|
|||
|
|
@ -9,7 +9,7 @@ class SopUsdImportLoader(load.LoaderPlugin):
|
|||
|
||||
label = "Load USD to SOPs"
|
||||
product_types = {"*"}
|
||||
representations = ["usd"]
|
||||
representations = {"usd"}
|
||||
order = -6
|
||||
icon = "code-fork"
|
||||
color = "orange"
|
||||
|
|
|
|||
|
|
@ -13,7 +13,7 @@ class VdbLoader(load.LoaderPlugin):
|
|||
|
||||
product_types = {"vdbcache"}
|
||||
label = "Load VDB"
|
||||
representations = ["vdb"]
|
||||
representations = {"vdb"}
|
||||
order = -10
|
||||
icon = "code-fork"
|
||||
color = "orange"
|
||||
|
|
|
|||
|
|
@ -10,7 +10,7 @@ class ShowInUsdview(load.LoaderPlugin):
|
|||
"""Open USD file in usdview"""
|
||||
|
||||
label = "Show in usdview"
|
||||
representations = ["*"]
|
||||
representations = {"*"}
|
||||
product_types = {"*"}
|
||||
extensions = {"usd", "usda", "usdlc", "usdnc", "abc"}
|
||||
order = 15
|
||||
|
|
|
|||
|
|
@ -0,0 +1,55 @@
|
|||
import pyblish.api
|
||||
import tempfile
|
||||
from ayon_core.pipeline import publish
|
||||
from ayon_core.hosts.houdini.api import lib
|
||||
from ayon_core.hosts.houdini.api.pipeline import IS_HEADLESS
|
||||
|
||||
|
||||
class ExtractActiveViewThumbnail(publish.Extractor):
|
||||
"""Set instance thumbnail to a screengrab of current active viewport.
|
||||
|
||||
This makes it so that if an instance does not have a thumbnail set yet that
|
||||
it will get a thumbnail of the currently active view at the time of
|
||||
publishing as a fallback.
|
||||
|
||||
"""
|
||||
order = pyblish.api.ExtractorOrder + 0.49
|
||||
label = "Extract Active View Thumbnail"
|
||||
families = ["workfile"]
|
||||
hosts = ["houdini"]
|
||||
|
||||
def process(self, instance):
|
||||
if IS_HEADLESS:
|
||||
self.log.debug(
|
||||
"Skip extraction of active view thumbnail, due to being in"
|
||||
"headless mode."
|
||||
)
|
||||
return
|
||||
|
||||
thumbnail = instance.data.get("thumbnailPath")
|
||||
if thumbnail:
|
||||
# A thumbnail was already set for this instance
|
||||
return
|
||||
|
||||
view_thumbnail = self.get_view_thumbnail(instance)
|
||||
if not view_thumbnail:
|
||||
return
|
||||
self.log.debug("Setting instance thumbnail path to: {}"
|
||||
.format(view_thumbnail)
|
||||
)
|
||||
instance.data["thumbnailPath"] = view_thumbnail
|
||||
|
||||
def get_view_thumbnail(self, instance):
|
||||
|
||||
sceneview = lib.get_scene_viewer()
|
||||
if sceneview is None:
|
||||
self.log.debug("Skipping Extract Active View Thumbnail"
|
||||
" because no scene view was detected.")
|
||||
return
|
||||
|
||||
with tempfile.NamedTemporaryFile("w", suffix=".jpg", delete=False) as tmp:
|
||||
lib.sceneview_snapshot(sceneview, tmp.name)
|
||||
thumbnail_path = tmp.name
|
||||
|
||||
instance.context.data["cleanupFullPaths"].append(thumbnail_path)
|
||||
return thumbnail_path
|
||||
|
|
@ -19,7 +19,7 @@ class FbxLoader(load.LoaderPlugin):
|
|||
"""Fbx Loader."""
|
||||
|
||||
product_types = {"camera"}
|
||||
representations = ["fbx"]
|
||||
representations = {"fbx"}
|
||||
order = -9
|
||||
icon = "code-fork"
|
||||
color = "white"
|
||||
|
|
|
|||
|
|
@ -78,7 +78,7 @@ class MaxSceneLoader(load.LoaderPlugin):
|
|||
"model",
|
||||
}
|
||||
|
||||
representations = ["max"]
|
||||
representations = {"max"}
|
||||
order = -8
|
||||
icon = "code-fork"
|
||||
color = "green"
|
||||
|
|
|
|||
|
|
@ -16,7 +16,7 @@ class ModelAbcLoader(load.LoaderPlugin):
|
|||
|
||||
product_types = {"model"}
|
||||
label = "Load Model with Alembic"
|
||||
representations = ["abc"]
|
||||
representations = {"abc"}
|
||||
order = -10
|
||||
icon = "code-fork"
|
||||
color = "orange"
|
||||
|
|
|
|||
|
|
@ -18,7 +18,7 @@ class FbxModelLoader(load.LoaderPlugin):
|
|||
"""Fbx Model Loader."""
|
||||
|
||||
product_types = {"model"}
|
||||
representations = ["fbx"]
|
||||
representations = {"fbx"}
|
||||
order = -9
|
||||
icon = "code-fork"
|
||||
color = "white"
|
||||
|
|
|
|||
|
|
@ -20,7 +20,7 @@ class ObjLoader(load.LoaderPlugin):
|
|||
"""Obj Loader."""
|
||||
|
||||
product_types = {"model"}
|
||||
representations = ["obj"]
|
||||
representations = {"obj"}
|
||||
order = -9
|
||||
icon = "code-fork"
|
||||
color = "white"
|
||||
|
|
|
|||
|
|
@ -24,7 +24,7 @@ class ModelUSDLoader(load.LoaderPlugin):
|
|||
|
||||
product_types = {"model"}
|
||||
label = "Load Model(USD)"
|
||||
representations = ["usda"]
|
||||
representations = {"usda"}
|
||||
order = -10
|
||||
icon = "code-fork"
|
||||
color = "orange"
|
||||
|
|
|
|||
|
|
@ -20,7 +20,7 @@ class AbcLoader(load.LoaderPlugin):
|
|||
|
||||
product_types = {"camera", "animation", "pointcache"}
|
||||
label = "Load Alembic"
|
||||
representations = ["abc"]
|
||||
representations = {"abc"}
|
||||
order = -10
|
||||
icon = "code-fork"
|
||||
color = "orange"
|
||||
|
|
|
|||
|
|
@ -23,7 +23,7 @@ class OxAbcLoader(load.LoaderPlugin):
|
|||
|
||||
product_types = {"camera", "animation", "pointcache"}
|
||||
label = "Load Alembic with Ornatrix"
|
||||
representations = ["abc"]
|
||||
representations = {"abc"}
|
||||
order = -10
|
||||
icon = "code-fork"
|
||||
color = "orange"
|
||||
|
|
|
|||
|
|
@ -18,7 +18,7 @@ class PointCloudLoader(load.LoaderPlugin):
|
|||
"""Point Cloud Loader."""
|
||||
|
||||
product_types = {"pointcloud"}
|
||||
representations = ["prt"]
|
||||
representations = {"prt"}
|
||||
order = -8
|
||||
icon = "code-fork"
|
||||
color = "green"
|
||||
|
|
|
|||
|
|
@ -24,7 +24,7 @@ class RedshiftProxyLoader(load.LoaderPlugin):
|
|||
|
||||
label = "Load Redshift Proxy"
|
||||
product_types = {"redshiftproxy"}
|
||||
representations = ["rs"]
|
||||
representations = {"rs"}
|
||||
order = -9
|
||||
icon = "code-fork"
|
||||
color = "white"
|
||||
|
|
|
|||
|
|
@ -17,7 +17,7 @@ class TyCacheLoader(load.LoaderPlugin):
|
|||
"""TyCache Loader."""
|
||||
|
||||
product_types = {"tycache"}
|
||||
representations = ["tyc"]
|
||||
representations = {"tyc"}
|
||||
order = -8
|
||||
icon = "code-fork"
|
||||
color = "green"
|
||||
|
|
|
|||
|
|
@ -22,15 +22,15 @@ class MayaAddon(AYONAddon, IHostAddon):
|
|||
if norm_path not in new_python_paths:
|
||||
new_python_paths.append(norm_path)
|
||||
|
||||
# add vendor path
|
||||
new_python_paths.append(
|
||||
os.path.join(MAYA_ROOT_DIR, "vendor", "python")
|
||||
)
|
||||
env["PYTHONPATH"] = os.pathsep.join(new_python_paths)
|
||||
|
||||
# Set default environments
|
||||
envs = {
|
||||
"AYON_LOG_NO_COLORS": "1",
|
||||
# For python module 'qtpy'
|
||||
"QT_API": "PySide2",
|
||||
# For python module 'Qt'
|
||||
"QT_PREFERRED_BINDING": "PySide2"
|
||||
}
|
||||
for key, value in envs.items():
|
||||
env[key] = value
|
||||
|
|
|
|||
|
|
@ -1,4 +1,5 @@
|
|||
import os
|
||||
import json
|
||||
import logging
|
||||
from functools import partial
|
||||
|
||||
|
|
@ -282,8 +283,18 @@ def install(project_settings):
|
|||
)
|
||||
return
|
||||
|
||||
config = project_settings["maya"]["scriptsmenu"]["definition"]
|
||||
_menu = project_settings["maya"]["scriptsmenu"]["name"]
|
||||
menu_settings = project_settings["maya"]["scriptsmenu"]
|
||||
menu_name = menu_settings["name"]
|
||||
config = menu_settings["definition"]
|
||||
|
||||
if menu_settings.get("definition_type") == "definition_json":
|
||||
data = menu_settings["definition_json"]
|
||||
try:
|
||||
config = json.loads(data)
|
||||
except json.JSONDecodeError as exc:
|
||||
print("Skipping studio menu, error decoding JSON definition.")
|
||||
log.error(exc)
|
||||
return
|
||||
|
||||
if not config:
|
||||
log.warning("Skipping studio menu, no definition found.")
|
||||
|
|
@ -291,8 +302,8 @@ def install(project_settings):
|
|||
|
||||
# run the launcher for Maya menu
|
||||
studio_menu = launchformaya.main(
|
||||
title=_menu.title(),
|
||||
objectName=_menu.title().lower().replace(" ", "_")
|
||||
title=menu_name.title(),
|
||||
objectName=menu_name.title().lower().replace(" ", "_")
|
||||
)
|
||||
|
||||
# apply configuration
|
||||
|
|
|
|||
|
|
@ -51,7 +51,7 @@ class AbcLoader(ayon_core.hosts.maya.api.plugin.ReferenceLoader):
|
|||
"camera",
|
||||
"pointcache",
|
||||
}
|
||||
representations = ["abc"]
|
||||
representations = {"abc"}
|
||||
|
||||
label = "Reference animation"
|
||||
order = -10
|
||||
|
|
@ -81,7 +81,7 @@ class FbxLoader(ayon_core.hosts.maya.api.plugin.ReferenceLoader):
|
|||
"animation",
|
||||
"camera",
|
||||
}
|
||||
representations = ["fbx"]
|
||||
representations = {"fbx"}
|
||||
|
||||
label = "Reference animation"
|
||||
order = -10
|
||||
|
|
|
|||
|
|
@ -19,7 +19,7 @@ class SetFrameRangeLoader(load.LoaderPlugin):
|
|||
"proxyAbc",
|
||||
"pointcache",
|
||||
}
|
||||
representations = ["abc"]
|
||||
representations = {"abc"}
|
||||
|
||||
label = "Set frame range"
|
||||
order = 11
|
||||
|
|
@ -54,7 +54,7 @@ class SetFrameRangeWithHandlesLoader(load.LoaderPlugin):
|
|||
"proxyAbc",
|
||||
"pointcache",
|
||||
}
|
||||
representations = ["abc"]
|
||||
representations = {"abc"}
|
||||
|
||||
label = "Set frame range (with handles)"
|
||||
order = 12
|
||||
|
|
@ -94,7 +94,7 @@ class ImportMayaLoader(ayon_core.hosts.maya.api.plugin.Loader):
|
|||
so you could also use it as a new base.
|
||||
|
||||
"""
|
||||
representations = ["ma", "mb", "obj"]
|
||||
representations = {"ma", "mb", "obj"}
|
||||
product_types = {
|
||||
"model",
|
||||
"pointcache",
|
||||
|
|
|
|||
|
|
@ -31,7 +31,7 @@ class ArnoldStandinLoader(load.LoaderPlugin):
|
|||
product_types = {
|
||||
"ass", "animation", "model", "proxyAbc", "pointcache", "usd"
|
||||
}
|
||||
representations = ["ass", "abc", "usda", "usdc", "usd"]
|
||||
representations = {"ass", "abc", "usda", "usdc", "usd"}
|
||||
|
||||
label = "Load as Arnold standin"
|
||||
order = -5
|
||||
|
|
|
|||
|
|
@ -13,7 +13,7 @@ from ayon_core.hosts.maya.api import setdress
|
|||
class AssemblyLoader(load.LoaderPlugin):
|
||||
|
||||
product_types = {"assembly"}
|
||||
representations = ["json"]
|
||||
representations = {"json"}
|
||||
|
||||
label = "Load Set Dress"
|
||||
order = -9
|
||||
|
|
|
|||
|
|
@ -13,7 +13,7 @@ class AudioLoader(load.LoaderPlugin):
|
|||
|
||||
product_types = {"audio"}
|
||||
label = "Load audio"
|
||||
representations = ["wav"]
|
||||
representations = {"wav"}
|
||||
icon = "volume-up"
|
||||
color = "orange"
|
||||
|
||||
|
|
|
|||
|
|
@ -14,7 +14,7 @@ class GpuCacheLoader(load.LoaderPlugin):
|
|||
"""Load Alembic as gpuCache"""
|
||||
|
||||
product_types = {"model", "animation", "proxyAbc", "pointcache"}
|
||||
representations = ["abc", "gpu_cache"]
|
||||
representations = {"abc", "gpu_cache"}
|
||||
|
||||
label = "Load Gpu Cache"
|
||||
order = -5
|
||||
|
|
|
|||
|
|
@ -93,7 +93,7 @@ class FileNodeLoader(load.LoaderPlugin):
|
|||
|
||||
product_types = {"image", "plate", "render", "review"}
|
||||
label = "Load file node"
|
||||
representations = ["exr", "tif", "png", "jpg"]
|
||||
representations = {"exr", "tif", "png", "jpg"}
|
||||
icon = "image"
|
||||
color = "orange"
|
||||
order = 2
|
||||
|
|
|
|||
|
|
@ -89,7 +89,7 @@ class ImagePlaneLoader(load.LoaderPlugin):
|
|||
|
||||
product_types = {"image", "plate", "render"}
|
||||
label = "Load imagePlane"
|
||||
representations = ["mov", "exr", "preview", "png", "jpg"]
|
||||
representations = {"mov", "exr", "preview", "png", "jpg"}
|
||||
icon = "image"
|
||||
color = "orange"
|
||||
|
||||
|
|
@ -171,7 +171,7 @@ class ImagePlaneLoader(load.LoaderPlugin):
|
|||
plug = "{}.{}".format(image_plane_shape, attr)
|
||||
cmds.setAttr(plug, value)
|
||||
|
||||
movie_representations = ["mov", "preview"]
|
||||
movie_representations = {"mov", "preview"}
|
||||
if context["representation"]["name"] in movie_representations:
|
||||
cmds.setAttr(image_plane_shape + ".type", 2)
|
||||
|
||||
|
|
|
|||
|
|
@ -18,7 +18,7 @@ class LookLoader(ayon_core.hosts.maya.api.plugin.ReferenceLoader):
|
|||
"""Specific loader for lookdev"""
|
||||
|
||||
product_types = {"look"}
|
||||
representations = ["ma"]
|
||||
representations = {"ma"}
|
||||
|
||||
label = "Reference look"
|
||||
order = -10
|
||||
|
|
|
|||
|
|
@ -9,7 +9,7 @@ class MatchmoveLoader(load.LoaderPlugin):
|
|||
"""
|
||||
|
||||
product_types = {"matchmove"}
|
||||
representations = ["py", "mel"]
|
||||
representations = {"py", "mel"}
|
||||
defaults = ["Camera", "Object", "Mocap"]
|
||||
|
||||
label = "Run matchmove script"
|
||||
|
|
|
|||
|
|
@ -17,7 +17,7 @@ class MayaUsdLoader(load.LoaderPlugin):
|
|||
"""Read USD data in a Maya USD Proxy"""
|
||||
|
||||
product_types = {"model", "usd", "pointcache", "animation"}
|
||||
representations = ["usd", "usda", "usdc", "usdz", "abc"]
|
||||
representations = {"usd", "usda", "usdc", "usdz", "abc"}
|
||||
|
||||
label = "Load USD to Maya Proxy"
|
||||
order = -1
|
||||
|
|
|
|||
|
|
@ -28,7 +28,7 @@ class MultiverseUsdLoader(load.LoaderPlugin):
|
|||
"pointcache",
|
||||
"animation",
|
||||
}
|
||||
representations = ["usd", "usda", "usdc", "usdz", "abc"]
|
||||
representations = {"usd", "usda", "usdc", "usdz", "abc"}
|
||||
|
||||
label = "Load USD to Multiverse"
|
||||
order = -10
|
||||
|
|
|
|||
|
|
@ -20,7 +20,7 @@ class MultiverseUsdOverLoader(load.LoaderPlugin):
|
|||
"""Reference file"""
|
||||
|
||||
product_types = {"mvUsdOverride"}
|
||||
representations = ["usda", "usd", "udsz"]
|
||||
representations = {"usda", "usd", "udsz"}
|
||||
|
||||
label = "Load Usd Override into Compound"
|
||||
order = -10
|
||||
|
|
|
|||
|
|
@ -23,7 +23,7 @@ class RedshiftProxyLoader(load.LoaderPlugin):
|
|||
"""Load Redshift proxy"""
|
||||
|
||||
product_types = {"redshiftproxy"}
|
||||
representations = ["rs"]
|
||||
representations = {"rs"}
|
||||
|
||||
label = "Import Redshift Proxy"
|
||||
order = -10
|
||||
|
|
|
|||
|
|
@ -107,7 +107,7 @@ class ReferenceLoader(plugin.ReferenceLoader):
|
|||
"matchmove",
|
||||
}
|
||||
|
||||
representations = ["ma", "abc", "fbx", "mb"]
|
||||
representations = {"ma", "abc", "fbx", "mb"}
|
||||
|
||||
label = "Reference"
|
||||
order = -10
|
||||
|
|
@ -269,7 +269,7 @@ class MayaUSDReferenceLoader(ReferenceLoader):
|
|||
|
||||
label = "Reference Maya USD"
|
||||
product_types = {"usd"}
|
||||
representations = ["usd"]
|
||||
representations = {"usd"}
|
||||
extensions = {"usd", "usda", "usdc"}
|
||||
|
||||
options = ReferenceLoader.options + [
|
||||
|
|
|
|||
|
|
@ -52,7 +52,7 @@ class RenderSetupLoader(load.LoaderPlugin):
|
|||
"""Load json preset for RenderSetup overwriting current one."""
|
||||
|
||||
product_types = {"rendersetup"}
|
||||
representations = ["json"]
|
||||
representations = {"json"}
|
||||
defaults = ['Main']
|
||||
|
||||
label = "Load RenderSetup template"
|
||||
|
|
|
|||
|
|
@ -13,7 +13,7 @@ class LoadVDBtoArnold(load.LoaderPlugin):
|
|||
"""Load OpenVDB for Arnold in aiVolume"""
|
||||
|
||||
product_types = {"vdbcache"}
|
||||
representations = ["vdb"]
|
||||
representations = {"vdb"}
|
||||
|
||||
label = "Load VDB to Arnold"
|
||||
icon = "cloud"
|
||||
|
|
|
|||
|
|
@ -19,7 +19,7 @@ class LoadVDBtoRedShift(load.LoaderPlugin):
|
|||
"""
|
||||
|
||||
product_types = {"vdbcache"}
|
||||
representations = ["vdb"]
|
||||
representations = {"vdb"}
|
||||
|
||||
label = "Load VDB to RedShift"
|
||||
icon = "cloud"
|
||||
|
|
|
|||
|
|
@ -78,7 +78,7 @@ class LoadVDBtoVRay(load.LoaderPlugin):
|
|||
"""Load OpenVDB in a V-Ray Volume Grid"""
|
||||
|
||||
product_types = {"vdbcache"}
|
||||
representations = ["vdb"]
|
||||
representations = {"vdb"}
|
||||
|
||||
label = "Load VDB to VRay"
|
||||
icon = "cloud"
|
||||
|
|
|
|||
|
|
@ -28,7 +28,7 @@ class VRayProxyLoader(load.LoaderPlugin):
|
|||
"""Load VRay Proxy with Alembic or VrayMesh."""
|
||||
|
||||
product_types = {"vrayproxy", "model", "pointcache", "animation"}
|
||||
representations = ["vrmesh", "abc"]
|
||||
representations = {"vrmesh", "abc"}
|
||||
|
||||
label = "Import VRay Proxy"
|
||||
order = -10
|
||||
|
|
|
|||
|
|
@ -18,7 +18,7 @@ class VRaySceneLoader(load.LoaderPlugin):
|
|||
"""Load Vray scene"""
|
||||
|
||||
product_types = {"vrayscene_layer"}
|
||||
representations = ["vrscene"]
|
||||
representations = {"vrscene"}
|
||||
|
||||
label = "Import VRay Scene"
|
||||
order = -10
|
||||
|
|
|
|||
|
|
@ -21,7 +21,7 @@ class XgenLoader(ayon_core.hosts.maya.api.plugin.ReferenceLoader):
|
|||
"""Load Xgen as reference"""
|
||||
|
||||
product_types = {"xgen"}
|
||||
representations = ["ma", "mb"]
|
||||
representations = {"ma", "mb"}
|
||||
|
||||
label = "Reference Xgen"
|
||||
icon = "code-fork"
|
||||
|
|
|
|||
|
|
@ -37,7 +37,7 @@ class YetiCacheLoader(load.LoaderPlugin):
|
|||
"""Load Yeti Cache with one or more Yeti nodes"""
|
||||
|
||||
product_types = {"yeticache", "yetiRig"}
|
||||
representations = ["fur"]
|
||||
representations = {"fur"}
|
||||
|
||||
label = "Load Yeti Cache"
|
||||
order = -9
|
||||
|
|
|
|||
|
|
@ -8,7 +8,7 @@ class YetiRigLoader(plugin.ReferenceLoader):
|
|||
"""This loader will load Yeti rig."""
|
||||
|
||||
product_types = {"yetiRig"}
|
||||
representations = ["ma"]
|
||||
representations = {"ma"}
|
||||
|
||||
label = "Load Yeti Rig"
|
||||
order = -9
|
||||
|
|
|
|||
|
|
@ -8,7 +8,7 @@ from maya import cmds # noqa
|
|||
import pyblish.api
|
||||
from ayon_core.hosts.maya.api import lib
|
||||
|
||||
SHAPE_ATTRS = ["castsShadows",
|
||||
SHAPE_ATTRS = {"castsShadows",
|
||||
"receiveShadows",
|
||||
"motionBlur",
|
||||
"primaryVisibility",
|
||||
|
|
@ -16,8 +16,7 @@ SHAPE_ATTRS = ["castsShadows",
|
|||
"visibleInReflections",
|
||||
"visibleInRefractions",
|
||||
"doubleSided",
|
||||
"opposite"]
|
||||
SHAPE_ATTRS = set(SHAPE_ATTRS)
|
||||
"opposite"}
|
||||
|
||||
|
||||
def get_pxr_multitexture_file_attrs(node):
|
||||
|
|
@ -59,9 +58,8 @@ for node_type in list(FILE_NODES.keys()):
|
|||
if node_type not in all_node_types:
|
||||
FILE_NODES.pop(node_type)
|
||||
|
||||
for node_type in RENDER_SET_TYPES:
|
||||
if node_type not in all_node_types:
|
||||
RENDER_SET_TYPES.remove(node_type)
|
||||
RENDER_SET_TYPES = [node_type for node_type in RENDER_SET_TYPES
|
||||
if node_type in all_node_types]
|
||||
del all_node_types
|
||||
|
||||
# Cache pixar dependency node types so we can perform a type lookup against it
|
||||
|
|
@ -109,8 +107,7 @@ def get_look_attrs(node):
|
|||
if cmds.objectType(node, isAType="shape"):
|
||||
attrs = cmds.listAttr(node, changedSinceFileOpen=True) or []
|
||||
for attr in attrs:
|
||||
if attr in SHAPE_ATTRS or \
|
||||
attr not in SHAPE_ATTRS and attr.startswith('ai'):
|
||||
if attr in SHAPE_ATTRS or attr.startswith('ai'):
|
||||
result.append(attr)
|
||||
return result
|
||||
|
||||
|
|
@ -290,7 +287,6 @@ class CollectLook(pyblish.api.InstancePlugin):
|
|||
families = ["look"]
|
||||
label = "Collect Look"
|
||||
hosts = ["maya"]
|
||||
maketx = True
|
||||
|
||||
def process(self, instance):
|
||||
"""Collect the Look in the instance with the correct layer settings"""
|
||||
|
|
@ -302,15 +298,12 @@ class CollectLook(pyblish.api.InstancePlugin):
|
|||
"""Collect looks.
|
||||
|
||||
Args:
|
||||
instance: Instance to collect.
|
||||
instance (pyblish.api.Instance): Instance to collect.
|
||||
|
||||
"""
|
||||
self.log.debug("Looking for look associations "
|
||||
"for %s" % instance.data['name'])
|
||||
|
||||
# Lookup set (optimization)
|
||||
instance_lookup = set(cmds.ls(instance, long=True))
|
||||
|
||||
# Discover related object sets
|
||||
self.log.debug("Gathering sets ...")
|
||||
sets = self.collect_sets(instance)
|
||||
|
|
@ -351,75 +344,15 @@ class CollectLook(pyblish.api.InstancePlugin):
|
|||
# Collect file nodes used by shading engines (if we have any)
|
||||
files = []
|
||||
look_sets = list(sets.keys())
|
||||
shader_attrs = [
|
||||
"surfaceShader",
|
||||
"volumeShader",
|
||||
"displacementShader",
|
||||
"aiSurfaceShader",
|
||||
"aiVolumeShader",
|
||||
"rman__surface",
|
||||
"rman__displacement"
|
||||
]
|
||||
if look_sets:
|
||||
self.log.debug("Found look sets: {}".format(look_sets))
|
||||
|
||||
# Get all material attrs for all look sets to retrieve their inputs
|
||||
existing_attrs = []
|
||||
for look in look_sets:
|
||||
for attr in shader_attrs:
|
||||
if cmds.attributeQuery(attr, node=look, exists=True):
|
||||
existing_attrs.append("{}.{}".format(look, attr))
|
||||
|
||||
materials = cmds.listConnections(existing_attrs,
|
||||
source=True,
|
||||
destination=False) or []
|
||||
|
||||
self.log.debug("Found materials:\n{}".format(materials))
|
||||
|
||||
self.log.debug("Found the following sets:\n{}".format(look_sets))
|
||||
# Get the entire node chain of the look sets
|
||||
# history = cmds.listHistory(look_sets, allConnections=True)
|
||||
# if materials list is empty, listHistory() will crash with
|
||||
# RuntimeError
|
||||
history = set()
|
||||
if materials:
|
||||
history = set(
|
||||
cmds.listHistory(materials, allConnections=True))
|
||||
|
||||
# Since we retrieved history only of the connected materials
|
||||
# connected to the look sets above we now add direct history
|
||||
# for some of the look sets directly
|
||||
# handling render attribute sets
|
||||
|
||||
# Maya (at least 2024) crashes with Warning when render set type
|
||||
# isn't available. cmds.ls() will return empty list
|
||||
if RENDER_SET_TYPES:
|
||||
render_sets = cmds.ls(look_sets, type=RENDER_SET_TYPES)
|
||||
if render_sets:
|
||||
history.update(
|
||||
cmds.listHistory(render_sets,
|
||||
future=False,
|
||||
pruneDagObjects=True)
|
||||
or []
|
||||
)
|
||||
|
||||
# Ensure unique entries only
|
||||
history = list(history)
|
||||
|
||||
files = cmds.ls(history,
|
||||
# It's important only node types are passed that
|
||||
# exist (e.g. for loaded plugins) because otherwise
|
||||
# the result will turn back empty
|
||||
type=list(FILE_NODES.keys()),
|
||||
long=True)
|
||||
|
||||
# Sort for log readability
|
||||
files.sort()
|
||||
files = self.collect_file_nodes(look_sets)
|
||||
|
||||
self.log.debug("Collected file nodes:\n{}".format(files))
|
||||
# Collect textures if any file nodes are found
|
||||
|
||||
# Collect texture resources if any file nodes are found
|
||||
resources = []
|
||||
for node in files: # sort for log readability
|
||||
for node in files:
|
||||
resources.extend(self.collect_resources(node))
|
||||
instance.data["resources"] = resources
|
||||
self.log.debug("Collected resources: {}".format(resources))
|
||||
|
|
@ -439,6 +372,78 @@ class CollectLook(pyblish.api.InstancePlugin):
|
|||
|
||||
self.log.debug("Collected look for %s" % instance)
|
||||
|
||||
def collect_file_nodes(self, look_sets):
|
||||
"""Get the entire node chain of the look sets and return file nodes
|
||||
|
||||
Arguments:
|
||||
look_sets (List[str]): List of sets and shading engines relevant
|
||||
to the look.
|
||||
|
||||
Returns:
|
||||
List[str]: List of file node names.
|
||||
|
||||
"""
|
||||
|
||||
shader_attrs = [
|
||||
"surfaceShader",
|
||||
"volumeShader",
|
||||
"displacementShader",
|
||||
"aiSurfaceShader",
|
||||
"aiVolumeShader",
|
||||
"rman__surface",
|
||||
"rman__displacement"
|
||||
]
|
||||
|
||||
# Get all material attrs for all look sets to retrieve their inputs
|
||||
existing_attrs = []
|
||||
for look_set in look_sets:
|
||||
for attr in shader_attrs:
|
||||
if cmds.attributeQuery(attr, node=look_set, exists=True):
|
||||
existing_attrs.append("{}.{}".format(look_set, attr))
|
||||
|
||||
materials = cmds.listConnections(existing_attrs,
|
||||
source=True,
|
||||
destination=False) or []
|
||||
|
||||
self.log.debug("Found materials:\n{}".format(materials))
|
||||
|
||||
# Get the entire node chain of the look sets
|
||||
# history = cmds.listHistory(look_sets, allConnections=True)
|
||||
# if materials list is empty, listHistory() will crash with
|
||||
# RuntimeError
|
||||
history = set()
|
||||
if materials:
|
||||
history.update(cmds.listHistory(materials, allConnections=True))
|
||||
|
||||
# Since we retrieved history only of the connected materials connected
|
||||
# to the look sets above we now add direct history for some of the
|
||||
# look sets directly handling render attribute sets
|
||||
|
||||
# Maya (at least 2024) crashes with Warning when render set type
|
||||
# isn't available. cmds.ls() will return empty list
|
||||
if RENDER_SET_TYPES:
|
||||
render_sets = cmds.ls(look_sets, type=RENDER_SET_TYPES)
|
||||
if render_sets:
|
||||
history.update(
|
||||
cmds.listHistory(render_sets,
|
||||
future=False,
|
||||
pruneDagObjects=True)
|
||||
or []
|
||||
)
|
||||
|
||||
# Get file nodes in the material history
|
||||
files = cmds.ls(list(history),
|
||||
# It's important only node types are passed that
|
||||
# exist (e.g. for loaded plugins) because otherwise
|
||||
# the result will turn back empty
|
||||
type=list(FILE_NODES.keys()),
|
||||
long=True)
|
||||
|
||||
# Sort for log readability
|
||||
files.sort()
|
||||
|
||||
return files
|
||||
|
||||
def collect_sets(self, instance):
|
||||
"""Collect all objectSets which are of importance for publishing
|
||||
|
||||
|
|
@ -446,7 +451,8 @@ class CollectLook(pyblish.api.InstancePlugin):
|
|||
which need to be
|
||||
|
||||
Args:
|
||||
instance (list): all nodes to be published
|
||||
instance (pyblish.api.Instance): publish instance containing all
|
||||
nodes to be published.
|
||||
|
||||
Returns:
|
||||
dict
|
||||
|
|
@ -624,7 +630,7 @@ class CollectLook(pyblish.api.InstancePlugin):
|
|||
"source": source, # required for resources
|
||||
"files": files,
|
||||
"color_space": color_space
|
||||
} # required for resources
|
||||
}
|
||||
|
||||
|
||||
class CollectModelRenderSets(CollectLook):
|
||||
|
|
@ -639,13 +645,13 @@ class CollectModelRenderSets(CollectLook):
|
|||
families = ["model"]
|
||||
label = "Collect Model Render Sets"
|
||||
hosts = ["maya"]
|
||||
maketx = True
|
||||
|
||||
def collect_sets(self, instance):
|
||||
"""Collect all related objectSets except shadingEngines
|
||||
|
||||
Args:
|
||||
instance (list): all nodes to be published
|
||||
instance (pyblish.api.Instance): publish instance containing all
|
||||
nodes to be published.
|
||||
|
||||
Returns:
|
||||
dict
|
||||
|
|
@ -661,7 +667,7 @@ class CollectModelRenderSets(CollectLook):
|
|||
if objset in sets:
|
||||
continue
|
||||
|
||||
if "shadingEngine" in cmds.nodeType(objset, inherited=True):
|
||||
if cmds.objectType(objset, isAType="shadingEngine"):
|
||||
continue
|
||||
|
||||
sets[objset] = {"uuid": lib.get_id(objset), "members": list()}
|
||||
|
|
|
|||
|
|
@ -12,11 +12,7 @@ import logging
|
|||
from maya import cmds
|
||||
from maya import mel
|
||||
|
||||
try:
|
||||
from PySide2 import QtGui, QtWidgets
|
||||
except ImportError:
|
||||
from PySide import QtGui
|
||||
QtWidgets = QtGui
|
||||
from qtpy import QtGui, QtWidgets
|
||||
|
||||
version_info = (2, 3, 0)
|
||||
|
||||
|
|
@ -873,7 +869,11 @@ def _get_screen_size():
|
|||
if _in_standalone():
|
||||
return [0, 0]
|
||||
|
||||
rect = QtWidgets.QDesktopWidget().screenGeometry(-1)
|
||||
try:
|
||||
rect = QtWidgets.QDesktopWidget().screenGeometry(-1)
|
||||
except AttributeError:
|
||||
# in Qt6 it is a different call
|
||||
rect = QtWidgets.QApplication.primaryScreen().availableGeometry()
|
||||
return [rect.width(), rect.height()]
|
||||
|
||||
|
||||
|
|
@ -19,7 +19,7 @@ class SetFrameRangeLoader(load.LoaderPlugin):
|
|||
"yeticache",
|
||||
"pointcache",
|
||||
}
|
||||
representations = ["*"]
|
||||
representations = {"*"}
|
||||
extensions = {"*"}
|
||||
|
||||
label = "Set frame range"
|
||||
|
|
@ -53,7 +53,7 @@ class SetFrameRangeWithHandlesLoader(load.LoaderPlugin):
|
|||
"yeticache",
|
||||
"pointcache",
|
||||
}
|
||||
representations = ["*"]
|
||||
representations = {"*"}
|
||||
|
||||
label = "Set frame range (with handles)"
|
||||
order = 12
|
||||
|
|
|
|||
|
|
@ -22,7 +22,7 @@ class LoadBackdropNodes(load.LoaderPlugin):
|
|||
"""Loading Published Backdrop nodes (workfile, nukenodes)"""
|
||||
|
||||
product_types = {"workfile", "nukenodes"}
|
||||
representations = ["*"]
|
||||
representations = {"*"}
|
||||
extensions = {"nk"}
|
||||
|
||||
label = "Import Nuke Nodes"
|
||||
|
|
|
|||
|
|
@ -21,7 +21,7 @@ class AlembicCameraLoader(load.LoaderPlugin):
|
|||
"""
|
||||
|
||||
product_types = {"camera"}
|
||||
representations = ["*"]
|
||||
representations = {"*"}
|
||||
extensions = {"abc"}
|
||||
|
||||
label = "Load Alembic Camera"
|
||||
|
|
|
|||
|
|
@ -42,7 +42,7 @@ class LoadClip(plugin.NukeLoader):
|
|||
"prerender",
|
||||
"review",
|
||||
}
|
||||
representations = ["*"]
|
||||
representations = {"*"}
|
||||
extensions = set(
|
||||
ext.lstrip(".") for ext in IMAGE_EXTENSIONS.union(VIDEO_EXTENSIONS)
|
||||
)
|
||||
|
|
|
|||
|
|
@ -19,7 +19,7 @@ class LoadEffects(load.LoaderPlugin):
|
|||
"""Loading colorspace soft effect exported from nukestudio"""
|
||||
|
||||
product_types = {"effect"}
|
||||
representations = ["*"]
|
||||
representations = {"*"}
|
||||
extensions = {"json"}
|
||||
|
||||
label = "Load Effects - nodes"
|
||||
|
|
|
|||
|
|
@ -20,7 +20,7 @@ class LoadEffectsInputProcess(load.LoaderPlugin):
|
|||
"""Loading colorspace soft effect exported from nukestudio"""
|
||||
|
||||
product_types = {"effect"}
|
||||
representations = ["*"]
|
||||
representations = {"*"}
|
||||
extensions = {"json"}
|
||||
|
||||
label = "Load Effects - Input Process"
|
||||
|
|
|
|||
|
|
@ -22,7 +22,7 @@ class LoadGizmo(load.LoaderPlugin):
|
|||
"""Loading nuke Gizmo"""
|
||||
|
||||
product_types = {"gizmo"}
|
||||
representations = ["*"]
|
||||
representations = {"*"}
|
||||
extensions = {"nk"}
|
||||
|
||||
label = "Load Gizmo"
|
||||
|
|
|
|||
|
|
@ -24,7 +24,7 @@ class LoadGizmoInputProcess(load.LoaderPlugin):
|
|||
"""Loading colorspace soft effect exported from nukestudio"""
|
||||
|
||||
product_types = {"gizmo"}
|
||||
representations = ["*"]
|
||||
representations = {"*"}
|
||||
extensions = {"nk"}
|
||||
|
||||
label = "Load Gizmo - Input Process"
|
||||
|
|
|
|||
|
|
@ -32,7 +32,7 @@ class LoadImage(load.LoaderPlugin):
|
|||
"review",
|
||||
"image",
|
||||
}
|
||||
representations = ["*"]
|
||||
representations = {"*"}
|
||||
extensions = set(
|
||||
ext.lstrip(".") for ext in IMAGE_EXTENSIONS
|
||||
)
|
||||
|
|
|
|||
|
|
@ -8,7 +8,7 @@ class MatchmoveLoader(load.LoaderPlugin):
|
|||
"""
|
||||
|
||||
product_types = {"matchmove"}
|
||||
representations = ["*"]
|
||||
representations = {"*"}
|
||||
extensions = {"py"}
|
||||
|
||||
defaults = ["Camera", "Object"]
|
||||
|
|
|
|||
|
|
@ -19,7 +19,7 @@ class AlembicModelLoader(load.LoaderPlugin):
|
|||
"""
|
||||
|
||||
product_types = {"model", "pointcache", "animation"}
|
||||
representations = ["*"]
|
||||
representations = {"*"}
|
||||
extensions = {"abc"}
|
||||
|
||||
label = "Load Alembic"
|
||||
|
|
|
|||
Some files were not shown because too many files have changed in this diff Show more
Loading…
Add table
Add a link
Reference in a new issue