Example #1
0
    def __init__(self, obj, mipmap_level=0):
        """Construct from a color or from a NumPy array

        :param obj: RGB triple (uint8), or a HxWx4 or HxWx3 numpy array which
           can be either uint8 or uint16.
        :param mipmap_level: mipmap level, used internally. Root is zero.
        """

        if not isinstance(obj, numpy.ndarray):
            r, g, b = obj
            obj = numpy.zeros((N, N, 3), dtype='uint8')
            obj[:, :, :] = r, g, b

        height, width = obj.shape[0:2]
        if height % N or width % N:
            raise BackgroundError('unsupported background tile size: %dx%d' % (width, height))

        super(Background, self).__init__(mipmap_level=0, looped=True,
                                         looped_size=(width, height))
        self.load_from_numpy(obj, 0, 0)

        # Generate mipmap
        if mipmap_level <= MAX_MIPMAP_LEVEL:
            mipmap_obj = numpy.zeros((height, width, 4), dtype='uint16')
            for ty in range(height/N*2):
                for tx in range(width/N*2):
                    with self.tile_request(tx, ty, readonly=True) as src:
                        mypaintlib.tile_downscale_rgba16(src, mipmap_obj, tx*N/2, ty*N/2)

            self.mipmap = Background(mipmap_obj, mipmap_level+1)
            self.mipmap.parent = self
            self.mipmap_level = mipmap_level
    def __init__(self, obj, mipmap_level=0):

        if not isinstance(obj, numpy.ndarray):
            r, g, b = obj
            obj = numpy.zeros((N, N, 3), dtype='uint8')
            obj[:,:,:] = r, g, b

        height, width = obj.shape[0:2]
        if height % N or width % N:
            raise BackgroundError, 'unsupported background tile size: %dx%d' % (width, height)

        Surface.__init__(self, mipmap_level=0,
                                      looped=True, looped_size=(width, height))
        self.load_from_numpy(obj, 0, 0)

        # Generate mipmap
        if mipmap_level <= MAX_MIPMAP_LEVEL:
            mipmap_obj = numpy.zeros((height, width, 4), dtype='uint16')
            for ty in range(height/N*2):
                for tx in range(width/N*2):
                    with self.tile_request(tx, ty, readonly=True) as src:
                        mypaintlib.tile_downscale_rgba16(src, mipmap_obj, tx*N/2, ty*N/2)

            self.mipmap = Background(mipmap_obj, mipmap_level+1)
            self.mipmap.parent = self
            self.mipmap_level = mipmap_level
 def get_tile_memory(self, tx, ty, readonly):
     # OPTIMIZE: do some profiling to check if this function is a bottleneck
     #           yes it is
     # Note: we must return memory that stays valid for writing until the
     # last end_atomic(), because of the caching in tiledsurface.hpp.
     t = self.tiledict.get((tx, ty))
     if t is None:
         if readonly:
             t = transparent_tile
         else:
             t = Tile()
             self.tiledict[(tx, ty)] = t
     if t is mipmap_dirty_tile:
         # regenerate mipmap
         t = Tile()
         self.tiledict[(tx, ty)] = t
         empty = True
         for x in xrange(2):
             for y in xrange(2):
                 src = self.parent.get_tile_memory(tx*2 + x, ty*2 + y, True)
                 mypaintlib.tile_downscale_rgba16(src, t.rgba, x*N/2, y*N/2)
                 if src is not transparent_tile.rgba:
                     empty = False
         if empty:
             # rare case, no need to speed it up
             del self.tiledict[(tx, ty)]
             t = transparent_tile
     if t.readonly and not readonly:
         # shared memory, get a private copy for writing
         t = t.copy()
         self.tiledict[(tx, ty)] = t
     if not readonly:
         assert self.mipmap_level == 0
         self._mark_mipmap_dirty(tx, ty)
     return t.rgba
Example #4
0
    def __init__(self, obj, mipmap_level=0):
        """Construct from a color or from a NumPy array

        :param obj: RGB triple (uint8), or a HxWx4 or HxWx3 numpy array which
           can be either uint8 or uint16.
        :param mipmap_level: mipmap level, used internally. Root is zero.
        """

        if not isinstance(obj, numpy.ndarray):
            r, g, b = obj
            obj = numpy.zeros((N, N, 3), dtype='uint8')
            obj[:, :, :] = r, g, b

        height, width = obj.shape[0:2]
        if height % N or width % N:
            raise BackgroundError('unsupported background tile size: %dx%d' %
                                  (width, height))

        super(Background, self).__init__(mipmap_level=0,
                                         looped=True,
                                         looped_size=(width, height))
        self.load_from_numpy(obj, 0, 0)

        # Generate mipmap
        if mipmap_level <= MAX_MIPMAP_LEVEL:
            mipmap_obj = numpy.zeros((height, width, 4), dtype='uint16')
            for ty in range(height / N * 2):
                for tx in range(width / N * 2):
                    with self.tile_request(tx, ty, readonly=True) as src:
                        mypaintlib.tile_downscale_rgba16(
                            src, mipmap_obj, tx * N / 2, ty * N / 2)

            self.mipmap = Background(mipmap_obj, mipmap_level + 1)
            self.mipmap.parent = self
            self.mipmap_level = mipmap_level
 def get_tile_memory(self, tx, ty, readonly):
     # OPTIMIZE: do some profiling to check if this function is a bottleneck
     #           yes it is
     # Note: we must return memory that stays valid for writing until the
     # last end_atomic(), because of the caching in tiledsurface.hpp.
     t = self.tiledict.get((tx, ty))
     if t is None:
         if readonly:
             t = transparent_tile
         else:
             t = Tile()
             self.tiledict[(tx, ty)] = t
     if t is mipmap_dirty_tile:
         # regenerate mipmap
         t = Tile()
         self.tiledict[(tx, ty)] = t
         empty = True
         for x in xrange(2):
             for y in xrange(2):
                 src = self.parent.get_tile_memory(tx*2 + x, ty*2 + y, True)
                 mypaintlib.tile_downscale_rgba16(src, t.rgba, x*N/2, y*N/2)
                 if src is not transparent_tile.rgba:
                     empty = False
         if empty:
             # rare case, no need to speed it up
             del self.tiledict[(tx, ty)]
             t = transparent_tile
     if t.readonly and not readonly:
         # shared memory, get a private copy for writing
         t = t.copy()
         self.tiledict[(tx, ty)] = t
     if not readonly:
         assert self.mipmap_level == 0
         self._mark_mipmap_dirty(tx, ty)
     return t.rgba
Example #6
0
    def __init__(self, obj, mipmap_level=0):
        if isinstance(obj, gdk.Pixbuf):
            obj = helpers.gdkpixbuf2numpy(obj)
        elif not isinstance(obj, numpy.ndarray):
            r, g, b = obj
            obj = numpy.zeros((N, N, 3), dtype='uint8')
            obj[:,:,:] = r, g, b

        self.tw = obj.shape[1]/N
        self.th = obj.shape[0]/N
        #print obj
        if obj.shape[0:2] != (self.th*N, self.tw*N):
            raise BackgroundError, 'unsupported background tile size: %dx%d' % (obj.shape[0], obj.shape[1])
        if obj.dtype == 'uint8':
            obj = (obj.astype('uint32') * (1<<15) / 255).astype('uint16')

        self.tiles = {}
        for ty in range(self.th):
            for tx in range(self.tw):
                # make sure we have linear memory (optimization)
                tile = numpy.empty((N, N, 4), dtype='uint16') # rgbu
                tile[:,:,:3] = obj[N*ty:N*(ty+1), N*tx:N*(tx+1), :3]
                self.tiles[tx, ty] = tile
        
        # generate mipmap
        self.mipmap_level = mipmap_level
        if mipmap_level < MAX_MIPMAP_LEVEL:
            mipmap_obj = numpy.zeros((self.th*N, self.tw*N, 4), dtype='uint16')
            for ty in range(self.th*2):
                for tx in range(self.tw*2):
                    src = self.get_tile_memory(tx, ty)
                    mypaintlib.tile_downscale_rgba16(src, mipmap_obj, tx*N/2, ty*N/2)
            self.mipmap = Background(mipmap_obj, mipmap_level+1)
Example #7
0
    def _regenerate_mipmap(self, t, tx, ty):
        t = _Tile()
        self.tiledict[(tx, ty)] = t
        empty = True

        for x in xrange(2):
            for y in xrange(2):
                src = self.parent.tiledict.get((tx*2 + x, ty*2 + y), transparent_tile)
                if src is mipmap_dirty_tile:
                    src = self.parent._regenerate_mipmap(src, tx*2 + x, ty*2 + y)
                mypaintlib.tile_downscale_rgba16(src.rgba, t.rgba, x*N/2, y*N/2)
                if src.rgba is not transparent_tile.rgba:
                    empty = False
        if empty:
            # rare case, no need to speed it up
            del self.tiledict[(tx, ty)]
            t = transparent_tile
        return t
Example #8
0
    def _regenerate_mipmap(self, t, tx, ty):
        t = _Tile()
        self.tiledict[(tx, ty)] = t
        empty = True

        for x in xrange(2):
            for y in xrange(2):
                src = self.parent.tiledict.get((tx*2 + x, ty*2 + y), transparent_tile)
                if src is mipmap_dirty_tile:
                    src = self.parent._regenerate_mipmap(src, tx*2 + x, ty*2 + y)
                mypaintlib.tile_downscale_rgba16(src.rgba, t.rgba, x*N/2, y*N/2)
                if src.rgba is not transparent_tile.rgba:
                    empty = False
        if empty:
            # rare case, no need to speed it up
            del self.tiledict[(tx, ty)]
            t = transparent_tile
        return t