Beispiel #1
0
 def test_interface(self):
     
     OCIO.ClearAllCaches()
     #self.assertEqual("1.0.8", OCIO.version)
     #self.assertEqual(16779264, OCIO.hexversion)
     self.assertEqual(OCIO.Constants.LOGGING_LEVEL_INFO, OCIO.GetLoggingLevel())
     OCIO.SetLoggingLevel(OCIO.Constants.LOGGING_LEVEL_NONE)
     self.assertEqual(OCIO.Constants.LOGGING_LEVEL_NONE, OCIO.GetLoggingLevel())
     foo = OCIO.GetCurrentConfig()
     self.assertEqual(self.FOO, foo.serialize())
     OCIO.SetLoggingLevel(OCIO.Constants.LOGGING_LEVEL_INFO)
     bar = OCIO.Config().CreateFromStream(foo.serialize())
     OCIO.SetCurrentConfig(bar)
     wee = OCIO.GetCurrentConfig()
Beispiel #2
0
    def __init__(self):
        QtGui.QWidget.__init__(self)
        QtGui.QGridLayout(self)
        self.setWindowTitle(WINDOW_NAME)
        self.setMinimumWidth(300)

        config = OCIO.GetCurrentConfig()

        self.__inputColorSpace = OCIO.Constants.ROLE_DEFAULT
        inputColorSpaces = [
            OCIO.Constants.ROLE_TEXTURE_PAINT, 'dt8',
            OCIO.Constants.ROLE_SCENE_LINEAR
        ]
        for cs in inputColorSpaces:
            if config.getColorSpace(cs) is None: continue
            self.__inputColorSpace = cs
            break

        self.__fStopOffset = 0.0
        self.__viewGamma = 1.0
        self.__swizzle = (True, True, True, True)

        self.__filter_cacheID = None
        self.__filter = None
        self.__texture3d_cacheID = None
        self.__counter_hack = 0

        self.__buildUI()
        self.__rebuildFilter()
Beispiel #3
0
    def _on_display_changed(self, action):
        with self._ocio_signals_blocked():

            config = ocio.GetCurrentConfig()
            display = action.text()

            # Re-populate views
            current_view = self.view()
            views = list(config.getViews(display))

            self.view_box.clear()
            self.view_box.addItems(views)

            if current_view in views:
                # Preserve current view if possible
                view_idx = views.index(current_view)
            else:
                # Fallback on default if not
                view_idx = self.view_box.findText(
                    config.getDefaultView(display))

            if view_idx != -1:
                self.view_box.setCurrentIndex(view_idx)

            self.image_plane.update_ocio_proc(display=display,
                                              view=self.view())
	def testAvailableColorSpaces( self ) :

		config = PyOpenColorIO.GetCurrentConfig()
		
		self.assertEqual(
			GafferImage.OpenColorIOTransform.availableColorSpaces(),
			[ cs.getName() for cs in config.getColorSpaces() ]
		)
Beispiel #5
0
    def __rebuildFilter(self):
        config = OCIO.GetCurrentConfig()
        display = config.getDefaultDisplay()
        view = config.getDefaultView(display)
        transform = CreateOCIODisplayTransform(config, self.__inputColorSpace,
                                               display, view, self.__swizzle,
                                               self.__fStopOffset,
                                               self.__viewGamma)

        processor = config.getProcessor(transform)

        shaderDesc = dict([('language', OCIO.Constants.GPU_LANGUAGE_GLSL_1_3),
                           ('functionName', 'display_ocio_$ID_'),
                           ('lut3DEdgeLen', LUT3D_SIZE)])

        filterCacheID = processor.getGpuShaderTextCacheID(shaderDesc)
        if filterCacheID != self.__filter_cacheID:
            self.__filter_cacheID = filterCacheID
            mari.app.log("OCIODisplay: Creating filter %s" %
                         self.__filter_cacheID)

            desc = "sampler3D lut3d_ocio_$ID_;\n"
            desc += processor.getGpuShaderText(shaderDesc)
            body = "{ Out = display_ocio_$ID_(Out, lut3d_ocio_$ID_); }"

            # Clear the existing color managment filter stack and create a new filter
            # HACK: Increment a counter by 1 each time to force a refresh
            #self.__counter_hack += 1
            #name = "OCIO %s %s %s v%d" % (display, view, self.__inputColorSpace, self.__counter_hack)
            name = "OCIO %s %s %s" % (display, view, self.__inputColorSpace)

            self.__filter = None
            self.__texture3d_cacheID = None

            mari.gl_render.clearPostFilterStack()
            self.__filter = mari.gl_render.createPostFilter(name, desc, body)
            mari.gl_render.appendPostFilter(self.__filter)
        else:
            mari.app.log('OCIODisplay: no shader text update required')

        texture3d_cacheID = processor.getGpuLut3DCacheID(shaderDesc)
        if texture3d_cacheID != self.__texture3d_cacheID:
            lut3d = processor.getGpuLut3D(shaderDesc)

            mari.app.log("OCIODisplay: Updating 3dlut %s" % texture3d_cacheID)

            if self.__texture3d_cacheID is None:
                self.__filter.setTexture3D("lut3d_ocio_$ID_", LUT3D_SIZE,
                                           LUT3D_SIZE, LUT3D_SIZE,
                                           self.__filter.FORMAT_RGB, lut3d)
            else:
                self.__filter.updateTexture3D("lut3d_ocio_$ID_", lut3d)

            self.__texture3d_cacheID = texture3d_cacheID
        else:
            mari.app.log("OCIODisplay: No lut3d update required")
Beispiel #6
0
def defaultColorSpace(fileName, fileFormat, dataType, metadata):

    config = PyOpenColorIO.GetCurrentConfig()

    linear = config.getColorSpace(
        PyOpenColorIO.Constants.ROLE_SCENE_LINEAR).getName()
    log = config.getColorSpace(
        PyOpenColorIO.Constants.ROLE_COMPOSITING_LOG).getName()
    display = config.getColorSpace(
        PyOpenColorIO.Constants.ROLE_COLOR_PICKING).getName()

    colorSpaces = {
        "bmp": display,
        "cineon": log,
        "dds": display,
        "dpx": {
            "uint8": display,
            "uint16": display,
            "uint10": log,
            "uint12": log,
        },
        "fits": {
            "uint8": display,
            "uint16": display,
            "uint32": linear,
            "float": linear,
            "double": linear,
        },
        "ico": display,
        "iff": display,
        "jpeg": display,
        "jpeg2000": display,
        "openexr": linear,
        "png": display,
        "pnm": display,
        "psd": display,
        "raw": linear,
        "rla": display,
        "sgi": display,
        "softimage": display,
        "targa": display,
        "tiff": {
            "uint8": display,
            "uint16": display,
            "uint32": linear,
            "float": linear,
        },
        "zfile": linear,
    }

    s = colorSpaces[fileFormat]
    if isinstance(s, str):
        return s
    else:
        return s[dataType]
Beispiel #7
0
def register_viewers(also_remove="default"):
    """Registers the a viewer process for each display device/view, and
    sets the default viewer process.

    ``also_remove`` can be set to either:
    
    - "default" to remove the default sRGB/rec709 viewer processes
    - "all" to remove all processes
    - "none" to leave existing viewer processes untouched
    """

    if also_remove not in ("default", "none", "all"):
        raise ValueError(
            "also_remove should be set to 'default', 'none' or 'all'")

    if also_remove == "default":
        nuke.ViewerProcess.unregister('rec709')
        nuke.ViewerProcess.unregister('sRGB')
        nuke.ViewerProcess.unregister('None')
    elif also_remove == "all":
        # Unregister all processes, including None, which should be defined in config.ocio
        for curname in nuke.ViewerProcess.registeredNames():
            nuke.ViewerProcess.unregister(curname)

    # Formats the display and transform, e.g "Film1D (sRGB)"
    DISPLAY_UI_FORMAT = "%(view)s (%(display)s)"

    import PyOpenColorIO as OCIO
    config = OCIO.GetCurrentConfig()

    # For every display, loop over every view
    for display in config.getDisplays():
        for view in config.getViews(display):
            # Register the node
            nuke.ViewerProcess.register(name=DISPLAY_UI_FORMAT % {
                'view': view,
                "display": display
            },
                                        call=nuke.nodes.OCIODisplay,
                                        args=(),
                                        kwargs={
                                            "display": display,
                                            "view": view,
                                            "layer": "all"
                                        })

    # Get the default display and view, set it as the default used on Nuke startup
    defaultDisplay = config.getDefaultDisplay()
    defaultView = config.getDefaultView(defaultDisplay)

    nuke.knobDefault(
        "Viewer.viewerProcess", DISPLAY_UI_FORMAT % {
            'view': defaultView,
            "display": defaultDisplay
        })
def convertImage(filename = '',fileOutName = '',format='tif'):
    # open the file
    inputFile = oiio.ImageInput.open(filename)
    # check if the input file is valid
    if not inputFile:
        print 'Could not open: "' + filename + '"'
        print '\tError: "', oiio.geterror()
        return
    # get the spec of the input file
    spec = inputFile.spec()
    nchans = spec.nchannels
    # read the image and return the pixels as array type
    pixels = inputFile.read_image(oiio.FLOAT)
    # check that the pixels are ok
    if not pixels:
        print 'Could not read:', inputFile.geterror()
        return
    inputFile.close() #we're done with the file at this point
    # open the OCIO config
    config = OCIO.GetCurrentConfig()
    #"""
    transform = OCIO.ColorSpaceTransform()
    transform.setSrc('srgb8')
    transform.setDst('acescg')
    #transform.setDirection(OCIO.Constants.TRANSFORM_DIR_INVERSE)
    processor = config.getProcessor(transform)
    #"""
    """
    # get the processor to transform from srgb8 to acescg space
    processor = config.getProcessor('srgb8','acescg')
    #processor = config.getProcessor('linear','srgb8')

    """
    # apply the transform
    buf = processor.applyRGBA(pixels)
    # convert the list to an array type
    imgTrans = array('f',[0,0,0,0])
    imgTrans.fromlist(buf)
    # create an output image
    output = oiio.ImageOutput.create(fileOutName)
    # if tif format output as 16bit otherwise 8bit
    # if format != 'tif':
    #     spec.set_format(oiio.UINT8)
    # else:
    #     spec.set_format(oiio.UINT16)
    spec.set_format(oiio.HALF)
    # open and write the data transformed
    output.open(fileOutName,spec,oiio.Create)
    output.write_image(imgTrans)
    output.close()
    print 'done'
def _simplify_transform(
    transform,
    optimization=ocio.OPTIMIZATION_VERY_GOOD,
    direction=ocio.TRANSFORM_DIR_FORWARD,
    config=None,
    context=None,
):
    config = config or ocio.GetCurrentConfig()
    context = context or config.getCurrentContext()
    proc = config.getProcessor(
        transform=transform, context=context, direction=direction
    )
    gt = proc.getOptimizedProcessor(optimization).createGroupTransform()
    return gt[0] if len(gt) < 2 else gt
Beispiel #10
0
def __ocioConfig( plug ) :

	try :
		context = plug.ancestor( Gaffer.ScriptNode ).context()
		with context :
			if plug.node()["__shader"]["name"].getValue() != "color_manager_ocio" :
				return None
			config = plug.node()["parameters"]["config"].getValue()
		if not config :
			return PyOpenColorIO.GetCurrentConfig()
		else :
			return PyOpenColorIO.Config.CreateFromFile( context.substitute( config ) )
	except :
		return None
Beispiel #11
0
    def ocioConfig(self):
        """
        Return an OCIO config instance.
        """
        import PyOpenColorIO as ocio

        # open color io configuration
        if self.option('ocioConfig'):
            config = ocio.Config.CreateFromFile(self.option('ocioConfig'))

        # otherwise loading configuration from $OCIO environment variable
        elif 'OCIO' in os.environ:
            config = ocio.GetCurrentConfig()
        else:
            raise OcioConfigurationError(
                'Could not find an OCIO configuration to be loaded.')

        return config
Beispiel #12
0
    def __buildUI(self):
        config = OCIO.GetCurrentConfig()

        self.layout().addWidget(QtGui.QLabel("Input Color Space", self), 0, 0)
        csWidget = QtGui.QComboBox(self)
        self.layout().addWidget(csWidget, 0, 1)
        csIndex = None
        for name in (cs.getName() for cs in config.getColorSpaces()):
            csWidget.addItem(name)
            if name == self.__inputColorSpace:
                csIndex = csWidget.count - 1
        if csIndex is not None:
            csWidget.setCurrentIndex(csIndex)
        csWidget.connect(QtCore.SIGNAL('currentIndexChanged(const QString &)'),
                         self.__csChanged)

        # This doesnt work until the Horizontal enum is exposed.
        """
Beispiel #13
0
def ocio_populate_viewer(remove_nuke_default=True):
    """Registers the a viewer process for each display/transform, and
    sets the default

    Also unregisters the default Nuke viewer processes (sRGB/rec709)
    unless remove_nuke_default is False
    """

    # TODO: How to we unregister all? This assumes no other luts
    # have been registered by other viewer processes
    if remove_nuke_default:
        nuke.ViewerProcess.unregister('rec709')
        nuke.ViewerProcess.unregister('sRGB')

    # Formats the display and transform, e.g "Film1D (sRGB)"
    DISPLAY_UI_FORMAT = "%(view)s (%(display)s)"

    import PyOpenColorIO as OCIO
    config = OCIO.GetCurrentConfig()

    # For every display, loop over every view
    for display in config.getDisplays():
        for view in config.getViews(display):
            nuke.ViewerProcess.register(name=DISPLAY_UI_FORMAT % {
                'view': view,
                "display": display
            },
                                        call=nuke.nodes.OCIODisplay,
                                        args=(),
                                        kwargs={
                                            "display": display,
                                            "view": view
                                        })

    # Get the default display and view, register it as the
    # default used on Nuke startup
    defaultDisplay = config.getDefaultDisplay()
    defaultView = config.getDefaultView(defaultDisplay)

    nuke.knobDefault(
        "Viewer.viewerProcess", DISPLAY_UI_FORMAT % {
            'view': defaultView,
            "display": defaultDisplay
        })
Beispiel #14
0
def __colorSpacePresetValues(plug):

    config = PyOpenColorIO.GetCurrentConfig()

    return IECore.StringVectorData(
        [""] + [cs.getName() for cs in config.getColorSpaces()])
Beispiel #15
0
def findColorSpacesNames():
    config = ocio.GetCurrentConfig()
    colorSpaces = [cs.getName() for cs in config.getColorSpaces()]
    return colorSpaces
Beispiel #16
0
def convertImage(filename=__FILEIN__, fileOutName=__FILEOUT__, format='tif'):
    # open the file
    inputFile = oiio.ImageInput.open(filename)
    # check if the input file is valid
    if not inputFile:
        print 'Could not open: "' + filename + '"'
        print '\tError: "', oiio.geterror()
        return
    # get the spec of the input file
    spec = inputFile.spec()
    nchans = spec.nchannels
    # read the image and return the pixels as array type
    pixels = inputFile.read_image(oiio.FLOAT)
    # check that the pixels are ok
    if not pixels:
        print 'Could not read:', inputFile.geterror()
        return
    inputFile.close()  #we're done with the file at this point
    # open the OCIO config
    config = OCIO.GetCurrentConfig()
    # get the processor to transform from linear to Asterix2_Film space

    newConfig = OCIO.Config()
    colorspace = OCIO.ColorSpace(name='rawInput')
    group = OCIO.GroupTransform()
    main_lut = OCIO.FileTransform(
        '/s/prodanim/asterix2/_sandbox/duda/tmp/ocioLut/test.csp',
        interpolation=OCIO.Constants.INTERP_LINEAR,
        direction=OCIO.Constants.TRANSFORM_DIR_FORWARD)
    group.push_back(main_lut)
    colorspace.setTransform(group, OCIO.Constants.COLORSPACE_DIR_TO_REFERENCE)
    newConfig.addColorSpace(colorspace)

    colorspace = OCIO.ColorSpace(name='srgb8')
    group = OCIO.GroupTransform()
    main_lut = OCIO.FileTransform(
        '/s/prodanim/asterix2/_sandbox/duda/tmp/ocioLut/linTosrgbA2.csp',
        interpolation=OCIO.Constants.INTERP_LINEAR,
        direction=OCIO.Constants.TRANSFORM_DIR_FORWARD)
    group.push_back(main_lut)
    colorspace.setTransform(group, OCIO.Constants.COLORSPACE_DIR_TO_REFERENCE)
    newConfig.addColorSpace(colorspace)
    colorspace = OCIO.ColorSpace(name='processedOutput')
    newConfig.addColorSpace(colorspace)
    newProccessor = newConfig.getProcessor(
        'rawInput',
        'srgb8',
    )
    # apply the transform
    buf = newProccessor.applyRGBA(pixels)

    #processor = config.getProcessor('Asterix2_Film','srgb8')
    #buf = processor.applyRGBA(pixels)
    # convert the list to an array type
    imgTrans = array('f', [0, 0, 0, 0])
    imgTrans.fromlist(buf)
    # create an output image
    output = oiio.ImageOutput.create(__FILEOUT__)
    # if tif format output as 16bit otherwise 8bit
    if format != 'tif':
        spec.set_format(oiio.UINT8)
    else:
        spec.set_format(oiio.UINT16)
    # open and write the data transformed
    output.open(__FILEOUT__, spec, oiio.Create)
    output.write_image(imgTrans)
    output.close()
Beispiel #17
0
def __viewPresetValues( plug ) :

	config = PyOpenColorIO.GetCurrentConfig()
	display = plug.parent()["display"].getValue()

	return IECore.StringVectorData( [ "" ] + config.getViews( display ) )
Beispiel #18
0
def __displayPresetValues( plug ) :

	config = PyOpenColorIO.GetCurrentConfig()

	return IECore.StringVectorData( [ "" ] + config.getDisplays() )
Beispiel #19
0
 def get_cfg(self):
     return OCIO.GetCurrentConfig()
Beispiel #20
0
    def update_ocio_proc(self,
                         input_cs=None,
                         display=None,
                         view=None,
                         channel=None):
        """
        Update one or more aspects of the OCIO GPU renderer. Parameters
        are cached so not providing a parameter maintains the existing
        state. This will trigger a GL update IF the underlying OCIO ops
        in the processor have changed.

        :param str input_cs: Override the input color space name (how
            the image texture should be interpreted by OCIO). If this
            is wrong, the rendered results will look wrong in most
            cases.
        :param str display: OCIO display representing the current
            display device colors are being viewed on.
        :param str view: OCIO view defining the output transform for
            the given display.
        :param int channel: ImagePlaneChannels value to toggle channel
            isolation.
        """
        if input_cs:
            self._ocio_input_cs = input_cs
        if display:
            self._ocio_display = display
        if view:
            self._ocio_view = view
        if channel is not None:
            self._update_ocio_channel_hot(channel)

        # Can a processor be made?
        if not all((self._ocio_input_cs, self._ocio_display, self._ocio_view)):
            return

        config = ocio.GetCurrentConfig()

        # Build transforms needed for viewing pipeline
        exposure_tr = ocio.ExposureContrastTransform(
            exposure=self._ocio_exposure, dynamicExposure=True)
        channel_view_tr = ocio.MatrixTransform.View(
            channelHot=self._ocio_channel_hot,
            lumaCoef=config.getDefaultLumaCoefs())
        display_view_tr = ocio.DisplayViewTransform(src=self._ocio_input_cs,
                                                    display=self._ocio_display,
                                                    view=self._ocio_view)
        gamma_tr = ocio.ExposureContrastTransform(gamma=self._ocio_gamma,
                                                  pivot=1.0,
                                                  dynamicGamma=True)

        # Mimic OCIO v1 DisplayTransform for consistency with DCCs
        viewing_pipeline = ocio.LegacyViewingPipeline()
        viewing_pipeline.setLinearCC(exposure_tr)
        viewing_pipeline.setChannelView(channel_view_tr)
        viewing_pipeline.setDisplayViewTransform(display_view_tr)
        viewing_pipeline.setDisplayCC(gamma_tr)

        # Create processor
        proc = viewing_pipeline.getProcessor(config)

        if proc.getCacheID() != self._ocio_proc_cache_id:
            self._ocio_shader_desc = ocio.GpuShaderDesc.CreateShaderDesc(
                language=ocio.GPU_LANGUAGE_GLSL_4_0)
            self._ocio_proc_cache_id = proc.getCacheID()
            ocio_gpu_proc = proc.getDefaultGPUProcessor()
            ocio_gpu_proc.extractGpuShaderInfo(self._ocio_shader_desc)

            self._allocate_ocio_tex()
            self._build_program()

            # Set initial dynamic property state
            self._update_ocio_dyn_prop(ocio.DYNAMIC_PROPERTY_EXPOSURE,
                                       self._ocio_exposure)
            self._update_ocio_dyn_prop(ocio.DYNAMIC_PROPERTY_GAMMA,
                                       self._ocio_gamma)

            self.update()
Beispiel #21
0
    def load_image(self, image_path):
        """
        Load an image into the image plane texture.

        :param str image_path: Image file path
        :return: Input color space name
        :rtype: str
        """
        config = ocio.GetCurrentConfig()

        # Get input color space (file rule)
        cs_name, rule_idx = config.getColorSpaceFromFilepath(image_path)
        if not cs_name:
            # Use previous or config default
            if self._ocio_input_cs:
                cs_name = self._ocio_input_cs
            else:
                cs_name = ocio.ROLE_DEFAULT
        self._ocio_input_cs = cs_name

        # Get default view for input color space (viewing rule)
        self._ocio_view = config.getDefaultView(self._ocio_display,
                                                self._ocio_input_cs)

        buf = oiio.ImageBuf(image_path)
        spec = buf.spec()

        # Convert to RGBA, filling missing color channels with 0.0, and a
        # missing alpha with 1.0.
        if spec.nchannels < 4:
            buf = oiio.ImageBufAlgo.channels(
                buf,
                tuple(
                    list(range(spec.nchannels)) +
                    ([0.0] * (4 - spec.nchannels - 1)) + [1.0]),
                newchannelnames=("R", "G", "B", "A"))
        elif spec.nchannels > 4:
            buf = oiio.ImageBufAlgo.channels(buf, (0, 1, 2, 3),
                                             newchannelnames=("R", "G", "B",
                                                              "A"))

        # Get pixels as 32-bit float NumPy array
        data = buf.get_pixels(oiio.FLOAT)

        # Stash image size for pan/zoom calculations
        self._image_pos.x = spec.x
        self._image_pos.y = spec.y
        self._image_size.x = spec.width
        self._image_size.y = spec.height

        # Load image data into texture
        self.makeCurrent()

        GL.glBindTexture(GL.GL_TEXTURE_2D, self._image_tex)
        GL.glTexImage2D(GL.GL_TEXTURE_2D, 0, GL.GL_RGBA32F, spec.width,
                        spec.height, 0, GL.GL_RGBA, GL.GL_FLOAT, data.ravel())

        self._update_model_view_mat(update=False)

        self.update_ocio_proc(input_cs=self._ocio_input_cs,
                              view=self._ocio_view)
Beispiel #22
0
writeModeLabelsAndValues = [("Scanline", 0), ("Tile", 1)]

GafferUI.PlugValueWidget.registerCreator(
    GafferImage.ImageWriter,
    "writeMode",
    GafferUI.EnumPlugValueWidget,
    labelsAndValues=writeModeLabelsAndValues)

# Constant
GafferUI.PlugValueWidget.registerCreator(GafferImage.Constant, "format",
                                         GafferImageUI.FormatPlugValueWidget)

# OpenColorIO
ocioColorSpaceLabelsAndValues = [("None", "")]
import PyOpenColorIO as OCIO
config = OCIO.GetCurrentConfig()
for cs in config.getColorSpaces():
    ocioColorSpaceLabelsAndValues.append((cs.getName(), cs.getName()))

GafferUI.PlugValueWidget.registerCreator(
    GafferImage.OpenColorIO,
    "inputSpace",
    GafferUI.EnumPlugValueWidget,
    labelsAndValues=ocioColorSpaceLabelsAndValues)

GafferUI.PlugValueWidget.registerCreator(
    GafferImage.OpenColorIO,
    "outputSpace",
    GafferUI.EnumPlugValueWidget,
    labelsAndValues=ocioColorSpaceLabelsAndValues)
def _add_default_colorspaces_and_roles(config=None, scene_linear="ACEScg"):
    # create default colorspaces

    linear_allocation_vars = [-8, 5, 0.00390625]
    # data / no-color
    raw = ocio.ColorSpace(name="raw", isData=True, equalityGroup="nc", encoding="data")

    # Scene and display reference
    aces = ocio.ColorSpace(
        name="ACES2065-1",
        equalityGroup="ap0",
        encoding="scene-linear",
        allocation=ocio.ALLOCATION_LG2,
        allocationVars=linear_allocation_vars,
    )

    xyzd65 = ocio.ColorSpace(
        name="CIE-XYZ (D65)",
        equalityGroup="xyz",
        encoding="display-linear",
        referenceSpace=ocio.REFERENCE_SPACE_DISPLAY,
        allocation=ocio.ALLOCATION_LG2,
        allocationVars=linear_allocation_vars,
    )

    # Other linear reference spaces
    acescg = ocio.ColorSpace(
        name="ACEScg",
        equalityGroup="ap1",
        toReference=ocio.BuiltinTransform("ACEScg_to_ACES2065-1"),
        encoding="scene-linear",
        allocation=ocio.ALLOCATION_LG2,
        allocationVars=linear_allocation_vars,
    )

    lin709 = ocio.ColorSpace(
        name="Linear-Rec709",
        encoding="scene-linear",
        toReference=ocio.GroupTransform(
            [
                ocio.BuiltinTransform(
                    "ACES-AP1_to_LINEAR-REC709_BFD",
                    direction=ocio.TRANSFORM_DIR_INVERSE,
                ),
                ocio.BuiltinTransform("ACEScg_to_ACES2065-1"),
            ]
        ),
        allocation=ocio.ALLOCATION_LG2,
        allocationVars=linear_allocation_vars,
    )

    cfg = config or ocio.GetCurrentConfig()

    # add default colorspaces to config and update roles
    _ = [cfg.addColorSpace(cs) for cs in [raw, aces, xyzd65, acescg, lin709]]

    scene_linear = {acescg.getName(): acescg, lin709.getName(): lin709}[scene_linear]

    cfg.setRole("aces_interchange", aces.getName())
    cfg.setRole("cie_xyz_d65_interchange", xyzd65.getName())
    cfg.setRole(ocio.ROLE_DATA, raw.getName())
    cfg.setRole(ocio.ROLE_DEFAULT, scene_linear.getName())
    cfg.setRole(ocio.ROLE_REFERENCE, aces.getName())
    cfg.setRole(ocio.ROLE_SCENE_LINEAR, scene_linear.getName())

    # add default colorimetry view transform to config
    cfg.addViewTransform(
        ocio.ViewTransform(
            name="colorimetry",
            referenceSpace=ocio.REFERENCE_SPACE_SCENE,
            fromReference=ocio.BuiltinTransform("ACES-AP0_to_CIE-XYZ-D65_BFD"),
        )
    )
    return cfg
Beispiel #24
0
    def _init_ocio(self):
        """
        Runs exactly once to initialize all OCIO parameters and
        initiate creation of the initial OCIO processor.
        """
        # TODO: implement ColorSpaceMenuHelper

        with self._ocio_signals_blocked():

            # Assumes OCIO env var is set
            config = ocio.GetCurrentConfig()

            # Populate input color spaces
            all_cs_names = [cs.getName() for cs in config.getColorSpaces()]
            all_cs_names.sort()

            for action in self.input_cs_action_group.actions():
                self.input_cs_action_group.removeAction(action)
            self.input_cs_menu.clear()

            for i, cs_name in enumerate(all_cs_names):
                action = self.input_cs_menu.addAction(cs_name)
                action.setCheckable(True)
                if i == 0:
                    action.setChecked(True)
                self.input_cs_action_group.addAction(action)

            cs_actions = self.input_cs_action_group.actions()
            default_cs = config.getColorSpace(ocio.ROLE_DEFAULT)
            if default_cs:
                default_cs_name = default_cs.getName()
                if default_cs_name in all_cs_names:
                    cs_idx = all_cs_names.index(default_cs_name)
                    cs_actions[cs_idx].setChecked(True)

            # Populate displays
            for action in self.display_action_group.actions():
                self.display_action_group.removeAction(action)
            self.display_menu.clear()

            displays = list(config.getDisplays())

            for i, display in enumerate(displays):
                action = self.display_menu.addAction(display)
                action.setCheckable(True)
                if i == 0:
                    action.setChecked(True)
                self.display_action_group.addAction(action)

            default_display = config.getDefaultDisplay()

            # Populate views. They will be re-populated whenever the display
            # changes.
            self.view_box.clear()
            self.view_box.addItems(config.getViews(default_display))

            default_view = config.getDefaultView(default_display)

            # Set default display/view
            self.set_display_view(default_display, default_view)

            # Build OCIO processors
            self.image_plane.update_ocio_proc(
                input_cs=self.input_color_space(),
                display=self.display(),
                view=self.view())
Beispiel #25
0
def RegisterOCIODisplay():
    if not hasattr(mari.gl_render, "createPostFilter"):
        print "Error: This version of Mari does not support the mari.gl_render.createPostFilter API"
        return

    # OpenColorIO SETUP
    # Use OpenColorIO to generate the shader text and the 3dlut
    starttime = time.time()

    config = OCIO.GetCurrentConfig()
    display = config.getDefaultDisplay()
    view = config.getDefaultView(display)
    transform = CreateOCIODisplayTransform(config, INPUT_IMAGE_COLORSPACE,
                                           display, view, SWIZZLE,
                                           FSTOP_OFFSET, VIEW_GAMMA)

    processor = config.getProcessor(transform)

    shaderDesc = dict([('language', OCIO.Constants.GPU_LANGUAGE_GLSL_1_3),
                       ('functionName', 'display_ocio_$ID_'),
                       ('lut3DEdgeLen', LUT3D_SIZE)])
    shaderText = processor.getGpuShaderText(shaderDesc)
    print "OCIO Setup: %0.1f ms" % (1000 * (time.time() - starttime))

    starttime = time.time()
    lut3d = processor.getGpuLut3D(shaderDesc)
    print "OCIO 3D Lut creation: %0.1f ms" % (1000 * (time.time() - starttime))

    starttime = time.time()
    # Clear the existing color managment filter stack
    mari.gl_render.clearPostFilterStack()

    # Create variable pre-declarations
    desc = "sampler3D lut3d_ocio_$ID_;\n"
    desc += shaderText

    # Set the body of the filter
    body = "{ Out = display_ocio_$ID_(Out, lut3d_ocio_$ID_); }"

    # HACK: Increment a counter by 1 each time to force a refresh
    if not hasattr(mari, "ocio_counter_hack"):
        mari.ocio_counter_hack = 0
    else:
        mari.ocio_counter_hack += 1
    ocio_counter_hack = mari.ocio_counter_hack

    # Create a new filter
    name = "OCIO %s %s %s v%d" % (display, view, INPUT_IMAGE_COLORSPACE,
                                  ocio_counter_hack)
    postfilter = mari.gl_render.createPostFilter(name, desc, body)

    print "Mari Setup: %0.1f ms" % (1000 * (time.time() - starttime))

    starttime = time.time()
    # Set the texture to use for the given sampler on this filter
    postfilter.setTexture3D("lut3d_ocio_$ID_", LUT3D_SIZE, LUT3D_SIZE,
                            LUT3D_SIZE, postfilter.FORMAT_RGB, lut3d)
    print "Mari Texture Upload: %0.1f ms" % (1000 * (time.time() - starttime))

    # Append the filter to the end of the current list of filters
    mari.gl_render.appendPostFilter(postfilter)