예제 #1
0
    def _reload(self, children):
        parent_revision = tank.find(self.path)

        # go through each revision in the bundle
        # find matching connected reference with same container
        # update
        for child_revision in self._bundle.revisions:
            if os.path.splitext(child_revision.system.filesystem_location)[1] in (".ma", ".mb"):
                for ref_node in self.node.members():
                    ref = pm.FileReference(ref_node)
                    r2 = tank.find(ref.path)
                    if str(r2) == str(child_revision):
                        # same reference, done with this revision
                        break
                    elif str(r2.container) == str(child_revision.container):
                        # same container, different revision
                        # replace the revision with this one
                        ref.replaceWith(child_revision.system.vfs_full_paths[0])
                        break

        # now go through connected reference nodes
        # if one is connected, but doesn't belong, unlink it
        # NOTE: we don't remove it -- leave it up to the user to do that
        for ref_node in self.node.members():
            ref = pm.FileReference(ref_node)
            revision = tank.find(ref.path)
            if not revision in self._bundle.revisions:
                self.node.remove(ref_node)
def load_all_geocaches(node):
    # Get the shot from the scene container
    shot = node.scene.container.labels['Shot']

    print "\nLoading all geocaches for", shot

    # get all latest geocaches for that shot
    geocaches = tank.get_children(tank.find("GeoCache"), ["container has_label %s" % shot])
    for geocache in geocaches:
#        if geocache == geocache.container.latest_revisions['GeoCache']:  # is it the latest?
        if geocache == tank.find('GeoCache(LATEST, %s)' % geocache.container):  # is it the latest?
            # We only load the latest geocaches revisions
            load_one_geocache(node, geocache)
예제 #3
0
    def valid_revision_types(self):
        """
        Returns the list of valid revision types. Types are filtered against the extension_hint and
        restrict_resource_type properties of the revision type and the valid_revision_types property
        of the container. The first entry is always None.

        :rtype: list of strings
        """
        # check for valid revision types
        # TODO: simplify when list_* returns types instead of strings
        valid_rts = [tank.find(rt) for rt in tank.list_revision_types()]

        # check for matching extension
        if isinstance(self._data.path, basestring):
            ext = os.path.splitext(self._data.path)[1].lstrip('.')
            valid_rts = [rt for rt in valid_rts \
                            if rt.properties.extension_hint is not None and \
                               ext in rt.properties.extension_hint.split(',')]

            # check for matching sequence vs. single file
            if hasattr(self._data, "frame_range") and self._data.frame_range is not None:
                resource_type = tank.constants.ResourceType.SEQUENCE
            else:
                if os.path.exists(self._data.path) and os.path.isdir(self._data.path):
                    resource_type = tank.constants.ResourceType.FOLDER
                else:
                    resource_type = tank.constants.ResourceType.SINGLE_FILE

            valid_rts = [rt for rt in valid_rts if rt.properties.restrict_resource_type in (resource_type, None)]

            return [None] + sorted(valid_rts, key=lambda rt: rt.system.name)
        else:
            return [None]
예제 #4
0
    def get_latest_master_audio(self,
                                revision_type="Audio",
                                return_tank_object=False):
        """
        Return the latest audio for a shot.
        By default it returns the file path to the audio.
        If return_tank_object=True, it will return the Tank revision object.
        """
        import traceback

        if self._cache_latest_tank_audio == "_search_but_not_found":
            return None

        audio_container = projectAwareness.get_tank_audio_container(
            self.project.name, self.scene.name, self.name, audio_name="master")

        try:
            audio_address = "%(revision_type)s(latest, %(audio_container)s)" % vars(
            )
            rev = tank.find(audio_address)

        except tank.common.errors.TankNotFound, e:
            self._cache_latest_tank_audio = "_search_but_not_found"
            print "Tank Not Found: can not find audio under %s" % audio_address

            return None
예제 #5
0
    def collectReviews(self, tank_obj):
        # extract the tank information for the reviews
        rev_type = tank_obj.get_entity_type()
        container = tank_obj.get_container()
        container_address = str(container)

        # replace the review type for the container
        if ('ReviewType(creative)' in container_address):
            container_address = container_address.replace(
                'ReviewType(creative)', 'ReviewType(technical)')
        elif ('ReviewType(technical)' in container_address):
            container_address = container_address.replace(
                'ReviewType(technical)', 'ReviewType(creative)')
        else:
            return []

        # create the mapping
        try:
            matching = tank.find(container_address).get_object()
        except TankNotFound:
            return []

        # make sure our revisions are of the same type, and come from the same root maya scene
        mscene = self.findAncestor('MayaScene', tank_obj)
        revisions = [
            rev for rev in matching.get_revisions()
            if rev.get_entity_type() == rev_type
            and self.findAncestor('MayaScene', rev) == mscene
        ]
        revisions.reverse()

        return revisions
예제 #6
0
def determine_aux_data_from_tank_address(tank_rev, include_shotgun_data=False):
    import tank
    if type(tank_rev) in (str, unicode):
        tank_rev = tank.find(tank_rev)

    return determine_aux_data_from_vfs_path(
        tank_rev=tank_rev, include_shotgun_data=include_shotgun_data)
예제 #7
0
def collectFrameData(address):
    frames_address  = address.replace('Movie(','Frames(')
    try:
        tank_frames = tank.find(frames_address)
    except:
        tank_frames = None
        core.warn( 'Could not find tank address: %s...' % address )
    
    imageSource = ''
    sourceStart = 0
    sourceEnd   = 0
    stereo_pair = []
    
    if ( tank_frames ):
        filepath                    = tank_frames.system.filesystem_location
        
        # extract the stereo pair information from the tank frames object
        stereo_pair                 = tank_frames.properties['stereo_pair']
        if ( not stereo_pair ):
            stereo_pair = ['left']
            
        spath, sname, smin, smax    = get_frame_sequence_source(filepath)
        
        if ( not (spath and sname) ):
            core.warn( 'Could not extract frame data from %s' % filepath )
        else:
            imageSource = os.path.join(spath,sname)
            sourceStart = smin
            sourceEnd   = smax
    
    return (imageSource,sourceStart,sourceEnd,stereo_pair)
 def collectReviews( self, tank_obj ):
     # extract the tank information for the reviews
     rev_type            = tank_obj.get_entity_type()
     container           = tank_obj.get_container()
     container_address   = str(container)
     
     # replace the review type for the container
     if ( 'ReviewType(creative)' in container_address ):
         container_address = container_address.replace('ReviewType(creative)','ReviewType(technical)')
     elif ( 'ReviewType(technical)' in container_address ):
         container_address = container_address.replace('ReviewType(technical)','ReviewType(creative)')
     else:
         return []
     
     # create the mapping
     try:
         matching            = tank.find(container_address).get_object()
     except TankNotFound:
         return []
     
     # make sure our revisions are of the same type, and come from the same root maya scene
     mscene    = self.findAncestor( 'MayaScene', tank_obj )
     revisions = [ rev for rev in matching.get_revisions() if rev.get_entity_type() == rev_type and self.findAncestor( 'MayaScene', rev ) == mscene ]
     revisions.reverse()
     
     return revisions
예제 #9
0
    def syncSceneShotVersionBar(self):
        '''
        update the tank version combo by looking at the path
        populate the tank versions combo box if the source comes from tank
        '''
        if not self.cboSourceVersion.isVisible():
            return

        self.stateTankVersionChanging = True
        QtGui.QApplication.setOverrideCursor(QtCore.Qt.WaitCursor)

        # get the source data
        sourceData = self.tableView.getShotData(self.tableView.getSelectedRow()[0])

        if isEditSourceMovie(sourceData["Source Name"]):
            path = os.path.join(sourceData["Source Path"], sourceData["Source Name"])
        else:
            path = sourceData["Source Path"]

        # check if it specify a tank version
        rev = None
        try:
            rev = tank.find(path)
        except tank.common.errors.TankNotFound, e:
            pass
예제 #10
0
def get_revision_type(parent_container, path, frame_range):
    # start with all revision types
    valid_rts = [tank.find(rt) for rt in tank.list_revision_types()]

    if parent_container and len(parent_container.system.type.properties.valid_revision_types) > 0:
        valid_rts = [rt for rt in valid_rts if rt in parent_container.system.type.properties.valid_revision_types]

    # filter by extension
    ext = os.path.splitext(path)[1].lstrip(".")
    valid_rts = [rt for rt in valid_rts \
                    if rt.properties.extension_hint is not None and \
                       ext in rt.properties.extension_hint.split(',')]

    # filter by resource type
    if frame_range is None:
        if os.path.exists(path) and os.path.isdir(path):
            resource_type = tank.common.constants.ResourceType.FOLDER
        else:
            resource_type = tank.common.constants.ResourceType.SINGLE_FILE
    else:
        resource_type = tank.common.constants.ResourceType.SEQUENCE

    valid_rts = [rt for rt in valid_rts if rt.properties.restrict_resource_type in (resource_type, None)]

    if len(valid_rts) > 0:
        return valid_rts[0]
    else:
        return None
예제 #11
0
    def get_latest_master_audio(self, revision_type="Audio", return_tank_object=False):
        """
        Return the latest audio for a shot.
        By default it returns the file path to the audio.
        If return_tank_object=True, it will return the Tank revision object.
        """
        import traceback

        if self._cache_latest_tank_audio == "_search_but_not_found":
            return None

        audio_container = projectAwareness.get_tank_audio_container(self.project.name,
                                                   self.scene.name,
                                                   self.name,
                                                   audio_name="master")

        try:
            audio_address = "%(revision_type)s(latest, %(audio_container)s)" % vars()
            rev = tank.find(audio_address)


        except tank.common.errors.TankNotFound, e:
            self._cache_latest_tank_audio = "_search_but_not_found"
            print "Tank Not Found: can not find audio under %s" % audio_address

            return None
예제 #12
0
 def last_revision(self):
     """
     Returns the last revision stored by the delegate
     """
     if self.is_revision():
         return self.revision
     elif hasattr(self._data, "last_revision_id"):
         return tank.find(self._data.last_revision_id) if self._data.last_revision_id is not None else None
     else:
         return None
예제 #13
0
def get(work_path):
    """Returns container, revision_type associated with the work path."""
    # if it's a revision, it's definitely not a working path
    # TODO: get from tank config
    if work_path[0:5] == "/tank":
        raise NotWorkingPathError("%s is not a working path." % work_path)

    dir = None
    filename = None
    ext = None
    resource_type = None

    if os.path.isdir(work_path):
        dir = work_path
    elif os.path.isfile(work_path):
        dir, filename = os.path.split(work_path)
        filename, ext = os.path.splitext(filename)
        resource_type = tank.common.constants.ResourceType.SINGLE_FILE
    else:
        # strip off names until we find a directory that exists
        ext = os.path.splitext(work_path)[1]
        partial_path = work_path
        while partial_path not in ("/", ""):
            if os.path.isdir(partial_path):
                dir = partial_path
                break
            partial_path = os.path.split(partial_path)[0]

    # bail, can't parse
    if dir is None:
        raise NotWorkingPathError("%s is not a working path." % work_path)

    # TODO: more hard-coded values
    partial_path = dir.replace("/dfs1/net", "").replace("/prod/" + os.environ["TANK_PROJECT"].lower() + "/work", "")
    partial_path = re.sub(r"(.*?)([.][^/]*)(.*)", r"\1\3", partial_path)

    # iterate over the path, stripping the final directory off each time until we find a match
    container = None
    while partial_path != "/":
        try:
            container = tank.find(partial_path)
            break
        except:
            pass
        partial_path = os.path.split(partial_path)[0]

    if container is not None or ext is not None or resource_type is not None:
        # identify the revision type
        revision_type = _get_revision_type(container, ext, resource_type)
    else:
        revision_type = None

    return container, revision_type
예제 #14
0
    def filterAcceptsRow(self, sourceRow, sourceParent):
        index = self.sourceModel().index(sourceRow, 0, sourceParent)

        if not index.isValid():
            return False
        else:
            obj = index.data(Qt.UserRole).toPyObject()
            
            # workaround until get_latest_versions is implemented in the server api
            obj = tank.find(str(obj))
 
            return (self._filter == RevisionResultsProxyModel.FilterAll) or \
                   (self._filter == RevisionResultsProxyModel.FilterRecommended and obj.system.recommended) or \
                   (self._filter == RevisionResultsProxyModel.FilterLatest and obj in obj.container.latest_revisions.values())
예제 #15
0
def collectMovieData(address):
    movie_address  = address.replace('Frames(','Movie(')
    try:
        tank_movie = tank.find(movie_address)
    except:
        tank_movie = None
        core.warn( 'Could not find tank address: %s...' % address )
    
    # load data from the tank movie
    videoSource = ''
    if ( tank_movie ):
        videoSource = tank_movie.system.filesystem_location
        
    return videoSource
예제 #16
0
    def valid_container_types(self):
        """
        Returns a list of valid container types. If this node's revision type is not
        None, only containers whose valid_revision_type property contains the revision
        type are returned. The first entry is always None.

        :rtype: list of EntityType or None
        """
        valid_cts = [tank.find(ct) for ct in tank.list_container_types()]

        if self._revision_type is not None:
            # filter by valid revision type
            valid_cts = [ct for ct in valid_cts if self._revision_type in ct.properties.valid_revision_types or ct.properties.valid_revision_types is None]

        return [None] + sorted(valid_cts, key=lambda ct: ct.system.name)
예제 #17
0
 def sinfoFilepath( self ):
     if ( self._sinfoFilepath != None ):
         return self._sinfoFilepath
     
     # extract the sinfo address
     sinfo_address = self.tankAddress().replace('Frames','SInfoFile').replace('Movie','SInfoFile')
     if ( not sinfo_address ):
         self._sinfoFilepath = ''
         return self._sinfoFilepath
     
     try:
         self._sinfoFilepath = tank.find(sinfo_address).system.filesystem_location
     except:
         self._sinfoFilepath = ''
         
     return self._sinfoFilepath
예제 #18
0
    def add_dependency(self, path, subset=(), name=None, delegate=None):
        """
        Explicitly adds a dependency to the scene.
        :param path: The path to the dependency. Dependencies are resolved using
                     delegates in Node.__init__.
        :type path: string
        :param subset: subset of child revisions that will be added. this must be
                       a subset of new_dependency.data.children
        """
        try:
            revision = None
            container, revision_type = sandbox.get(path)
            ext = os.path.splitext(path)[1]
            frame_range = None
        except:
            revision = tank.find(path)
            container = revision.container
            revision_type = revision.system.type
            ext = os.path.splitext(revision.resource_path)[1]
            if revision.resource_type == tank.constants.ResourceType.SEQUENCE:
                frame_range = revision.frame_range
                path = os.path.join(revision.system.vfs_full_paths[0], os.path.split(revision.resource_path)[1])
            else:
                frame_range = None

        # find matching delegate
        if delegate is None:
            delegate = plugins.get_one_delegate(ext=ext, attrs=("add_dependency",))

        # consult the namer plugin
        if name is None:
            name = plugins.get_one_namer().get_node_name(self.container, container, revision_type, path)

        data = delegate.add_dependency(name, path, frame_range, self._data)
        dependency = Dependency(delegate, data, self)

#        # add any children first
#        for r in data.children:
#            if r in subset:
#                dependency.add_dependency(r.system.vfs_full_paths[0])

        self.dependencies.append(dependency)
        if hasattr(data, "update"):
            #children = [d.data for d in dependency.dependencies]
            dependency._pending_action = Action("update", func=data.update, kwargs={"reload": True})

        return dependency
예제 #19
0
def _get_label_types(container_type):
    """
    Returns the label types associated with a container type.

    :param container_type: The container type.
    :type limit: tank.local.EntityType
    :rtype: list of tank.local.EntityTypes (label types)
    """
    assert isinstance(container_type, tank.TankType), container_type
    assert container_type.properties.container_type == tank.constants.ContainerType.CONTAINER, container_type.properties.container_type

    # TODO: find the constants for "label" and "Entity Type"
    label_types = [tank.find(field.properties.validation["address"]) \
                       for field in container_type.fields.values() \
                           if field.properties.type == "label" and \
                              field.properties.validation["type"] == "Entity Type"]

    return sorted(label_types, key=lambda lt: lt.system.name)
예제 #20
0
    def sinfoFilepath(self):
        if (self._sinfoFilepath != None):
            return self._sinfoFilepath

        # extract the sinfo address
        sinfo_address = self.tankAddress().replace('Frames',
                                                   'SInfoFile').replace(
                                                       'Movie', 'SInfoFile')
        if (not sinfo_address):
            self._sinfoFilepath = ''
            return self._sinfoFilepath

        try:
            self._sinfoFilepath = tank.find(
                sinfo_address).system.filesystem_location
        except:
            self._sinfoFilepath = ''

        return self._sinfoFilepath
예제 #21
0
def get_node_name(parent_container, container, revision_type, path):
    # attempt to come up with a useful node name
    name = None

    # 1. if all of the new container's labels are contained in our container's labels,
    #    use the new container type's name (sans _vXX)
    # example: referencing a model in a texture should call the namespace "model"
    if parent_container is not None and container is not None \
            and all(l in container.labels.values() for l in parent_container.labels.values()):
        name = re.sub(r"_v[0-9]+", "", container.system.type_name)

        # 1a. if the container has a name, append that with an underscore, e.g. "model_arm"
        if tank.find(container.system.type_name).properties.use_name:
            name += "_" + container.system.name

    # 2. if the container has an Asset label that is not ANY, use that with 01 appended
    elif container.labels.has_key("Asset") and container.labels["Asset"].system.name != "ANY":
        name = container.labels["Asset"].system.name + "01"

    # 3. if the container has a name, use that with 01 appended
    elif container is not None and container.system.type.properties.use_name:
        name = container.system.name + "01"

    # 4. use the first label's value that doesn't start with a number, with 01 appended
    elif container is not None and len(container.labels.values()) > 0:
        for label in container.labels.values():
            if label.system.name[0].isalpha():
                name = label.system.name
                break
        if name is not None:
            name += "01"

    # 5. fall back on using the filename minus extensions
    if name is None:
        name = os.path.split(path)[1]
        while name.find('.') != -1:
            name = os.path.splitext(name)[0]

    # camelCaps, not CapitalCaps
    name = name[0].lower() + name[1:]

    return name
예제 #22
0
def collectAudioData(address):
    try:
        tank_audio  = tank.find(address)
    except:
        tank_audio = None
        core.warn( 'Could not find tank address: %s...' % address )
    
    audioSource = ''
    audioStart  = 0
    audioOffset = 0
    
    # load data from the tank audio
    if ( tank_audio ):
        pipeline_data       = tank_audio.properties.get('pipeline_data',{})
        
        audioSource         = tank_audio.system.filesystem_location
        audioStart          = pipeline_data.get('start_frame',-1)
        audioOffset         = pipeline_data.get('start_offset',0)
    
    return (audioSource,audioStart,audioOffset)
예제 #23
0
def _get_revision_type(container, ext, resource_type):
    # check for valid revision types
    if container is not None:
        # TODO: container.system.type_object returns a local API object
        valid_rts = container.system.type.properties.valid_revision_types

    if container is None or len(valid_rts) == 0:
        valid_rts = [tank.find(t) for t in tank.list_revision_types()]

    # check for matching extension
    if ext is not None:
        valid_rts = [rt for rt in valid_rts if rt.properties.has_key("extension_hint") and rt.properties.extension_hint is not None and ext.lstrip('.') in rt.properties.extension_hint.split(',')]

    # check for matching resource type
    if resource_type is not None:
        valid_rts = [rt for rt in valid_rts if rt.properties.restrict_resource_type in (resource_type, None)]

    # return the first match or None
    try:
        return valid_rts[0]
    except IndexError:
        return None
예제 #24
0
 def status(self):
     """
     Returns the status (StatusType)
     """
     if self._version is not None and self._revision_type is not None:
         if len(self._container.properties.recommended) > 0:
             # in the case that we have recommended versions
             if len(self._container.properties.recommended) > 0 and \
                     self._version == sorted([r.system.name for r in self._container.properties.recommended], reverse=True)[0]:
                 return "recommended+latest"
             else:
                 return "recommended+outofdate"
         else:
             # FIXME: not sure why it doesn't work if I omit the string conversion
             # FIXME: fails in tank 1.14, should be fixed in 1.15
             #if str(self._revision) in [str(r) for r in self._container.latest_revisions.values()]:
             if str(self._revision) in [str(r) for r in tank.find(str(self._container)).latest_revisions.values()]:
                 return "general+latest"
             else:
                 return "general+outofdate"
     else:
         return "unknown"
예제 #25
0
    def test_dependencies_match(self):
        assert len(self._scene.dependencies) == 2
        assert self._scene.dependencies[0].data.name == "ref1"
        assert self._scene.dependencies[1].data.name == "ref2"

        scene = self._scene
        ref1 = self._scene.dependencies[0]
        ref2 = self._scene.dependencies[1]

        scene.container = tank.find("animation(shot(sh_0000), sequence(seq_001), department(animation))")
        scene.revision_type = tank.find("xml")
        ref1.container = tank.find("animation(shot(sh_0001), sequence(seq_001), department(animation))")
        ref1.revision_type = tank.find("xml")
        ref2.container = tank.find("animation(shot(sh_0002), sequence(seq_001), department(animation))")
        ref2.revision_type = tank.find("xml")

        scene.publish(description="test")
def attach_haircaches(node):
    namespace = node.data.reference.namespace
    start_time = pm.playbackOptions(query=True, minTime=True)
    end_time = pm.playbackOptions(query=True, maxTime=True)
    node_labels = node.labels.values()
    scene_labels = node.scene.labels.values()
    container_type = tank.find(plugin_utils.get_latest_container('Anim_v'))

    # find hairsystems in the given namespace
    for hairsystem in pm.ls(namespace + ":*", type="hairSystem"):
        name = str(hairsystem.stripNamespace())

        # find container with node and scene labels named the same as the
        # hair system (same type as scene container)
        labels_set = set(node_labels + [label for label in scene_labels if label.system.type.system.name != 'Layer'])
        container = tank.find_ex(container_type, name=name, labels=labels_set)


        # find latest revision of type HairCache
        revision = container.latest_revisions["HairCache"]
        cache_filename = revision.system.vfs_full_paths[0]

        cache_name = "cache_" + namespace.replace(":", "_") + "_" + name

        if pm.objExists(cache_name):
            diskcache = pm.ls(cache_name)
        else:
            # create and set-up the node
            diskcache = pm.createNode("diskCache", name=cache_name)

        hairsystem_start_time = hairsystem.startFrame.get()

        # set the start/end time
        diskcache.startTime.set(hairsystem_start_time)
        diskcache.endTime.set(end_time)

        # set some sane defaults
        diskcache.enable.set(True)
        diskcache.samplingType.set(0)
        # TODO: may need to grab this from a revision attribute
        diskcache.samplingRate.set(1)
        diskcache.cacheType.set("mchp")
        diskcache.copyLocally.set(1)

        # set the filename
        if diskcache.cacheName.isLocked():
            diskcache.cacheName.unlock()
        diskcache.cacheName.set(cache_filename)
        # need to lock it to prevent it from being changed on save
        diskcache.cacheName.lock()

        # not sure what this is for, but the cache is ignored if it's not set
        # following the naming convention maya uses: hidden1_namespace_hairSystemName.mchp
        if diskcache.hiddenCacheName.isLocked():
            diskcache.hiddenCacheName.unlock()
        hidden_cache_name = "hidden1_" + namespace.replace(":", "_") + "_" + name + ".mchp"
        diskcache.hiddenCacheName.set(hidden_cache_name)

        # finally, connect the cache node to the hair system
        if not diskcache.diskCache.isConnected():
            diskcache.diskCache.connect(hairsystem.diskCache)
예제 #27
0
 def tankObject( self ):
     if ( self._tankAddress ):
         return tank.find(self._tankAddress.replace('Movie(','Frames(')).get_object()
     return None
예제 #28
0
 def tankObject(self):
     if (self._tankAddress):
         return tank.find(self._tankAddress.replace(
             'Movie(', 'Frames(')).get_object()
     return None
예제 #29
0
def determine_aux_data_from_vfs_path(path=None, tank_rev=None, project=None, include_shotgun_data=False):
    '''
    Given the tank vfs path, return
    ex: {"context_type":"shot", "scene":"19d","shot":"19d_010"}

    include shotgun data will query additional shotgun information
    '''
    TANK_VFS_ROOT = tank.util.config.virtual_tree.fuse_mount_point
    import FullContextSession

    if project==None:
        project = os.environ.get("DRD_JOB", "hf2")

    if not tank_rev:
        if path and path.startswith(TANK_VFS_ROOT):

            try:
                if os.path.isfile(path):
                    tank_rev = tank.find(path)
                elif re.search("\.([0-9]+)_([0-9]+)\.[a-zA-Z0-9]+$", path):
                    tank_rev = tank.find(path)
                else:
                    tank_rev = tank.find(os.path.split(path)[0])

            except:
                print "Warning: failed to find tank object from path %s" % path
                import traceback
                traceback.print_exc()

        elif re.search("/([0-9]+)/r([0-9]+)_", path):
            useless, rid = re.search("/([0-9]+)/r([0-9]+)_", path).groups()
            tank_rev = tank.server.Em().get_revision_by_id(int(rid))
            tank_rev = tank.find(str(tank_rev))

    if type(tank_rev)==tank.asset.tank_revision.TankRevision:
        tank_asset_rev = tank_rev
        tank_rev = tank_rev.get_object()

    # ensure the revision is from a tank render container

    if not tank_rev or not is_tank_render_container(project, tank_rev.get_asset()):
        return None

    # now we have the tank address, get the scene shot
    data_hash = determine_aux_data_from_tank_address_fast(str(tank_rev))

    if data_hash.has_key("scene") and data_hash["scene"] and data_hash["shot"]:
        data_hash.update( {
                        #"rev_name": tank_rev.get_name(),
                        "context_type":"shot",
                        'tank_asset_rev_obj':tank_asset_rev,
                        'tank_rev_obj':tank_rev,
                        'tank_rev_id':(tank_rev.get_asset().get_id(), tank_rev.get_id()),
                        })

        if include_shotgun_data and FullContextSession.get_project().get_scene(data_hash["scene"]):
            c_shot = FullContextSession.get_project().get_scene(data_hash["scene"]).get_shot(data_hash["shot"], no_exception=True)
            if c_shot:
                data_hash["cut_range"] = c_shot.get_cut_info()
                data_hash["cut_order"] = c_shot.get_cut_order(as_string=True)
                data_hash["cut_order_index"]    = c_shot.get_cut_order()

        return data_hash
    else:
        print "Warning: can not determine scene shot from address %s..." % tank_rev
예제 #30
0
def get_scene_shot_from_tank_address(address):

    asset = tank.find(address).asset

    return asset.labels["Scene"].system.name, asset.labels["SceneShot"].system.name
예제 #31
0
def get_scene_shot_from_tank_address(address):

    asset = tank.find(address).asset

    return asset.labels["Scene"].system.name, asset.labels[
        "SceneShot"].system.name
예제 #32
0
def determine_aux_data_from_tank_address(tank_rev, include_shotgun_data=False):
    import tank
    if type(tank_rev) in (str,unicode):
        tank_rev = tank.find(tank_rev)

    return  determine_aux_data_from_vfs_path(tank_rev = tank_rev, include_shotgun_data=include_shotgun_data )
예제 #33
0
def determine_aux_data_from_vfs_path(path=None,
                                     tank_rev=None,
                                     project=None,
                                     include_shotgun_data=False):
    '''
    Given the tank vfs path, return
    ex: {"context_type":"shot", "scene":"19d","shot":"19d_010"}

    include shotgun data will query additional shotgun information
    '''
    TANK_VFS_ROOT = tank.util.config.virtual_tree.fuse_mount_point
    import FullContextSession

    if project == None:
        project = os.environ.get("DRD_JOB", "hf2")

    if not tank_rev:
        if path and path.startswith(TANK_VFS_ROOT):

            try:
                if os.path.isfile(path):
                    tank_rev = tank.find(path)
                elif re.search("\.([0-9]+)_([0-9]+)\.[a-zA-Z0-9]+$", path):
                    tank_rev = tank.find(path)
                else:
                    tank_rev = tank.find(os.path.split(path)[0])

            except:
                print "Warning: failed to find tank object from path %s" % path
                import traceback
                traceback.print_exc()

        elif re.search("/([0-9]+)/r([0-9]+)_", path):
            useless, rid = re.search("/([0-9]+)/r([0-9]+)_", path).groups()
            tank_rev = tank.server.Em().get_revision_by_id(int(rid))
            tank_rev = tank.find(str(tank_rev))

    if type(tank_rev) == tank.asset.tank_revision.TankRevision:
        tank_asset_rev = tank_rev
        tank_rev = tank_rev.get_object()

    # ensure the revision is from a tank render container

    if not tank_rev or not is_tank_render_container(project,
                                                    tank_rev.get_asset()):
        return None

    # now we have the tank address, get the scene shot
    data_hash = determine_aux_data_from_tank_address_fast(str(tank_rev))

    if data_hash.has_key("scene") and data_hash["scene"] and data_hash["shot"]:
        data_hash.update({
            #"rev_name": tank_rev.get_name(),
            "context_type":
            "shot",
            'tank_asset_rev_obj':
            tank_asset_rev,
            'tank_rev_obj':
            tank_rev,
            'tank_rev_id': (tank_rev.get_asset().get_id(), tank_rev.get_id()),
        })

        if include_shotgun_data and FullContextSession.get_project().get_scene(
                data_hash["scene"]):
            c_shot = FullContextSession.get_project().get_scene(
                data_hash["scene"]).get_shot(data_hash["shot"],
                                             no_exception=True)
            if c_shot:
                data_hash["cut_range"] = c_shot.get_cut_info()
                data_hash["cut_order"] = c_shot.get_cut_order(as_string=True)
                data_hash["cut_order_index"] = c_shot.get_cut_order()

        return data_hash
    else:
        print "Warning: can not determine scene shot from address %s..." % tank_rev
예제 #34
0
 def __init__(self, parent=None, **kwargs):
     super(LabelCullProxyModel, self).__init__(parent, dynamicSortFilter=True, **kwargs)
     self._includeRevisionTypes = False
     self._validContainerTypes = frozenset(tank.find(ct) for ct in tank.list_container_types())
     self._validRevisionTypes = frozenset(tank.find(rt) for rt in tank.list_revision_types())
     self._selectionModel = None
예제 #35
0
 def fetchMore(self):
     if self.children is None:
         return sorted([RevisionTypeItem(tank.find(rt), self) for rt in tank.list_revision_types()])
예제 #36
0
 def fetchMore(self):
     if self.children is None:
         return sorted([ContainerTypeItem(tank.find(ct), self) for ct in tank.list_container_types()])
예제 #37
0
 def __init__(self):
     super(RootItem, self).__init__()
     self.children = [RevisionMetaItem(self), ContainerMetaItem(self)]
     self.children.extend(sorted([LabelTypeItem(tank.find(lt), self) for lt in tank.list_label_types()]))