def __refreshTexture(self, tex, idx): """Refreshes the given :class:`.RenderTexture`. :arg tex: The ``RenderTexture`` to refresh. :arg idx: Index of the ``RenderTexture``. """ globj = self.__globj zpos = self.__indexToZpos(idx) xax = self.__xax yax = self.__yax axes = (self.__xax, self.__yax, self.__zax) if not globj.ready(): return lo, hi = globj.getDisplayBounds() res = globj.getDataResolution(xax, yax) if res is not None: width = res[xax] height = res[yax] else: width = self.__defaultWidth height = self.__defaultHeight if width > self.__maxWidth: width = self.__maxWidth if height > self.__maxHeight: height = self.__maxHeight log.debug('Refreshing render texture for slice {} (zpos {}, ' 'zax {}): {} x {}'.format(idx, zpos, self.__zax, width, height)) tex.setSize(width, height) oldSize = gl.glGetIntegerv(gl.GL_VIEWPORT) oldProjMat = gl.glGetFloatv( gl.GL_PROJECTION_MATRIX) oldMVMat = gl.glGetFloatv( gl.GL_MODELVIEW_MATRIX) tex.bindAsRenderTarget() glroutines.show2D(xax, yax, width, height, lo, hi) glroutines.clear((0, 0, 0, 0)) with glroutines.disabled(gl.GL_BLEND): globj.preDraw() globj.draw2D(zpos, axes) globj.postDraw() tex.unbindAsRenderTarget() gl.glViewport(*oldSize) gl.glMatrixMode(gl.GL_PROJECTION) gl.glLoadMatrixf(oldProjMat) gl.glMatrixMode(gl.GL_MODELVIEW) gl.glLoadMatrixf(oldMVMat) self.__textureDirty[idx] = False
def _draw(self): """Draws the scene to the canvas. """ if not self._setGLContext(): return opts = self.opts glroutines.clear(opts.bgColour) if not self.__setViewport(): return overlays, globjs = self.getGLObjects() if len(overlays) == 0: return # If occlusion is on, we offset the # depth of each overlay so that, where # a depth collision occurs, overlays # which are higher in the list will get # drawn above (closer to the screen) # than lower ones. depthOffset = transform.scaleOffsetXform(1, [0, 0, 0.1]) depthOffset = np.array(depthOffset, dtype=np.float32, copy=False) xform = np.array(self.__viewMat, dtype=np.float32, copy=False) for ovl, globj in zip(overlays, globjs): display = self.__displayCtx.getDisplay(ovl) if not globj.ready(): continue if not display.enabled: continue if opts.occlusion: xform = transform.concat(depthOffset, xform) elif isinstance(ovl, fslimage.Image): gl.glClear(gl.GL_DEPTH_BUFFER_BIT) log.debug('Drawing {} [{}]'.format(ovl, globj)) globj.preDraw(xform=xform) globj.draw3D(xform=xform) globj.postDraw(xform=xform) if opts.showCursor: with glroutines.enabled((gl.GL_DEPTH_TEST)): self.__drawCursor() if opts.showLegend: self.__drawLegend()
def _draw(self, *a): """Draws the current scene to the canvas. """ if self.destroyed: return width, height = self.GetSize() if width == 0 or height == 0: return if not self._setGLContext(): return opts = self.opts axes = (opts.xax, opts.yax, opts.zax) overlays, globjs = self._getGLObjects() # See comment in SliceCanvas._draw # regarding this test if any([not g.ready() for g in globjs]): return if opts.renderMode == 'offscreen': log.debug('Rendering to off-screen texture') rt = self._offscreenRenderTexture lo = [None] * 3 hi = [None] * 3 lo[opts.xax], hi[opts.xax] = opts.displayBounds.x lo[opts.yax], hi[opts.yax] = opts.displayBounds.y lo[opts.zax], hi[opts.zax] = opts.zrange rt.bindAsRenderTarget() rt.setRenderViewport(opts.xax, opts.yax, lo, hi) glroutines.clear((0, 0, 0, 0)) else: self._setViewport(invertX=False, invertY=False) glroutines.clear(opts.bgColour) startSlice = opts.ncols * opts.topRow endSlice = startSlice + opts.nrows * opts.ncols if endSlice > self._nslices: endSlice = self._nslices # Draw all the slices for all the overlays. for overlay, globj in zip(overlays, globjs): display = self.displayCtx.getDisplay(overlay) globj = self._glObjects.get(overlay, None) if not display.enabled: continue log.debug('Drawing {} slices ({} - {}) for ' 'overlay {} directly to canvas'.format( endSlice - startSlice, startSlice, endSlice, overlay)) zposes = self._sliceLocs[overlay][startSlice:endSlice] xforms = self._transforms[overlay][startSlice:endSlice] xforms = self.__prepareSliceTransforms(globj, xforms) if opts.renderMode == 'prerender': rt, name = self._prerenderTextures.get(overlay, (None, None)) if rt is None: continue log.debug('Drawing {} slices ({} - {}) for overlay {} ' 'from pre-rendered texture'.format( endSlice - startSlice, startSlice, endSlice, overlay)) for zpos, xform in zip(zposes, xforms): rt.draw(zpos, xform) else: globj.preDraw() globj.drawAll(axes, zposes, xforms) globj.postDraw() if opts.renderMode == 'offscreen': rt.unbindAsRenderTarget() rt.restoreViewport() self._setViewport(invertX=False, invertY=False) glroutines.clear(opts.bgColour) rt.drawOnBounds(0, opts.displayBounds.xlo, opts.displayBounds.xhi, opts.displayBounds.ylo, opts.displayBounds.yHi, opts.xax, opts.yax) if len(self.overlayList) > 0: if opts.showCursor: self._drawCursor() if opts.showGridLines: self._drawGridLines() if opts.highlightSlice: self._drawSliceHighlight() self.getAnnotations().draw(opts.pos[opts.zax])
def _draw(self): """Draws the scene to the canvas. """ if self.destroyed: return if not self._setGLContext(): return opts = self.opts glroutines.clear(opts.bgColour) if not self.__setViewport(): return overlays, globjs = self.getGLObjects() if len(overlays) == 0: return # If occlusion is on, we offset the # depth of each overlay so that, where # a depth collision occurs, overlays # which are higher in the list will get # drawn above (closer to the screen) # than lower ones. depthOffset = affine.scaleOffsetXform(1, [0, 0, 0.1]) depthOffset = np.array(depthOffset, dtype=np.float32, copy=False) xform = np.array(self.__viewMat, dtype=np.float32, copy=False) for ovl, globj in zip(overlays, globjs): display = self.__displayCtx.getDisplay(ovl) if not globj.ready(): continue if not display.enabled: continue if opts.occlusion: xform = affine.concat(depthOffset, xform) elif isinstance(ovl, fslimage.Image): gl.glClear(gl.GL_DEPTH_BUFFER_BIT) log.debug('Drawing {} [{}]'.format(ovl, globj)) globj.preDraw(xform=xform) globj.draw3D(xform=xform) globj.postDraw(xform=xform) if opts.showCursor: with glroutines.enabled((gl.GL_DEPTH_TEST)): self.__drawCursor() if opts.showLegend: self.__drawLegend() if opts.showLight: self.__drawLight() # Testing click-to-near/far clipping plane transformation if hasattr(self, 'points'): colours = [(1, 0, 0, 1), (0, 0, 1, 1)] gl.glPointSize(5) gl.glBegin(gl.GL_LINES) for i, p in enumerate(self.points): gl.glColor4f(*colours[i % 2]) p = affine.transform(p, self.viewMatrix) gl.glVertex3f(*p) gl.glEnd()