def test_applyBricon(): rgb = np.random.random((10, 3)) rgba = np.random.random((10, 4)) # bricon of 0.5/0.5 should have no effect assert np.all(np.isclose(rgb, fslcm.applyBricon(rgb, 0.5, 0.5))) assert np.all(np.isclose(rgba, fslcm.applyBricon(rgba, 0.5, 0.5))) # we should be able to pass in a single # colour onergb = [0.3, 0.4, 0.5] onergba = [0.3, 0.4, 0.5, 0.6] assert np.all(np.isclose(onergb, fslcm.applyBricon(onergb, 0.5, 0.5))) assert np.all(np.isclose(onergba, fslcm.applyBricon(onergba, 0.5, 0.5)))
def refreshColourTextures(self, *a): """Overrides :meth:`.GLVolume.refreshColourTexture`. Creates a colour texture which contains the current mask colour, and a transformation matrix which maps from the current :attr:`.MaskOpts.threshold` range to the texture range, so that voxels within this range are coloured, and voxels outside the range are transparent (or vice versa, if the :attr:`.MaskOpts.invert` flag is set). """ display = self.display opts = self.opts alpha = display.alpha / 100.0 colour = opts.colour dmin = opts.threshold[0] dmax = opts.threshold[1] colour = colour[:3] colour = colourmaps.applyBricon(colour, display.brightness / 100.0, display.contrast / 100.0) if opts.invert: cmap = np.tile([0.0, 0.0, 0.0, 0.0], (4, 1)) border = np.array(colour, dtype=np.float32) else: cmap = np.tile([colour], (4, 1)) border = np.array([0.0, 0.0, 0.0, 0.0], dtype=np.float32) self.colourTexture.set(cmap=cmap, border=border, displayRange=(dmin, dmax), alpha=alpha)
def getColour(self): """Prepares and returns the mask colour for use in the fragment shader. """ display = self.display opts = self.opts alpha = display.alpha / 100.0 colour = opts.colour colour = colour[:3] colour = colourmaps.applyBricon(colour, display.brightness / 100.0, display.contrast / 100.0) return list(colour) + [alpha]
def __refresh(self, *a): """Configures the underlying OpenGL texture. """ lut = self.__lut alpha = self.__alpha brightness = self.__brightness contrast = self.__contrast if lut is None: return if brightness is None: brightness = 0.5 if contrast is None: contrast = 0.5 # Enough memory is allocated for the lut texture # so that shader programs can use label values # as indices into the texture. Not very memory # efficient, but greatly reduces complexity. nvals = lut.max() + 1 data = np.zeros((nvals, 4), dtype=np.uint8) for lbl in lut: value = lbl.value colour = fslcmaps.applyBricon(lbl.colour, brightness, contrast) data[value, :3] = [np.floor(c * 255) for c in colour[:3]] if not lbl.enabled: data[value, 3] = 0 elif alpha is not None: data[value, 3] = 255 * alpha else: data[value, 3] = 255 data = data.ravel('C') self.bindTexture() # Values out of range are clipped gl.glTexParameterfv(gl.GL_TEXTURE_1D, gl.GL_TEXTURE_BORDER_COLOR, np.array([0, 0, 0, 0], dtype=np.float32)) gl.glTexParameteri(gl.GL_TEXTURE_1D, gl.GL_TEXTURE_WRAP_S, gl.GL_CLAMP_TO_BORDER) # Nearest neighbour interpolation gl.glTexParameteri(gl.GL_TEXTURE_1D, gl.GL_TEXTURE_MAG_FILTER, gl.GL_NEAREST) gl.glTexParameteri(gl.GL_TEXTURE_1D, gl.GL_TEXTURE_MIN_FILTER, gl.GL_NEAREST) gl.glTexImage1D(gl.GL_TEXTURE_1D, 0, gl.GL_RGBA8, nvals, 0, gl.GL_RGBA, gl.GL_UNSIGNED_BYTE, data) self.unbindTexture()
def getConstantColour(self): """Returns the current :attr::`colour`, adjusted according to the current :attr:`.Display.brightness`, :attr:`.Display.contrast`, and :attr:`.Display.alpha`. """ display = self.display # Only apply bricon if there is no vertex data assigned if self.vertexData is None: brightness = display.brightness / 100.0 contrast = display.contrast / 100.0 else: brightness = 0.5 contrast = 0.5 colour = list( fslcmaps.applyBricon(self.colour[:3], brightness, contrast)) colour.append(display.alpha / 100.0) return colour