Ejemplo n.º 1
0
def convertImageToTexture(image):
    size = coin.SbVec2s(image.width(), image.height())
    buffersize = image.byteCount()

    soImage = coin.SoSFImage()
    width = size[0]
    height = size[1]
    imageBytes = b''

    for y in range(height - 1, -1, -1):
        for x in range(width):
            rgb = image.pixel(x, y)
            color = qtutils.QColor()
            color.setRgba(rgb)
            alpha = color.alpha()
            value = 0

            if alpha < 255:
                value = 254 - alpha
            else:
                value = color.lightness()

            if IS_PY_3:
                imageBytes = imageBytes + chr(value).encode('latin-1')
            else:
                imageBytes = imageBytes + chr(value)

    soImage.setValue(size, 1, imageBytes)

    return soImage
Ejemplo n.º 2
0
    def coinSetUp(self):
        #print "coinSetUp"
        self.TexW = 10
        self.TexH = 100

        self.sg = FreeCADGui.ActiveDocument.ActiveView.getSceneGraph()
        #print str( FreeCADGui.ActiveDocument.Document.Label )
        #print str( self.sg )

        self.stripes = coin.SoTexture2()
        self.sg.insertChild(self.stripes, 0)
        self.stripes.filename = ""

        self.string = '\xff' * 50 + '\x00' * self.StripeWidth
        self.chars = self.string * self.TexW * self.TexH

        self.img = coin.SoSFImage()
        self.img.setValue(
            coin.SbVec2s(len(self.string) * self.TexW, self.TexH), 1,
            self.chars)

        self.stripes.image = self.img

        # **** here we can transform the texture
        self.transTexture = coin.SoTexture2Transform()
        self.sg.insertChild(self.transTexture, 1)
        #transTexture.translation.setValue(1, 1)
        self.transTexture.scaleFactor.setValue(self.Scale, self.Scale)
        self.transTexture.rotation.setValue(1. * self.Rotation / 100)
        #transTexture.center.setValue(0, .5)

        self.tc = coin.SoTextureCoordinateEnvironment()
        self.sg.insertChild(self.tc, 2)
    def _reinitTexture(self, obj):
        if _pixelContainer.get(obj.Name):
            del _pixelContainer[obj.Name]
        _pixelContainer[obj.Name] = FPPixelContainer.PixelContainer(
            obj.ResolutionX, obj.ResolutionY)
        _pixelContainer[obj.Name].clear(Proto.Color(r=0, g=0, b=0, a=255))
        pixelStr = _pixelContainer[obj.Name].toString()
        resolution = coin.SbVec2s(obj.ResolutionX, obj.ResolutionY)

        for child in obj.Group:
            rootNode = child.ViewObject.RootNode

            # find texture node
            tex = _findNodeIn(coin.SoTexture2.getClassTypeId(), rootNode)
            if not tex:
                #FreeCAD.Console.PrintMessage("inserting new texture\n")
                tex = coin.SoTexture2()
                rootNode.insertChild(tex, 1)
            tex.model = coin.SoTexture2.REPLACE
            # create the image for the texture
            image = coin.SoSFImage()
            #FreeCAD.Console.PrintMessage("Initial Texture begin:\n" + self._getTextureString(obj) + "\nTexture End")
            image.setValue(
                resolution,
                FPPixelContainer.PixelContainer.NUM_COLOR_COMPONENTS, pixelStr)
            tex.image = image

            # find complexity node
            complexity = _findNodeIn(coin.SoComplexity.getClassTypeId(),
                                     rootNode)
            if not complexity:
                #FreeCAD.Console.PrintMessage("inserting new complexity\n")
                complexity = coin.SoComplexity()
                rootNode.insertChild(complexity, 1)
            complexity.textureQuality = 0.00001
Ejemplo n.º 4
0
def load_texture(filename, size=None, gui=App.GuiUp):
    """Return a Coin.SoSFImage to use as a texture for a 2D plane.

    This function only works if the graphical interface is available
    as the visual properties that can be applied to a shape
    are attributes of the view provider (`obj.ViewObject`).

    Parameters
    ----------
    filename: str
        A path to a pixel image file (PNG) that can be used as a texture
        on the face of an object.

    size: tuple of two int, or a single int, optional
        It defaults to `None`.
        If a tuple is given, the two values define the width and height
        in pixels to which the loaded image will be scaled.
        If it is a single value, it is used for both dimensions.

        If it is `None`, the size will be determined from the `QImage`
        created from `filename`.

        CURRENTLY the input `size` parameter IS NOT USED.
        It always uses the `QImage` to determine this information.

    gui: bool, optional
        It defaults to the value of `App.GuiUp`, which is `True`
        when the interface exists, and `False` otherwise.

        This value can be set to `False` to simulate
        when the interface is not available.

    Returns
    -------
    coin.SoSFImage
        An image object with the appropriate size, number of components
        (grayscale, grayscale and transparency, color,
        color and transparency), and byte data.

        It returns `None` if the interface is not available,
        or if there is a problem creating the image.
    """
    if gui:
        # from pivy import coin
        # from PySide import QtGui, QtSvg
        try:
            p = QtGui.QImage(filename)

            if p.isNull():
                _wrn("load_texture: " + _tr("image is Null"))

                if not os.path.exists(filename):
                    raise FileNotFoundError(-1,
                                            _tr("filename does not exist "
                                                "on the system or "
                                                "on the resource file"),
                                            filename)

            # This is buggy so it was de-activated.
            #
            # TODO: allow SVGs to use resolutions
            # if size and (".svg" in filename.lower()):
            #    # this is a pattern, not a texture
            #    if isinstance(size, int):
            #        size = (size, size)
            #    svgr = QtSvg.QSvgRenderer(filename)
            #    p = QtGui.QImage(size[0], size[1],
            #                     QtGui.QImage.Format_ARGB32)
            #    pa = QtGui.QPainter()
            #    pa.begin(p)
            #    svgr.render(pa)
            #    pa.end()
            # else:
            #    p = QtGui.QImage(filename)
            size = coin.SbVec2s(p.width(), p.height())
            buffersize = p.byteCount()
            width = size[0]
            height = size[1]
            numcomponents = int(float(buffersize) / (width * height))

            img = coin.SoSFImage()
            byteList = []
            # isPy2 = sys.version_info.major < 3
            isPy2 = six.PY2

            # The SoSFImage needs to be filled with bytes.
            # The pixel information is converted into a Qt color, gray,
            # red, green, blue, or transparency (alpha),
            # depending on the input image.
            #
            # If Python 2 is used, the color is turned into a character,
            # which is of type 'byte', and added to the byte list.
            # If Python 3 is used, characters are unicode strings,
            # so they need to be encoded into 'latin-1'
            # to produce the correct bytes for the list.
            for y in range(height):
                # line = width*numcomponents*(height-(y));
                for x in range(width):
                    rgb = p.pixel(x, y)
                    if numcomponents == 1 or numcomponents == 2:
                        gray = chr(QtGui.qGray(rgb))
                        if isPy2:
                            byteList.append(gray)
                        else:
                            byteList.append(gray.encode('latin-1'))

                        if numcomponents == 2:
                            alpha = chr(QtGui.qAlpha(rgb))
                            if isPy2:
                                byteList.append(alpha)
                            else:
                                byteList.append(alpha.encode('latin-1'))
                    elif numcomponents == 3 or numcomponents == 4:
                        red = chr(QtGui.qRed(rgb))
                        green = chr(QtGui.qGreen(rgb))
                        blue = chr(QtGui.qBlue(rgb))

                        if isPy2:
                            byteList.append(red)
                            byteList.append(green)
                            byteList.append(blue)
                        else:
                            byteList.append(red.encode('latin-1'))
                            byteList.append(green.encode('latin-1'))
                            byteList.append(blue.encode('latin-1'))

                        if numcomponents == 4:
                            alpha = chr(QtGui.qAlpha(rgb))
                            if isPy2:
                                byteList.append(alpha)
                            else:
                                byteList.append(alpha.encode('latin-1'))
                    # line += numcomponents

            _bytes = b"".join(byteList)
            img.setValue(size, numcomponents, _bytes)
        except FileNotFoundError as exc:
            _wrn("load_texture: {0}, {1}".format(exc.strerror,
                                                 exc.filename))
            return None
        except Exception as exc:
            _wrn(str(exc))
            _wrn("load_texture: " + _tr("unable to load texture"))
            return None
        else:
            return img
    return None