def enable(self): camNode = Camera('shadowCam') camNode.setCameraMask(CIGlobals.ShadowCameraBitmask) self.shadowLens = OrthographicLens() self.shadowLens.setFilmSize(60 * 4, 60 * 4) camNode.setLens(self.shadowLens) self.shadowCamArm = camera.attachNewNode('shadowCamArm') self.shadowCam = self.shadowCamArm.attachNewNode(camNode) self.shadowCamArm.setPos(0, 40, 0) self.shadowCam.setPos(0, -40, 0) self.shadowTex = Texture('shadow') self.shadowTex.setBorderColor(self.clearColor) self.shadowTex.setWrapU(Texture.WMBorderColor) self.shadowTex.setWrapV(Texture.WMBorderColor) self.casterState = NodePath('temp') self.casterState.setColorScaleOff(10) self.casterState.setColor(self.shadowColor, self.shadowColor, self.shadowColor, 1, 10) self.casterState.setTextureOff(10) self.casterState.setLightOff(10) self.casterState.setFogOff(10) camNode.setInitialState(self.casterState.getState()) render.hide(CIGlobals.ShadowCameraBitmask) self.shadowStage = TextureStage('shadow') self.shadowStage.setSort(1000) self.turnOnShadows()
def _initDepthCapture(self): for camera in self.cameras: camNode = Camera('Depth camera') camNode.setCameraMask(self.cameraMask) lens = PerspectiveLens() lens.setFov(self.fov) lens.setAspectRatio(float(self.size[0]) / float(self.size[1])) lens.setNear(self.zNear) lens.setFar(self.zFar) camNode.setLens(lens) camNode.setScene(self.scene.scene) cam = camera.attachNewNode(camNode) winprops = WindowProperties.size(self.size[0], self.size[1]) fbprops = FrameBufferProperties.getDefault() fbprops = FrameBufferProperties(fbprops) fbprops.setRgbColor(False) fbprops.setRgbaBits(0, 0, 0, 0) fbprops.setStencilBits(0) fbprops.setMultisamples(0) fbprops.setBackBuffers(0) fbprops.setDepthBits(16) flags = GraphicsPipe.BFFbPropsOptional if self.mode == 'onscreen': flags = flags | GraphicsPipe.BFRequireWindow elif self.mode == 'offscreen': flags = flags | GraphicsPipe.BFRefuseWindow else: raise Exception('Unsupported rendering mode: %s' % (self.mode)) buf = self.graphicsEngine.makeOutput(self.pipe, 'Depth buffer', 0, fbprops, winprops, flags) if buf is None: raise Exception('Unable to create depth buffer') # Set to render at the end buf.setSort(10000) dr = buf.makeDisplayRegion() dr.setSort(0) dr.setCamera(cam) dr = camNode.getDisplayRegion(0) tex = Texture() tex.setFormat(Texture.FDepthComponent) tex.setComponentType(Texture.TFloat) buf.addRenderTexture(tex, GraphicsOutput.RTMCopyRam, GraphicsOutput.RTPDepth) # XXX: should use tex.setMatchFramebufferFormat(True)? agent = camera.getParent() self.depthBuffers[agent.getName()] = buf self.depthTextures[agent.getName()] = tex
def _initRgbCapture(self): for camera in self.cameras: camNode = Camera('Semantic camera') camNode.setCameraMask(self.cameraMask) lens = PerspectiveLens() lens.setFov(self.fov) lens.setAspectRatio(float(self.size[0]) / float(self.size[1])) lens.setNear(self.zNear) lens.setFar(self.zFar) camNode.setLens(lens) camNode.setScene(self.scene.scene) cam = camera.attachNewNode(camNode) winprops = WindowProperties.size(self.size[0], self.size[1]) fbprops = FrameBufferProperties.getDefault() fbprops = FrameBufferProperties(fbprops) fbprops.setRgbaBits(8, 8, 8, 8) flags = GraphicsPipe.BFFbPropsOptional if self.mode == 'onscreen': flags = flags | GraphicsPipe.BFRequireWindow elif self.mode == 'offscreen': flags = flags | GraphicsPipe.BFRefuseWindow else: raise Exception('Unsupported rendering mode: %s' % (self.mode)) buf = self.graphicsEngine.makeOutput(self.pipe, 'RGB-buffer-Semantics', 0, fbprops, winprops, flags) if buf is None: raise Exception('Unable to create RGB buffer') # Set to render at the end buf.setSort(10000) dr = buf.makeDisplayRegion() dr.setSort(0) dr.setCamera(cam) dr = camNode.getDisplayRegion(0) tex = Texture() tex.setFormat(Texture.FRgba8) tex.setComponentType(Texture.TUnsignedByte) buf.addRenderTexture(tex, GraphicsOutput.RTMCopyRam, GraphicsOutput.RTPColor) # XXX: should use tex.setMatchFramebufferFormat(True)? self.rgbBuffers[camera.getNetTag('agent-id')] = buf self.rgbTextures[camera.getNetTag('agent-id')] = tex
def makeCamera(self, win, sort=0, scene=None, displayRegion=(0, 1, 0, 1), stereo=None, aspectRatio=None, clearDepth=0, clearColor=None, lens=None, camName='cam', mask=None, useCamera=None): """ Makes a new 3-d camera associated with the indicated window, and creates a display region in the indicated subrectangle. If stereo is True, then a stereo camera is created, with a pair of DisplayRegions. If stereo is False, then a standard camera is created. If stereo is None or omitted, a stereo camera is created if the window says it can render in stereo. If useCamera is not None, it is a NodePath to be used as the camera to apply to the window, rather than creating a new camera. """ # self.camera is the parent node of all cameras: a node that # we can move around to move all cameras as a group. if self.camera == None: # We make it a ModelNode with the PTLocal flag, so that # a wayward flatten operations won't attempt to mangle the # camera. self.camera = self.render.attachNewNode(ModelNode('camera')) self.camera.node().setPreserveTransform(ModelNode.PTLocal) builtins.camera = self.camera self.mouse2cam.node().setNode(self.camera.node()) if useCamera: # Use the existing camera node. cam = useCamera camNode = useCamera.node() assert (isinstance(camNode, Camera)) lens = camNode.getLens() cam.reparentTo(self.camera) else: # Make a new Camera node. camNode = Camera(camName) if lens == None: lens = PerspectiveLens() if aspectRatio == None: aspectRatio = self.getAspectRatio(win) lens.setAspectRatio(aspectRatio) cam = self.camera.attachNewNode(camNode) if lens != None: camNode.setLens(lens) if scene != None: camNode.setScene(scene) if mask != None: if (isinstance(mask, int)): mask = BitMask32(mask) camNode.setCameraMask(mask) if self.cam == None: self.cam = cam self.camNode = camNode self.camLens = lens self.camList.append(cam) # Now, make a DisplayRegion for the camera. if stereo is not None: if stereo: dr = win.makeStereoDisplayRegion(*displayRegion) else: dr = win.makeMonoDisplayRegion(*displayRegion) else: dr = win.makeDisplayRegion(*displayRegion) dr.setSort(sort) dr.disableClears() # By default, we do not clear 3-d display regions (the entire # window will be cleared, which is normally sufficient). But # we will if clearDepth is specified. if clearDepth: dr.setClearDepthActive(1) if clearColor: dr.setClearColorActive(1) dr.setClearColor(clearColor) dr.setCamera(cam) return cam
class VoxelizePass(RenderPass): """ This pass manages voxelizing the scene from multiple directions to generate a 3D voxel grid. It handles the camera setup and provides a simple interface. """ def __init__(self): RenderPass.__init__(self) def getID(self): return "VoxelizePass" def getRequiredInputs(self): return { } def setVoxelGridResolution(self, voxelGridResolution): """ Sets the voxel grid resolution, this is the amount of voxels in every direction, so the voxel grid will have voxelGridResolution**3 total voxels. """ self.voxelGridResolution = voxelGridResolution def setVoxelGridSize(self, voxelGridSize): """ Sets the size of the voxel grid in world space units. This is the size going from the mid of the voxel grid, so the effective voxel grid will have twice the size specified in voxelGridSize """ self.voxelGridSize = voxelGridSize def setPhotonScaleFactor(self, factor): """ Sets the density of the photon grid. A number of 1 means that for every bright voxel 1 photon will be spawned. A number of 4 for example means that for ever bright voxel 4x4x4 = 64 Photons will be spawned. """ self.photonScaleFactor = factor def setActive(self, active): """ Enables and disables this pass """ self.target.setActive(active) def initVoxelStorage(self): """ Creates t he 3D Texture to store the voxel generation grid """ self.voxelGenTex = Texture("VoxelsTemp") self.voxelGenTex.setup3dTexture(self.voxelGridResolution.x, self.voxelGridResolution.y, self.voxelGridResolution.z, Texture.TInt, Texture.FR32i) # Set appropriate filter types self.voxelGenTex.setMinfilter(SamplerState.FTNearest) self.voxelGenTex.setMagfilter(Texture.FTNearest) self.voxelGenTex.setWrapU(Texture.WMClamp) self.voxelGenTex.setWrapV(Texture.WMClamp) self.voxelGenTex.setWrapW(Texture.WMClamp) self.voxelGenTex.setClearColor(Vec4(0)) # Register texture MemoryMonitor.addTexture("Voxel Temp Texture", self.voxelGenTex) def getVoxelTex(self): """ Returns a handle to the generated voxel texture """ return self.voxelGenTex def clearGrid(self): """ Clears the voxel grid """ self.voxelGenTex.clearImage() def create(self): # Create voxelize camera self.voxelizeCamera = Camera("VoxelizeScene") self.voxelizeCamera.setCameraMask(BitMask32.bit(4)) self.voxelizeCameraNode = Globals.render.attachNewNode(self.voxelizeCamera) self.voxelizeLens = OrthographicLens() self.voxelizeLens.setFilmSize(self.voxelGridSize.x*2, self.voxelGridSize.y*2) self.voxelizeLens.setNearFar(0.0, self.voxelGridSize.x*2) self.voxelizeCamera.setLens(self.voxelizeLens) self.voxelizeCamera.setTagStateKey("VoxelizePassShader") Globals.render.setTag("VoxelizePassShader", "Default") # Create voxelize tareet self.target = RenderTarget("VoxelizePass") self.target.setSize(self.voxelGridResolution.x * self.photonScaleFactor) # self.target.setColorWrite(False) self.target.addColorTexture() self.target.setCreateOverlayQuad(False) self.target.setSource(self.voxelizeCameraNode, Globals.base.win) self.target.prepareSceneRender() self.target.setActive(False) self.target.getInternalRegion().setSort(-400) self.target.getInternalBuffer().setSort(-399) def voxelizeSceneFromDirection(self, gridPos, direction="x"): """ Voxelizes the scene from a given direction. This method handles setting the camera position aswell as the near and far plane. If the pass was disabled, it also enables this pass. """ assert(direction in "x y z".split()) self.setActive(True) if direction == "x": self.voxelizeLens.setFilmSize(self.voxelGridSize.y*2, self.voxelGridSize.z*2) self.voxelizeLens.setNearFar(0.0, self.voxelGridSize.x*2) self.voxelizeCameraNode.setPos(gridPos - Vec3(self.voxelGridSize.x, 0, 0)) self.voxelizeCameraNode.lookAt(gridPos) elif direction == "y": self.voxelizeLens.setFilmSize(self.voxelGridSize.x*2, self.voxelGridSize.z*2) self.voxelizeLens.setNearFar(0.0, self.voxelGridSize.y*2) self.voxelizeCameraNode.setPos(gridPos - Vec3(0, self.voxelGridSize.y, 0)) self.voxelizeCameraNode.lookAt(gridPos) elif direction == "z": self.voxelizeLens.setFilmSize(self.voxelGridSize.x*2, self.voxelGridSize.y*2) self.voxelizeLens.setNearFar(0.0, self.voxelGridSize.z*2) self.voxelizeCameraNode.setPos(gridPos + Vec3(0, 0, self.voxelGridSize.z)) self.voxelizeCameraNode.lookAt(gridPos) def setShaders(self): """ Creates the tag state and loades the voxelizer shader """ voxelizeShader = Shader.load(Shader.SLGLSL, "Shader/GI/Voxelize.vertex", "Shader/GI/Voxelize.fragment") # Create tag state initialState = NodePath("VoxelizerState") initialState.setShader(voxelizeShader, 500) initialState.setAttrib(CullFaceAttrib.make(CullFaceAttrib.MCullNone)) initialState.setDepthWrite(False) initialState.setDepthTest(False) initialState.setAttrib(DepthTestAttrib.make(DepthTestAttrib.MNone)) initialState.setShaderInput("giVoxelGenerationTex", self.voxelGenTex) # Apply tag state self.voxelizeCamera.setTagState("Default", initialState.getState()) return [voxelizeShader] def getOutputs(self): return { }
def make_camera(self, output, sort=0, dr_dims=(0, 1, 0, 1), aspect_ratio=None, clear_depth=False, clear_color=None, lens=None, cam_name="camera0", mask=None): """ Makes a new 3-d camera associated with the indicated window, and creates a display region in the indicated subrectangle. If stereo is True, then a stereo camera is created, with a pair of DisplayRegions. If stereo is False, then a standard camera is created. If stereo is None or omitted, a stereo camera is created if the window says it can render in stereo. If useCamera is not None, it is a NodePath to be used as the camera to apply to the window, rather than creating a new camera. Args: output (GraphicsOutput): Output object. Keyword Args: sort (int): Sort order. dr_dims (Iterable, 4): DisplayRegion dimensions. aspect_ratio (float): Aspect ratio. clear_depth (bool): Indicator to clear depth buffer. clear_color (bool): Indicator to clear color buffer. lens (Lens): Lens object. cam_name (str): Window name. mask (BitMask32): Bit mask that indicates which objects to render. Return: (NodePath): Camera nodepath. """ # self.cameras is the parent node of all cameras: a node that # we can move around to move all cameras as a group. if self.cameras is None: # We make it a ModelNode with the PTLocal flag, so that a # wayward flatten operations won't attempt to mangle the # camera. self.cameras = self.root.attachNewNode(ModelNode("cameras")) self.cameras.node().setPreserveTransform(ModelNode.PTLocal) # Make a new Camera node. cam_node = Camera(cam_name) if lens is None: lens = PerspectiveLens() if aspect_ratio is None: aspect_ratio = self.get_aspect_ratio(output) lens.setAspectRatio(aspect_ratio) lens.setNear(0.1) lens.setFar(1000.0) if lens is not None: cam_node.setLens(lens) camera = self.cameras.attachNewNode(cam_node) # Masks out part of scene from camera if mask is not None: if (isinstance(mask, int)): mask = BitMask32(mask) cam_node.setCameraMask(mask) # Make a display region dr = output.makeDisplayRegion(*dr_dims) # By default, we do not clear 3-d display regions (the entire # window will be cleared, which is normally sufficient). But # we will if clearDepth is specified. if clear_depth: dr.setClearDepthActive(1) if clear_color: dr.setClearColorActive(1) dr.setClearColor(clear_color) dr.setSort(sort) dr.setCamera(camera) dr.setActive(True) return camera
def __init__(self): # Player Model setup self.player = Actor("Player", {"Run":"Player-Run", "Sidestep":"Player-Sidestep", "Idle":"Player-Idle"}) self.player.setBlend(frameBlend = True) self.player.setPos(0, 0, 0) self.player.pose("Idle", 0) self.player.reparentTo(render) self.player.hide() self.footstep = base.audio3d.loadSfx('footstep.ogg') self.footstep.setLoop(True) base.audio3d.attachSoundToObject(self.footstep, self.player) # Create a brush to paint on the texture splat = PNMImage("../data/Splat.png") self.colorBrush = PNMBrush.makeImage(splat, 6, 6, 1) CamMask = BitMask32.bit(0) AvBufMask = BitMask32.bit(1) self.avbuf = None if base.win: self.avbufTex = Texture('avbuf') self.avbuf = base.win.makeTextureBuffer('avbuf', 256, 256, self.avbufTex, True) cam = Camera('avbuf') cam.setLens(base.camNode.getLens()) self.avbufCam = base.cam.attachNewNode(cam) dr = self.avbuf.makeDisplayRegion() dr.setCamera(self.avbufCam) self.avbuf.setActive(False) self.avbuf.setClearColor((1, 0, 0, 1)) cam.setCameraMask(AvBufMask) base.camNode.setCameraMask(CamMask) # avbuf renders everything it sees with the gradient texture. tex = loader.loadTexture('gradient.png') np = NodePath('np') np.setTexture(tex, 100) np.setColor((1, 1, 1, 1), 100) np.setColorScaleOff(100) np.setTransparency(TransparencyAttrib.MNone, 100) np.setLightOff(100) cam.setInitialState(np.getState()) #render.hide(AvBufMask) # Setup a texture stage to paint on the player self.paintTs = TextureStage('paintTs') self.paintTs.setMode(TextureStage.MDecal) self.paintTs.setSort(10) self.paintTs.setPriority(10) self.tex = Texture('paint_av_%s'%id(self)) # Setup a PNMImage that will hold the paintable texture of the player self.imageSizeX = 64 self.imageSizeY = 64 self.p = PNMImage(self.imageSizeX, self.imageSizeY, 4) self.p.fill(1) self.p.alphaFill(0) self.tex.load(self.p) self.tex.setWrapU(self.tex.WMClamp) self.tex.setWrapV(self.tex.WMClamp) # Apply the paintable texture to the avatar self.player.setTexture(self.paintTs, self.tex) # team self.playerTeam = "" # A lable that will display the players team self.lblTeam = DirectLabel( scale = 1, pos = (0, 0, 3), frameColor = (0, 0, 0, 0), text = "TEAM", text_align = TextNode.ACenter, text_fg = (0,0,0,1)) self.lblTeam.reparentTo(self.player) self.lblTeam.setBillboardPointEye() # basic player values self.maxHits = 3 self.currentHits = 0 self.isOut = False self.TorsorControl = self.player.controlJoint(None,"modelRoot","Torsor") # setup the collision detection # wall and object collision self.playerSphere = CollisionSphere(0, 0, 1, 1) self.playerCollision = self.player.attachNewNode(CollisionNode("playerCollision%d"%id(self))) self.playerCollision.node().addSolid(self.playerSphere) base.pusher.addCollider(self.playerCollision, self.player) base.cTrav.addCollider(self.playerCollision, base.pusher) # foot (walk) collision self.playerFootRay = self.player.attachNewNode(CollisionNode("playerFootCollision%d"%id(self))) self.playerFootRay.node().addSolid(CollisionRay(0, 0, 2, 0, 0, -1)) self.playerFootRay.node().setIntoCollideMask(0) self.lifter = CollisionHandlerFloor() self.lifter.addCollider(self.playerFootRay, self.player) base.cTrav.addCollider(self.playerFootRay, self.lifter) # Player weapon setup self.gunAttach = self.player.exposeJoint(None, "modelRoot", "WeaponSlot_R") self.color = LPoint3f(1, 1, 1) self.gun = Gun(id(self)) self.gun.reparentTo(self.gunAttach) self.gun.hide() self.gun.setColor(self.color) self.hud = None # Player controls setup self.keyMap = {"left":0, "right":0, "forward":0, "backward":0} # screen sizes self.winXhalf = base.win.getXSize() / 2 self.winYhalf = base.win.getYSize() / 2 self.mouseSpeedX = 0.1 self.mouseSpeedY = 0.1 # AI controllable variables self.AIP = 0.0 self.AIH = 0.0 self.movespeed = 5.0 self.userControlled = False self.accept("Bulet-hit-playerCollision%d" % id(self), self.hit) self.accept("window-event", self.recalcAspectRatio)
class VoxelizePass(RenderPass): """ This pass manages voxelizing the scene from multiple directions to generate a 3D voxel grid. It handles the camera setup and provides a simple interface. """ def __init__(self, pipeline): RenderPass.__init__(self) self.pipeline = pipeline def getID(self): return "VoxelizePass" def getRequiredInputs(self): return { # Lighting "renderedLightsBuffer": "Variables.renderedLightsBuffer", "lights": "Variables.allLights", "shadowAtlasPCF": "ShadowScenePass.atlasPCF", "shadowAtlas": "ShadowScenePass.atlas", "shadowSources": "Variables.allShadowSources", "directionToFace": "Variables.directionToFaceLookup", "cameraPosition": "Variables.cameraPosition", "mainCam": "Variables.mainCam", "mainRender": "Variables.mainRender", } def setVoxelGridResolution(self, voxelGridResolution): """ Sets the voxel grid resolution, this is the amount of voxels in every direction, so the voxel grid will have voxelGridResolution**3 total voxels. """ self.voxelGridResolution = voxelGridResolution def setVoxelGridSize(self, voxelGridSize): """ Sets the size of the voxel grid in world space units. This is the size going from the mid of the voxel grid, so the effective voxel grid will have twice the size specified in voxelGridSize """ self.voxelGridSize = voxelGridSize def setGridResolutionMultiplier(self, factor): """ Sets the density of the voxel grid. """ self.gridResolutionMultiplier = factor def setActive(self, active): """ Enables and disables this pass """ if hasattr(self, "target"): self.target.setActive(active) def getVoxelTex(self): """ Returns a handle to the generated voxel texture """ return self.voxelGenTex def clearGrid(self): """ Clears the voxel grid """ self.voxelGenTex.clearImage() def create(self): # Create voxelize camera self.voxelizeCamera = Camera("VoxelizeCamera") self.voxelizeCamera.setCameraMask(BitMask32.bit(4)) self.voxelizeCameraNode = Globals.render.attachNewNode(self.voxelizeCamera) self.voxelizeLens = OrthographicLens() self.voxelizeLens.setFilmSize(self.voxelGridSize * 2, self.voxelGridSize * 2) self.voxelizeLens.setNearFar(0.0, self.voxelGridSize * 2) self.voxelizeCamera.setLens(self.voxelizeLens) self.voxelizeCamera.setTagStateKey("VoxelizePassShader") Globals.render.setTag("VoxelizePassShader", "Default") # Create voxelize tareet self.target = RenderTarget("VoxelizePass") self.target.setSize(self.voxelGridResolution * self.gridResolutionMultiplier) if self.pipeline.settings.useDebugAttachments: self.target.addColorTexture() else: self.target.setColorWrite(False) self.target.setCreateOverlayQuad(False) self.target.setSource(self.voxelizeCameraNode, Globals.base.win) self.target.prepareSceneRender() self.target.setActive(False) # self.target.getInternalRegion().setSort(-400) # self.target.getInternalBuffer().setSort(-399) def voxelizeSceneFromDirection(self, gridPos, direction="x"): """ Voxelizes the scene from a given direction. This method handles setting the camera position aswell as the near and far plane. If the pass was disabled, it also enables this pass. """ assert direction in ["x", "y", "z"] self.setActive(True) if direction == "x": self.voxelizeLens.setFilmSize(self.voxelGridSize * 2, self.voxelGridSize * 2) self.voxelizeLens.setNearFar(0.0, self.voxelGridSize * 2) self.voxelizeCameraNode.setPos(gridPos - Vec3(self.voxelGridSize, 0, 0)) self.voxelizeCameraNode.lookAt(gridPos) elif direction == "y": self.voxelizeLens.setFilmSize(self.voxelGridSize * 2, self.voxelGridSize * 2) self.voxelizeLens.setNearFar(0.0, self.voxelGridSize * 2) self.voxelizeCameraNode.setPos(gridPos - Vec3(0, self.voxelGridSize, 0)) self.voxelizeCameraNode.lookAt(gridPos) elif direction == "z": self.voxelizeLens.setFilmSize(self.voxelGridSize * 2, self.voxelGridSize * 2) self.voxelizeLens.setNearFar(0.0, self.voxelGridSize * 2) self.voxelizeCameraNode.setPos(gridPos + Vec3(0, 0, self.voxelGridSize)) self.voxelizeCameraNode.lookAt(gridPos) def setShaders(self): """ Creates the tag state and loades the voxelizer shader """ self.registerTagState("Default", NodePath("DefaultVoxelizeState")) return [] def registerTagState(self, name, state): """ Registers a new tag state """ state.setAttrib(CullFaceAttrib.make(CullFaceAttrib.MCullNone)) state.setDepthWrite(False) state.setDepthTest(False) state.setAttrib(DepthTestAttrib.make(DepthTestAttrib.MNone)) state.setShaderInput("voxelizeCam", self.voxelizeCameraNode) self.voxelizeCamera.setTagState(name, state.getState()) def setShaderInput(self, *args): Globals.base.render.setShaderInput(*args) def getOutputs(self): return {}
class Viewport(QtWidgets.QWidget, DirectObject): ClearColor = LEGlobals.vec3GammaToLinear(Vec4(0.361, 0.361, 0.361, 1.0)) def __init__(self, vpType, window, doc): DirectObject.__init__(self) QtWidgets.QWidget.__init__(self, window) self.doc = doc self.setFocusPolicy(QtCore.Qt.StrongFocus) self.setMouseTracking(True) self.qtWindow = None self.qtWidget = None self.window = window self.type = vpType self.spec = VIEWPORT_SPECS[self.type] self.lens = None self.camNode = None self.camera = None self.cam = None self.win = None self.displayRegion = None self.mouseWatcher = None self.mouseWatcherNp = None self.buttonThrower = None self.clickRay = None self.clickNode = None self.clickNp = None self.clickQueue = None self.tickTask = None self.zoom = 1.0 self.gizmo = None self.inputDevice = None self.mouseAndKeyboard = None self.lastRenderTime = 0.0 self.enabled = False self.needsUpdate = True # 2D stuff copied from ShowBase :( self.camera2d = None self.cam2d = None self.render2d = None self.aspect2d = None self.a2dBackground = None self.a2dTop = None self.a2dBottom = None self.a2dLeft = None self.a2dRight = None self.a2dTopCenter = None self.a2dTopCenterNs = None self.a2dBottomCenter = None self.a2dBottomCenterNs = None self.a2dRightCenter = None self.a2dRightCenterNs = None self.a2dTopLeft = None self.a2dTopLeftNs = None self.a2dTopRight = None self.a2dTopRightNs = None self.a2dBottomLeft = None self.a2dBottomLeftNs = None self.a2dBottomRight = None self.a2dBottomRightNs = None self.__oldAspectRatio = None self.gridRoot = self.doc.render.attachNewNode("gridRoot") self.gridRoot.setLightOff(1) #self.gridRoot.setBSPMaterial("phase_14/materials/unlit.mat") #self.gridRoot.setDepthWrite(False) self.gridRoot.setBin("background", 0) self.gridRoot.hide(~self.getViewportMask()) self.grid = None def updateView(self, now=False): if now: self.renderView() else: self.needsUpdate = True def getGizmoAxes(self): raise NotImplementedError def getMouseRay(self, collRay=False): ray = CollisionRay() ray.setFromLens(self.camNode, self.getMouse()) if collRay: return ray else: return Ray(ray.getOrigin(), ray.getDirection()) def hasMouse(self): return self.mouseWatcher.hasMouse() def getMouse(self): if self.mouseWatcher.hasMouse(): return self.mouseWatcher.getMouse() return Point2(0, 0) def is3D(self): return self.type == VIEWPORT_3D def is2D(self): return self.type != VIEWPORT_3D def makeGrid(self): raise NotImplementedError def getViewportMask(self): return BitMask32.bit(self.type) def getViewportFullMask(self): return self.getViewportMask() def makeLens(self): raise NotImplementedError def getGridAxes(self): raise NotImplementedError def expand(self, point): return point def initialize(self): self.lens = self.makeLens() self.camera = self.doc.render.attachNewNode( ModelNode("viewportCameraParent")) self.camNode = Camera("viewportCamera") self.camNode.setLens(self.lens) self.camNode.setCameraMask(self.getViewportMask()) self.cam = self.camera.attachNewNode(self.camNode) winprops = WindowProperties.getDefault() winprops.setParentWindow(int(self.winId())) winprops.setForeground(False) winprops.setUndecorated(True) gsg = self.doc.gsg output = base.graphicsEngine.makeOutput( base.pipe, "viewportOutput", 0, FrameBufferProperties.getDefault(), winprops, (GraphicsPipe.BFFbPropsOptional | GraphicsPipe.BFRequireWindow), gsg) self.qtWindow = QtGui.QWindow.fromWinId( output.getWindowHandle().getIntHandle()) self.qtWidget = QtWidgets.QWidget.createWindowContainer( self.qtWindow, self, QtCore.Qt.WindowDoesNotAcceptFocus | QtCore.Qt.WindowTransparentForInput | QtCore.Qt.WindowStaysOnBottomHint | QtCore.Qt.BypassWindowManagerHint | QtCore.Qt.SubWindow) #, #(QtCore.Qt.FramelessWindowHint | QtCore.Qt.WindowDoesNotAcceptFocus #| QtCore.Qt.WindowTransparentForInput | QtCore.Qt.BypassWindowManagerHint #| QtCore.Qt.SubWindow | QtCore.Qt.WindowStaysOnBottomHint)) self.qtWidget.setFocusPolicy(QtCore.Qt.NoFocus) self.inputDevice = output.getInputDevice(0) assert output is not None, "Unable to create viewport output!" dr = output.makeDisplayRegion() dr.disableClears() dr.setCamera(self.cam) self.displayRegion = dr output.disableClears() output.setClearColor(Viewport.ClearColor) output.setClearColorActive(True) output.setClearDepthActive(True) output.setActive(True) self.win = output # keep track of the mouse in this viewport mak = MouseAndKeyboard(self.win, 0, "mouse") mouse = base.dataRoot.attachNewNode(mak) self.mouseAndKeyboard = mouse self.mouseWatcher = MouseWatcher() self.mouseWatcher.setDisplayRegion(self.displayRegion) mw = mouse.attachNewNode(self.mouseWatcher) self.mouseWatcherNp = mw # listen for keyboard and mouse events in this viewport bt = ButtonThrower("kbEvents") bt.setButtonDownEvent("btndown") bt.setButtonUpEvent("btnup") mods = ModifierButtons() mods.addButton(KeyboardButton.shift()) mods.addButton(KeyboardButton.control()) mods.addButton(KeyboardButton.alt()) mods.addButton(KeyboardButton.meta()) bt.setModifierButtons(mods) self.buttonThrower = mouse.attachNewNode(bt) # collision objects for clicking on objects from this viewport self.clickRay = CollisionRay() self.clickNode = CollisionNode("viewportClickRay") self.clickNode.addSolid(self.clickRay) self.clickNp = NodePath(self.clickNode) self.clickQueue = CollisionHandlerQueue() self.setupRender2d() self.setupCamera2d() self.gizmo = ViewportGizmo(self) self.doc.viewportMgr.addViewport(self) self.makeGrid() def cleanup(self): self.grid.cleanup() self.grid = None self.gridRoot.removeNode() self.gridRoot = None self.lens = None self.camNode = None self.cam.removeNode() self.cam = None self.camera.removeNode() self.camera = None self.spec = None self.doc = None self.type = None self.window = None self.zoom = None self.gizmo.cleanup() self.gizmo = None self.clickNp.removeNode() self.clickNp = None self.clickQueue.clearEntries() self.clickQueue = None self.clickNode = None self.clickRay = None self.buttonThrower.removeNode() self.buttonThrower = None self.inputDevice = None self.mouseWatcherNp.removeNode() self.mouseWatcherNp = None self.mouseWatcher = None self.mouseAndKeyboard.removeNode() self.mouseAndKeyboard = None self.win.removeAllDisplayRegions() self.displayRegion = None base.graphicsEngine.removeWindow(self.win) self.win = None self.camera2d.removeNode() self.camera2d = None self.cam2d = None self.render2d.removeNode() self.render2d = None self.a2dBackground = None self.a2dTop = None self.a2dBottom = None self.a2dLeft = None self.a2dRight = None self.aspect2d = None self.a2dTopCenter = None self.a2dTopCenterNs = None self.a2dBottomCenter = None self.a2dBottomCenterNs = None self.a2dLeftCenter = None self.a2dLeftCenterNs = None self.a2dRightCenter = None self.a2dRightCenterNs = None self.a2dTopLeft = None self.a2dTopLeftNs = None self.a2dTopRight = None self.a2dTopRightNs = None self.a2dBottomLeft = None self.a2dBottomLeftNs = None self.a2dBottomRight = None self.a2dBottomRightNs = None self.__oldAspectRatio = None self.qtWindow.deleteLater() self.qtWidget.deleteLater() self.qtWindow = None self.qtWidget = None self.deleteLater() def keyPressEvent(self, event): button = LEUtils.keyboardButtonFromQtKey(event.key()) if button: self.inputDevice.buttonDown(button) def keyReleaseEvent(self, event): button = LEUtils.keyboardButtonFromQtKey(event.key()) if button: self.inputDevice.buttonUp(button) def enterEvent(self, event): # Give ourselves focus. self.setFocus() QtWidgets.QWidget.enterEvent(self, event) def mouseMoveEvent(self, event): self.inputDevice.setPointerInWindow(event.pos().x(), event.pos().y()) QtWidgets.QWidget.mouseMoveEvent(self, event) def leaveEvent(self, event): self.clearFocus() self.inputDevice.setPointerOutOfWindow() self.inputDevice.focusLost() QtWidgets.QWidget.leaveEvent(self, event) def mousePressEvent(self, event): btn = event.button() if btn == QtCore.Qt.LeftButton: self.inputDevice.buttonDown(MouseButton.one()) elif btn == QtCore.Qt.MiddleButton: self.inputDevice.buttonDown(MouseButton.two()) elif btn == QtCore.Qt.RightButton: self.inputDevice.buttonDown(MouseButton.three()) QtWidgets.QWidget.mousePressEvent(self, event) def mouseReleaseEvent(self, event): btn = event.button() if btn == QtCore.Qt.LeftButton: self.inputDevice.buttonUp(MouseButton.one()) elif btn == QtCore.Qt.MiddleButton: self.inputDevice.buttonUp(MouseButton.two()) elif btn == QtCore.Qt.RightButton: self.inputDevice.buttonUp(MouseButton.three()) QtWidgets.QWidget.mouseReleaseEvent(self, event) def wheelEvent(self, event): ang = event.angleDelta().y() if ang > 0: self.inputDevice.buttonDown(MouseButton.wheelUp()) self.inputDevice.buttonUp(MouseButton.wheelUp()) else: self.inputDevice.buttonDown(MouseButton.wheelDown()) self.inputDevice.buttonUp(MouseButton.wheelDown()) QtWidgets.QWidget.wheelEvent(self, event) def getAspectRatio(self): return self.win.getXSize() / self.win.getYSize() def setupRender2d(self): ## This is the root of the 2-D scene graph. self.render2d = NodePath("viewport-render2d") # Set up some overrides to turn off certain properties which # we probably won't need for 2-d objects. # It's probably important to turn off the depth test, since # many 2-d objects will be drawn over each other without # regard to depth position. # We used to avoid clearing the depth buffer before drawing # render2d, but nowadays we clear it anyway, since we # occasionally want to put 3-d geometry under render2d, and # it's simplest (and seems to be easier on graphics drivers) # if the 2-d scene has been cleared first. self.render2d.setDepthTest(0) self.render2d.setDepthWrite(0) self.render2d.setMaterialOff(1) self.render2d.setTwoSided(1) self.aspect2d = self.render2d.attachNewNode("viewport-aspect2d") aspectRatio = self.getAspectRatio() self.aspect2d.setScale(1.0 / aspectRatio, 1.0, 1.0) self.a2dBackground = self.aspect2d.attachNewNode("a2dBackground") ## The Z position of the top border of the aspect2d screen. self.a2dTop = 1.0 ## The Z position of the bottom border of the aspect2d screen. self.a2dBottom = -1.0 ## The X position of the left border of the aspect2d screen. self.a2dLeft = -aspectRatio ## The X position of the right border of the aspect2d screen. self.a2dRight = aspectRatio self.a2dTopCenter = self.aspect2d.attachNewNode("a2dTopCenter") self.a2dTopCenterNs = self.aspect2d.attachNewNode("a2dTopCenterNS") self.a2dBottomCenter = self.aspect2d.attachNewNode("a2dBottomCenter") self.a2dBottomCenterNs = self.aspect2d.attachNewNode( "a2dBottomCenterNS") self.a2dLeftCenter = self.aspect2d.attachNewNode("a2dLeftCenter") self.a2dLeftCenterNs = self.aspect2d.attachNewNode("a2dLeftCenterNS") self.a2dRightCenter = self.aspect2d.attachNewNode("a2dRightCenter") self.a2dRightCenterNs = self.aspect2d.attachNewNode("a2dRightCenterNS") self.a2dTopLeft = self.aspect2d.attachNewNode("a2dTopLeft") self.a2dTopLeftNs = self.aspect2d.attachNewNode("a2dTopLeftNS") self.a2dTopRight = self.aspect2d.attachNewNode("a2dTopRight") self.a2dTopRightNs = self.aspect2d.attachNewNode("a2dTopRightNS") self.a2dBottomLeft = self.aspect2d.attachNewNode("a2dBottomLeft") self.a2dBottomLeftNs = self.aspect2d.attachNewNode("a2dBottomLeftNS") self.a2dBottomRight = self.aspect2d.attachNewNode("a2dBottomRight") self.a2dBottomRightNs = self.aspect2d.attachNewNode("a2dBottomRightNS") # Put the nodes in their places self.a2dTopCenter.setPos(0, 0, self.a2dTop) self.a2dTopCenterNs.setPos(0, 0, self.a2dTop) self.a2dBottomCenter.setPos(0, 0, self.a2dBottom) self.a2dBottomCenterNs.setPos(0, 0, self.a2dBottom) self.a2dLeftCenter.setPos(self.a2dLeft, 0, 0) self.a2dLeftCenterNs.setPos(self.a2dLeft, 0, 0) self.a2dRightCenter.setPos(self.a2dRight, 0, 0) self.a2dRightCenterNs.setPos(self.a2dRight, 0, 0) self.a2dTopLeft.setPos(self.a2dLeft, 0, self.a2dTop) self.a2dTopLeftNs.setPos(self.a2dLeft, 0, self.a2dTop) self.a2dTopRight.setPos(self.a2dRight, 0, self.a2dTop) self.a2dTopRightNs.setPos(self.a2dRight, 0, self.a2dTop) self.a2dBottomLeft.setPos(self.a2dLeft, 0, self.a2dBottom) self.a2dBottomLeftNs.setPos(self.a2dLeft, 0, self.a2dBottom) self.a2dBottomRight.setPos(self.a2dRight, 0, self.a2dBottom) self.a2dBottomRightNs.setPos(self.a2dRight, 0, self.a2dBottom) def setupCamera2d(self, sort=10, displayRegion=(0, 1, 0, 1), coords=(-1, 1, -1, 1)): dr = self.win.makeMonoDisplayRegion(*displayRegion) dr.setSort(10) # Enable clearing of the depth buffer on this new display # region (see the comment in setupRender2d, above). dr.setClearDepthActive(1) # Make any texture reloads on the gui come up immediately. dr.setIncompleteRender(False) left, right, bottom, top = coords # Now make a new Camera node. cam2dNode = Camera('cam2d') lens = OrthographicLens() lens.setFilmSize(right - left, top - bottom) lens.setFilmOffset((right + left) * 0.5, (top + bottom) * 0.5) lens.setNearFar(-1000, 1000) cam2dNode.setLens(lens) # self.camera2d is the analog of self.camera, although it's # not as clear how useful it is. self.camera2d = self.render2d.attachNewNode('camera2d') camera2d = self.camera2d.attachNewNode(cam2dNode) dr.setCamera(camera2d) self.cam2d = camera2d return camera2d def mouse1Up(self): pass def mouse1Down(self): pass def mouse2Up(self): pass def mouse2Down(self): pass def mouse3Up(self): pass def mouse3Down(self): pass def mouseEnter(self): self.updateView() def mouseExit(self): pass def mouseMove(self): pass def wheelUp(self): pass def wheelDown(self): pass def shouldRender(self): if not self.enabled: return False now = globalClock.getRealTime() if self.lastRenderTime != 0: elapsed = now - self.lastRenderTime if elapsed <= 0: return False frameRate = 1 / elapsed if frameRate > 100.0: # Never render faster than 100Hz return False return self.needsUpdate def renderView(self): self.lastRenderTime = globalClock.getRealTime() self.needsUpdate = False #self.win.setActive(1) base.requestRender() def tick(self): if self.shouldRender(): self.renderView() else: pass #self.win.setActive(0) def getViewportName(self): return self.spec.name def getViewportCenterPixels(self): return LPoint2i(self.win.getXSize() // 2, self.win.getYSize() // 2) def centerCursor(self, cursor): center = self.getViewportCenterPixels() cursor.setPos( self.mapToGlobal(QtCore.QPoint(self.width() / 2, self.height() / 2))) self.inputDevice.setPointerInWindow(center.x, center.y) def viewportToWorld(self, viewport, vec=False): front = Point3() back = Point3() self.lens.extrude(viewport, front, back) world = (front + back) / 2 worldMat = self.cam.getMat(render) if vec: world = worldMat.xformVec(world) else: world = worldMat.xformPoint(world) return world def worldToViewport(self, world): # move into local camera space invMat = Mat4(self.cam.getMat(render)) invMat.invertInPlace() local = invMat.xformPoint(world) point = Point2() self.lens.project(local, point) return point def zeroUnusedCoordinate(self, vec): pass def click(self, mask, queue=None, traverser=None, root=None): if not self.mouseWatcher.hasMouse(): return None if not queue: queue = self.clickQueue self.clickRay.setFromLens(self.camNode, self.mouseWatcher.getMouse()) self.clickNode.setFromCollideMask(mask) self.clickNode.setIntoCollideMask(BitMask32.allOff()) self.clickNp.reparentTo(self.cam) queue.clearEntries() if not traverser: base.clickTraverse(self.clickNp, queue) else: if not root: root = self.doc.render traverser.addCollider(self.clickNp, queue) traverser.traverse(root) traverser.removeCollider(self.clickNp) queue.sortEntries() self.clickNp.reparentTo(NodePath()) return queue.getEntries() def fixRatio(self, size=None): if not self.lens: return if size is None: aspectRatio = self.win.getXSize() / self.win.getYSize() else: if size.y > 0: aspectRatio = size.x / size.y else: aspectRatio = 1.0 if self.is2D(): zoomFactor = (1.0 / self.zoom) * 100.0 self.lens.setFilmSize(zoomFactor * aspectRatio, zoomFactor) else: self.lens.setAspectRatio(aspectRatio) if aspectRatio != self.__oldAspectRatio: self.__oldAspectRatio = aspectRatio # Fix up some anything that depends on the aspectRatio if aspectRatio < 1: # If the window is TALL, lets expand the top and bottom self.aspect2d.setScale(1.0, aspectRatio, aspectRatio) self.a2dTop = 1.0 / aspectRatio self.a2dBottom = -1.0 / aspectRatio self.a2dLeft = -1 self.a2dRight = 1.0 else: # If the window is WIDE, lets expand the left and right self.aspect2d.setScale(1.0 / aspectRatio, 1.0, 1.0) self.a2dTop = 1.0 self.a2dBottom = -1.0 self.a2dLeft = -aspectRatio self.a2dRight = aspectRatio # Reposition the aspect2d marker nodes self.a2dTopCenter.setPos(0, 0, self.a2dTop) self.a2dTopCenterNs.setPos(0, 0, self.a2dTop) self.a2dBottomCenter.setPos(0, 0, self.a2dBottom) self.a2dBottomCenterNs.setPos(0, 0, self.a2dBottom) self.a2dLeftCenter.setPos(self.a2dLeft, 0, 0) self.a2dLeftCenterNs.setPos(self.a2dLeft, 0, 0) self.a2dRightCenter.setPos(self.a2dRight, 0, 0) self.a2dRightCenterNs.setPos(self.a2dRight, 0, 0) self.a2dTopLeft.setPos(self.a2dLeft, 0, self.a2dTop) self.a2dTopLeftNs.setPos(self.a2dLeft, 0, self.a2dTop) self.a2dTopRight.setPos(self.a2dRight, 0, self.a2dTop) self.a2dTopRightNs.setPos(self.a2dRight, 0, self.a2dTop) self.a2dBottomLeft.setPos(self.a2dLeft, 0, self.a2dBottom) self.a2dBottomLeftNs.setPos(self.a2dLeft, 0, self.a2dBottom) self.a2dBottomRight.setPos(self.a2dRight, 0, self.a2dBottom) self.a2dBottomRightNs.setPos(self.a2dRight, 0, self.a2dBottom) def resizeEvent(self, event): if not self.win: return newsize = LVector2i(event.size().width(), event.size().height()) self.qtWidget.resize(newsize[0], newsize[1]) self.qtWidget.move(0, 0) #props = WindowProperties() #props.setSize(newsize) #props.setOrigin(0, 0) #self.win.requestProperties(props) self.fixRatio(newsize) self.onResize(newsize) self.updateView() def onResize(self, newsize): pass def draw(self): pass def enable(self): # Render to the viewport self.win.setActive(True) self.enabled = True def disable(self): # Don't render to the viewport self.win.setActive(False) self.enabled = False
def create(self): # Create the atlas target self.target = RenderTarget("ShadowAtlas") self.target.setSize(self.size) self.target.addDepthTexture() self.target.setDepthBits(32) self.target.setColorWrite(False) self.target.setCreateOverlayQuad(False) # self.target.setActive(False) self.target.setSource( NodePath(Camera("tmp")), Globals.base.win) self.target.prepareSceneRender() self.target.setClearDepth(False) # Set the appropriate filter modes dTex = self.target.getDepthTexture() dTex.setWrapU(SamplerState.WMClamp) dTex.setWrapV(SamplerState.WMClamp) # Remove the default postprocess quad # self.target.getQuad().node().removeAllChildren() # self.target.getInternalRegion().setSort(-200) self.target.getInternalRegion().disableClears() self.target.getInternalBuffer().disableClears() # self.target.getInternalBuffer().setSort(-300) # Create default initial state initialState = NodePath("InitialState") initialState.setAttrib(ColorWriteAttrib.make(ColorWriteAttrib.COff)) # Create a camera for each update self.shadowCameras = [] for i in xrange(self.maxRegions): shadowCam = Camera("ShadowComputeCamera") shadowCam.setTagStateKey("ShadowPassShader") shadowCam.setInitialState(initialState.getState()) shadowCam.setCameraMask(BitMask32.bit(3)) shadowCamNode = self.shadowScene.attachNewNode(shadowCam) self.shadowCameras.append(shadowCamNode) # Create regions self.renderRegions = [] buff = self.target.getInternalBuffer() for i in xrange(self.maxRegions): dr = buff.makeDisplayRegion() dr.setSort(1000) dr.setClearDepthActive(True) dr.setClearDepth(1.0) # dr.setClearColorActive(False) # dr.setClearColor(Vec4(1,1,1,1)) dr.setCamera(self.shadowCameras[i]) dr.setActive(False) self.renderRegions.append(dr) self.pcfSampleState = SamplerState() self.pcfSampleState.setMinfilter(SamplerState.FTShadow) self.pcfSampleState.setMagfilter(SamplerState.FTShadow) self.pcfSampleState.setWrapU(SamplerState.WMClamp) self.pcfSampleState.setWrapV(SamplerState.WMClamp)
class VoxelizePass(RenderPass): """ This pass manages voxelizing the scene from multiple directions to generate a 3D voxel grid. It handles the camera setup and provides a simple interface. """ def __init__(self, pipeline): RenderPass.__init__(self) self.pipeline = pipeline def getID(self): return "VoxelizePass" def getRequiredInputs(self): return { # Lighting "renderedLightsBuffer": "Variables.renderedLightsBuffer", "lights": "Variables.allLights", "shadowAtlasPCF": "ShadowScenePass.atlasPCF", "shadowAtlas": "ShadowScenePass.atlas", "shadowSources": "Variables.allShadowSources", "directionToFace": "Variables.directionToFaceLookup", "cameraPosition": "Variables.cameraPosition", "mainCam": "Variables.mainCam", "mainRender": "Variables.mainRender", } def setVoxelGridResolution(self, voxelGridResolution): """ Sets the voxel grid resolution, this is the amount of voxels in every direction, so the voxel grid will have voxelGridResolution**3 total voxels. """ self.voxelGridResolution = voxelGridResolution def setVoxelGridSize(self, voxelGridSize): """ Sets the size of the voxel grid in world space units. This is the size going from the mid of the voxel grid, so the effective voxel grid will have twice the size specified in voxelGridSize """ self.voxelGridSize = voxelGridSize def setGridResolutionMultiplier(self, factor): """ Sets the density of the voxel grid. """ self.gridResolutionMultiplier = factor def setActive(self, active): """ Enables and disables this pass """ if hasattr(self, "target"): self.target.setActive(active) def getVoxelTex(self): """ Returns a handle to the generated voxel texture """ return self.voxelGenTex def clearGrid(self): """ Clears the voxel grid """ self.voxelGenTex.clearImage() def create(self): # Create voxelize camera self.voxelizeCamera = Camera("VoxelizeCamera") self.voxelizeCamera.setCameraMask(BitMask32.bit(4)) self.voxelizeCameraNode = Globals.render.attachNewNode( self.voxelizeCamera) self.voxelizeLens = OrthographicLens() self.voxelizeLens.setFilmSize(self.voxelGridSize * 2, self.voxelGridSize * 2) self.voxelizeLens.setNearFar(0.0, self.voxelGridSize * 2) self.voxelizeCamera.setLens(self.voxelizeLens) self.voxelizeCamera.setTagStateKey("VoxelizePassShader") Globals.render.setTag("VoxelizePassShader", "Default") # Create voxelize tareet self.target = RenderTarget("VoxelizePass") self.target.setSize(self.voxelGridResolution * self.gridResolutionMultiplier) if self.pipeline.settings.useDebugAttachments: self.target.addColorTexture() else: self.target.setColorWrite(False) self.target.setCreateOverlayQuad(False) self.target.setSource(self.voxelizeCameraNode, Globals.base.win) self.target.prepareSceneRender() self.target.setActive(False) # self.target.getInternalRegion().setSort(-400) # self.target.getInternalBuffer().setSort(-399) def voxelizeSceneFromDirection(self, gridPos, direction="x"): """ Voxelizes the scene from a given direction. This method handles setting the camera position aswell as the near and far plane. If the pass was disabled, it also enables this pass. """ assert (direction in ["x", "y", "z"]) self.setActive(True) if direction == "x": self.voxelizeLens.setFilmSize(self.voxelGridSize * 2, self.voxelGridSize * 2) self.voxelizeLens.setNearFar(0.0, self.voxelGridSize * 2) self.voxelizeCameraNode.setPos(gridPos - Vec3(self.voxelGridSize, 0, 0)) self.voxelizeCameraNode.lookAt(gridPos) elif direction == "y": self.voxelizeLens.setFilmSize(self.voxelGridSize * 2, self.voxelGridSize * 2) self.voxelizeLens.setNearFar(0.0, self.voxelGridSize * 2) self.voxelizeCameraNode.setPos(gridPos - Vec3(0, self.voxelGridSize, 0)) self.voxelizeCameraNode.lookAt(gridPos) elif direction == "z": self.voxelizeLens.setFilmSize(self.voxelGridSize * 2, self.voxelGridSize * 2) self.voxelizeLens.setNearFar(0.0, self.voxelGridSize * 2) self.voxelizeCameraNode.setPos(gridPos + Vec3(0, 0, self.voxelGridSize)) self.voxelizeCameraNode.lookAt(gridPos) def setShaders(self): """ Creates the tag state and loades the voxelizer shader """ self.registerTagState("Default", NodePath("DefaultVoxelizeState")) return [] def registerTagState(self, name, state): """ Registers a new tag state """ state.setAttrib(CullFaceAttrib.make(CullFaceAttrib.MCullNone)) state.setDepthWrite(False) state.setDepthTest(False) state.setAttrib(DepthTestAttrib.make(DepthTestAttrib.MNone)) state.setShaderInput("voxelizeCam", self.voxelizeCameraNode) self.voxelizeCamera.setTagState(name, state.getState()) def setShaderInput(self, *args): Globals.base.render.setShaderInput(*args) def getOutputs(self): return {}