mirror of
https://github.com/ynput/ayon-core.git
synced 2025-12-24 21:04:40 +01:00
Merge branch 'develop' into 2.x/develop
This commit is contained in:
commit
1f9a20ec02
233 changed files with 11532 additions and 221 deletions
|
|
@ -1,3 +1,7 @@
|
|||
from .settings import (
|
||||
system_settings,
|
||||
project_settings
|
||||
)
|
||||
from pypeapp import (
|
||||
Logger,
|
||||
Anatomy,
|
||||
|
|
@ -49,6 +53,9 @@ from .lib import (
|
|||
from .lib import _subprocess as subprocess
|
||||
|
||||
__all__ = [
|
||||
"system_settings",
|
||||
"project_settings",
|
||||
|
||||
"Logger",
|
||||
"Anatomy",
|
||||
"project_overrides_dir_path",
|
||||
|
|
|
|||
|
|
@ -46,13 +46,14 @@ class ResolvePrelaunch(PypeHook):
|
|||
"`RESOLVE_UTILITY_SCRIPTS_DIR` or reinstall DaVinci Resolve. \n"
|
||||
f"RESOLVE_UTILITY_SCRIPTS_DIR: `{us_dir}`"
|
||||
)
|
||||
self.log.debug(f"-- us_dir: `{us_dir}`")
|
||||
|
||||
# correctly format path for pre python script
|
||||
pre_py_sc = os.path.normpath(env.get("PRE_PYTHON_SCRIPT", ""))
|
||||
env["PRE_PYTHON_SCRIPT"] = pre_py_sc
|
||||
|
||||
self.log.debug(f"-- pre_py_sc: `{pre_py_sc}`...")
|
||||
try:
|
||||
__import__("pype.resolve")
|
||||
__import__("pype.hosts.resolve")
|
||||
__import__("pyblish")
|
||||
|
||||
except ImportError as e:
|
||||
|
|
@ -62,6 +63,7 @@ class ResolvePrelaunch(PypeHook):
|
|||
else:
|
||||
# Resolve Setup integration
|
||||
importlib.reload(utils)
|
||||
self.log.debug(f"-- utils.__file__: `{utils.__file__}`")
|
||||
utils.setup(env)
|
||||
|
||||
return True
|
||||
|
|
|
|||
|
|
@ -1,17 +1,34 @@
|
|||
from .utils import (
|
||||
setup,
|
||||
get_resolve_module
|
||||
)
|
||||
|
||||
from .pipeline import (
|
||||
install,
|
||||
uninstall,
|
||||
ls,
|
||||
containerise,
|
||||
publish,
|
||||
launch_workfiles_app
|
||||
launch_workfiles_app,
|
||||
maintained_selection
|
||||
)
|
||||
|
||||
from .utils import (
|
||||
setup,
|
||||
get_resolve_module
|
||||
from .lib import (
|
||||
get_project_manager,
|
||||
get_current_project,
|
||||
get_current_sequence,
|
||||
get_current_track_items,
|
||||
create_current_sequence_media_bin,
|
||||
create_compound_clip,
|
||||
swap_clips,
|
||||
get_pype_clip_metadata,
|
||||
set_project_manager_to_folder_name
|
||||
)
|
||||
|
||||
from .menu import launch_pype_menu
|
||||
|
||||
from .plugin import Creator
|
||||
|
||||
from .workio import (
|
||||
open_file,
|
||||
save_file,
|
||||
|
|
@ -21,12 +38,8 @@ from .workio import (
|
|||
work_root
|
||||
)
|
||||
|
||||
from .lib import (
|
||||
get_project_manager,
|
||||
set_project_manager_to_folder_name
|
||||
)
|
||||
|
||||
from .menu import launch_pype_menu
|
||||
bmdvr = None
|
||||
bmdvf = None
|
||||
|
||||
__all__ = [
|
||||
# pipeline
|
||||
|
|
@ -37,6 +50,7 @@ __all__ = [
|
|||
"reload_pipeline",
|
||||
"publish",
|
||||
"launch_workfiles_app",
|
||||
"maintained_selection",
|
||||
|
||||
# utils
|
||||
"setup",
|
||||
|
|
@ -44,16 +58,30 @@ __all__ = [
|
|||
|
||||
# lib
|
||||
"get_project_manager",
|
||||
"get_current_project",
|
||||
"get_current_sequence",
|
||||
"get_current_track_items",
|
||||
"create_current_sequence_media_bin",
|
||||
"create_compound_clip",
|
||||
"swap_clips",
|
||||
"get_pype_clip_metadata",
|
||||
"set_project_manager_to_folder_name",
|
||||
|
||||
# menu
|
||||
"launch_pype_menu",
|
||||
|
||||
# plugin
|
||||
"Creator",
|
||||
|
||||
# workio
|
||||
"open_file",
|
||||
"save_file",
|
||||
"current_file",
|
||||
"has_unsaved_changes",
|
||||
"file_extensions",
|
||||
"work_root"
|
||||
"work_root",
|
||||
|
||||
# singleton with black magic resolve module
|
||||
"bmdvr",
|
||||
"bmdvf"
|
||||
]
|
||||
|
|
|
|||
|
|
@ -21,9 +21,9 @@ class SelectInvalidAction(pyblish.api.Action):
|
|||
def process(self, context, plugin):
|
||||
|
||||
try:
|
||||
from pype.hosts.resolve.utils import get_resolve_module
|
||||
resolve = get_resolve_module()
|
||||
self.log.debug(resolve)
|
||||
from . import get_project_manager
|
||||
pm = get_project_manager()
|
||||
self.log.debug(pm)
|
||||
except ImportError:
|
||||
raise ImportError("Current host is not Resolve")
|
||||
|
||||
|
|
|
|||
|
|
@ -1,20 +1,406 @@
|
|||
import sys
|
||||
from .utils import get_resolve_module
|
||||
from pypeapp import Logger
|
||||
import json
|
||||
from opentimelineio import opentime
|
||||
from pprint import pformat
|
||||
|
||||
from pype.api import Logger
|
||||
|
||||
log = Logger().get_logger(__name__, "resolve")
|
||||
|
||||
self = sys.modules[__name__]
|
||||
self.pm = None
|
||||
self.rename_index = 0
|
||||
self.rename_add = 0
|
||||
self.pype_metadata_key = "VFX Notes"
|
||||
|
||||
|
||||
def get_project_manager():
|
||||
from . import bmdvr
|
||||
if not self.pm:
|
||||
resolve = get_resolve_module()
|
||||
self.pm = resolve.GetProjectManager()
|
||||
self.pm = bmdvr.GetProjectManager()
|
||||
return self.pm
|
||||
|
||||
|
||||
def get_current_project():
|
||||
# initialize project manager
|
||||
get_project_manager()
|
||||
|
||||
return self.pm.GetCurrentProject()
|
||||
|
||||
|
||||
def get_current_sequence():
|
||||
# get current project
|
||||
project = get_current_project()
|
||||
|
||||
return project.GetCurrentTimeline()
|
||||
|
||||
|
||||
def get_current_track_items(
|
||||
filter=False,
|
||||
track_type=None,
|
||||
selecting_color=None):
|
||||
""" Gets all available current timeline track items
|
||||
"""
|
||||
track_type = track_type or "video"
|
||||
selecting_color = selecting_color or "Chocolate"
|
||||
project = get_current_project()
|
||||
sequence = get_current_sequence()
|
||||
selected_clips = list()
|
||||
|
||||
# get all tracks count filtered by track type
|
||||
selected_track_count = sequence.GetTrackCount(track_type)
|
||||
|
||||
# loop all tracks and get items
|
||||
_clips = dict()
|
||||
for track_index in range(1, (int(selected_track_count) + 1)):
|
||||
track_name = sequence.GetTrackName(track_type, track_index)
|
||||
track_track_items = sequence.GetItemListInTrack(
|
||||
track_type, track_index)
|
||||
_clips[track_index] = track_track_items
|
||||
|
||||
_data = {
|
||||
"project": project,
|
||||
"sequence": sequence,
|
||||
"track": {
|
||||
"name": track_name,
|
||||
"index": track_index,
|
||||
"type": track_type}
|
||||
}
|
||||
# get track item object and its color
|
||||
for clip_index, ti in enumerate(_clips[track_index]):
|
||||
data = _data.copy()
|
||||
data["clip"] = {
|
||||
"item": ti,
|
||||
"index": clip_index
|
||||
}
|
||||
ti_color = ti.GetClipColor()
|
||||
if filter is True:
|
||||
if selecting_color in ti_color:
|
||||
selected_clips.append(data)
|
||||
# ti.ClearClipColor()
|
||||
else:
|
||||
selected_clips.append(data)
|
||||
|
||||
return selected_clips
|
||||
|
||||
|
||||
def create_current_sequence_media_bin(sequence):
|
||||
seq_name = sequence.GetName()
|
||||
media_pool = get_current_project().GetMediaPool()
|
||||
root_folder = media_pool.GetRootFolder()
|
||||
sub_folders = root_folder.GetSubFolderList()
|
||||
testing_names = list()
|
||||
|
||||
print(f"_ sub_folders: {sub_folders}")
|
||||
for subfolder in sub_folders:
|
||||
subf_name = subfolder.GetName()
|
||||
if seq_name in subf_name:
|
||||
testing_names.append(subfolder)
|
||||
else:
|
||||
testing_names.append(False)
|
||||
|
||||
matching = next((f for f in testing_names if f is not False), None)
|
||||
|
||||
if not matching:
|
||||
new_folder = media_pool.AddSubFolder(root_folder, seq_name)
|
||||
media_pool.SetCurrentFolder(new_folder)
|
||||
else:
|
||||
media_pool.SetCurrentFolder(matching)
|
||||
|
||||
return media_pool.GetCurrentFolder()
|
||||
|
||||
|
||||
def get_name_with_data(clip_data, presets):
|
||||
"""
|
||||
Take hierarchy data from presets and build name with parents data
|
||||
|
||||
Args:
|
||||
clip_data (dict): clip data from `get_current_track_items()`
|
||||
presets (dict): data from create plugin
|
||||
|
||||
Returns:
|
||||
list: name, data
|
||||
|
||||
"""
|
||||
def _replace_hash_to_expression(name, text):
|
||||
_spl = text.split("#")
|
||||
_len = (len(_spl) - 1)
|
||||
_repl = f"{{{name}:0>{_len}}}"
|
||||
new_text = text.replace(("#" * _len), _repl)
|
||||
return new_text
|
||||
|
||||
# presets data
|
||||
clip_name = presets["clipName"]
|
||||
hierarchy = presets["hierarchy"]
|
||||
hierarchy_data = presets["hierarchyData"].copy()
|
||||
count_from = presets["countFrom"]
|
||||
steps = presets["steps"]
|
||||
|
||||
# reset rename_add
|
||||
if self.rename_add < count_from:
|
||||
self.rename_add = count_from
|
||||
|
||||
# shot num calculate
|
||||
if self.rename_index == 0:
|
||||
shot_num = self.rename_add
|
||||
else:
|
||||
shot_num = self.rename_add + steps
|
||||
|
||||
print(f"shot_num: {shot_num}")
|
||||
|
||||
# clip data
|
||||
_data = {
|
||||
"sequence": clip_data["sequence"].GetName(),
|
||||
"track": clip_data["track"]["name"].replace(" ", "_"),
|
||||
"shot": shot_num
|
||||
}
|
||||
|
||||
# solve # in test to pythonic explression
|
||||
for k, v in hierarchy_data.items():
|
||||
if "#" not in v:
|
||||
continue
|
||||
hierarchy_data[k] = _replace_hash_to_expression(k, v)
|
||||
|
||||
# fill up pythonic expresisons
|
||||
for k, v in hierarchy_data.items():
|
||||
hierarchy_data[k] = v.format(**_data)
|
||||
|
||||
# fill up clip name and hierarchy keys
|
||||
hierarchy = hierarchy.format(**hierarchy_data)
|
||||
clip_name = clip_name.format(**hierarchy_data)
|
||||
|
||||
self.rename_add = shot_num
|
||||
print(f"shot_num: {shot_num}")
|
||||
|
||||
return (clip_name, {
|
||||
"hierarchy": hierarchy,
|
||||
"hierarchyData": hierarchy_data
|
||||
})
|
||||
|
||||
|
||||
def create_compound_clip(clip_data, folder, rename=False, **kwargs):
|
||||
"""
|
||||
Convert timeline object into nested timeline object
|
||||
|
||||
Args:
|
||||
clip_data (dict): timeline item object packed into dict
|
||||
with project, timeline (sequence)
|
||||
folder (resolve.MediaPool.Folder): media pool folder object,
|
||||
rename (bool)[optional]: renaming in sequence or not
|
||||
kwargs (optional): additional data needed for rename=True (presets)
|
||||
|
||||
Returns:
|
||||
resolve.MediaPoolItem: media pool item with compound clip timeline(cct)
|
||||
"""
|
||||
# get basic objects form data
|
||||
project = clip_data["project"]
|
||||
sequence = clip_data["sequence"]
|
||||
clip = clip_data["clip"]
|
||||
|
||||
# get details of objects
|
||||
clip_item = clip["item"]
|
||||
track = clip_data["track"]
|
||||
|
||||
mp = project.GetMediaPool()
|
||||
|
||||
# get clip attributes
|
||||
clip_attributes = get_clip_attributes(clip_item)
|
||||
print(f"_ clip_attributes: {pformat(clip_attributes)}")
|
||||
|
||||
if rename:
|
||||
presets = kwargs.get("presets")
|
||||
if presets:
|
||||
name, data = get_name_with_data(clip_data, presets)
|
||||
# add hirarchy data to clip attributes
|
||||
clip_attributes.update(data)
|
||||
else:
|
||||
name = "{:0>3}_{:0>4}".format(
|
||||
int(track["index"]), int(clip["index"]))
|
||||
else:
|
||||
# build name
|
||||
clip_name_split = clip_item.GetName().split(".")
|
||||
name = "_".join([
|
||||
track["name"],
|
||||
str(track["index"]),
|
||||
clip_name_split[0],
|
||||
str(clip["index"])]
|
||||
)
|
||||
|
||||
# get metadata
|
||||
mp_item = clip_item.GetMediaPoolItem()
|
||||
mp_props = mp_item.GetClipProperty()
|
||||
|
||||
mp_first_frame = int(mp_props["Start"])
|
||||
mp_last_frame = int(mp_props["End"])
|
||||
|
||||
# initialize basic source timing for otio
|
||||
ci_l_offset = clip_item.GetLeftOffset()
|
||||
ci_duration = clip_item.GetDuration()
|
||||
rate = float(mp_props["FPS"])
|
||||
|
||||
# source rational times
|
||||
mp_in_rc = opentime.RationalTime((ci_l_offset), rate)
|
||||
mp_out_rc = opentime.RationalTime((ci_l_offset + ci_duration - 1), rate)
|
||||
|
||||
# get frame in and out for clip swaping
|
||||
in_frame = opentime.to_frames(mp_in_rc)
|
||||
out_frame = opentime.to_frames(mp_out_rc)
|
||||
|
||||
# keep original sequence
|
||||
sq_origin = sequence
|
||||
|
||||
# Set current folder to input media_pool_folder:
|
||||
mp.SetCurrentFolder(folder)
|
||||
|
||||
# check if clip doesnt exist already:
|
||||
clips = folder.GetClipList()
|
||||
cct = next((c for c in clips
|
||||
if c.GetName() in name), None)
|
||||
|
||||
if cct:
|
||||
print(f"_ cct exists: {cct}")
|
||||
else:
|
||||
# Create empty timeline in current folder and give name:
|
||||
cct = mp.CreateEmptyTimeline(name)
|
||||
|
||||
# check if clip doesnt exist already:
|
||||
clips = folder.GetClipList()
|
||||
cct = next((c for c in clips
|
||||
if c.GetName() in name), None)
|
||||
print(f"_ cct created: {cct}")
|
||||
|
||||
# Set current timeline to created timeline:
|
||||
project.SetCurrentTimeline(cct)
|
||||
|
||||
# Add input clip to the current timeline:
|
||||
mp.AppendToTimeline([{
|
||||
"mediaPoolItem": mp_item,
|
||||
"startFrame": mp_first_frame,
|
||||
"endFrame": mp_last_frame
|
||||
}])
|
||||
|
||||
# Set current timeline to the working timeline:
|
||||
project.SetCurrentTimeline(sq_origin)
|
||||
|
||||
# Add collected metadata and attributes to the comound clip:
|
||||
if mp_item.GetMetadata(self.pype_metadata_key):
|
||||
clip_attributes[self.pype_metadata_key] = mp_item.GetMetadata(
|
||||
self.pype_metadata_key)[self.pype_metadata_key]
|
||||
|
||||
# stringify
|
||||
clip_attributes = json.dumps(clip_attributes)
|
||||
|
||||
# add attributes to metadata
|
||||
for k, v in mp_item.GetMetadata().items():
|
||||
cct.SetMetadata(k, v)
|
||||
|
||||
# add metadata to cct
|
||||
cct.SetMetadata(self.pype_metadata_key, clip_attributes)
|
||||
|
||||
# reset start timecode of the compound clip
|
||||
cct.SetClipProperty("Start TC", mp_props["Start TC"])
|
||||
|
||||
# swap clips on timeline
|
||||
swap_clips(clip_item, cct, name, in_frame, out_frame)
|
||||
|
||||
cct.SetClipColor("Pink")
|
||||
return cct
|
||||
|
||||
|
||||
def swap_clips(from_clip, to_clip, to_clip_name, to_in_frame, to_out_frame):
|
||||
"""
|
||||
Swaping clips on timeline in timelineItem
|
||||
|
||||
It will add take and activate it to the frame range which is inputted
|
||||
|
||||
Args:
|
||||
from_clip (resolve.mediaPoolItem)
|
||||
to_clip (resolve.mediaPoolItem)
|
||||
to_clip_name (str): name of to_clip
|
||||
to_in_frame (float): cut in frame, usually `GetLeftOffset()`
|
||||
to_out_frame (float): cut out frame, usually left offset plus duration
|
||||
|
||||
Returns:
|
||||
bool: True if successfully replaced
|
||||
|
||||
"""
|
||||
# add clip item as take to timeline
|
||||
take = from_clip.AddTake(
|
||||
to_clip,
|
||||
float(to_in_frame),
|
||||
float(to_out_frame)
|
||||
)
|
||||
|
||||
if not take:
|
||||
return False
|
||||
|
||||
for take_index in range(1, (int(from_clip.GetTakesCount()) + 1)):
|
||||
take_item = from_clip.GetTakeByIndex(take_index)
|
||||
take_mp_item = take_item["mediaPoolItem"]
|
||||
if to_clip_name in take_mp_item.GetName():
|
||||
from_clip.SelectTakeByIndex(take_index)
|
||||
from_clip.FinalizeTake()
|
||||
return True
|
||||
return False
|
||||
|
||||
|
||||
def validate_tc(x):
|
||||
# Validate and reformat timecode string
|
||||
|
||||
if len(x) != 11:
|
||||
print('Invalid timecode. Try again.')
|
||||
|
||||
c = ':'
|
||||
colonized = x[:2] + c + x[3:5] + c + x[6:8] + c + x[9:]
|
||||
|
||||
if colonized.replace(':', '').isdigit():
|
||||
print(f"_ colonized: {colonized}")
|
||||
return colonized
|
||||
else:
|
||||
print('Invalid timecode. Try again.')
|
||||
|
||||
|
||||
def get_pype_clip_metadata(clip):
|
||||
"""
|
||||
Get pype metadata created by creator plugin
|
||||
|
||||
Attributes:
|
||||
clip (resolve.TimelineItem): resolve's object
|
||||
|
||||
Returns:
|
||||
dict: hierarchy, orig clip attributes
|
||||
"""
|
||||
mp_item = clip.GetMediaPoolItem()
|
||||
metadata = mp_item.GetMetadata()
|
||||
|
||||
return metadata.get(self.pype_metadata_key)
|
||||
|
||||
|
||||
def get_clip_attributes(clip):
|
||||
"""
|
||||
Collect basic atrributes from resolve timeline item
|
||||
|
||||
Args:
|
||||
clip (resolve.TimelineItem): timeline item object
|
||||
|
||||
Returns:
|
||||
dict: all collected attributres as key: values
|
||||
"""
|
||||
mp_item = clip.GetMediaPoolItem()
|
||||
|
||||
data = {
|
||||
"clipIn": clip.GetStart(),
|
||||
"clipOut": clip.GetEnd(),
|
||||
"clipLeftOffset": clip.GetLeftOffset(),
|
||||
"clipRightOffset": clip.GetRightOffset(),
|
||||
"clipMarkers": clip.GetMarkers(),
|
||||
"clipFlags": clip.GetFlagList(),
|
||||
"sourceId": mp_item.GetMediaId(),
|
||||
"sourceProperties": mp_item.GetClipProperty()
|
||||
}
|
||||
return data
|
||||
|
||||
|
||||
def set_project_manager_to_folder_name(folder_name):
|
||||
"""
|
||||
Sets context of Project manager to given folder by name.
|
||||
|
|
|
|||
|
|
@ -1,6 +1,7 @@
|
|||
QWidget {
|
||||
background-color: #282828;
|
||||
border-radius: 3;
|
||||
font-size: 13px;
|
||||
}
|
||||
|
||||
QPushButton {
|
||||
|
|
@ -20,10 +21,38 @@ QPushButton:hover {
|
|||
color: #e64b3d;
|
||||
}
|
||||
|
||||
QSpinBox {
|
||||
border: 1px solid #090909;
|
||||
background-color: #201f1f;
|
||||
color: #ffffff;
|
||||
padding: 2;
|
||||
max-width: 8em;
|
||||
qproperty-alignment: AlignCenter;
|
||||
}
|
||||
|
||||
QLineEdit {
|
||||
border: 1px solid #090909;
|
||||
border-radius: 3px;
|
||||
background-color: #201f1f;
|
||||
color: #ffffff;
|
||||
padding: 2;
|
||||
min-width: 10em;
|
||||
qproperty-alignment: AlignCenter;
|
||||
}
|
||||
|
||||
#PypeMenu {
|
||||
border: 1px solid #fef9ef;
|
||||
}
|
||||
|
||||
#Spacer {
|
||||
QVBoxLayout {
|
||||
background-color: #282828;
|
||||
}
|
||||
|
||||
#Devider {
|
||||
border: 1px solid #090909;
|
||||
background-color: #585858;
|
||||
}
|
||||
|
||||
QLabel {
|
||||
color: #77776b;
|
||||
}
|
||||
|
|
|
|||
|
|
@ -2,27 +2,23 @@
|
|||
Basic avalon integration
|
||||
"""
|
||||
import os
|
||||
# import sys
|
||||
import contextlib
|
||||
from avalon.tools import workfiles
|
||||
from avalon import api as avalon
|
||||
from pyblish import api as pyblish
|
||||
from pypeapp import Logger
|
||||
import pype
|
||||
from pype.api import Logger
|
||||
|
||||
log = Logger().get_logger(__name__, "resolve")
|
||||
|
||||
# self = sys.modules[__name__]
|
||||
|
||||
AVALON_CONFIG = os.environ["AVALON_CONFIG"]
|
||||
PARENT_DIR = os.path.dirname(__file__)
|
||||
PACKAGE_DIR = os.path.dirname(PARENT_DIR)
|
||||
PLUGINS_DIR = os.path.join(PACKAGE_DIR, "plugins")
|
||||
|
||||
LOAD_PATH = os.path.join(PLUGINS_DIR, "resolve", "load")
|
||||
CREATE_PATH = os.path.join(PLUGINS_DIR, "resolve", "create")
|
||||
INVENTORY_PATH = os.path.join(PLUGINS_DIR, "resolve", "inventory")
|
||||
LOAD_PATH = os.path.join(pype.PLUGINS_DIR, "resolve", "load")
|
||||
CREATE_PATH = os.path.join(pype.PLUGINS_DIR, "resolve", "create")
|
||||
INVENTORY_PATH = os.path.join(pype.PLUGINS_DIR, "resolve", "inventory")
|
||||
|
||||
PUBLISH_PATH = os.path.join(
|
||||
PLUGINS_DIR, "resolve", "publish"
|
||||
pype.PLUGINS_DIR, "resolve", "publish"
|
||||
).replace("\\", "/")
|
||||
|
||||
AVALON_CONTAINERS = ":AVALON_CONTAINERS"
|
||||
|
|
@ -40,11 +36,13 @@ def install():
|
|||
See the Maya equivalent for inspiration on how to implement this.
|
||||
|
||||
"""
|
||||
from . import get_resolve_module
|
||||
|
||||
# Disable all families except for the ones we explicitly want to see
|
||||
family_states = [
|
||||
"imagesequence",
|
||||
"mov"
|
||||
"mov",
|
||||
"clip"
|
||||
]
|
||||
avalon.data["familiesStateDefault"] = False
|
||||
avalon.data["familiesStateToggled"] = family_states
|
||||
|
|
@ -59,6 +57,8 @@ def install():
|
|||
avalon.register_plugin_path(avalon.Creator, CREATE_PATH)
|
||||
avalon.register_plugin_path(avalon.InventoryAction, INVENTORY_PATH)
|
||||
|
||||
get_resolve_module()
|
||||
|
||||
|
||||
def uninstall():
|
||||
"""Uninstall all tha was installed
|
||||
|
|
@ -140,3 +140,26 @@ def publish(parent):
|
|||
"""Shorthand to publish from within host"""
|
||||
from avalon.tools import publish
|
||||
return publish.show(parent)
|
||||
|
||||
|
||||
@contextlib.contextmanager
|
||||
def maintained_selection():
|
||||
"""Maintain selection during context
|
||||
|
||||
Example:
|
||||
>>> with maintained_selection():
|
||||
... node['selected'].setValue(True)
|
||||
>>> print(node['selected'].value())
|
||||
False
|
||||
"""
|
||||
try:
|
||||
# do the operation
|
||||
yield
|
||||
finally:
|
||||
pass
|
||||
|
||||
|
||||
def reset_selection():
|
||||
"""Deselect all selected nodes
|
||||
"""
|
||||
pass
|
||||
|
|
|
|||
|
|
@ -1,6 +1,182 @@
|
|||
import re
|
||||
from avalon import api
|
||||
# from pype.hosts.resolve import lib as drlib
|
||||
from pype.hosts import resolve
|
||||
from avalon.vendor import qargparse
|
||||
from pype.api import config
|
||||
|
||||
from Qt import QtWidgets, QtCore
|
||||
|
||||
|
||||
class CreatorWidget(QtWidgets.QDialog):
|
||||
|
||||
# output items
|
||||
items = dict()
|
||||
|
||||
def __init__(self, name, info, presets, parent=None):
|
||||
super(CreatorWidget, self).__init__(parent)
|
||||
|
||||
self.setObjectName(name)
|
||||
|
||||
self.setWindowFlags(
|
||||
QtCore.Qt.Window
|
||||
| QtCore.Qt.CustomizeWindowHint
|
||||
| QtCore.Qt.WindowTitleHint
|
||||
| QtCore.Qt.WindowCloseButtonHint
|
||||
| QtCore.Qt.WindowStaysOnTopHint
|
||||
)
|
||||
self.setWindowTitle(name or "Pype Creator Input")
|
||||
|
||||
# Where inputs and labels are set
|
||||
self.content_widget = [QtWidgets.QWidget(self)]
|
||||
top_layout = QtWidgets.QFormLayout(self.content_widget[0])
|
||||
top_layout.setObjectName("ContentLayout")
|
||||
top_layout.addWidget(Spacer(5, self))
|
||||
|
||||
# first add widget tag line
|
||||
top_layout.addWidget(QtWidgets.QLabel(info))
|
||||
|
||||
top_layout.addWidget(Spacer(5, self))
|
||||
|
||||
# main dynamic layout
|
||||
self.content_widget.append(QtWidgets.QWidget(self))
|
||||
content_layout = QtWidgets.QFormLayout(self.content_widget[-1])
|
||||
|
||||
# add preset data into input widget layout
|
||||
self.items = self.add_presets_to_layout(content_layout, presets)
|
||||
|
||||
# Confirmation buttons
|
||||
btns_widget = QtWidgets.QWidget(self)
|
||||
btns_layout = QtWidgets.QHBoxLayout(btns_widget)
|
||||
|
||||
cancel_btn = QtWidgets.QPushButton("Cancel")
|
||||
btns_layout.addWidget(cancel_btn)
|
||||
|
||||
ok_btn = QtWidgets.QPushButton("Ok")
|
||||
btns_layout.addWidget(ok_btn)
|
||||
|
||||
# Main layout of the dialog
|
||||
main_layout = QtWidgets.QVBoxLayout(self)
|
||||
main_layout.setContentsMargins(10, 10, 10, 10)
|
||||
main_layout.setSpacing(0)
|
||||
|
||||
# adding content widget
|
||||
for w in self.content_widget:
|
||||
main_layout.addWidget(w)
|
||||
|
||||
main_layout.addWidget(btns_widget)
|
||||
|
||||
ok_btn.clicked.connect(self._on_ok_clicked)
|
||||
cancel_btn.clicked.connect(self._on_cancel_clicked)
|
||||
|
||||
stylesheet = resolve.menu.load_stylesheet()
|
||||
self.setStyleSheet(stylesheet)
|
||||
|
||||
def _on_ok_clicked(self):
|
||||
self.result = self.value(self.items)
|
||||
self.close()
|
||||
|
||||
def _on_cancel_clicked(self):
|
||||
self.result = None
|
||||
self.close()
|
||||
|
||||
def value(self, data):
|
||||
for k, v in data.items():
|
||||
if isinstance(v, dict):
|
||||
print(f"nested: {k}")
|
||||
data[k] = self.value(v)
|
||||
elif getattr(v, "value", None):
|
||||
print(f"normal int: {k}")
|
||||
result = v.value()
|
||||
data[k] = result()
|
||||
else:
|
||||
print(f"normal text: {k}")
|
||||
result = v.text()
|
||||
data[k] = result()
|
||||
return data
|
||||
|
||||
def camel_case_split(self, text):
|
||||
matches = re.finditer(
|
||||
'.+?(?:(?<=[a-z])(?=[A-Z])|(?<=[A-Z])(?=[A-Z][a-z])|$)', text)
|
||||
return " ".join([str(m.group(0)).capitalize() for m in matches])
|
||||
|
||||
def create_row(self, layout, type, text, **kwargs):
|
||||
# get type attribute from qwidgets
|
||||
attr = getattr(QtWidgets, type)
|
||||
|
||||
# convert label text to normal capitalized text with spaces
|
||||
label_text = self.camel_case_split(text)
|
||||
|
||||
# assign the new text to lable widget
|
||||
label = QtWidgets.QLabel(label_text)
|
||||
label.setObjectName("LineLabel")
|
||||
|
||||
# create attribute name text strip of spaces
|
||||
attr_name = text.replace(" ", "")
|
||||
|
||||
# create attribute and assign default values
|
||||
setattr(
|
||||
self,
|
||||
attr_name,
|
||||
attr(parent=self))
|
||||
|
||||
# assign the created attribute to variable
|
||||
item = getattr(self, attr_name)
|
||||
for func, val in kwargs.items():
|
||||
if getattr(item, func):
|
||||
func_attr = getattr(item, func)
|
||||
func_attr(val)
|
||||
|
||||
# add to layout
|
||||
layout.addRow(label, item)
|
||||
|
||||
return item
|
||||
|
||||
def add_presets_to_layout(self, content_layout, data):
|
||||
for k, v in data.items():
|
||||
if isinstance(v, dict):
|
||||
# adding spacer between sections
|
||||
self.content_widget.append(QtWidgets.QWidget(self))
|
||||
devider = QtWidgets.QVBoxLayout(self.content_widget[-1])
|
||||
devider.addWidget(Spacer(5, self))
|
||||
devider.setObjectName("Devider")
|
||||
|
||||
# adding nested layout with label
|
||||
self.content_widget.append(QtWidgets.QWidget(self))
|
||||
nested_content_layout = QtWidgets.QFormLayout(
|
||||
self.content_widget[-1])
|
||||
nested_content_layout.setObjectName("NestedContentLayout")
|
||||
|
||||
# add nested key as label
|
||||
self.create_row(nested_content_layout, "QLabel", k)
|
||||
data[k] = self.add_presets_to_layout(nested_content_layout, v)
|
||||
elif isinstance(v, str):
|
||||
print(f"layout.str: {k}")
|
||||
print(f"content_layout: {content_layout}")
|
||||
data[k] = self.create_row(
|
||||
content_layout, "QLineEdit", k, setText=v)
|
||||
elif isinstance(v, int):
|
||||
print(f"layout.int: {k}")
|
||||
print(f"content_layout: {content_layout}")
|
||||
data[k] = self.create_row(
|
||||
content_layout, "QSpinBox", k, setValue=v)
|
||||
return data
|
||||
|
||||
|
||||
class Spacer(QtWidgets.QWidget):
|
||||
def __init__(self, height, *args, **kwargs):
|
||||
super(self.__class__, self).__init__(*args, **kwargs)
|
||||
|
||||
self.setFixedHeight(height)
|
||||
|
||||
real_spacer = QtWidgets.QWidget(self)
|
||||
real_spacer.setObjectName("Spacer")
|
||||
real_spacer.setFixedHeight(height)
|
||||
|
||||
layout = QtWidgets.QVBoxLayout(self)
|
||||
layout.setContentsMargins(0, 0, 0, 0)
|
||||
layout.addWidget(real_spacer)
|
||||
|
||||
self.setLayout(layout)
|
||||
|
||||
|
||||
def get_reference_node_parents(ref):
|
||||
|
|
@ -73,3 +249,25 @@ class SequenceLoader(api.Loader):
|
|||
"""Remove an existing `container`
|
||||
"""
|
||||
pass
|
||||
|
||||
|
||||
class Creator(api.Creator):
|
||||
"""Creator class wrapper
|
||||
"""
|
||||
marker_color = "Purple"
|
||||
|
||||
def __init__(self, *args, **kwargs):
|
||||
super(Creator, self).__init__(*args, **kwargs)
|
||||
self.presets = config.get_presets()['plugins']["resolve"][
|
||||
"create"].get(self.__class__.__name__, {})
|
||||
|
||||
# adding basic current context resolve objects
|
||||
self.project = resolve.get_current_project()
|
||||
self.sequence = resolve.get_current_sequence()
|
||||
|
||||
if (self.options or {}).get("useSelection"):
|
||||
self.selected = resolve.get_current_track_items(filter=True)
|
||||
else:
|
||||
self.selected = resolve.get_current_track_items(filter=False)
|
||||
|
||||
self.widget = CreatorWidget
|
||||
|
|
|
|||
|
|
@ -1,7 +1,7 @@
|
|||
#!/usr/bin/env python
|
||||
import time
|
||||
from pype.hosts.resolve.utils import get_resolve_module
|
||||
from pypeapp import Logger
|
||||
from pype.api import Logger
|
||||
|
||||
log = Logger().get_logger(__name__, "resolve")
|
||||
|
||||
|
|
|
|||
|
|
@ -3,7 +3,7 @@ import sys
|
|||
import avalon.api as avalon
|
||||
import pype
|
||||
|
||||
from pypeapp import Logger
|
||||
from pype.api import Logger
|
||||
|
||||
log = Logger().get_logger(__name__)
|
||||
|
||||
|
|
|
|||
|
|
@ -1,65 +0,0 @@
|
|||
#! python3
|
||||
# -*- coding: utf-8 -*-
|
||||
|
||||
|
||||
# convert clip def
|
||||
def convert_clip(timeline=None):
|
||||
"""Convert timeline item (clip) into compound clip pype container
|
||||
|
||||
Args:
|
||||
timeline (MediaPool.Timeline): Object of timeline
|
||||
|
||||
Returns:
|
||||
bool: `True` if success
|
||||
|
||||
Raises:
|
||||
Exception: description
|
||||
|
||||
"""
|
||||
pass
|
||||
|
||||
|
||||
# decorator function create_current_timeline_media_bin()
|
||||
def create_current_timeline_media_bin(timeline=None):
|
||||
"""Convert timeline item (clip) into compound clip pype container
|
||||
|
||||
Args:
|
||||
timeline (MediaPool.Timeline): Object of timeline
|
||||
|
||||
Returns:
|
||||
bool: `True` if success
|
||||
|
||||
Raises:
|
||||
Exception: description
|
||||
|
||||
"""
|
||||
pass
|
||||
|
||||
|
||||
# decorator function get_selected_track_items()
|
||||
def get_selected_track_items():
|
||||
"""Convert timeline item (clip) into compound clip pype container
|
||||
|
||||
Args:
|
||||
timeline (MediaPool.Timeline): Object of timeline
|
||||
|
||||
Returns:
|
||||
bool: `True` if success
|
||||
|
||||
Raises:
|
||||
Exception: description
|
||||
|
||||
"""
|
||||
print("testText")
|
||||
|
||||
|
||||
# PypeCompoundClip() class
|
||||
class PypeCompoundClip(object):
|
||||
"""docstring for ."""
|
||||
|
||||
def __init__(self, arg):
|
||||
super(self).__init__()
|
||||
self.arg = arg
|
||||
|
||||
def create_compound_clip(self):
|
||||
pass
|
||||
|
|
@ -1,57 +0,0 @@
|
|||
import os
|
||||
import sys
|
||||
import pype
|
||||
import importlib
|
||||
import pyblish.api
|
||||
import pyblish.util
|
||||
import avalon.api
|
||||
from avalon.tools import publish
|
||||
from pypeapp import Logger
|
||||
|
||||
log = Logger().get_logger(__name__)
|
||||
|
||||
|
||||
def main(env):
|
||||
# Registers pype's Global pyblish plugins
|
||||
pype.install()
|
||||
|
||||
# Register Host (and it's pyblish plugins)
|
||||
host_name = env["AVALON_APP"]
|
||||
# TODO not sure if use "pype." or "avalon." for host import
|
||||
host_import_str = f"pype.{host_name}"
|
||||
|
||||
try:
|
||||
host_module = importlib.import_module(host_import_str)
|
||||
except ModuleNotFoundError:
|
||||
log.error((
|
||||
f"Host \"{host_name}\" can't be imported."
|
||||
f" Import string \"{host_import_str}\" failed."
|
||||
))
|
||||
return False
|
||||
|
||||
avalon.api.install(host_module)
|
||||
|
||||
# Register additional paths
|
||||
addition_paths_str = env.get("PUBLISH_PATHS") or ""
|
||||
addition_paths = addition_paths_str.split(os.pathsep)
|
||||
for path in addition_paths:
|
||||
path = os.path.normpath(path)
|
||||
if not os.path.exists(path):
|
||||
continue
|
||||
|
||||
pyblish.api.register_plugin_path(path)
|
||||
|
||||
# Register project specific plugins
|
||||
project_name = os.environ["AVALON_PROJECT"]
|
||||
project_plugins_paths = env.get("PYPE_PROJECT_PLUGINS") or ""
|
||||
for path in project_plugins_paths.split(os.pathsep):
|
||||
plugin_path = os.path.join(path, project_name, "plugins")
|
||||
if os.path.exists(plugin_path):
|
||||
pyblish.api.register_plugin_path(plugin_path)
|
||||
|
||||
return publish.show()
|
||||
|
||||
|
||||
if __name__ == "__main__":
|
||||
result = main(os.environ)
|
||||
sys.exit(not bool(result))
|
||||
|
|
@ -1,35 +0,0 @@
|
|||
#! python3
|
||||
# -*- coding: utf-8 -*-
|
||||
import os
|
||||
from pypeapp import execute, Logger
|
||||
from pype.hosts.resolve.utils import get_resolve_module
|
||||
|
||||
log = Logger().get_logger("Resolve")
|
||||
|
||||
CURRENT_DIR = os.getenv("RESOLVE_UTILITY_SCRIPTS_DIR", "")
|
||||
python_dir = os.getenv("PYTHON36_RESOLVE")
|
||||
python_exe = os.path.normpath(
|
||||
os.path.join(python_dir, "python.exe")
|
||||
)
|
||||
|
||||
resolve = get_resolve_module()
|
||||
PM = resolve.GetProjectManager()
|
||||
P = PM.GetCurrentProject()
|
||||
|
||||
log.info(P.GetName())
|
||||
|
||||
|
||||
# ______________________________________________________
|
||||
# testing subprocessing Scripts
|
||||
testing_py = os.path.join(CURRENT_DIR, "ResolvePageSwitcher.py")
|
||||
testing_py = os.path.normpath(testing_py)
|
||||
log.info(f"Testing path to script: `{testing_py}`")
|
||||
|
||||
returncode = execute(
|
||||
[python_exe, os.path.normpath(testing_py)],
|
||||
env=dict(os.environ)
|
||||
)
|
||||
|
||||
# Check if output file exists
|
||||
if returncode != 0:
|
||||
log.error("Executing failed!")
|
||||
21
pype/hosts/resolve/utility_scripts/test.py
Normal file
21
pype/hosts/resolve/utility_scripts/test.py
Normal file
|
|
@ -0,0 +1,21 @@
|
|||
#! python3
|
||||
import sys
|
||||
from pype.api import Logger
|
||||
import DaVinciResolveScript as bmdvr
|
||||
|
||||
|
||||
log = Logger().get_logger(__name__)
|
||||
|
||||
|
||||
def main():
|
||||
import pype.hosts.resolve as bmdvr
|
||||
bm = bmdvr.utils.get_resolve_module()
|
||||
log.info(f"blackmagicmodule: {bm}")
|
||||
|
||||
|
||||
print(f"_>> bmdvr.scriptapp(Resolve): {bmdvr.scriptapp('Resolve')}")
|
||||
|
||||
|
||||
if __name__ == "__main__":
|
||||
result = main()
|
||||
sys.exit(not bool(result))
|
||||
|
|
@ -9,18 +9,16 @@ import os
|
|||
import shutil
|
||||
|
||||
from pypeapp import Logger
|
||||
|
||||
log = Logger().get_logger(__name__, "resolve")
|
||||
|
||||
self = sys.modules[__name__]
|
||||
self.bmd = None
|
||||
|
||||
|
||||
def get_resolve_module():
|
||||
from pype.hosts import resolve
|
||||
# dont run if already loaded
|
||||
if self.bmd:
|
||||
return self.bmd
|
||||
|
||||
if resolve.bmdvr:
|
||||
log.info(("resolve module is assigned to "
|
||||
f"`pype.hosts.resolve.bmdvr`: {resolve.bmdvr}"))
|
||||
return resolve.bmdvr
|
||||
try:
|
||||
"""
|
||||
The PYTHONPATH needs to be set correctly for this import
|
||||
|
|
@ -71,8 +69,14 @@ def get_resolve_module():
|
|||
)
|
||||
sys.exit()
|
||||
# assign global var and return
|
||||
self.bmd = bmd.scriptapp("Resolve")
|
||||
return self.bmd
|
||||
bmdvr = bmd.scriptapp("Resolve")
|
||||
# bmdvf = bmd.scriptapp("Fusion")
|
||||
resolve.bmdvr = bmdvr
|
||||
resolve.bmdvf = bmdvr.Fusion()
|
||||
log.info(("Assigning resolve module to "
|
||||
f"`pype.hosts.resolve.bmdvr`: {resolve.bmdvr}"))
|
||||
log.info(("Assigning resolve module to "
|
||||
f"`pype.hosts.resolve.bmdvf`: {resolve.bmdvf}"))
|
||||
|
||||
|
||||
def _sync_utility_scripts(env=None):
|
||||
|
|
|
|||
|
|
@ -2,8 +2,9 @@
|
|||
|
||||
import os
|
||||
from pypeapp import Logger
|
||||
from .lib import (
|
||||
from . import (
|
||||
get_project_manager,
|
||||
get_current_project,
|
||||
set_project_manager_to_folder_name
|
||||
)
|
||||
|
||||
|
|
@ -26,7 +27,7 @@ def save_file(filepath):
|
|||
pm = get_project_manager()
|
||||
file = os.path.basename(filepath)
|
||||
fname, _ = os.path.splitext(file)
|
||||
project = pm.GetCurrentProject()
|
||||
project = get_current_project()
|
||||
name = project.GetName()
|
||||
|
||||
if "Untitled Project" not in name:
|
||||
|
|
|
|||
5
pype/modules/websocket_server/__init__.py
Normal file
5
pype/modules/websocket_server/__init__.py
Normal file
|
|
@ -0,0 +1,5 @@
|
|||
from .websocket_server import WebSocketServer
|
||||
|
||||
|
||||
def tray_init(tray_widget, main_widget):
|
||||
return WebSocketServer()
|
||||
0
pype/modules/websocket_server/hosts/__init__.py
Normal file
0
pype/modules/websocket_server/hosts/__init__.py
Normal file
47
pype/modules/websocket_server/hosts/external_app_1.py
Normal file
47
pype/modules/websocket_server/hosts/external_app_1.py
Normal file
|
|
@ -0,0 +1,47 @@
|
|||
import asyncio
|
||||
|
||||
from pype.api import Logger
|
||||
from wsrpc_aiohttp import WebSocketRoute
|
||||
|
||||
log = Logger().get_logger("WebsocketServer")
|
||||
|
||||
|
||||
class ExternalApp1(WebSocketRoute):
|
||||
"""
|
||||
One route, mimicking external application (like Harmony, etc).
|
||||
All functions could be called from client.
|
||||
'do_notify' function calls function on the client - mimicking
|
||||
notification after long running job on the server or similar
|
||||
"""
|
||||
|
||||
def init(self, **kwargs):
|
||||
# Python __init__ must be return "self".
|
||||
# This method might return anything.
|
||||
log.debug("someone called ExternalApp1 route")
|
||||
return kwargs
|
||||
|
||||
async def server_function_one(self):
|
||||
log.info('In function one')
|
||||
|
||||
async def server_function_two(self):
|
||||
log.info('In function two')
|
||||
return 'function two'
|
||||
|
||||
async def server_function_three(self):
|
||||
log.info('In function three')
|
||||
asyncio.ensure_future(self.do_notify())
|
||||
return '{"message":"function tree"}'
|
||||
|
||||
async def server_function_four(self, *args, **kwargs):
|
||||
log.info('In function four args {} kwargs {}'.format(args, kwargs))
|
||||
ret = dict(**kwargs)
|
||||
ret["message"] = "function four received arguments"
|
||||
return str(ret)
|
||||
|
||||
# This method calls function on the client side
|
||||
async def do_notify(self):
|
||||
import time
|
||||
time.sleep(5)
|
||||
log.info('Calling function on server after delay')
|
||||
awesome = 'Somebody server_function_three method!'
|
||||
await self.socket.call('notify', result=awesome)
|
||||
179
pype/modules/websocket_server/test_client/wsrpc_client.html
Normal file
179
pype/modules/websocket_server/test_client/wsrpc_client.html
Normal file
|
|
@ -0,0 +1,179 @@
|
|||
<!DOCTYPE html>
|
||||
<html lang="en">
|
||||
<head>
|
||||
<meta charset="UTF-8">
|
||||
<title>Title</title>
|
||||
|
||||
<!-- CSS only -->
|
||||
<link rel="stylesheet" href="https://stackpath.bootstrapcdn.com/bootstrap/4.5.0/css/bootstrap.min.css" integrity="sha384-9aIt2nRpC12Uk9gS9baDl411NQApFmC26EwAOH8WgZl5MYYxFfc+NcPb1dKGj7Sk" crossorigin="anonymous">
|
||||
|
||||
<script src="https://code.jquery.com/jquery-3.5.1.slim.min.js" integrity="sha384-DfXdz2htPH0lsSSs5nCTpuj/zy4C+OGpamoFVy38MVBnE+IbbVYUew+OrCXaRkfj" crossorigin="anonymous"></script>
|
||||
<script src="https://cdn.jsdelivr.net/npm/popper.js@1.16.0/dist/umd/popper.min.js" integrity="sha384-Q6E9RHvbIyZFJoft+2mJbHaEWldlvI9IOYy5n3zV9zzTtmI3UksdQRVvoxMfooAo" crossorigin="anonymous"></script>
|
||||
<script src="https://stackpath.bootstrapcdn.com/bootstrap/4.5.0/js/bootstrap.min.js" integrity="sha384-OgVRvuATP1z7JjHLkuOU7Xw704+h835Lr+6QL9UvYjZE3Ipu6Tp75j7Bh/kR0JKI" crossorigin="anonymous"></script>
|
||||
|
||||
<script type="text/javascript" src="//unpkg.com/@wsrpc/client"></script>
|
||||
<script>
|
||||
WSRPC.DEBUG = true;
|
||||
WSRPC.TRACE = true;
|
||||
var url = (window.location.protocol==="https):"?"wss://":"ws://") + window.location.host + '/ws/';
|
||||
url = 'ws://localhost:8099/ws/';
|
||||
RPC = new WSRPC(url, 5000);
|
||||
|
||||
console.log(RPC.state());
|
||||
// Configure client API, that can be called from server
|
||||
RPC.addRoute('notify', function (data) {
|
||||
console.log('Server called client route "notify":', data);
|
||||
alert('Server called client route "notify":', data)
|
||||
return data.result;
|
||||
});
|
||||
RPC.connect();
|
||||
console.log(RPC.state());
|
||||
|
||||
$(document).ready(function() {
|
||||
function NoReturn(){
|
||||
// Call stateful route
|
||||
// After you call that route, server would execute 'notify' route on the
|
||||
// client, that is registered above.
|
||||
RPC.call('ExternalApp1.server_function_one').then(function (data) {
|
||||
console.log('Result for calling server route "server_function_one": ', data);
|
||||
alert('Function "server_function_two" returned: '+data);
|
||||
}, function (error) {
|
||||
alert(error);
|
||||
});
|
||||
}
|
||||
|
||||
function ReturnValue(){
|
||||
// Call stateful route
|
||||
// After you call that route, server would execute 'notify' route on the
|
||||
// client, that is registered above.
|
||||
RPC.call('ExternalApp1.server_function_two').then(function (data) {
|
||||
console.log('Result for calling server route "server_function_two": ', data);
|
||||
alert('Function "server_function_two" returned: '+data);
|
||||
}, function (error) {
|
||||
alert(error);
|
||||
});
|
||||
}
|
||||
|
||||
function ValueAndNotify(){
|
||||
// After you call that route, server would execute 'notify' route on the
|
||||
// client, that is registered above.
|
||||
RPC.call('ExternalApp1.server_function_three').then(function (data) {
|
||||
console.log('Result for calling server route "server_function_three": ', data);
|
||||
alert('Function "server_function_three" returned: '+data);
|
||||
}, function (error) {
|
||||
alert(error);
|
||||
});
|
||||
}
|
||||
|
||||
function SendValue(){
|
||||
// After you call that route, server would execute 'notify' route on the
|
||||
// client, that is registered above.
|
||||
RPC.call('ExternalApp1.server_function_four', {foo: 'one', bar:'two'}).then(function (data) {
|
||||
console.log('Result for calling server route "server_function_four": ', data);
|
||||
alert('Function "server_function_four" returned: '+data);
|
||||
}, function (error) {
|
||||
alert(error);
|
||||
});
|
||||
}
|
||||
|
||||
$('#noReturn').click(function() {
|
||||
NoReturn();
|
||||
})
|
||||
|
||||
$('#returnValue').click(function() {
|
||||
ReturnValue();
|
||||
})
|
||||
|
||||
$('#valueAndNotify').click(function() {
|
||||
ValueAndNotify();
|
||||
})
|
||||
|
||||
$('#sendValue').click(function() {
|
||||
SendValue();
|
||||
})
|
||||
|
||||
})
|
||||
|
||||
<!-- // Call stateless method-->
|
||||
<!-- RPC.call('test2').then(function (data) {-->
|
||||
<!-- console.log('Result for calling server route "test2"', data);-->
|
||||
<!-- });-->
|
||||
</script>
|
||||
</head>
|
||||
<body>
|
||||
|
||||
<div class="d-flex flex-column flex-md-row align-items-center p-3 px-md-4 mb-3 bg-white border-bottom shadow-sm">
|
||||
<h5 class="my-0 mr-md-auto font-weight-normal">Test of wsrpc javascript client</h5>
|
||||
|
||||
</div>
|
||||
|
||||
<div class="container">
|
||||
<div class="card-deck mb-3 text-center">
|
||||
<div class="card mb-4 shadow-sm">
|
||||
<div class="card-header">
|
||||
<h4 class="my-0 font-weight-normal">No return value</h4>
|
||||
</div>
|
||||
<div class="card-body">
|
||||
<ul class="list-unstyled mt-3 mb-4">
|
||||
<li>Calls server_function_one</li>
|
||||
<li>Function only logs on server</li>
|
||||
<li>No return value</li>
|
||||
<li> </li>
|
||||
<li> </li>
|
||||
<li> </li>
|
||||
</ul>
|
||||
<button type="button" id="noReturn" class="btn btn-lg btn-block btn-outline-primary">Call server</button>
|
||||
</div>
|
||||
</div>
|
||||
<div class="card mb-4 shadow-sm">
|
||||
<div class="card-header">
|
||||
<h4 class="my-0 font-weight-normal">Return value</h4>
|
||||
</div>
|
||||
<div class="card-body">
|
||||
<ul class="list-unstyled mt-3 mb-4">
|
||||
<li>Calls server_function_two</li>
|
||||
<li>Function logs on server</li>
|
||||
<li>Returns simple text value</li>
|
||||
<li> </li>
|
||||
<li> </li>
|
||||
<li> </li>
|
||||
</ul>
|
||||
<button type="button" id="returnValue" class="btn btn-lg btn-block btn-outline-primary">Call server</button>
|
||||
</div>
|
||||
</div>
|
||||
<div class="card mb-4 shadow-sm">
|
||||
<div class="card-header">
|
||||
<h4 class="my-0 font-weight-normal">Notify</h4>
|
||||
</div>
|
||||
<div class="card-body">
|
||||
<ul class="list-unstyled mt-3 mb-4">
|
||||
<li>Calls server_function_three</li>
|
||||
<li>Function logs on server</li>
|
||||
<li>Returns json payload </li>
|
||||
<li>Server then calls function ON the client after delay</li>
|
||||
<li> </li>
|
||||
</ul>
|
||||
<button type="button" id="valueAndNotify" class="btn btn-lg btn-block btn-outline-primary">Call server</button>
|
||||
</div>
|
||||
</div>
|
||||
<div class="card mb-4 shadow-sm">
|
||||
<div class="card-header">
|
||||
<h4 class="my-0 font-weight-normal">Send value</h4>
|
||||
</div>
|
||||
<div class="card-body">
|
||||
<ul class="list-unstyled mt-3 mb-4">
|
||||
<li>Calls server_function_four</li>
|
||||
<li>Function logs on server</li>
|
||||
<li>Returns modified sent values</li>
|
||||
<li> </li>
|
||||
<li> </li>
|
||||
<li> </li>
|
||||
</ul>
|
||||
<button type="button" id="sendValue" class="btn btn-lg btn-block btn-outline-primary">Call server</button>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
</body>
|
||||
</html>
|
||||
34
pype/modules/websocket_server/test_client/wsrpc_client.py
Normal file
34
pype/modules/websocket_server/test_client/wsrpc_client.py
Normal file
|
|
@ -0,0 +1,34 @@
|
|||
import asyncio
|
||||
|
||||
from wsrpc_aiohttp import WSRPCClient
|
||||
|
||||
"""
|
||||
Simple testing Python client for wsrpc_aiohttp
|
||||
Calls sequentially multiple methods on server
|
||||
"""
|
||||
|
||||
loop = asyncio.get_event_loop()
|
||||
|
||||
|
||||
async def main():
|
||||
print("main")
|
||||
client = WSRPCClient("ws://127.0.0.1:8099/ws/",
|
||||
loop=asyncio.get_event_loop())
|
||||
|
||||
client.add_route('notify', notify)
|
||||
await client.connect()
|
||||
print("connected")
|
||||
print(await client.proxy.ExternalApp1.server_function_one())
|
||||
print(await client.proxy.ExternalApp1.server_function_two())
|
||||
print(await client.proxy.ExternalApp1.server_function_three())
|
||||
print(await client.proxy.ExternalApp1.server_function_four(foo="one"))
|
||||
await client.close()
|
||||
|
||||
|
||||
def notify(socket, *args, **kwargs):
|
||||
print("called from server")
|
||||
|
||||
|
||||
if __name__ == "__main__":
|
||||
# loop.run_until_complete(main())
|
||||
asyncio.run(main())
|
||||
187
pype/modules/websocket_server/websocket_server.py
Normal file
187
pype/modules/websocket_server/websocket_server.py
Normal file
|
|
@ -0,0 +1,187 @@
|
|||
from pype.api import config, Logger
|
||||
|
||||
import threading
|
||||
from aiohttp import web
|
||||
import asyncio
|
||||
from wsrpc_aiohttp import STATIC_DIR, WebSocketAsync
|
||||
|
||||
import os
|
||||
import sys
|
||||
import pyclbr
|
||||
import importlib
|
||||
|
||||
log = Logger().get_logger("WebsocketServer")
|
||||
|
||||
|
||||
class WebSocketServer():
|
||||
"""
|
||||
Basic POC implementation of asychronic websocket RPC server.
|
||||
Uses class in external_app_1.py to mimic implementation for single
|
||||
external application.
|
||||
'test_client' folder contains two test implementations of client
|
||||
|
||||
WIP
|
||||
"""
|
||||
|
||||
def __init__(self):
|
||||
self.qaction = None
|
||||
self.failed_icon = None
|
||||
self._is_running = False
|
||||
default_port = 8099
|
||||
|
||||
try:
|
||||
self.presets = config.get_presets()["services"]["websocket_server"]
|
||||
except Exception:
|
||||
self.presets = {"default_port": default_port, "exclude_ports": []}
|
||||
log.debug((
|
||||
"There are not set presets for WebsocketServer."
|
||||
" Using defaults \"{}\""
|
||||
).format(str(self.presets)))
|
||||
|
||||
self.app = web.Application()
|
||||
|
||||
self.app.router.add_route("*", "/ws/", WebSocketAsync)
|
||||
self.app.router.add_static("/js", STATIC_DIR)
|
||||
self.app.router.add_static("/", ".")
|
||||
|
||||
# add route with multiple methods for single "external app"
|
||||
directories_with_routes = ['hosts']
|
||||
self.add_routes_for_directories(directories_with_routes)
|
||||
|
||||
self.websocket_thread = WebsocketServerThread(self, default_port)
|
||||
|
||||
def add_routes_for_directories(self, directories_with_routes):
|
||||
""" Loops through selected directories to find all modules and
|
||||
in them all classes implementing 'WebSocketRoute' that could be
|
||||
used as route.
|
||||
All methods in these classes are registered automatically.
|
||||
"""
|
||||
for dir_name in directories_with_routes:
|
||||
dir_name = os.path.join(os.path.dirname(__file__), dir_name)
|
||||
for file_name in os.listdir(dir_name):
|
||||
if '.py' in file_name and '__' not in file_name:
|
||||
self.add_routes_for_module(file_name, dir_name)
|
||||
|
||||
def add_routes_for_module(self, file_name, dir_name):
|
||||
""" Auto routes for all classes implementing 'WebSocketRoute'
|
||||
in 'file_name' in 'dir_name'
|
||||
"""
|
||||
module_name = file_name.replace('.py', '')
|
||||
module_info = pyclbr.readmodule(module_name, [dir_name])
|
||||
|
||||
for class_name, cls_object in module_info.items():
|
||||
sys.path.append(dir_name)
|
||||
if 'WebSocketRoute' in cls_object.super:
|
||||
log.debug('Adding route for {}'.format(class_name))
|
||||
module = importlib.import_module(module_name)
|
||||
cls = getattr(module, class_name)
|
||||
WebSocketAsync.add_route(class_name, cls)
|
||||
sys.path.pop()
|
||||
|
||||
def tray_start(self):
|
||||
self.websocket_thread.start()
|
||||
|
||||
def tray_exit(self):
|
||||
self.stop()
|
||||
|
||||
def stop_websocket_server(self):
|
||||
|
||||
self.stop()
|
||||
|
||||
@property
|
||||
def is_running(self):
|
||||
return self.websocket_thread.is_running
|
||||
|
||||
def stop(self):
|
||||
if not self.is_running:
|
||||
return
|
||||
try:
|
||||
log.debug("Stopping websocket server")
|
||||
self.websocket_thread.is_running = False
|
||||
self.websocket_thread.stop()
|
||||
except Exception:
|
||||
log.warning(
|
||||
"Error has happened during Killing websocket server",
|
||||
exc_info=True
|
||||
)
|
||||
|
||||
def thread_stopped(self):
|
||||
self._is_running = False
|
||||
|
||||
|
||||
class WebsocketServerThread(threading.Thread):
|
||||
""" Listener for websocket rpc requests.
|
||||
|
||||
It would be probably better to "attach" this to main thread (as for
|
||||
example Harmony needs to run something on main thread), but currently
|
||||
it creates separate thread and separate asyncio event loop
|
||||
"""
|
||||
def __init__(self, module, port):
|
||||
super(WebsocketServerThread, self).__init__()
|
||||
self.is_running = False
|
||||
self.port = port
|
||||
self.module = module
|
||||
self.loop = None
|
||||
self.runner = None
|
||||
self.site = None
|
||||
|
||||
def run(self):
|
||||
self.is_running = True
|
||||
|
||||
try:
|
||||
log.info("Starting websocket server")
|
||||
self.loop = asyncio.new_event_loop() # create new loop for thread
|
||||
asyncio.set_event_loop(self.loop)
|
||||
|
||||
self.loop.run_until_complete(self.start_server())
|
||||
|
||||
log.debug(
|
||||
"Running Websocket server on URL:"
|
||||
" \"ws://localhost:{}\"".format(self.port)
|
||||
)
|
||||
|
||||
asyncio.ensure_future(self.check_shutdown(), loop=self.loop)
|
||||
self.loop.run_forever()
|
||||
except Exception:
|
||||
log.warning(
|
||||
"Websocket Server service has failed", exc_info=True
|
||||
)
|
||||
finally:
|
||||
self.loop.close() # optional
|
||||
|
||||
self.is_running = False
|
||||
self.module.thread_stopped()
|
||||
log.info("Websocket server stopped")
|
||||
|
||||
async def start_server(self):
|
||||
""" Starts runner and TCPsite """
|
||||
self.runner = web.AppRunner(self.module.app)
|
||||
await self.runner.setup()
|
||||
self.site = web.TCPSite(self.runner, 'localhost', self.port)
|
||||
await self.site.start()
|
||||
|
||||
def stop(self):
|
||||
"""Sets is_running flag to false, 'check_shutdown' shuts server down"""
|
||||
self.is_running = False
|
||||
|
||||
async def check_shutdown(self):
|
||||
""" Future that is running and checks if server should be running
|
||||
periodically.
|
||||
"""
|
||||
while self.is_running:
|
||||
await asyncio.sleep(0.5)
|
||||
|
||||
log.debug("Starting shutdown")
|
||||
await self.site.stop()
|
||||
log.debug("Site stopped")
|
||||
await self.runner.cleanup()
|
||||
log.debug("Runner stopped")
|
||||
tasks = [task for task in asyncio.all_tasks() if
|
||||
task is not asyncio.current_task()]
|
||||
list(map(lambda task: task.cancel(), tasks)) # cancel all the tasks
|
||||
results = await asyncio.gather(*tasks, return_exceptions=True)
|
||||
log.debug(f'Finished awaiting cancelled tasks, results: {results}...')
|
||||
await self.loop.shutdown_asyncgens()
|
||||
# to really make sure everything else has time to stop
|
||||
await asyncio.sleep(0.07)
|
||||
self.loop.stop()
|
||||
79
pype/plugins/resolve/create/create_shot_clip.py
Normal file
79
pype/plugins/resolve/create/create_shot_clip.py
Normal file
|
|
@ -0,0 +1,79 @@
|
|||
from pprint import pformat
|
||||
from pype.hosts import resolve
|
||||
from pype.hosts.resolve import lib
|
||||
|
||||
|
||||
class CreateShotClip(resolve.Creator):
|
||||
"""Publishable clip"""
|
||||
|
||||
label = "Shot"
|
||||
family = "clip"
|
||||
icon = "film"
|
||||
defaults = ["Main"]
|
||||
|
||||
gui_name = "Pype sequencial rename with hirerarchy"
|
||||
gui_info = "Define sequencial rename and fill hierarchy data."
|
||||
gui_inputs = {
|
||||
"clipName": "{episode}{sequence}{shot}",
|
||||
"hierarchy": "{folder}/{sequence}/{shot}",
|
||||
"countFrom": 10,
|
||||
"steps": 10,
|
||||
"hierarchyData": {
|
||||
"folder": "shots",
|
||||
"shot": "sh####",
|
||||
"track": "{track}",
|
||||
"sequence": "sc010",
|
||||
"episode": "ep01"
|
||||
}
|
||||
}
|
||||
presets = None
|
||||
|
||||
def process(self):
|
||||
# solve gui inputs overwrites from presets
|
||||
# overwrite gui inputs from presets
|
||||
for k, v in self.gui_inputs.items():
|
||||
if isinstance(v, dict):
|
||||
# nested dictionary (only one level allowed)
|
||||
for _k, _v in v.items():
|
||||
if self.presets.get(_k):
|
||||
self.gui_inputs[k][_k] = self.presets[_k]
|
||||
if self.presets.get(k):
|
||||
self.gui_inputs[k] = self.presets[k]
|
||||
|
||||
# open widget for plugins inputs
|
||||
widget = self.widget(self.gui_name, self.gui_info, self.gui_inputs)
|
||||
widget.exec_()
|
||||
|
||||
print(f"__ selected_clips: {self.selected}")
|
||||
if len(self.selected) < 1:
|
||||
return
|
||||
|
||||
if not widget.result:
|
||||
print("Operation aborted")
|
||||
return
|
||||
|
||||
# sequence attrs
|
||||
sq_frame_start = self.sequence.GetStartFrame()
|
||||
sq_markers = self.sequence.GetMarkers()
|
||||
print(f"__ sq_frame_start: {pformat(sq_frame_start)}")
|
||||
print(f"__ seq_markers: {pformat(sq_markers)}")
|
||||
|
||||
# create media bin for compound clips (trackItems)
|
||||
mp_folder = resolve.create_current_sequence_media_bin(self.sequence)
|
||||
print(f"_ mp_folder: {mp_folder.GetName()}")
|
||||
|
||||
lib.rename_add = 0
|
||||
for i, t_data in enumerate(self.selected):
|
||||
lib.rename_index = i
|
||||
|
||||
# clear color after it is done
|
||||
t_data["clip"]["item"].ClearClipColor()
|
||||
|
||||
# convert track item to timeline media pool item
|
||||
resolve.create_compound_clip(
|
||||
t_data,
|
||||
mp_folder,
|
||||
rename=True,
|
||||
**dict(
|
||||
{"presets": widget.result})
|
||||
)
|
||||
162
pype/plugins/resolve/publish/collect_clips.py
Normal file
162
pype/plugins/resolve/publish/collect_clips.py
Normal file
|
|
@ -0,0 +1,162 @@
|
|||
import os
|
||||
from pyblish import api
|
||||
from pype.hosts import resolve
|
||||
import json
|
||||
|
||||
|
||||
class CollectClips(api.ContextPlugin):
|
||||
"""Collect all Track items selection."""
|
||||
|
||||
order = api.CollectorOrder + 0.01
|
||||
label = "Collect Clips"
|
||||
hosts = ["resolve"]
|
||||
|
||||
def process(self, context):
|
||||
# create asset_names conversion table
|
||||
if not context.data.get("assetsShared"):
|
||||
self.log.debug("Created `assetsShared` in context")
|
||||
context.data["assetsShared"] = dict()
|
||||
|
||||
projectdata = context.data["projectEntity"]["data"]
|
||||
selection = resolve.get_current_track_items(
|
||||
filter=True, selecting_color="Pink")
|
||||
|
||||
for clip_data in selection:
|
||||
data = dict()
|
||||
|
||||
# get basic objects form data
|
||||
project = clip_data["project"]
|
||||
sequence = clip_data["sequence"]
|
||||
clip = clip_data["clip"]
|
||||
|
||||
# sequence attrs
|
||||
sq_frame_start = sequence.GetStartFrame()
|
||||
self.log.debug(f"sq_frame_start: {sq_frame_start}")
|
||||
|
||||
sq_markers = sequence.GetMarkers()
|
||||
|
||||
# get details of objects
|
||||
clip_item = clip["item"]
|
||||
track = clip_data["track"]
|
||||
|
||||
mp = project.GetMediaPool()
|
||||
|
||||
# get clip attributes
|
||||
clip_metadata = resolve.get_pype_clip_metadata(clip_item)
|
||||
clip_metadata = json.loads(clip_metadata)
|
||||
self.log.debug(f"clip_metadata: {clip_metadata}")
|
||||
|
||||
compound_source_prop = clip_metadata["sourceProperties"]
|
||||
self.log.debug(f"compound_source_prop: {compound_source_prop}")
|
||||
|
||||
asset_name = clip_item.GetName()
|
||||
mp_item = clip_item.GetMediaPoolItem()
|
||||
mp_prop = mp_item.GetClipProperty()
|
||||
source_first = int(compound_source_prop["Start"])
|
||||
source_last = int(compound_source_prop["End"])
|
||||
source_duration = compound_source_prop["Frames"]
|
||||
fps = float(mp_prop["FPS"])
|
||||
self.log.debug(f"source_first: {source_first}")
|
||||
self.log.debug(f"source_last: {source_last}")
|
||||
self.log.debug(f"source_duration: {source_duration}")
|
||||
self.log.debug(f"fps: {fps}")
|
||||
|
||||
source_path = os.path.normpath(
|
||||
compound_source_prop["File Path"])
|
||||
source_name = compound_source_prop["File Name"]
|
||||
source_id = clip_metadata["sourceId"]
|
||||
self.log.debug(f"source_path: {source_path}")
|
||||
self.log.debug(f"source_name: {source_name}")
|
||||
self.log.debug(f"source_id: {source_id}")
|
||||
|
||||
clip_left_offset = int(clip_item.GetLeftOffset())
|
||||
clip_right_offset = int(clip_item.GetRightOffset())
|
||||
self.log.debug(f"clip_left_offset: {clip_left_offset}")
|
||||
self.log.debug(f"clip_right_offset: {clip_right_offset}")
|
||||
|
||||
# source in/out
|
||||
source_in = int(source_first + clip_left_offset)
|
||||
source_out = int(source_first + clip_right_offset)
|
||||
self.log.debug(f"source_in: {source_in}")
|
||||
self.log.debug(f"source_out: {source_out}")
|
||||
|
||||
clip_in = int(clip_item.GetStart() - sq_frame_start)
|
||||
clip_out = int(clip_item.GetEnd() - sq_frame_start)
|
||||
clip_duration = int(clip_item.GetDuration())
|
||||
self.log.debug(f"clip_in: {clip_in}")
|
||||
self.log.debug(f"clip_out: {clip_out}")
|
||||
self.log.debug(f"clip_duration: {clip_duration}")
|
||||
|
||||
is_sequence = False
|
||||
|
||||
self.log.debug(
|
||||
"__ assets_shared: {}".format(
|
||||
context.data["assetsShared"]))
|
||||
|
||||
# Check for clips with the same range
|
||||
# this is for testing if any vertically neighbouring
|
||||
# clips has been already processed
|
||||
clip_matching_with_range = next(
|
||||
(k for k, v in context.data["assetsShared"].items()
|
||||
if (v.get("_clipIn", 0) == clip_in)
|
||||
and (v.get("_clipOut", 0) == clip_out)
|
||||
), False)
|
||||
|
||||
# check if clip name is the same in matched
|
||||
# vertically neighbouring clip
|
||||
# if it is then it is correct and resent variable to False
|
||||
# not to be rised wrong name exception
|
||||
if asset_name in str(clip_matching_with_range):
|
||||
clip_matching_with_range = False
|
||||
|
||||
# rise wrong name exception if found one
|
||||
assert (not clip_matching_with_range), (
|
||||
"matching clip: {asset}"
|
||||
" timeline range ({clip_in}:{clip_out})"
|
||||
" conflicting with {clip_matching_with_range}"
|
||||
" >> rename any of clips to be the same as the other <<"
|
||||
).format(
|
||||
**locals())
|
||||
|
||||
if ("[" in source_name) and ("]" in source_name):
|
||||
is_sequence = True
|
||||
|
||||
data.update({
|
||||
"name": "_".join([
|
||||
track["name"], asset_name, source_name]),
|
||||
"item": clip_item,
|
||||
"source": mp_item,
|
||||
# "timecodeStart": str(source.timecodeStart()),
|
||||
"timelineStart": sq_frame_start,
|
||||
"sourcePath": source_path,
|
||||
"sourceFileHead": source_name,
|
||||
"isSequence": is_sequence,
|
||||
"track": track["name"],
|
||||
"trackIndex": track["index"],
|
||||
"sourceFirst": source_first,
|
||||
|
||||
"sourceIn": source_in,
|
||||
"sourceOut": source_out,
|
||||
"mediaDuration": source_duration,
|
||||
"clipIn": clip_in,
|
||||
"clipOut": clip_out,
|
||||
"clipDuration": clip_duration,
|
||||
"asset": asset_name,
|
||||
"subset": "plateMain",
|
||||
"family": "clip",
|
||||
"families": [],
|
||||
"handleStart": projectdata.get("handleStart", 0),
|
||||
"handleEnd": projectdata.get("handleEnd", 0)})
|
||||
|
||||
instance = context.create_instance(**data)
|
||||
|
||||
self.log.info("Created instance: {}".format(instance))
|
||||
self.log.info("Created instance.data: {}".format(instance.data))
|
||||
|
||||
context.data["assetsShared"][asset_name] = {
|
||||
"_clipIn": clip_in,
|
||||
"_clipOut": clip_out
|
||||
}
|
||||
self.log.info(
|
||||
"context.data[\"assetsShared\"]: {}".format(
|
||||
context.data["assetsShared"]))
|
||||
|
|
@ -1,17 +0,0 @@
|
|||
import pyblish.api
|
||||
from pype.hosts.resolve.utils import get_resolve_module
|
||||
|
||||
|
||||
class CollectProject(pyblish.api.ContextPlugin):
|
||||
"""Collect Project object"""
|
||||
|
||||
order = pyblish.api.CollectorOrder - 0.1
|
||||
label = "Collect Project"
|
||||
hosts = ["resolve"]
|
||||
|
||||
def process(self, context):
|
||||
resolve = get_resolve_module()
|
||||
PM = resolve.GetProjectManager()
|
||||
P = PM.GetCurrentProject()
|
||||
|
||||
self.log.info(P.GetName())
|
||||
29
pype/plugins/resolve/publish/collect_project.py
Normal file
29
pype/plugins/resolve/publish/collect_project.py
Normal file
|
|
@ -0,0 +1,29 @@
|
|||
import os
|
||||
import pyblish.api
|
||||
from pype.hosts.resolve.utils import get_resolve_module
|
||||
|
||||
|
||||
class CollectProject(pyblish.api.ContextPlugin):
|
||||
"""Collect Project object"""
|
||||
|
||||
order = pyblish.api.CollectorOrder - 0.1
|
||||
label = "Collect Project"
|
||||
hosts = ["resolve"]
|
||||
|
||||
def process(self, context):
|
||||
exported_projet_ext = ".drp"
|
||||
current_dir = os.getenv("AVALON_WORKDIR")
|
||||
resolve = get_resolve_module()
|
||||
PM = resolve.GetProjectManager()
|
||||
P = PM.GetCurrentProject()
|
||||
name = P.GetName()
|
||||
|
||||
fname = name + exported_projet_ext
|
||||
current_file = os.path.join(current_dir, fname)
|
||||
normalised = os.path.normpath(current_file)
|
||||
|
||||
context.data["project"] = P
|
||||
context.data["currentFile"] = normalised
|
||||
|
||||
self.log.info(name)
|
||||
self.log.debug(normalised)
|
||||
9
pype/settings/__init__.py
Normal file
9
pype/settings/__init__.py
Normal file
|
|
@ -0,0 +1,9 @@
|
|||
from .lib import (
|
||||
system_settings,
|
||||
project_settings
|
||||
)
|
||||
|
||||
__all__ = (
|
||||
"system_settings",
|
||||
"project_settings"
|
||||
)
|
||||
42
pype/settings/defaults/project_anatomy/colorspace.json
Normal file
42
pype/settings/defaults/project_anatomy/colorspace.json
Normal file
|
|
@ -0,0 +1,42 @@
|
|||
{
|
||||
"nuke": {
|
||||
"root": {
|
||||
"colorManagement": "Nuke",
|
||||
"OCIO_config": "nuke-default",
|
||||
"defaultViewerLUT": "Nuke Root LUTs",
|
||||
"monitorLut": "sRGB",
|
||||
"int8Lut": "sRGB",
|
||||
"int16Lut": "sRGB",
|
||||
"logLut": "Cineon",
|
||||
"floatLut": "linear"
|
||||
},
|
||||
"viewer": {
|
||||
"viewerProcess": "sRGB"
|
||||
},
|
||||
"write": {
|
||||
"render": {
|
||||
"colorspace": "linear"
|
||||
},
|
||||
"prerender": {
|
||||
"colorspace": "linear"
|
||||
},
|
||||
"still": {
|
||||
"colorspace": "sRGB"
|
||||
}
|
||||
},
|
||||
"read": {
|
||||
"[^-a-zA-Z0-9]beauty[^-a-zA-Z0-9]": "linear",
|
||||
"[^-a-zA-Z0-9](P|N|Z|crypto)[^-a-zA-Z0-9]": "linear",
|
||||
"[^-a-zA-Z0-9](plateRef)[^-a-zA-Z0-9]": "sRGB"
|
||||
}
|
||||
},
|
||||
"maya": {
|
||||
|
||||
},
|
||||
"houdini": {
|
||||
|
||||
},
|
||||
"resolve": {
|
||||
|
||||
}
|
||||
}
|
||||
55
pype/settings/defaults/project_anatomy/dataflow.json
Normal file
55
pype/settings/defaults/project_anatomy/dataflow.json
Normal file
|
|
@ -0,0 +1,55 @@
|
|||
{
|
||||
"nuke": {
|
||||
"nodes": {
|
||||
"connected": true,
|
||||
"modifymetadata": {
|
||||
"_id": "connect_metadata",
|
||||
"_previous": "ENDING",
|
||||
"metadata.set.pype_studio_name": "{PYPE_STUDIO_NAME}",
|
||||
"metadata.set.avalon_project_name": "{AVALON_PROJECT}",
|
||||
"metadata.set.avalon_project_code": "{PYPE_STUDIO_CODE}",
|
||||
"metadata.set.avalon_asset_name": "{AVALON_ASSET}"
|
||||
},
|
||||
"crop": {
|
||||
"_id": "connect_crop",
|
||||
"_previous": "connect_metadata",
|
||||
"box": [
|
||||
"{metadata.crop.x}",
|
||||
"{metadata.crop.y}",
|
||||
"{metadata.crop.right}",
|
||||
"{metadata.crop.top}"
|
||||
]
|
||||
},
|
||||
"write": {
|
||||
"render": {
|
||||
"_id": "output_write",
|
||||
"_previous": "connect_crop",
|
||||
"file_type": "exr",
|
||||
"datatype": "16 bit half",
|
||||
"compression": "Zip (1 scanline)",
|
||||
"autocrop": true,
|
||||
"tile_color": "0xff0000ff",
|
||||
"channels": "rgb"
|
||||
},
|
||||
"prerender": {
|
||||
"_id": "output_write",
|
||||
"_previous": "connect_crop",
|
||||
"file_type": "exr",
|
||||
"datatype": "16 bit half",
|
||||
"compression": "Zip (1 scanline)",
|
||||
"autocrop": false,
|
||||
"tile_color": "0xc9892aff",
|
||||
"channels": "rgba"
|
||||
},
|
||||
"still": {
|
||||
"_previous": "connect_crop",
|
||||
"channels": "rgba",
|
||||
"file_type": "tiff",
|
||||
"datatype": "16 bit",
|
||||
"compression": "LZW",
|
||||
"tile_color": "0x4145afff"
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
5
pype/settings/defaults/project_anatomy/roots.json
Normal file
5
pype/settings/defaults/project_anatomy/roots.json
Normal file
|
|
@ -0,0 +1,5 @@
|
|||
{
|
||||
"windows": "C:/projects",
|
||||
"linux": "/mnt/share/projects",
|
||||
"darwin": "/Volumes/path"
|
||||
}
|
||||
30
pype/settings/defaults/project_anatomy/templates.json
Normal file
30
pype/settings/defaults/project_anatomy/templates.json
Normal file
|
|
@ -0,0 +1,30 @@
|
|||
{
|
||||
"version_padding": 3,
|
||||
"version": "v{version:0>{@version_padding}}",
|
||||
"frame_padding": 4,
|
||||
"frame": "{frame:0>{@frame_padding}}",
|
||||
"work": {
|
||||
"folder": "{root}/{project[name]}/{hierarchy}/{asset}/work/{task}",
|
||||
"file": "{project[code]}_{asset}_{task}_{@version}<_{comment}>.{ext}",
|
||||
"path": "{@folder}/{@file}"
|
||||
},
|
||||
"render": {
|
||||
"folder": "{root}/{project[name]}/{hierarchy}/{asset}/publish/render/{subset}/{@version}",
|
||||
"file": "{project[code]}_{asset}_{subset}_{@version}<_{output}><.{@frame}>.{representation}",
|
||||
"path": "{@folder}/{@file}"
|
||||
},
|
||||
"texture": {
|
||||
"path": "{root}/{project[name]}/{hierarchy}/{asset}/publish/{family}/{subset}"
|
||||
},
|
||||
"publish": {
|
||||
"folder": "{root}/{project[name]}/{hierarchy}/{asset}/publish/{family}/{subset}/{@version}",
|
||||
"file": "{project[code]}_{asset}_{subset}_{@version}<_{output}><.{@frame}>.{representation}",
|
||||
"path": "{@folder}/{@file}",
|
||||
"thumbnail": "{thumbnail_root}/{project[name]}/{_id}_{thumbnail_type}{ext}"
|
||||
},
|
||||
"master": {
|
||||
"folder": "{root}/{project[name]}/{hierarchy}/{asset}/publish/{family}/{subset}/master",
|
||||
"file": "{project[code]}_{asset}_{subset}_master<_{output}><.{frame}>.{representation}",
|
||||
"path": "{@folder}/{@file}"
|
||||
}
|
||||
}
|
||||
|
|
@ -0,0 +1,16 @@
|
|||
{
|
||||
"sync_to_avalon": {
|
||||
"statuses_name_change": ["not ready", "ready"]
|
||||
},
|
||||
|
||||
"status_update": {
|
||||
"_ignore_": ["in progress", "ommited", "on hold"],
|
||||
"Ready": ["not ready"],
|
||||
"In Progress" : ["_any_"]
|
||||
},
|
||||
"status_version_to_task": {
|
||||
"__description__": "Status `from` (key) must be lowered!",
|
||||
"in progress": "in progress",
|
||||
"approved": "approved"
|
||||
}
|
||||
}
|
||||
|
|
@ -0,0 +1,165 @@
|
|||
[{
|
||||
"label": "FPS",
|
||||
"key": "fps",
|
||||
"type": "number",
|
||||
"is_hierarchical": true,
|
||||
"group": "avalon",
|
||||
"write_security_role": ["ALL"],
|
||||
"read_security_role": ["ALL"],
|
||||
"default": null,
|
||||
"config": {
|
||||
"isdecimal": true
|
||||
}
|
||||
}, {
|
||||
"label": "Applications",
|
||||
"key": "applications",
|
||||
"type": "enumerator",
|
||||
"entity_type": "show",
|
||||
"group": "avalon",
|
||||
"config": {
|
||||
"multiselect": true,
|
||||
"data": [
|
||||
{"blender_2.80": "Blender 2.80"},
|
||||
{"blender_2.81": "Blender 2.81"},
|
||||
{"blender_2.82": "Blender 2.82"},
|
||||
{"blender_2.83": "Blender 2.83"},
|
||||
{"celaction_local": "CelAction2D Local"},
|
||||
{"maya_2017": "Maya 2017"},
|
||||
{"maya_2018": "Maya 2018"},
|
||||
{"maya_2019": "Maya 2019"},
|
||||
{"nuke_10.0": "Nuke 10.0"},
|
||||
{"nuke_11.2": "Nuke 11.2"},
|
||||
{"nuke_11.3": "Nuke 11.3"},
|
||||
{"nuke_12.0": "Nuke 12.0"},
|
||||
{"nukex_10.0": "NukeX 10.0"},
|
||||
{"nukex_11.2": "NukeX 11.2"},
|
||||
{"nukex_11.3": "NukeX 11.3"},
|
||||
{"nukex_12.0": "NukeX 12.0"},
|
||||
{"nukestudio_10.0": "NukeStudio 10.0"},
|
||||
{"nukestudio_11.2": "NukeStudio 11.2"},
|
||||
{"nukestudio_11.3": "NukeStudio 11.3"},
|
||||
{"nukestudio_12.0": "NukeStudio 12.0"},
|
||||
{"harmony_17": "Harmony 17"},
|
||||
{"houdini_16.5": "Houdini 16.5"},
|
||||
{"houdini_17": "Houdini 17"},
|
||||
{"houdini_18": "Houdini 18"},
|
||||
{"photoshop_2020": "Photoshop 2020"},
|
||||
{"python_3": "Python 3"},
|
||||
{"python_2": "Python 2"},
|
||||
{"premiere_2019": "Premiere Pro 2019"},
|
||||
{"premiere_2020": "Premiere Pro 2020"},
|
||||
{"resolve_16": "BM DaVinci Resolve 16"}
|
||||
]
|
||||
}
|
||||
}, {
|
||||
"label": "Avalon auto-sync",
|
||||
"key": "avalon_auto_sync",
|
||||
"type": "boolean",
|
||||
"entity_type": "show",
|
||||
"group": "avalon",
|
||||
"write_security_role": ["API", "Administrator"],
|
||||
"read_security_role": ["API", "Administrator"]
|
||||
}, {
|
||||
"label": "Intent",
|
||||
"key": "intent",
|
||||
"type": "enumerator",
|
||||
"entity_type": "assetversion",
|
||||
"group": "avalon",
|
||||
"config": {
|
||||
"multiselect": false,
|
||||
"data": [
|
||||
{"test": "Test"},
|
||||
{"wip": "WIP"},
|
||||
{"final": "Final"}
|
||||
]
|
||||
}
|
||||
}, {
|
||||
"label": "Library Project",
|
||||
"key": "library_project",
|
||||
"type": "boolean",
|
||||
"entity_type": "show",
|
||||
"group": "avalon",
|
||||
"write_security_role": ["API", "Administrator"],
|
||||
"read_security_role": ["API", "Administrator"]
|
||||
}, {
|
||||
"label": "Clip in",
|
||||
"key": "clipIn",
|
||||
"type": "number",
|
||||
"is_hierarchical": true,
|
||||
"group": "avalon",
|
||||
"default": null
|
||||
}, {
|
||||
"label": "Clip out",
|
||||
"key": "clipOut",
|
||||
"type": "number",
|
||||
"is_hierarchical": true,
|
||||
"group": "avalon",
|
||||
"default": null
|
||||
}, {
|
||||
"label": "Frame start",
|
||||
"key": "frameStart",
|
||||
"type": "number",
|
||||
"is_hierarchical": true,
|
||||
"group": "avalon",
|
||||
"default": null
|
||||
}, {
|
||||
"label": "Frame end",
|
||||
"key": "frameEnd",
|
||||
"type": "number",
|
||||
"is_hierarchical": true,
|
||||
"group": "avalon",
|
||||
"default": null
|
||||
}, {
|
||||
"label": "Tools",
|
||||
"key": "tools_env",
|
||||
"type": "enumerator",
|
||||
"is_hierarchical": true,
|
||||
"group": "avalon",
|
||||
"config": {
|
||||
"multiselect": true,
|
||||
"data": [
|
||||
{"mtoa_3.0.1": "mtoa_3.0.1"},
|
||||
{"mtoa_3.1.1": "mtoa_3.1.1"},
|
||||
{"mtoa_3.2.0": "mtoa_3.2.0"},
|
||||
{"yeti_2.1.2": "yeti_2.1"}
|
||||
]
|
||||
}
|
||||
}, {
|
||||
"label": "Resolution Width",
|
||||
"key": "resolutionWidth",
|
||||
"type": "number",
|
||||
"is_hierarchical": true,
|
||||
"group": "avalon",
|
||||
"default": null
|
||||
}, {
|
||||
"label": "Resolution Height",
|
||||
"key": "resolutionHeight",
|
||||
"type": "number",
|
||||
"is_hierarchical": true,
|
||||
"group": "avalon",
|
||||
"default": null
|
||||
}, {
|
||||
"label": "Pixel aspect",
|
||||
"key": "pixelAspect",
|
||||
"type": "number",
|
||||
"is_hierarchical": true,
|
||||
"group": "avalon",
|
||||
"config": {
|
||||
"isdecimal": true
|
||||
}
|
||||
}, {
|
||||
"label": "Frame handles start",
|
||||
"key": "handleStart",
|
||||
"type": "number",
|
||||
"is_hierarchical": true,
|
||||
"group": "avalon",
|
||||
"default": null
|
||||
}, {
|
||||
"label": "Frame handles end",
|
||||
"key": "handleEnd",
|
||||
"type": "number",
|
||||
"is_hierarchical": true,
|
||||
"group": "avalon",
|
||||
"default": null
|
||||
}
|
||||
]
|
||||
|
|
@ -0,0 +1,5 @@
|
|||
{
|
||||
"server_url": "",
|
||||
"api_key": "",
|
||||
"api_user": ""
|
||||
}
|
||||
|
|
@ -0,0 +1 @@
|
|||
{}
|
||||
|
|
@ -0,0 +1,5 @@
|
|||
{
|
||||
"TestAction": {
|
||||
"ignore_me": true
|
||||
}
|
||||
}
|
||||
|
|
@ -0,0 +1,18 @@
|
|||
{
|
||||
"fps": 25,
|
||||
"frameStart": 1001,
|
||||
"frameEnd": 1100,
|
||||
"clipIn": 1001,
|
||||
"clipOut": 1100,
|
||||
"handleStart": 10,
|
||||
"handleEnd": 10,
|
||||
|
||||
"resolutionHeight": 1080,
|
||||
"resolutionWidth": 1920,
|
||||
"pixelAspect": 1.0,
|
||||
"applications": [
|
||||
"maya_2019", "nuke_11.3", "nukex_11.3", "nukestudio_11.3", "deadline"
|
||||
],
|
||||
"tools_env": [],
|
||||
"avalon_auto_sync": true
|
||||
}
|
||||
|
|
@ -0,0 +1,8 @@
|
|||
{
|
||||
"Model": ["model"],
|
||||
"Render Globals": ["light", "render"],
|
||||
"Layout": ["layout"],
|
||||
"Set Dress": ["setdress"],
|
||||
"Look": ["look"],
|
||||
"Rig": ["rigging"]
|
||||
}
|
||||
|
|
@ -0,0 +1,22 @@
|
|||
{
|
||||
"__project_root__": {
|
||||
"prod" : {},
|
||||
"resources" : {
|
||||
"footage": {
|
||||
"plates": {},
|
||||
"offline": {}
|
||||
},
|
||||
"audio": {},
|
||||
"art_dept": {}
|
||||
},
|
||||
"editorial" : {},
|
||||
"assets[ftrack.Library]": {
|
||||
"characters[ftrack]": {},
|
||||
"locations[ftrack]": {}
|
||||
},
|
||||
"shots[ftrack.Sequence]": {
|
||||
"scripts": {},
|
||||
"editorial[ftrack.Folder]": {}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
|
@ -0,0 +1,8 @@
|
|||
{
|
||||
"compositing": ["nuke", "ae"],
|
||||
"modeling": ["maya", "app2"],
|
||||
"lookdev": ["substance"],
|
||||
"animation": [],
|
||||
"lighting": [],
|
||||
"rigging": []
|
||||
}
|
||||
|
|
@ -0,0 +1,7 @@
|
|||
{
|
||||
"last_workfile_on_startup": [
|
||||
{
|
||||
"enabled": false
|
||||
}
|
||||
]
|
||||
}
|
||||
108
pype/settings/defaults/project_settings/maya/capture.json
Normal file
108
pype/settings/defaults/project_settings/maya/capture.json
Normal file
|
|
@ -0,0 +1,108 @@
|
|||
{
|
||||
"Codec": {
|
||||
"compression": "jpg",
|
||||
"format": "image",
|
||||
"quality": 95
|
||||
},
|
||||
"Display Options": {
|
||||
"background": [
|
||||
0.7137254901960784,
|
||||
0.7137254901960784,
|
||||
0.7137254901960784
|
||||
],
|
||||
"backgroundBottom": [
|
||||
0.7137254901960784,
|
||||
0.7137254901960784,
|
||||
0.7137254901960784
|
||||
],
|
||||
"backgroundTop": [
|
||||
0.7137254901960784,
|
||||
0.7137254901960784,
|
||||
0.7137254901960784
|
||||
],
|
||||
"override_display": true
|
||||
},
|
||||
"Generic": {
|
||||
"isolate_view": true,
|
||||
"off_screen": true
|
||||
},
|
||||
"IO": {
|
||||
"name": "",
|
||||
"open_finished": false,
|
||||
"raw_frame_numbers": false,
|
||||
"recent_playblasts": [],
|
||||
"save_file": false
|
||||
},
|
||||
"PanZoom": {
|
||||
"pan_zoom": true
|
||||
},
|
||||
"Renderer": {
|
||||
"rendererName": "vp2Renderer"
|
||||
},
|
||||
"Resolution": {
|
||||
"height": 1080,
|
||||
"mode": "Custom",
|
||||
"percent": 1.0,
|
||||
"width": 1920
|
||||
},
|
||||
"Time Range": {
|
||||
"end_frame": 25,
|
||||
"frame": "",
|
||||
"start_frame": 0,
|
||||
"time": "Time Slider"
|
||||
},
|
||||
"Viewport Options": {
|
||||
"cameras": false,
|
||||
"clipGhosts": false,
|
||||
"controlVertices": false,
|
||||
"deformers": false,
|
||||
"dimensions": false,
|
||||
"displayLights": 0,
|
||||
"dynamicConstraints": false,
|
||||
"dynamics": false,
|
||||
"fluids": false,
|
||||
"follicles": false,
|
||||
"gpuCacheDisplayFilter": false,
|
||||
"greasePencils": false,
|
||||
"grid": false,
|
||||
"hairSystems": false,
|
||||
"handles": false,
|
||||
"high_quality": true,
|
||||
"hud": false,
|
||||
"hulls": false,
|
||||
"ikHandles": false,
|
||||
"imagePlane": false,
|
||||
"joints": false,
|
||||
"lights": false,
|
||||
"locators": false,
|
||||
"manipulators": false,
|
||||
"motionTrails": false,
|
||||
"nCloths": false,
|
||||
"nParticles": false,
|
||||
"nRigids": false,
|
||||
"nurbsCurves": false,
|
||||
"nurbsSurfaces": false,
|
||||
"override_viewport_options": true,
|
||||
"particleInstancers": false,
|
||||
"pivots": false,
|
||||
"planes": false,
|
||||
"pluginShapes": false,
|
||||
"polymeshes": true,
|
||||
"shadows": false,
|
||||
"strokes": false,
|
||||
"subdivSurfaces": false,
|
||||
"textures": false,
|
||||
"twoSidedLighting": true
|
||||
},
|
||||
"Camera Options": {
|
||||
"displayGateMask": false,
|
||||
"displayResolution": false,
|
||||
"displayFilmGate": false,
|
||||
"displayFieldChart": false,
|
||||
"displaySafeAction": false,
|
||||
"displaySafeTitle": false,
|
||||
"displayFilmPivot": false,
|
||||
"displayFilmOrigin": false,
|
||||
"overscan": 1.0
|
||||
}
|
||||
}
|
||||
|
|
@ -0,0 +1,19 @@
|
|||
{
|
||||
"3delight": 41,
|
||||
"arnold": 46,
|
||||
"arnold_sf": 57,
|
||||
"gelato": 30,
|
||||
"harware": 3,
|
||||
"krakatoa": 51,
|
||||
"file_layers": 7,
|
||||
"mentalray": 2,
|
||||
"mentalray_sf": 6,
|
||||
"redshift": 55,
|
||||
"renderman": 29,
|
||||
"software": 1,
|
||||
"software_sf": 5,
|
||||
"turtle": 10,
|
||||
"vector": 4,
|
||||
"vray": 37,
|
||||
"ffmpeg": 48
|
||||
}
|
||||
|
|
@ -0,0 +1,11 @@
|
|||
{
|
||||
"ExtractCelactionDeadline": {
|
||||
"enabled": true,
|
||||
"deadline_department": "",
|
||||
"deadline_priority": 50,
|
||||
"deadline_pool": "",
|
||||
"deadline_pool_secondary": "",
|
||||
"deadline_group": "",
|
||||
"deadline_chunk_size": 10
|
||||
}
|
||||
}
|
||||
|
|
@ -0,0 +1 @@
|
|||
{}
|
||||
|
|
@ -0,0 +1,7 @@
|
|||
{
|
||||
"IntegrateFtrackNote": {
|
||||
"enabled": false,
|
||||
"note_with_intent_template": "{intent}: {comment}",
|
||||
"note_labels": []
|
||||
}
|
||||
}
|
||||
|
|
@ -0,0 +1 @@
|
|||
{}
|
||||
|
|
@ -0,0 +1 @@
|
|||
{}
|
||||
|
|
@ -0,0 +1 @@
|
|||
{}
|
||||
|
|
@ -0,0 +1,98 @@
|
|||
{
|
||||
"IntegrateMasterVersion": {
|
||||
"enabled": false
|
||||
},
|
||||
"ExtractJpegEXR": {
|
||||
"enabled": true,
|
||||
"ffmpeg_args": {
|
||||
"input": [
|
||||
"-gamma 2.2"
|
||||
],
|
||||
"output": []
|
||||
}
|
||||
},
|
||||
"ExtractReview": {
|
||||
"enabled": true,
|
||||
"profiles": [
|
||||
{
|
||||
"families": [],
|
||||
"hosts": [],
|
||||
"outputs": {
|
||||
"h264": {
|
||||
"filter": {
|
||||
"families": [
|
||||
"render",
|
||||
"review",
|
||||
"ftrack"
|
||||
]
|
||||
},
|
||||
"ext": "mp4",
|
||||
"ffmpeg_args": {
|
||||
"input": [
|
||||
"-gamma 2.2"
|
||||
],
|
||||
"video_filters": [],
|
||||
"audio_filters": [],
|
||||
"output": [
|
||||
"-pix_fmt yuv420p",
|
||||
"-crf 18",
|
||||
"-intra"
|
||||
]
|
||||
},
|
||||
"tags": [
|
||||
"burnin",
|
||||
"ftrackreview"
|
||||
]
|
||||
}
|
||||
}
|
||||
}
|
||||
]
|
||||
},
|
||||
"ExtractBurnin": {
|
||||
"enabled": false,
|
||||
"options": {
|
||||
"font_size": 42,
|
||||
"opacity": 1,
|
||||
"bg_opacity": 0,
|
||||
"x_offset": 5,
|
||||
"y_offset": 5,
|
||||
"bg_padding": 5
|
||||
},
|
||||
"fields": {},
|
||||
"profiles": [
|
||||
{
|
||||
"burnins": {
|
||||
"burnin": {
|
||||
"TOP_LEFT": "{yy}-{mm}-{dd}",
|
||||
"TOP_RIGHT": "{anatomy[version]}",
|
||||
"TOP_CENTERED": "",
|
||||
"BOTTOM_RIGHT": "{frame_start}-{current_frame}-{frame_end}",
|
||||
"BOTTOM_CENTERED": "{asset}",
|
||||
"BOTTOM_LEFT": "{username}"
|
||||
}
|
||||
}
|
||||
}
|
||||
]
|
||||
},
|
||||
"IntegrateAssetNew": {
|
||||
"template_name_profiles": {
|
||||
"publish": {
|
||||
"families": [],
|
||||
"tasks": []
|
||||
},
|
||||
"render": {
|
||||
"families": [
|
||||
"review",
|
||||
"render",
|
||||
"prerender"
|
||||
]
|
||||
}
|
||||
}
|
||||
},
|
||||
"ProcessSubmittedJobOnFarm": {
|
||||
"enabled": false,
|
||||
"deadline_department": "",
|
||||
"deadline_pool": "",
|
||||
"deadline_group": ""
|
||||
}
|
||||
}
|
||||
|
|
@ -0,0 +1 @@
|
|||
{}
|
||||
|
|
@ -0,0 +1,9 @@
|
|||
{
|
||||
"Preset n1": {
|
||||
"ValidateNoAnimation": false,
|
||||
"ValidateShapeDefaultNames": false
|
||||
},
|
||||
"Preset n2": {
|
||||
"ValidateNoAnimation": false
|
||||
}
|
||||
}
|
||||
|
|
@ -0,0 +1,18 @@
|
|||
{
|
||||
"colors": {
|
||||
"model": [0.821, 0.518, 0.117],
|
||||
"rig": [0.144, 0.443, 0.463],
|
||||
"pointcache": [0.368, 0.821, 0.117],
|
||||
"animation": [0.368, 0.821, 0.117],
|
||||
"ass": [1.0, 0.332, 0.312],
|
||||
"camera": [0.447, 0.312, 1.0],
|
||||
"fbx": [1.0, 0.931, 0.312],
|
||||
"mayaAscii": [0.312, 1.0, 0.747],
|
||||
"setdress": [0.312, 1.0, 0.747],
|
||||
"layout": [0.312, 1.0, 0.747],
|
||||
"vdbcache": [0.312, 1.0, 0.428],
|
||||
"vrayproxy": [0.258, 0.95, 0.541],
|
||||
"yeticache": [0.2, 0.8, 0.3],
|
||||
"yetiRig": [0, 0.8, 0.5]
|
||||
}
|
||||
}
|
||||
|
|
@ -0,0 +1,17 @@
|
|||
{
|
||||
"ValidateModelName": {
|
||||
"enabled": false,
|
||||
"material_file": "/path/to/shader_name_definition.txt",
|
||||
"regex": "(.*)_(\\d)*_(?P<shader>.*)_(GEO)"
|
||||
},
|
||||
"ValidateAssemblyName": {
|
||||
"enabled": false
|
||||
},
|
||||
"ValidateShaderName": {
|
||||
"enabled": false,
|
||||
"regex": "(?P<asset>.*)_(.*)_SHD"
|
||||
},
|
||||
"ValidateMeshHasOverlappingUVs": {
|
||||
"enabled": false
|
||||
}
|
||||
}
|
||||
|
|
@ -0,0 +1,136 @@
|
|||
[
|
||||
{
|
||||
"tasks": [
|
||||
"lighting"
|
||||
],
|
||||
"current_context": [
|
||||
{
|
||||
"subset_name_filters": [
|
||||
".+[Mm]ain"
|
||||
],
|
||||
"families": [
|
||||
"model"
|
||||
],
|
||||
"repre_names": [
|
||||
"abc",
|
||||
"ma"
|
||||
],
|
||||
"loaders": [
|
||||
"ReferenceLoader"
|
||||
]
|
||||
},
|
||||
{
|
||||
"families": [
|
||||
"animation",
|
||||
"pointcache"
|
||||
],
|
||||
"repre_names": [
|
||||
"abc"
|
||||
],
|
||||
"loaders": [
|
||||
"ReferenceLoader"
|
||||
]
|
||||
},
|
||||
{
|
||||
"families": [
|
||||
"rendersetup"
|
||||
],
|
||||
"repre_names": [
|
||||
"json"
|
||||
],
|
||||
"loaders": [
|
||||
"RenderSetupLoader"
|
||||
]
|
||||
},
|
||||
{
|
||||
"families": [
|
||||
"camera"
|
||||
],
|
||||
"repre_names": [
|
||||
"abc"
|
||||
],
|
||||
"loaders": [
|
||||
"ReferenceLoader"
|
||||
]
|
||||
}
|
||||
],
|
||||
"linked_assets": [
|
||||
{
|
||||
"families": [
|
||||
"setdress"
|
||||
],
|
||||
"repre_names": [
|
||||
"ma"
|
||||
],
|
||||
"loaders": [
|
||||
"ReferenceLoader"
|
||||
]
|
||||
},
|
||||
{
|
||||
"families": [
|
||||
"ass"
|
||||
],
|
||||
"repre_names": [
|
||||
"ass"
|
||||
],
|
||||
"loaders": [
|
||||
"assLoader"
|
||||
]
|
||||
}
|
||||
]
|
||||
},
|
||||
{
|
||||
"tasks": [
|
||||
"animation"
|
||||
],
|
||||
"current_context": [
|
||||
{
|
||||
"families": [
|
||||
"camera"
|
||||
],
|
||||
"repre_names": [
|
||||
"abc",
|
||||
"ma"
|
||||
],
|
||||
"loaders": [
|
||||
"ReferenceLoader"
|
||||
]
|
||||
},
|
||||
{
|
||||
"families": [
|
||||
"audio"
|
||||
],
|
||||
"repre_names": [
|
||||
"wav"
|
||||
],
|
||||
"loaders": [
|
||||
"RenderSetupLoader"
|
||||
]
|
||||
}
|
||||
],
|
||||
"linked_assets": [
|
||||
{
|
||||
"families": [
|
||||
"setdress"
|
||||
],
|
||||
"repre_names": [
|
||||
"proxy"
|
||||
],
|
||||
"loaders": [
|
||||
"ReferenceLoader"
|
||||
]
|
||||
},
|
||||
{
|
||||
"families": [
|
||||
"rig"
|
||||
],
|
||||
"repre_names": [
|
||||
"ass"
|
||||
],
|
||||
"loaders": [
|
||||
"rigLoader"
|
||||
]
|
||||
}
|
||||
]
|
||||
}
|
||||
]
|
||||
|
|
@ -0,0 +1,8 @@
|
|||
{
|
||||
"CreateWriteRender": {
|
||||
"fpath_template": "{work}/renders/nuke/{subset}/{subset}.{frame}.{ext}"
|
||||
},
|
||||
"CreateWritePrerender": {
|
||||
"fpath_template": "{work}/prerenders/nuke/{subset}/{subset}.{frame}.{ext}"
|
||||
}
|
||||
}
|
||||
|
|
@ -0,0 +1 @@
|
|||
{}
|
||||
|
|
@ -0,0 +1,53 @@
|
|||
{
|
||||
"ExtractThumbnail": {
|
||||
"enabled": true,
|
||||
"nodes": {
|
||||
"Reformat": [
|
||||
[
|
||||
"type",
|
||||
"to format"
|
||||
],
|
||||
[
|
||||
"format",
|
||||
"HD_1080"
|
||||
],
|
||||
[
|
||||
"filter",
|
||||
"Lanczos6"
|
||||
],
|
||||
[
|
||||
"black_outside",
|
||||
true
|
||||
],
|
||||
[
|
||||
"pbb",
|
||||
false
|
||||
]
|
||||
]
|
||||
}
|
||||
},
|
||||
"ValidateNukeWriteKnobs": {
|
||||
"enabled": false,
|
||||
"knobs": {
|
||||
"render": {
|
||||
"review": true
|
||||
}
|
||||
}
|
||||
},
|
||||
"ExtractReviewDataLut": {
|
||||
"enabled": false
|
||||
},
|
||||
"ExtractReviewDataMov": {
|
||||
"enabled": true,
|
||||
"viewer_lut_raw": false
|
||||
},
|
||||
"ExtractSlateFrame": {
|
||||
"viewer_lut_raw": false
|
||||
},
|
||||
"NukeSubmitDeadline": {
|
||||
"deadline_priority": 50,
|
||||
"deadline_pool": "",
|
||||
"deadline_pool_secondary": "",
|
||||
"deadline_chunk_size": 1
|
||||
}
|
||||
}
|
||||
|
|
@ -0,0 +1,23 @@
|
|||
[
|
||||
{
|
||||
"tasks": [
|
||||
"compositing"
|
||||
],
|
||||
"current_context": [
|
||||
{
|
||||
"families": [
|
||||
"render",
|
||||
"plate"
|
||||
],
|
||||
"repre_names": [
|
||||
"exr",
|
||||
"dpx"
|
||||
],
|
||||
"loaders": [
|
||||
"LoadSequence"
|
||||
]
|
||||
}
|
||||
],
|
||||
"linked_assets": []
|
||||
}
|
||||
]
|
||||
|
|
@ -0,0 +1,10 @@
|
|||
{
|
||||
"strict": {
|
||||
"ValidateVersion": true,
|
||||
"VersionUpWorkfile": true
|
||||
},
|
||||
"benevolent": {
|
||||
"ValidateVersion": false,
|
||||
"VersionUpWorkfile": false
|
||||
}
|
||||
}
|
||||
|
|
@ -0,0 +1,9 @@
|
|||
{
|
||||
"CollectInstanceVersion": {
|
||||
"enabled": false
|
||||
},
|
||||
"ExtractReviewCutUpVideo": {
|
||||
"enabled": true,
|
||||
"tags_addition": []
|
||||
}
|
||||
}
|
||||
|
|
@ -0,0 +1,7 @@
|
|||
{
|
||||
"CreateShotClip": {
|
||||
"clipName": "{track}{sequence}{shot}",
|
||||
"folder": "takes",
|
||||
"steps": 20
|
||||
}
|
||||
}
|
||||
|
|
@ -0,0 +1,27 @@
|
|||
{
|
||||
"ExtractThumbnailSP": {
|
||||
"ffmpeg_args": {
|
||||
"input": [
|
||||
"-gamma 2.2"
|
||||
],
|
||||
"output": []
|
||||
}
|
||||
},
|
||||
"ExtractReviewSP": {
|
||||
"outputs": {
|
||||
"h264": {
|
||||
"input": [
|
||||
"-gamma 2.2"
|
||||
],
|
||||
"output": [
|
||||
"-pix_fmt yuv420p",
|
||||
"-crf 18"
|
||||
],
|
||||
"tags": [
|
||||
"preview"
|
||||
],
|
||||
"ext": "mov"
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
|
@ -0,0 +1,8 @@
|
|||
{
|
||||
"MyTestCreator": {
|
||||
"my_test_property": "B",
|
||||
"active": false,
|
||||
"new_property": "new",
|
||||
"family": "new_family"
|
||||
}
|
||||
}
|
||||
|
|
@ -0,0 +1,10 @@
|
|||
{
|
||||
"MyTestPlugin": {
|
||||
"label": "loaded from preset",
|
||||
"optional": true,
|
||||
"families": ["changed", "by", "preset"]
|
||||
},
|
||||
"MyTestRemovedPlugin": {
|
||||
"enabled": false
|
||||
}
|
||||
}
|
||||
|
|
@ -0,0 +1,5 @@
|
|||
{
|
||||
"frameStart": 1001,
|
||||
"handleStart": 0,
|
||||
"handleEnd": 0
|
||||
}
|
||||
|
|
@ -0,0 +1,21 @@
|
|||
{
|
||||
"defaultTasks": ["Layout", "Animation"],
|
||||
"taskToSubsets": {
|
||||
"Layout": ["reference", "audio"],
|
||||
"Animation": ["audio"]
|
||||
},
|
||||
"subsetToRepresentations": {
|
||||
"reference": {
|
||||
"preset": "h264",
|
||||
"representation": "mp4"
|
||||
},
|
||||
"thumbnail": {
|
||||
"preset": "jpeg_thumb",
|
||||
"representation": "jpg"
|
||||
},
|
||||
"audio": {
|
||||
"preset": "48khz",
|
||||
"representation": "wav"
|
||||
}
|
||||
}
|
||||
}
|
||||
|
|
@ -0,0 +1,90 @@
|
|||
{
|
||||
"create_look": {
|
||||
"name": "look",
|
||||
"label": "Look",
|
||||
"family": "look",
|
||||
"icon": "paint-brush",
|
||||
"defaults": ["Main"],
|
||||
"help": "Shader connections defining shape look"
|
||||
},
|
||||
"create_model": {
|
||||
"name": "model",
|
||||
"label": "Model",
|
||||
"family": "model",
|
||||
"icon": "cube",
|
||||
"defaults": ["Main", "Proxy", "Sculpt"],
|
||||
"help": "Polygonal static geometry"
|
||||
},
|
||||
"create_workfile": {
|
||||
"name": "workfile",
|
||||
"label": "Workfile",
|
||||
"family": "workfile",
|
||||
"icon": "cube",
|
||||
"defaults": ["Main"],
|
||||
"help": "Working scene backup"
|
||||
},
|
||||
"create_camera": {
|
||||
"name": "camera",
|
||||
"label": "Camera",
|
||||
"family": "camera",
|
||||
"icon": "video-camera",
|
||||
"defaults": ["Main"],
|
||||
"help": "Single baked camera"
|
||||
},
|
||||
"create_pointcache": {
|
||||
"name": "pointcache",
|
||||
"label": "Pointcache",
|
||||
"family": "pointcache",
|
||||
"icon": "gears",
|
||||
"defaults": ["Main"],
|
||||
"help": "Alembic pointcache for animated data"
|
||||
},
|
||||
"create_rig": {
|
||||
"name": "rig",
|
||||
"label": "Rig",
|
||||
"family": "rig",
|
||||
"icon": "wheelchair",
|
||||
"defaults": ["Main"],
|
||||
"help": "Artist-friendly rig with controls"
|
||||
},
|
||||
"create_layout": {
|
||||
"name": "layout",
|
||||
"label": "Layout",
|
||||
"family": "layout",
|
||||
"icon": "cubes",
|
||||
"defaults": ["Main"],
|
||||
"help": "Simple scene for animators with camera"
|
||||
},
|
||||
"create_plate": {
|
||||
"name": "plate",
|
||||
"label": "Plate",
|
||||
"family": "plate",
|
||||
"icon": "camera",
|
||||
"defaults": ["Main", "BG", "Reference"],
|
||||
"help": "Plates for compositors"
|
||||
},
|
||||
"create_matchmove": {
|
||||
"name": "matchmove",
|
||||
"label": "Matchmove script",
|
||||
"family": "matchmove",
|
||||
"icon": "empire",
|
||||
"defaults": ["Camera", "Object", "Mocap"],
|
||||
"help": "Script exported from matchmoving application"
|
||||
},
|
||||
"create_images": {
|
||||
"name": "image",
|
||||
"label": "Image file",
|
||||
"family": "image",
|
||||
"icon": "image",
|
||||
"defaults": ["ConceptArt", "Reference", "Texture", "MattePaint"],
|
||||
"help": "Holder for all kinds of image data"
|
||||
},
|
||||
"create_editorial": {
|
||||
"name": "editorial",
|
||||
"label": "Editorial",
|
||||
"family": "editorial",
|
||||
"icon": "image",
|
||||
"defaults": ["Main"],
|
||||
"help": "Editorial files to generate shots."
|
||||
}
|
||||
}
|
||||
|
|
@ -0,0 +1,212 @@
|
|||
{
|
||||
"width": 1920,
|
||||
"height": 1080,
|
||||
"destination_path": "{destination_path}",
|
||||
"style": {
|
||||
"*": {
|
||||
"font-family": "arial",
|
||||
"font-color": "#ffffff",
|
||||
"font-bold": false,
|
||||
"font-italic": false,
|
||||
"bg-color": "#0077ff",
|
||||
"alignment-horizontal": "left",
|
||||
"alignment-vertical": "top"
|
||||
},
|
||||
"layer": {
|
||||
"padding": 0,
|
||||
"margin": 0
|
||||
},
|
||||
"rectangle": {
|
||||
"padding": 0,
|
||||
"margin": 0,
|
||||
"bg-color": "#E9324B",
|
||||
"fill": true
|
||||
},
|
||||
"main_frame": {
|
||||
"padding": 0,
|
||||
"margin": 0,
|
||||
"bg-color": "#252525"
|
||||
},
|
||||
"table": {
|
||||
"padding": 0,
|
||||
"margin": 0,
|
||||
"bg-color": "transparent"
|
||||
},
|
||||
"table-item": {
|
||||
"padding": 5,
|
||||
"padding-bottom": 10,
|
||||
"margin": 0,
|
||||
"bg-color": "#212121",
|
||||
"bg-alter-color": "#272727",
|
||||
"font-color": "#dcdcdc",
|
||||
"font-bold": false,
|
||||
"font-italic": false,
|
||||
"alignment-horizontal": "left",
|
||||
"alignment-vertical": "top",
|
||||
"word-wrap": false,
|
||||
"ellide": true,
|
||||
"max-lines": 1
|
||||
},
|
||||
"table-item-col[0]": {
|
||||
"font-size": 20,
|
||||
"font-color": "#898989",
|
||||
"font-bold": true,
|
||||
"ellide": false,
|
||||
"word-wrap": true,
|
||||
"max-lines": null
|
||||
},
|
||||
"table-item-col[1]": {
|
||||
"font-size": 40,
|
||||
"padding-left": 10
|
||||
},
|
||||
"#colorbar": {
|
||||
"bg-color": "#9932CC"
|
||||
}
|
||||
},
|
||||
"items": [{
|
||||
"type": "layer",
|
||||
"direction": 1,
|
||||
"name": "MainLayer",
|
||||
"style": {
|
||||
"#MainLayer": {
|
||||
"width": 1094,
|
||||
"height": 1000,
|
||||
"margin": 25,
|
||||
"padding": 0
|
||||
},
|
||||
"#LeftSide": {
|
||||
"margin-right": 25
|
||||
}
|
||||
},
|
||||
"items": [{
|
||||
"type": "layer",
|
||||
"name": "LeftSide",
|
||||
"items": [{
|
||||
"type": "layer",
|
||||
"direction": 1,
|
||||
"style": {
|
||||
"table-item": {
|
||||
"bg-color": "transparent",
|
||||
"padding-bottom": 20
|
||||
},
|
||||
"table-item-col[0]": {
|
||||
"font-size": 20,
|
||||
"font-color": "#898989",
|
||||
"alignment-horizontal": "right"
|
||||
},
|
||||
"table-item-col[1]": {
|
||||
"alignment-horizontal": "left",
|
||||
"font-bold": true,
|
||||
"font-size": 40
|
||||
}
|
||||
},
|
||||
"items": [{
|
||||
"type": "table",
|
||||
"values": [
|
||||
["Show:", "{project[name]}"]
|
||||
],
|
||||
"style": {
|
||||
"table-item-field[0:0]": {
|
||||
"width": 150
|
||||
},
|
||||
"table-item-field[0:1]": {
|
||||
"width": 580
|
||||
}
|
||||
}
|
||||
}, {
|
||||
"type": "table",
|
||||
"values": [
|
||||
["Submitting For:", "{intent}"]
|
||||
],
|
||||
"style": {
|
||||
"table-item-field[0:0]": {
|
||||
"width": 160
|
||||
},
|
||||
"table-item-field[0:1]": {
|
||||
"width": 218,
|
||||
"alignment-horizontal": "right"
|
||||
}
|
||||
}
|
||||
}]
|
||||
}, {
|
||||
"type": "rectangle",
|
||||
"style": {
|
||||
"bg-color": "#bc1015",
|
||||
"width": 1108,
|
||||
"height": 5,
|
||||
"fill": true
|
||||
}
|
||||
}, {
|
||||
"type": "table",
|
||||
"use_alternate_color": true,
|
||||
"values": [
|
||||
["Version name:", "{version_name}"],
|
||||
["Date:", "{date}"],
|
||||
["Shot Types:", "{shot_type}"],
|
||||
["Submission Note:", "{submission_note}"]
|
||||
],
|
||||
"style": {
|
||||
"table-item": {
|
||||
"padding-bottom": 20
|
||||
},
|
||||
"table-item-field[0:1]": {
|
||||
"font-bold": true
|
||||
},
|
||||
"table-item-field[3:0]": {
|
||||
"word-wrap": true,
|
||||
"ellide": true,
|
||||
"max-lines": 4
|
||||
},
|
||||
"table-item-col[0]": {
|
||||
"alignment-horizontal": "right",
|
||||
"width": 150
|
||||
},
|
||||
"table-item-col[1]": {
|
||||
"alignment-horizontal": "left",
|
||||
"width": 958
|
||||
}
|
||||
}
|
||||
}]
|
||||
}, {
|
||||
"type": "layer",
|
||||
"name": "RightSide",
|
||||
"items": [{
|
||||
"type": "placeholder",
|
||||
"name": "thumbnail",
|
||||
"path": "{thumbnail_path}",
|
||||
"style": {
|
||||
"width": 730,
|
||||
"height": 412
|
||||
}
|
||||
}, {
|
||||
"type": "placeholder",
|
||||
"name": "colorbar",
|
||||
"path": "{color_bar_path}",
|
||||
"return_data": true,
|
||||
"style": {
|
||||
"width": 730,
|
||||
"height": 55
|
||||
}
|
||||
}, {
|
||||
"type": "table",
|
||||
"use_alternate_color": true,
|
||||
"values": [
|
||||
["Vendor:", "{vendor}"],
|
||||
["Shot Name:", "{shot_name}"],
|
||||
["Frames:", "{frame_start} - {frame_end} ({duration})"]
|
||||
],
|
||||
"style": {
|
||||
"table-item-col[0]": {
|
||||
"alignment-horizontal": "left",
|
||||
"width": 200
|
||||
},
|
||||
"table-item-col[1]": {
|
||||
"alignment-horizontal": "right",
|
||||
"width": 530,
|
||||
"font-size": 30
|
||||
}
|
||||
}
|
||||
}]
|
||||
}]
|
||||
}]
|
||||
}
|
||||
|
|
@ -0,0 +1,4 @@
|
|||
{
|
||||
"dev_mode": false,
|
||||
"install_unreal_python_engine": false
|
||||
}
|
||||
|
|
@ -0,0 +1,16 @@
|
|||
{
|
||||
"AVALON_CONFIG": "pype",
|
||||
"AVALON_PROJECTS": "{PYPE_PROJECTS_PATH}",
|
||||
"AVALON_USERNAME": "avalon",
|
||||
"AVALON_PASSWORD": "secret",
|
||||
"AVALON_DEBUG": "1",
|
||||
"AVALON_MONGO": "mongodb://localhost:2707",
|
||||
"AVALON_DB": "avalon",
|
||||
"AVALON_DB_DATA": "{PYPE_SETUP_PATH}/../mongo_db_data",
|
||||
"AVALON_EARLY_ADOPTER": "1",
|
||||
"AVALON_SCHEMA": "{PYPE_MODULE_ROOT}/schema",
|
||||
"AVALON_LOCATION": "http://127.0.0.1",
|
||||
"AVALON_LABEL": "Pype",
|
||||
"AVALON_TIMEOUT": "1000",
|
||||
"AVALON_THUMBNAIL_ROOT": ""
|
||||
}
|
||||
|
|
@ -0,0 +1,7 @@
|
|||
{
|
||||
"BLENDER_USER_SCRIPTS": "{PYPE_SETUP_PATH}/repos/avalon-core/setup/blender",
|
||||
"PYTHONPATH": [
|
||||
"{PYPE_SETUP_PATH}/repos/avalon-core/setup/blender",
|
||||
"{PYTHONPATH}"
|
||||
]
|
||||
}
|
||||
|
|
@ -0,0 +1,3 @@
|
|||
{
|
||||
"CELACTION_TEMPLATE": "{PYPE_MODULE_ROOT}/pype/hosts/celaction/celaction_template_scene.scn"
|
||||
}
|
||||
|
|
@ -0,0 +1,3 @@
|
|||
{
|
||||
"DEADLINE_REST_URL": "http://localhost:8082"
|
||||
}
|
||||
|
|
@ -0,0 +1,18 @@
|
|||
{
|
||||
"FTRACK_SERVER": "https://pype.ftrackapp.com",
|
||||
"FTRACK_ACTIONS_PATH": [
|
||||
"{PYPE_MODULE_ROOT}/pype/modules/ftrack/actions"
|
||||
],
|
||||
"FTRACK_EVENTS_PATH": [
|
||||
"{PYPE_MODULE_ROOT}/pype/modules/ftrack/events"
|
||||
],
|
||||
"PYTHONPATH": [
|
||||
"{PYPE_MODULE_ROOT}/pype/vendor",
|
||||
"{PYTHONPATH}"
|
||||
],
|
||||
"PYBLISHPLUGINPATH": [
|
||||
"{PYPE_MODULE_ROOT}/pype/plugins/ftrack/publish"
|
||||
],
|
||||
"FTRACK_EVENTS_MONGO_DB": "pype",
|
||||
"FTRACK_EVENTS_MONGO_COL": "ftrack_events"
|
||||
}
|
||||
|
|
@ -0,0 +1,44 @@
|
|||
{
|
||||
"PYPE_STUDIO_NAME": "Studio Name",
|
||||
"PYPE_STUDIO_CODE": "stu",
|
||||
"PYPE_APP_ROOT": "{PYPE_SETUP_PATH}/pypeapp",
|
||||
"PYPE_MODULE_ROOT": "{PYPE_SETUP_PATH}/repos/pype",
|
||||
"PYPE_PROJECT_PLUGINS": "",
|
||||
"STUDIO_SOFT": "{PYP_SETUP_ROOT}/soft",
|
||||
"FFMPEG_PATH": {
|
||||
"windows": "{VIRTUAL_ENV}/localized/ffmpeg_exec/windows/bin;{PYPE_SETUP_PATH}/vendor/ffmpeg_exec/windows/bin",
|
||||
"darwin": "{VIRTUAL_ENV}/localized/ffmpeg_exec/darwin/bin:{PYPE_SETUP_PATH}/vendor/ffmpeg_exec/darwin/bin",
|
||||
"linux": "{VIRTUAL_ENV}/localized/ffmpeg_exec/linux:{PYPE_SETUP_PATH}/vendor/ffmpeg_exec/linux"
|
||||
},
|
||||
"DJV_PATH": {
|
||||
"windows": [
|
||||
"C:/Program Files/djv-1.1.0-Windows-64/bin/djv_view.exe",
|
||||
"C:/Program Files/DJV/bin/djv_view.exe",
|
||||
"{STUDIO_SOFT}/djv/windows/bin/djv_view.exe"
|
||||
],
|
||||
"linux": [
|
||||
"usr/local/djv/djv_view",
|
||||
"{STUDIO_SOFT}/djv/linux/bin/djv_view"
|
||||
],
|
||||
"darwin": "Application/DJV.app/Contents/MacOS/DJV"
|
||||
},
|
||||
"PATH": [
|
||||
"{PYPE_CONFIG}/launchers",
|
||||
"{PYPE_APP_ROOT}",
|
||||
"{FFMPEG_PATH}",
|
||||
"{PATH}"
|
||||
],
|
||||
"PYPE_OCIO_CONFIG": "{STUDIO_SOFT}/OpenColorIO-Configs",
|
||||
"PYTHONPATH": {
|
||||
"windows": "{VIRTUAL_ENV}/Lib/site-packages;{PYPE_MODULE_ROOT}/pype/tools;{PYTHONPATH}",
|
||||
"linux": "{VIRTUAL_ENV}/lib/python{PYTHON_VERSION}/site-packages:{PYPE_MODULE_ROOT}/pype/tools:{PYTHONPATH}",
|
||||
"darwin": "{VIRTUAL_ENV}/lib/python{PYTHON_VERSION}/site-packages:{PYPE_MODULE_ROOT}/pype/tools:{PYTHONPATH}"
|
||||
},
|
||||
"PYPE_PROJECT_CONFIGS": "{PYPE_SETUP_PATH}/../studio-project-configs",
|
||||
"PYPE_PYTHON_EXE": {
|
||||
"windows": "{VIRTUAL_ENV}/Scripts/python.exe",
|
||||
"linux": "{VIRTUAL_ENV}/Scripts/python",
|
||||
"darwin": "{VIRTUAL_ENV}/bin/python"
|
||||
},
|
||||
"PYBLISH_GUI": "pyblish_pype"
|
||||
}
|
||||
|
|
@ -0,0 +1,4 @@
|
|||
{
|
||||
"AVALON_HARMONY_WORKFILES_ON_LAUNCH": "1",
|
||||
"PYBLISH_GUI_ALWAYS_EXEC": "1"
|
||||
}
|
||||
|
|
@ -0,0 +1,12 @@
|
|||
{
|
||||
"HOUDINI_PATH": {
|
||||
"darwin": "{PYPE_MODULE_ROOT}/setup/houdini:&",
|
||||
"linux": "{PYPE_MODULE_ROOT}/setup/houdini:&",
|
||||
"windows": "{PYPE_MODULE_ROOT}/setup/houdini;&"
|
||||
},
|
||||
"HOUDINI_MENU_PATH": {
|
||||
"darwin": "{PYPE_MODULE_ROOT}/setup/houdini:&",
|
||||
"linux": "{PYPE_MODULE_ROOT}/setup/houdini:&",
|
||||
"windows": "{PYPE_MODULE_ROOT}/setup/houdini;&"
|
||||
}
|
||||
}
|
||||
|
|
@ -0,0 +1,14 @@
|
|||
{
|
||||
"PYTHONPATH": [
|
||||
"{PYPE_SETUP_PATH}/repos/avalon-core/setup/maya",
|
||||
"{PYPE_SETUP_PATH}/repos/maya-look-assigner",
|
||||
"{PYTHON_ENV}/python2/Lib/site-packages",
|
||||
"{PYTHONPATH}"
|
||||
],
|
||||
"MAYA_DISABLE_CLIC_IPM": "Yes",
|
||||
"MAYA_DISABLE_CIP": "Yes",
|
||||
"MAYA_DISABLE_CER": "Yes",
|
||||
"PYMEL_SKIP_MEL_INIT": "Yes",
|
||||
"LC_ALL": "C",
|
||||
"PYPE_LOG_NO_COLORS": "Yes"
|
||||
}
|
||||
|
|
@ -0,0 +1,11 @@
|
|||
{
|
||||
"MAYA_VERSION": "2018",
|
||||
"MAYA_LOCATION": {
|
||||
"darwin": "/Applications/Autodesk/maya{MAYA_VERSION}/Maya.app/Contents",
|
||||
"linux": "/usr/autodesk/maya{MAYA_VERSION}",
|
||||
"windows": "C:/Program Files/Autodesk/Maya{MAYA_VERSION}"
|
||||
},
|
||||
"DYLD_LIBRARY_PATH": {
|
||||
"darwin": "{MAYA_LOCATION}/MacOS"
|
||||
}
|
||||
}
|
||||
|
|
@ -0,0 +1,11 @@
|
|||
{
|
||||
"MAYA_VERSION": "2020",
|
||||
"MAYA_LOCATION": {
|
||||
"darwin": "/Applications/Autodesk/maya{MAYA_VERSION}/Maya.app/Contents",
|
||||
"linux": "/usr/autodesk/maya{MAYA_VERSION}",
|
||||
"windows": "C:/Program Files/Autodesk/Maya{MAYA_VERSION}"
|
||||
},
|
||||
"DYLD_LIBRARY_PATH": {
|
||||
"darwin": "{MAYA_LOCATION}/MacOS"
|
||||
}
|
||||
}
|
||||
|
|
@ -0,0 +1,14 @@
|
|||
{
|
||||
"PYTHONPATH": [
|
||||
"{PYPE_SETUP_PATH}/repos/avalon-core/setup/maya",
|
||||
"{PYPE_SETUP_PATH}/repos/maya-look-assigner",
|
||||
"{PYTHON_ENV}/python2/Lib/site-packages",
|
||||
"{PYTHONPATH}"
|
||||
],
|
||||
"MAYA_DISABLE_CLIC_IPM": "Yes",
|
||||
"MAYA_DISABLE_CIP": "Yes",
|
||||
"MAYA_DISABLE_CER": "Yes",
|
||||
"PYMEL_SKIP_MEL_INIT": "Yes",
|
||||
"LC_ALL": "C",
|
||||
"PYPE_LOG_NO_COLORS": "Yes"
|
||||
}
|
||||
|
|
@ -0,0 +1,11 @@
|
|||
{
|
||||
"MAYA_VERSION": "2019",
|
||||
"MAYA_LOCATION": {
|
||||
"darwin": "/Applications/Autodesk/maya{MAYA_VERSION}/Maya.app/Contents",
|
||||
"linux": "/usr/autodesk/maya{MAYA_VERSION}",
|
||||
"windows": "C:/Program Files/Autodesk/Maya{MAYA_VERSION}"
|
||||
},
|
||||
"DYLD_LIBRARY_PATH": {
|
||||
"darwin": "{MAYA_LOCATION}/MacOS"
|
||||
}
|
||||
}
|
||||
|
|
@ -0,0 +1,23 @@
|
|||
{
|
||||
"MTOA": "{PYPE_STUDIO_SOFTWARE}/arnold/mtoa_{MAYA_VERSION}_{MTOA_VERSION}",
|
||||
"MTOA_VERSION": "3.1.1",
|
||||
"MAYA_RENDER_DESC_PATH": "{MTOA}",
|
||||
"MAYA_MODULE_PATH": "{MTOA}",
|
||||
"ARNOLD_PLUGIN_PATH": "{MTOA}/shaders",
|
||||
"MTOA_EXTENSIONS_PATH": {
|
||||
"darwin": "{MTOA}/extensions",
|
||||
"linux": "{MTOA}/extensions",
|
||||
"windows": "{MTOA}/extensions"
|
||||
},
|
||||
"MTOA_EXTENSIONS": {
|
||||
"darwin": "{MTOA}/extensions",
|
||||
"linux": "{MTOA}/extensions",
|
||||
"windows": "{MTOA}/extensions"
|
||||
},
|
||||
"DYLD_LIBRARY_PATH": {
|
||||
"darwin": "{MTOA}/bin"
|
||||
},
|
||||
"PATH": {
|
||||
"windows": "{PATH};{MTOA}/bin"
|
||||
}
|
||||
}
|
||||
|
|
@ -0,0 +1,3 @@
|
|||
{
|
||||
"MUSTER_REST_URL": "http://127.0.0.1:9890"
|
||||
}
|
||||
|
|
@ -0,0 +1,15 @@
|
|||
{
|
||||
"NUKE_PATH": [
|
||||
"{PYPE_SETUP_PATH}/repos/avalon-core/setup/nuke/nuke_path",
|
||||
"{PYPE_MODULE_ROOT}/setup/nuke/nuke_path",
|
||||
"{PYPE_STUDIO_PLUGINS}/nuke"
|
||||
],
|
||||
"PATH": {
|
||||
"windows": "C:/Program Files (x86)/QuickTime/QTSystem/;{PATH}"
|
||||
},
|
||||
"PYPE_LOG_NO_COLORS": "True",
|
||||
"PYTHONPATH": {
|
||||
"windows": "{VIRTUAL_ENV}/Lib/site-packages;{PYTHONPATH}",
|
||||
"linux": "{VIRTUAL_ENV}/lib/python3.6/site-packages:{PYTHONPATH}"
|
||||
}
|
||||
}
|
||||
|
|
@ -0,0 +1,11 @@
|
|||
{
|
||||
"HIERO_PLUGIN_PATH": [
|
||||
"{PYPE_MODULE_ROOT}/setup/nukestudio/hiero_plugin_path"
|
||||
],
|
||||
"PATH": {
|
||||
"windows": "C:/Program Files (x86)/QuickTime/QTSystem/;{PATH}"
|
||||
},
|
||||
"WORKFILES_STARTUP": "0",
|
||||
"TAG_ASSETBUILD_STARTUP": "0",
|
||||
"PYPE_LOG_NO_COLORS": "True"
|
||||
}
|
||||
|
|
@ -0,0 +1,4 @@
|
|||
{
|
||||
"PYPE_LOG_NO_COLORS": "Yes",
|
||||
"QT_PREFERRED_BINDING": "PySide"
|
||||
}
|
||||
|
|
@ -0,0 +1,10 @@
|
|||
{
|
||||
"NUKE_PATH": [
|
||||
"{PYPE_SETUP_PATH}/repos/avalon-core/setup/nuke/nuke_path",
|
||||
"{PYPE_MODULE_ROOT}/setup/nuke/nuke_path",
|
||||
"{PYPE_STUDIO_PLUGINS}/nuke"
|
||||
],
|
||||
"PATH": {
|
||||
"windows": "C:/Program Files (x86)/QuickTime/QTSystem/;{PATH}"
|
||||
}
|
||||
}
|
||||
|
|
@ -0,0 +1,4 @@
|
|||
{
|
||||
"PYPE_LOG_NO_COLORS": "Yes",
|
||||
"QT_PREFERRED_BINDING": "PySide"
|
||||
}
|
||||
|
|
@ -0,0 +1,4 @@
|
|||
{
|
||||
"AVALON_PHOTOSHOP_WORKFILES_ON_LAUNCH": "1",
|
||||
"PYTHONPATH": "{PYTHONPATH}"
|
||||
}
|
||||
|
|
@ -0,0 +1,11 @@
|
|||
{
|
||||
"EXTENSIONS_PATH": {
|
||||
"windows": "{USERPROFILE}/AppData/Roaming/Adobe/CEP/extensions",
|
||||
"darvin": "{USER}/Library/Application Support/Adobe/CEP/extensions"
|
||||
},
|
||||
"EXTENSIONS_CACHE_PATH": {
|
||||
"windows": "{USERPROFILE}/AppData/Local/Temp/cep_cache",
|
||||
"darvin": "{USER}/Library/Application Support/Adobe/CEP/cep_cache"
|
||||
},
|
||||
"installed_zxp": ""
|
||||
}
|
||||
|
|
@ -0,0 +1,40 @@
|
|||
{
|
||||
"RESOLVE_UTILITY_SCRIPTS_SOURCE_DIR": [
|
||||
"{STUDIO_SOFT}/davinci_resolve/scripts/python"
|
||||
],
|
||||
"RESOLVE_SCRIPT_API": {
|
||||
"windows": "{PROGRAMDATA}/Blackmagic Design/DaVinci Resolve/Support/Developer/Scripting",
|
||||
"darvin": "/Library/Application Support/Blackmagic Design/DaVinci Resolve/Developer/Scripting",
|
||||
"linux": "/opt/resolve/Developer/Scripting"
|
||||
},
|
||||
"RESOLVE_SCRIPT_LIB": {
|
||||
"windows": "C:/Program Files/Blackmagic Design/DaVinci Resolve/fusionscript.dll",
|
||||
"darvin": "/Applications/DaVinci Resolve/DaVinci Resolve.app/Contents/Libraries/Fusion/fusionscript.so",
|
||||
"linux": "/opt/resolve/libs/Fusion/fusionscript.so"
|
||||
},
|
||||
"RESOLVE_UTILITY_SCRIPTS_DIR": {
|
||||
"windows": "{PROGRAMDATA}/Blackmagic Design/DaVinci Resolve/Fusion/Scripts/Comp",
|
||||
"darvin": "/Library/Application Support/Blackmagic Design/DaVinci Resolve/Fusion/Scripts/Comp",
|
||||
"linux": "/opt/resolve/Fusion/Scripts/Comp"
|
||||
},
|
||||
"PYTHON36_RESOLVE": {
|
||||
"windows": "{LOCALAPPDATA}/Programs/Python/Python36",
|
||||
"darvin": "~/Library/Python/3.6/bin",
|
||||
"linux": "/opt/Python/3.6/bin"
|
||||
},
|
||||
"PYTHONPATH": [
|
||||
"{PYTHON36_RESOLVE}/Lib/site-packages",
|
||||
"{VIRTUAL_ENV}/Lib/site-packages",
|
||||
"{PYTHONPATH}",
|
||||
"{RESOLVE_SCRIPT_API}/Modules",
|
||||
"{PYTHONPATH}"
|
||||
],
|
||||
"PATH": [
|
||||
"{PYTHON36_RESOLVE}",
|
||||
"{PYTHON36_RESOLVE}/Scripts",
|
||||
"{PATH}"
|
||||
],
|
||||
"PRE_PYTHON_SCRIPT": "{PYPE_MODULE_ROOT}/pype/resolve/preload_console.py",
|
||||
"PYPE_LOG_NO_COLORS": "True",
|
||||
"RESOLVE_DEV": "True"
|
||||
}
|
||||
|
|
@ -0,0 +1,4 @@
|
|||
{
|
||||
"AVALON_TOONBOOM_WORKFILES_ON_LAUNCH": "1",
|
||||
"PYBLISH_LITE_ALWAYS_EXEC": "1"
|
||||
}
|
||||
|
|
@ -0,0 +1,5 @@
|
|||
{
|
||||
"AVALON_UNREAL_PLUGIN": "{PYPE_SETUP_PATH}/repos/avalon-unreal-integration",
|
||||
"PYPE_LOG_NO_COLORS": "True",
|
||||
"QT_PREFERRED_BINDING": "PySide"
|
||||
}
|
||||
|
|
@ -0,0 +1,15 @@
|
|||
{
|
||||
"VRAY_VERSION": "43001",
|
||||
"VRAY_ROOT": "C:/vray/vray_{VRAY_VERSION}",
|
||||
"MAYA_RENDER_DESC_PATH": "{VRAY_ROOT}/maya_root/bin/rendererDesc",
|
||||
"VRAY_FOR_MAYA2019_MAIN": "{VRAY_ROOT}/maya_vray",
|
||||
"VRAY_FOR_MAYA2019_PLUGINS": "{VRAY_ROOT}/maya_vray/vrayplugins",
|
||||
"VRAY_PLUGINS": "{VRAY_ROOT}/maya_vray/vrayplugins",
|
||||
"VRAY_OSL_PATH_MAYA2019": "{VRAY_ROOT}/vray/opensl",
|
||||
"PATH": "{VRAY_ROOT}/maya_root/bin;{PATH}",
|
||||
"MAYA_PLUG_IN_PATH": "{VRAY_ROOT}/maya_vray/plug-ins",
|
||||
"MAYA_SCRIPT_PATH": "{VRAY_ROOT}/maya_vray/scripts",
|
||||
"PYTHONPATH": "{VRAY_ROOT}/maya_vray/scripts;{PYTHONPATH}",
|
||||
"XBMLANGPATH": "{VRAY_ROOT}/maya_vray/icons;{XBMLANGPATH}",
|
||||
"VRAY_AUTH_CLIENT_FILE_PATH": "{VRAY_ROOT}"
|
||||
}
|
||||
|
|
@ -0,0 +1,34 @@
|
|||
{
|
||||
"blender_2.80": true,
|
||||
"blender_2.81": true,
|
||||
"blender_2.82": true,
|
||||
"blender_2.83": true,
|
||||
"celaction_local": true,
|
||||
"celaction_remote": true,
|
||||
"harmony_17": true,
|
||||
"maya_2017": true,
|
||||
"maya_2018": true,
|
||||
"maya_2019": true,
|
||||
"maya_2020": true,
|
||||
"nuke_10.0": true,
|
||||
"nuke_11.2": true,
|
||||
"nuke_11.3": true,
|
||||
"nuke_12.0": true,
|
||||
"nukex_10.0": true,
|
||||
"nukex_11.2": true,
|
||||
"nukex_11.3": true,
|
||||
"nukex_12.0": true,
|
||||
"nukestudio_10.0": true,
|
||||
"nukestudio_11.2": true,
|
||||
"nukestudio_11.3": true,
|
||||
"nukestudio_12.0": true,
|
||||
"houdini_16": true,
|
||||
"houdini_16.5": false,
|
||||
"houdini_17": true,
|
||||
"houdini_18": true,
|
||||
"premiere_2019": true,
|
||||
"premiere_2020": true,
|
||||
"resolve_16": true,
|
||||
"storyboardpro_7": true,
|
||||
"unreal_4.24": true
|
||||
}
|
||||
|
|
@ -0,0 +1,8 @@
|
|||
{
|
||||
"items": {
|
||||
"wip": "WIP",
|
||||
"test": "TEST",
|
||||
"final": "FINAL"
|
||||
},
|
||||
"default": "wip"
|
||||
}
|
||||
6
pype/settings/defaults/system_settings/global/tools.json
Normal file
6
pype/settings/defaults/system_settings/global/tools.json
Normal file
|
|
@ -0,0 +1,6 @@
|
|||
{
|
||||
"mtoa_3.0.1": true,
|
||||
"mtoa_3.1.1": true,
|
||||
"mtoa_3.2.0": true,
|
||||
"yeti_2.1.2": true
|
||||
}
|
||||
|
|
@ -0,0 +1,28 @@
|
|||
{
|
||||
"item_usage": {
|
||||
"User settings": false,
|
||||
"Ftrack": true,
|
||||
"Muster": false,
|
||||
"Avalon": true,
|
||||
"Clockify": false,
|
||||
"Standalone Publish": true,
|
||||
"Logging": true,
|
||||
"Idle Manager": true,
|
||||
"Timers Manager": true,
|
||||
"Rest Api": true,
|
||||
"Adobe Communicator": true
|
||||
},
|
||||
"attributes": {
|
||||
"Rest Api": {
|
||||
"default_port": 8021,
|
||||
"exclude_ports": []
|
||||
},
|
||||
"Timers Manager": {
|
||||
"full_time": 15.0,
|
||||
"message_time": 0.5
|
||||
},
|
||||
"Clockify": {
|
||||
"workspace_name": ""
|
||||
}
|
||||
}
|
||||
}
|
||||
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