コード例 #1
0
def color_region(request, graphics_pipe):
    """Creates and returns a DisplayRegion with a depth buffer."""

    engine = core.GraphicsEngine()
    engine.set_threading_model("")

    # Vulkan needs no host window.
    if graphics_pipe.get_interface_name() != "Vulkan":
        host_fbprops = core.FrameBufferProperties()
        host_fbprops.force_hardware = True

        host = engine.make_output(
            graphics_pipe,
            'host',
            0,
            host_fbprops,
            core.WindowProperties.size(32, 32),
            core.GraphicsPipe.BF_refuse_window,
        )
        engine.open_windows()

        if host is None:
            pytest.skip("GraphicsPipe cannot make offscreen buffers")

        host_gsg = host.gsg
    else:
        host = None
        host_gsg = None

    fbprops = core.FrameBufferProperties()
    fbprops.force_hardware = True
    fbprops.set_rgba_bits(8, 8, 8, 8)
    fbprops.srgb_color = request.param

    buffer = engine.make_output(
        graphics_pipe,
        'buffer',
        0,
        fbprops,
        core.WindowProperties.size(32, 32),
        core.GraphicsPipe.BF_refuse_window,
        host_gsg,
        host
    )
    engine.open_windows()

    if buffer is None:
        pytest.skip("Cannot make color buffer")

    if fbprops.srgb_color != buffer.get_fb_properties().srgb_color:
        pytest.skip("Cannot make buffer with required srgb_color setting")

    buffer.set_clear_color_active(True)
    buffer.set_clear_color((0, 0, 0, 1))

    yield buffer.make_display_region()

    if buffer is not None:
        engine.remove_window(buffer)
コード例 #2
0
def depth_region(request, graphics_pipe):
    """Creates and returns a DisplayRegion with a depth buffer."""

    engine = core.GraphicsEngine()
    engine.set_threading_model("")

    # Vulkan needs no host window.
    if graphics_pipe.get_interface_name() != "Vulkan":
        host_fbprops = core.FrameBufferProperties()
        host_fbprops.force_hardware = True

        host = engine.make_output(
            graphics_pipe,
            'host',
            0,
            host_fbprops,
            core.WindowProperties.size(32, 32),
            core.GraphicsPipe.BF_refuse_window,
        )
        engine.open_windows()

        if host is None:
            pytest.skip("GraphicsPipe cannot make offscreen buffers")

        host_gsg = host.gsg
    else:
        host = None
        host_gsg = None

    fbprops = core.FrameBufferProperties()
    fbprops.force_hardware = True
    fbprops.depth_bits = request.param

    if fbprops.depth_bits >= 32:
        fbprops.float_depth = True

    buffer = engine.make_output(graphics_pipe, 'buffer', 0, fbprops,
                                core.WindowProperties.size(32, 32),
                                core.GraphicsPipe.BF_refuse_window, host_gsg,
                                host)
    engine.open_windows()

    if buffer is None:
        pytest.skip("Cannot make depth buffer")

    if buffer.get_fb_properties().depth_bits != request.param:
        pytest.skip("Could not make buffer with desired bit count")

    yield buffer.make_display_region()

    if buffer is not None:
        engine.remove_window(buffer)
コード例 #3
0
    def _make_buffer(self, width, height):
        """Make an offscreen buffer.

        Arguments:
            width {int} -- target buffer width
            height {int} -- target buffer height
        """
        fb_prop = p3d.FrameBufferProperties(
            p3d.FrameBufferProperties.get_default())
        fb_prop.set_multisamples(self._multisamples)
        fb_prop.set_srgb_color(self._srgb_color)

        self._buffer = self._engine.make_output(
            self._pipe,
            name="offscreen",
            sort=0,
            fb_prop=p3d.FrameBufferProperties.get_default(),
            win_prop=p3d.WindowProperties(size=(width, height)),
            flags=p3d.GraphicsPipe.BFRefuseWindow)

        self._region = self._buffer.make_display_region()

        self._depth_tex = p3d.Texture()
        self._depth_tex.setFormat(p3d.Texture.FDepthComponent)
        self._buffer.addRenderTexture(self._depth_tex,
                                      p3d.GraphicsOutput.RTMCopyRam,
                                      p3d.GraphicsOutput.RTPDepth)

        self._color_tex = p3d.Texture()
        self._color_tex.setFormat(p3d.Texture.FRgba8)
        self._buffer.addRenderTexture(self._color_tex,
                                      p3d.GraphicsOutput.RTMCopyRam,
                                      p3d.GraphicsOutput.RTPColor)
コード例 #4
0
def window(pipe, engine):
    fbprops = p3d.FrameBufferProperties()
    fbprops.set_rgba_bits(8, 8, 8, 0)
    fbprops.set_depth_bits(24)
    winprops = p3d.WindowProperties.size(4, 3)
    flags = p3d.GraphicsPipe.BF_refuse_window
    return engine.make_output(pipe, 'window', 0, fbprops, winprops, flags)
コード例 #5
0
    def make_offscreen(self, sizex, sizey):
        sizex = p3d.Texture.up_to_power_2(sizex)
        sizey = p3d.Texture.up_to_power_2(sizey)

        if self.win and self.win.get_size()[0] == sizex and self.win.get_size(
        )[1] == sizey:
            # The current window is good, don't waste time making a new one
            return

        use_frame_rate_meter = self.frameRateMeter is not None
        self.setFrameRateMeter(False)

        self.graphicsEngine.remove_all_windows()
        self.win = None
        self.view_region = None

        # First try to create a 24bit buffer to minimize copy times
        fbprops = p3d.FrameBufferProperties()
        fbprops.set_rgba_bits(8, 8, 8, 0)
        fbprops.set_depth_bits(24)
        winprops = p3d.WindowProperties.size(sizex, sizey)
        flags = p3d.GraphicsPipe.BF_refuse_window
        #flags = p3d.GraphicsPipe.BF_require_window
        self.win = self.graphicsEngine.make_output(self.pipe, 'window', 0,
                                                   fbprops, winprops, flags)

        if self.win is None:
            # Try again with an alpha channel this time (32bit buffer)
            fbprops.set_rgba_bits(8, 8, 8, 8)
            self.win = self.graphicsEngine.make_output(self.pipe, 'window', 0,
                                                       fbprops, winprops,
                                                       flags)

        if self.win is None:
            print('Unable to open window')
            sys.exit(-1)

        disp_region = self.win.make_mono_display_region()
        disp_region.set_camera(self.cam)
        disp_region.set_active(True)
        disp_region.set_clear_color_active(True)
        disp_region.set_clear_color(self.bg_color)
        disp_region.set_clear_depth(1.0)
        disp_region.set_clear_depth_active(True)
        self.view_region = disp_region
        self.graphicsEngine.open_windows()

        self.setFrameRateMeter(use_frame_rate_meter)

        self.update_rman()

        self.texture = p3d.Texture()
        self.win.addRenderTexture(self.texture,
                                  p3d.GraphicsOutput.RTM_copy_ram)
コード例 #6
0
def test_multiple_targets(graphics_context):
    prepared = graphics_context['window'].get_gsg().get_prepared_objects()
    initial_texture_count = prepared.get_num_prepared_textures()

    graphics_context['frame_buffer_properties'] = p3d.FrameBufferProperties()
    graphics_context['frame_buffer_properties'].set_rgb_color(True)
    graphics_context['frame_buffer_properties'].set_aux_rgba(1)
    rpass = lionrender.Pass('test', **graphics_context)
    graphics_context['engine'].render_frame()

    assert len(rpass.outputs) == 2
    assert prepared.get_num_prepared_textures() == initial_texture_count + 2
コード例 #7
0
    def __init__(
            self,
            name='depth-scene-pass',
            depth_bits=32,
            **pass_options
    ):
        fb_props = p3d.FrameBufferProperties()
        fb_props.set_depth_bits(depth_bits)
        fb_props.set_rgba_bits(0, 0, 0, 0)

        options = {
            'frame_buffer_properties': fb_props,
        }

        options.update(pass_options)
        super().__init__(name, **options)
コード例 #8
0
ファイル: ModelBrowser.py プロジェクト: tsp-team/panda3d
    def __init__(self, parent):
        AssetBrowser.__init__(self, parent)

        self.currentLoadContext = None

        # Set up an offscreen buffer to render the thumbnails of our models.

        props = core.WindowProperties()
        props.setSize(96, 96)
        fbprops = core.FrameBufferProperties()
        fbprops.setSrgbColor(True)
        fbprops.setRgbaBits(8, 8, 8, 0)
        flags = (core.GraphicsPipe.BFRefuseWindow
                 | core.GraphicsPipe.BFSizeSquare)
        self.buffer = base.graphicsEngine.makeOutput(base.pipe,
                                                     "modelBrowserBuffer", 0,
                                                     fbprops, props, flags,
                                                     None, None)
        gsg = self.buffer.getGsg()
        self.buffer.setClearColor(
            BSPUtils.vec3GammaToLinear(
                core.Vec4(82 / 255.0, 82 / 255.0, 82 / 255.0, 1.0)))
        self.buffer.setActive(False)

        self.displayRegion = self.buffer.makeDisplayRegion()

        self.render = core.NodePath("modelBrowserRoot")
        self.render.setShaderAuto()

        camNode = core.Camera("modelBrowserRenderCam")
        lens = core.PerspectiveLens()
        lens.setFov(40)
        camNode.setLens(lens)
        self.lens = lens
        self.camera = self.render.attachNewNode(camNode)
        # Isometric camera angle
        self.camera.setHpr(225, -30, 0)

        self.displayRegion.setCamera(self.camera)

        shgen = BSPShaderGenerator(self.buffer, gsg, self.camera, self.render)
        gsg.setShaderGenerator(shgen)
        for shader in ShaderGlobals.getShaders():
            shgen.addShader(shader)
        self.shaderGenerator = shgen

        base.graphicsEngine.openWindows()
コード例 #9
0
    def make_offscreen(self, sx, sy):
        sx = p3d.Texture.up_to_power_2(sx)
        sy = p3d.Texture.up_to_power_2(sy)

        if self.win and self.win.get_size()[0] == sx and self.win.get_size()[1] == sy:
            # The current window is good, don't waste time making a new one
            return

        use_frame_rate_meter = self.frameRateMeter is not None
        self.setFrameRateMeter(False)

        self.graphicsEngine.remove_all_windows()
        self.win = None
        self.view_region = None

        fbprops = p3d.FrameBufferProperties()
        fbprops.set_srgb_color(True)
        fbprops.set_rgba_bits(8, 8, 8, 0)
        fbprops.set_depth_bits(24)
        wp = p3d.WindowProperties.size(sx, sy)
        flags = p3d.GraphicsPipe.BF_refuse_window
        #flags = p3d.GraphicsPipe.BF_require_window
        self.win = self.graphicsEngine.make_output(
                self.pipe,
                'window',
                0,
                fbprops,
                wp,
                flags
        )

        dr = self.win.make_mono_display_region()
        dr.set_camera(self.cam)
        dr.set_active(True)
        dr.set_clear_color_active(True)
        dr.set_clear_color(self.bg)
        dr.set_clear_depth(1.0)
        dr.set_clear_depth_active(True)
        self.view_region = dr
        self.graphicsEngine.open_windows()

        self.setFrameRateMeter(use_frame_rate_meter)

        self.texture = p3d.Texture()
        self.win.addRenderTexture(self.texture, p3d.GraphicsOutput.RTM_copy_ram)
コード例 #10
0
 def makeFBO(self, name, auxrgba):
     # This routine creates an offscreen buffer.  All the complicated
     # parameters are basically demanding capabilities from the offscreen
     # buffer - we demand that it be able to render to texture on every
     # bitplane, that it can support aux bitplanes, that it track
     # the size of the host window, that it can render to texture
     # cumulatively, and so forth.
     winprops = p3dc.WindowProperties()
     props = p3dc.FrameBufferProperties()
     props.setRgbColor(True)
     props.setRgbaBits(8, 8, 8, 8)
     props.setDepthBits(1)
     props.setAuxRgba(auxrgba)
     return self.graphicsEngine.makeOutput(
         self.pipe, "model buffer", -2, props, winprops,
         p3dc.GraphicsPipe.BFSizeTrackHost
         | p3dc.GraphicsPipe.BFCanBindEvery
         | p3dc.GraphicsPipe.BFRttCumulative
         | p3dc.GraphicsPipe.BFRefuseWindow, self.win.getGsg(), self.win)
コード例 #11
0
    def _make_offscreen(self, sx, sy):
        fbprops = p3d.FrameBufferProperties(p3d.FrameBufferProperties.get_default())
        fbprops.set_srgb_color(True)
        fbprops.set_alpha_bits(0)
        wp = p3d.WindowProperties.size(sx, sy)
        flags = p3d.GraphicsPipe.BF_require_callback_window
        self.win = self.engine.make_output(self.pipe, 'viewport', 0, fbprops, wp, flags)
        self.win.disable_clears()

        def render_cb(cbdata):
            cbdata.upcall()
            cbdata.set_render_flag(True)
        self.win.set_render_callback(p3d.PythonCallbackObject(render_cb))

        dr = self.win.make_mono_display_region()
        dr.set_camera(self.view_camera)
        dr.set_active(True)
        dr.set_clear_color_active(True)
        dr.set_clear_depth(1.0)
        dr.set_clear_depth_active(True)
        self.view_region = dr
コード例 #12
0
    def _setup_tonemapping(self):
        if self._shader_ready:
            # Destroy previous buffers so we can re-create
            self.manager.cleanup()

            # Fix shadow buffers after FilterManager.cleanup()
            for casternp in self.render_node.find_all_matches(
                    '**/+LightLensNode'):
                caster = casternp.node()
                if caster.is_shadow_caster():
                    # caster.set_shadow_caster(False)
                    # caster.set_shadow_caster(True)
                    sbuff_size = caster.get_shadow_buffer_size()
                    caster.set_shadow_buffer_size((0, 0))
                    caster.set_shadow_buffer_size(sbuff_size)

        fbprops = p3d.FrameBufferProperties()
        fbprops.float_color = True
        fbprops.set_rgba_bits(16, 16, 16, 16)
        fbprops.set_depth_bits(24)
        fbprops.set_multisamples(self.msaa_samples)
        scene_tex = p3d.Texture()
        scene_tex.set_format(p3d.Texture.F_rgba16)
        scene_tex.set_component_type(p3d.Texture.T_float)
        self.tonemap_quad = self.manager.render_scene_into(colortex=scene_tex,
                                                           fbprops=fbprops)

        post_vert_str = _load_shader_str('post.vert')
        post_frag_str = _load_shader_str('tonemap.frag')
        tonemap_shader = p3d.Shader.make(
            p3d.Shader.SL_GLSL,
            vertex=post_vert_str,
            fragment=post_frag_str,
        )
        self.tonemap_quad.set_shader(tonemap_shader)
        self.tonemap_quad.set_shader_input('tex', scene_tex)
        self.tonemap_quad.set_shader_input('exposure', self.exposure)
コード例 #13
0
    def _setup_tonemapping(self):
        if self._shader_ready:
            # Destroy previous buffers so we can re-create
            self.manager.cleanup()

            # Fix shadow buffers after FilterManager.cleanup()
            for caster in self.get_all_casters():
                sbuff_size = caster.get_shadow_buffer_size()
                caster.set_shadow_buffer_size((0, 0))
                caster.set_shadow_buffer_size(sbuff_size)

        fbprops = p3d.FrameBufferProperties()
        fbprops.float_color = True
        fbprops.set_rgba_bits(16, 16, 16, 16)
        fbprops.set_depth_bits(24)
        fbprops.set_multisamples(self.msaa_samples)
        scene_tex = p3d.Texture()
        scene_tex.set_format(p3d.Texture.F_rgba16)
        scene_tex.set_component_type(p3d.Texture.T_float)
        self.tonemap_quad = self.manager.render_scene_into(colortex=scene_tex,
                                                           fbprops=fbprops)

        defines = {}
        if self.use_330:
            defines['USE_330'] = ''

        post_vert_str = _load_shader_str('post.vert', defines)
        post_frag_str = _load_shader_str('tonemap.frag', defines)
        tonemap_shader = p3d.Shader.make(
            p3d.Shader.SL_GLSL,
            vertex=post_vert_str,
            fragment=post_frag_str,
        )
        self.tonemap_quad.set_shader(tonemap_shader)
        self.tonemap_quad.set_shader_input('tex', scene_tex)
        self.tonemap_quad.set_shader_input('exposure', self.exposure)
コード例 #14
0
ファイル: app.py プロジェクト: rdb/hexima
    def setup_filters(self):
        fbprops = core.FrameBufferProperties()
        if self.quality >= 3:
            fbprops.multisamples = 16

        self.filters = FilterManager(base.win, base.cam)
        self.scene_tex = core.Texture()
        self.scene_tex.set_wrap_u(core.Texture.WM_clamp)
        self.scene_tex.set_wrap_v(core.Texture.WM_clamp)
        self.quad = self.filters.render_scene_into(colortex=self.scene_tex, fbprops=fbprops)

        if not self.quad and fbprops.multisamples:
            # Try without multisampling.
            fbprops.multisamples = None
            self.quad = self.filters.render_scene_into(colortex=self.scene_tex)
            if not self.quad:
                return

        if fbprops.multisamples:
            self.render.set_antialias(core.AntialiasAttrib.M_multisample)

        self.quad.clear_color()

        prev_tex = self.scene_tex

        if self.quality >= 3:
            intermediate_tex = core.Texture()
            intermediate_tex.set_minfilter(core.Texture.FT_linear)
            intermediate_tex.set_magfilter(core.Texture.FT_linear)
            intermediate_tex.set_wrap_u(core.Texture.WM_clamp)
            intermediate_tex.set_wrap_v(core.Texture.WM_clamp)
            intermediate_quad = self.filters.render_quad_into("blur-x", colortex=intermediate_tex)
            intermediate_quad.set_shader_input("image", prev_tex)
            intermediate_quad.set_shader_input("direction", (2, 0))
            intermediate_quad.set_shader_input("scale", self.blur_scale)
            intermediate_quad.set_shader(self.blur_shader)
            prev_tex = intermediate_tex

            intermediate_tex = core.Texture()
            intermediate_tex.set_minfilter(core.Texture.FT_linear)
            intermediate_tex.set_magfilter(core.Texture.FT_linear)
            intermediate_tex.set_wrap_u(core.Texture.WM_clamp)
            intermediate_tex.set_wrap_v(core.Texture.WM_clamp)
            intermediate_quad = self.filters.render_quad_into("blur-y", colortex=intermediate_tex)
            intermediate_quad.set_shader_input("image", prev_tex)
            intermediate_quad.set_shader_input("direction", (0, 2))
            intermediate_quad.set_shader_input("scale", self.blur_scale)
            intermediate_quad.set_shader(self.blur_shader)
            prev_tex = intermediate_tex

        intermediate_tex = core.Texture()
        intermediate_tex.set_minfilter(core.Texture.FT_linear)
        intermediate_tex.set_magfilter(core.Texture.FT_linear)
        intermediate_tex.set_wrap_u(core.Texture.WM_clamp)
        intermediate_tex.set_wrap_v(core.Texture.WM_clamp)
        intermediate_quad = self.filters.render_quad_into("blur-y", colortex=intermediate_tex)
        intermediate_quad.set_shader_input("image", prev_tex)
        intermediate_quad.set_shader_input("direction", (0, 4))
        intermediate_quad.set_shader_input("scale", self.blur_scale)
        intermediate_quad.set_shader(self.blur_shader)
        prev_tex = intermediate_tex

        self.blurred_tex = prev_tex
コード例 #15
0
ファイル: __init__.py プロジェクト: rdb/panda3d-simplepbr
def init(*,
         render_node=None,
         window=None,
         camera_node=None,
         msaa_samples=4,
         max_lights=8,
         use_normal_maps=False):
    '''Initialize the PBR render pipeline
    :param render_node: The node to attach the shader too, defaults to `base.render` if `None`
    :type render_node: `panda3d.core.NodePath`
    :param window: The window to attach the framebuffer too, defaults to `base.win` if `None`
    :type window: `panda3d.core.GraphicsOutput
    :param camera_node: The NodePath of the camera to use when rendering the scene, defaults to `base.cam` if `None`
    :type camera_node: `panda3d.core.NodePath
    :param msaa_samples: The number of samples to use for multisample anti-aliasing, defaults to 4
    :type msaa_samples: int
    :param max_lights: The maximum number of lights to render, defaults to 8
    :type max_lights: int
    :param use_normal_maps: Use normal maps, defaults to `False` (NOTE: Requires models with appropriate tangents)
    :type use_normal_maps: bool
    '''

    if render_node is None:
        render_node = base.render

    if window is None:
        window = base.win

    if camera_node is None:
        camera_node = base.cam

    # Do not force power-of-two textures
    p3d.Texture.set_textures_power_2(p3d.ATS_none)

    # PBR shader
    pbr_defines = {
        'MAX_LIGHTS': max_lights,
    }
    if use_normal_maps:
        pbr_defines['USE_NORMAL_MAP'] = ''

    pbr_vert_str = _load_shader_str('simplepbr.vert', pbr_defines)
    pbr_frag_str = _load_shader_str('simplepbr.frag', pbr_defines)
    pbrshader = p3d.Shader.make(
        p3d.Shader.SL_GLSL,
        vertex=pbr_vert_str,
        fragment=pbr_frag_str,
    )
    render_node.set_shader(pbrshader)

    # Tonemapping
    manager = FilterManager(window, camera_node)
    fbprops = p3d.FrameBufferProperties()
    fbprops.float_color = True
    fbprops.set_rgba_bits(16, 16, 16, 16)
    fbprops.set_depth_bits(24)
    fbprops.set_multisamples(msaa_samples)
    scene_tex = p3d.Texture()
    scene_tex.set_format(p3d.Texture.F_rgba16)
    scene_tex.set_component_type(p3d.Texture.T_float)
    tonemap_quad = manager.render_scene_into(colortex=scene_tex,
                                             fbprops=fbprops)

    post_vert_str = _load_shader_str('post.vert')
    post_frag_str = _load_shader_str('tonemap.frag')
    tonemap_shader = p3d.Shader.make(
        p3d.Shader.SL_GLSL,
        vertex=post_vert_str,
        fragment=post_frag_str,
    )
    tonemap_quad.set_shader(tonemap_shader)
    tonemap_quad.set_shader_input('tex', scene_tex)
コード例 #16
0
def init(*,
         render_node=None,
         window=None,
         camera_node=None,
         msaa_samples=4,
         max_lights=8):
    '''Initialize the PBR render pipeline
    :param render_node: The node to attach the shader too, defaults to `base.render` if `None`
    :type render_node: `panda3d.core.NodePath`
    :param window: The window to attach the framebuffer too, defaults to `base.win` if `None`
    :type window: `panda3d.core.GraphicsOutput
    :param camera_node: The NodePath of the camera to use when rendering the scene, defaults to `base.cam` if `None`
    :type camera_node: `panda3d.core.NodePath
    '''

    if render_node is None:
        render_node = base.render

    if window is None:
        window = base.win

    if camera_node is None:
        camera_node = base.cam

    # Do not force power-of-two textures
    p3d.Texture.set_textures_power_2(p3d.ATS_none)

    # PBR shader
    pbr_vert_str = _load_shader_str('simplepbr.vert')
    pbr_frag_str = _load_shader_str('simplepbr.frag', {
        'MAX_LIGHTS': max_lights,
    })
    pbrshader = p3d.Shader.make(
        p3d.Shader.SL_GLSL,
        vertex=pbr_vert_str,
        fragment=pbr_frag_str,
    )
    render_node.set_shader(pbrshader)

    # Tonemapping
    manager = FilterManager(window, camera_node)
    fbprops = p3d.FrameBufferProperties()
    fbprops.float_color = True
    fbprops.set_rgba_bits(16, 16, 16, 16)
    fbprops.set_depth_bits(24)
    fbprops.set_multisamples(msaa_samples)
    scene_tex = p3d.Texture()
    scene_tex.set_format(p3d.Texture.F_rgba16)
    scene_tex.set_component_type(p3d.Texture.T_float)
    tonemap_quad = manager.render_scene_into(colortex=scene_tex,
                                             fbprops=fbprops)

    post_vert_str = _load_shader_str('post.vert')
    post_frag_str = _load_shader_str('tonemap.frag')
    tonemap_shader = p3d.Shader.make(
        p3d.Shader.SL_GLSL,
        vertex=post_vert_str,
        fragment=post_frag_str,
    )
    tonemap_quad.set_shader(tonemap_shader)
    tonemap_quad.set_shader_input('tex', scene_tex)
コード例 #17
0
    def setup_fafnir(self):
        self.fafnir_np = p3d.NodePath(p3d.PandaNode("Fafnir"))
        global_shader = p3d.Shader.load(
            p3d.Shader.SL_GLSL,
            vertex="shaders/build_mesh_cache.vs",
            geometry="shaders/build_mesh_cache.gs",
            fragment="shaders/generate_primary_intersections.fs",
        )
        self.fafnir_np.set_shader(global_shader)
        self.mesh_cache = MeshCache(1, 1)
        self.material_cache = MaterialCache()
        self.draw_manager = DrawManager(self.fafnir_np)

        win_width = self.win.get_x_size()
        win_height = self.win.get_y_size()
        rtt_fb_prop = p3d.FrameBufferProperties()
        rtt_fb_prop.set_rgba_bits(32, 32, 32, 32)
        rtt_fb_prop.set_float_color(True)
        rtt_fb_prop.set_depth_bits(32)
        rtt_win_prop = p3d.WindowProperties().size(win_width, win_height)
        rtt_buffer = base.graphics_engine.make_output(
            base.pipe, 'Fafnir RTT Buffer', -100, rtt_fb_prop, rtt_win_prop,
            p3d.GraphicsPipe.BF_refuse_window, base.win.get_gsg(), base.win)
        intersection_texture = p3d.Texture()
        rtt_buffer.add_render_texture(intersection_texture,
                                      p3d.GraphicsOutput.RTM_bind_or_copy,
                                      p3d.GraphicsOutput.RTP_color)
        rtt_cam = base.make_camera(rtt_buffer)
        rtt_cam.reparent_to(self.fafnir_np)

        vdata = p3d.GeomVertexData('empty', p3d.GeomVertexFormat.get_empty(),
                                   p3d.GeomEnums.UH_static)
        resolve_shader = p3d.Shader.load(
            p3d.Shader.SL_GLSL,
            vertex='shaders/resolve_intersections.vs',
            fragment='shaders/resolve_intersections.fs')

        self.int_texture = intersection_texture
        self.draw_manager.set_inputs(self.int_texture,
                                     self.material_cache.count_texture)

        self.temp_nps = []

        def cb_update_draw_calls(cbdata):
            for np in self.temp_nps:
                np.remove_node()
            self.temp_nps = []

            tex = self.draw_manager._indirect_buffer
            gsg = self.win.get_gsg()
            if self.graphics_engine.extract_texture_data(tex, gsg):
                tex_view = memoryview(tex.get_ram_image()).cast('i')
                for call_idx in range(tex.get_x_size()):
                    i = call_idx * 4
                    primcount = tex_view[i + 1]
                    first = tex_view[i + 2]

                    prims = p3d.GeomPoints(p3d.GeomEnums.UH_dynamic)
                    prims.add_next_vertices(primcount)
                    geom = p3d.Geom(vdata)
                    geom.add_primitive(prims)
                    geom.set_bounds(p3d.OmniBoundingVolume())
                    node = p3d.GeomNode('Draw Call {}'.format(call_idx))
                    node.add_geom(geom)
                    path = p3d.NodePath(node)
                    path.set_bin('fixed', 50)
                    path.set_depth_test(False)
                    path.set_depth_write(False)
                    path.set_shader(resolve_shader)
                    path.set_shader_input('first', first)
                    window_size = p3d.LVector2i(win_width, win_height)
                    path.set_shader_input('window_size', window_size)
                    path.set_shader_input('vertex_cache',
                                          self.mesh_cache.vert_texture)
                    path.set_shader_input('index_cache',
                                          self.mesh_cache.index_texture)
                    path.set_shader_input('intersections', self.int_texture)
                    self.material_cache.bind(path)
                    path.reparent_to(self.render)
                    self.temp_nps.append(path)
            cbdata.upcall()

        cbnode = p3d.CallbackNode('UpdateDrawCalls')
        cbnode.set_draw_callback(
            p3d.PythonCallbackObject(cb_update_draw_calls))
        cb_np = self.render.attach_new_node(cbnode)
        cb_np.set_bin('fixed', 45)

        # taskMgr.add(task_update_draw_calls, 'Update Draw Calls', sort=55)

        def task_fafnir(task):
            # node_paths = self.fafnir_np.find_all_matches('**/+GeomNode')
            # self.material_list = self.fafnir_np.find_all_materials()
            # self.mesh_cache.update(self.node_paths)
            # self.mesh_cache.bind(self.fafnir_np)
            self.material_cache.update(self.material_list, self.node_paths)
            win_width = self.win.get_x_size()
            win_height = self.win.get_y_size()
            self.draw_manager.update(len(self.material_list), win_width,
                                     win_height)
            return task.cont

        taskMgr.add(task_fafnir, 'Gather mesh data')

        def read_texture():
            tex = self.draw_manager._indirect_buffer
            gsg = self.win.get_gsg()
            if self.graphics_engine.extract_texture_data(
                    tex, self.win.get_gsg()):
                view = memoryview(tex.get_ram_image()).cast('i')
                for i in range(16):
                    if i % 4 == 0:
                        print()
                    print(view[i])
                # success = tex.write(p3d.Filename('vertex_cache.png'))
                # print('Texture write: ', success)
            else:
                print('texture has no RAM image')

        self.accept('f1', read_texture)
コード例 #18
0
 def _make_default_buffer_props(self):
     fb_props = p3d.FrameBufferProperties()
     fb_props.set_rgb_color(True)
     fb_props.set_rgba_bits(8, 8, 8, 0)
     fb_props.set_depth_bits(24)
     return fb_props
コード例 #19
0
    def __init__(self):
        # Preliminary capabilities check.

        if not ape.base().win.getGsg().getSupportsBasicShaders():
            self.t = addTitle(
                "Shadow Demo: Video driver reports that shaders are not supported."
            )
            return
        if not ape.base().win.getGsg().getSupportsDepthTexture():
            self.t = addTitle(
                "Shadow Demo: Video driver reports that depth textures are not supported."
            )
            return

        # creating the offscreen buffer.

        winprops = p3dc.WindowProperties(size=(512, 512))
        props = p3dc.FrameBufferProperties()
        props.setRgbColor(1)
        props.setAlphaBits(1)
        props.setDepthBits(1)
        LBuffer = ape.base().graphicsEngine.makeOutput(
            ape.base().pipe, "offscreen buffer", -2, props, winprops,
            p3dc.GraphicsPipe.BFRefuseWindow,
            ape.base().win.getGsg(),
            ape.base().win)
        self.buffer = LBuffer

        if not LBuffer:
            self.t = addTitle(
                "Shadow Demo: Video driver cannot create an offscreen buffer.")
            return

        Ldepthmap = p3dc.Texture()
        LBuffer.addRenderTexture(Ldepthmap, p3dc.GraphicsOutput.RTMBindOrCopy,
                                 p3dc.GraphicsOutput.RTPDepthStencil)
        if ape.base().win.getGsg().getSupportsShadowFilter():
            Ldepthmap.setMinfilter(p3dc.Texture.FTShadow)
            Ldepthmap.setMagfilter(p3dc.Texture.FTShadow)

        # Adding a color texture is totally unnecessary, but it helps with
        # debugging.
        Lcolormap = p3dc.Texture()
        LBuffer.addRenderTexture(Lcolormap, p3dc.GraphicsOutput.RTMBindOrCopy,
                                 p3dc.GraphicsOutput.RTPColor)

        self.inst_p = addInstructions(0.06,
                                      'P : stop/start the Panda Rotation')
        self.inst_w = addInstructions(0.12, 'W : stop/start the Walk Cycle')
        self.inst_t = addInstructions(0.18, 'T : stop/start the Teapot')
        self.inst_l = addInstructions(0.24,
                                      'L : move light source far or close')
        self.inst_v = addInstructions(0.30,
                                      'V : View the Depth-Texture results')
        self.inst_u = addInstructions(0.36,
                                      'U : toggle updating the shadow map')
        self.inst_x = addInstructions(
            0.42, 'Left/Right Arrow : switch camera angles')
        self.inst_a = addInstructions(0.48,
                                      'Something about A/Z and push bias')

        ape.base().setBackgroundColor(0, 0, 0.2, 1)

        ape.base().camLens.setNearFar(1.0, 10000)
        ape.base().camLens.setFov(75)
        ape.base().disableMouse()

        # Load the scene.

        floorTex = ape.loader().loadTexture('maps/envir-ground.jpg')
        cm = p3dc.CardMaker('')
        cm.setFrame(-2, 2, -2, 2)
        floor = ape.render().attachNewNode(p3dc.PandaNode("floor"))
        for y in range(12):
            for x in range(12):
                nn = floor.attachNewNode(cm.generate())
                nn.setP(-90)
                nn.setPos((x - 6) * 4, (y - 6) * 4, 0)
        floor.setTexture(floorTex)
        floor.flattenStrong()

        self.pandaAxis = ape.render().attachNewNode('panda axis')
        self.pandaModel = Actor('panda-model', {'walk': 'panda-walk4'})
        self.pandaModel.reparentTo(self.pandaAxis)
        self.pandaModel.setPos(9, 0, 0)
        self.pandaModel.setShaderInput("scale", (0.01, 0.01, 0.01, 1.0))
        self.pandaWalk = self.pandaModel.actorInterval('walk', playRate=1.8)
        self.pandaWalk.loop()
        self.pandaMovement = self.pandaAxis.hprInterval(
            20.0, p3dc.LPoint3(-360, 0, 0), startHpr=p3dc.LPoint3(0, 0, 0))
        self.pandaMovement.loop()

        self.teapot = ape.loader().loadModel('teapot')
        self.teapot.reparentTo(ape.render())
        self.teapot.setPos(0, -20, 10)
        self.teapot.setShaderInput("texDisable", (1, 1, 1, 1))
        self.teapotMovement = self.teapot.hprInterval(
            50, p3dc.LPoint3(0, 360, 360))
        self.teapotMovement.loop()

        self.accept('escape', sys.exit)

        self.accept("arrow_left", self.incrementCameraPosition, [-1])
        self.accept("arrow_right", self.incrementCameraPosition, [1])
        self.accept("p", self.toggleInterval, [self.pandaMovement])
        self.accept("t", self.toggleInterval, [self.teapotMovement])
        self.accept("w", self.toggleInterval, [self.pandaWalk])
        self.accept("v", ape.base().bufferViewer.toggleEnable)
        self.accept("u", self.toggleUpdateShadowMap)
        self.accept("l", self.incrementLightPosition, [1])
        self.accept("o", ape.base().oobe)
        self.accept('a', self.adjustPushBias, [1.1])
        self.accept('z', self.adjustPushBias, [0.9])

        self.LCam = ape.base().makeCamera(LBuffer)
        self.LCam.node().setScene(ape.render())
        self.LCam.node().getLens().setFov(40)
        self.LCam.node().getLens().setNearFar(10, 100)

        # default values
        self.pushBias = 0.04
        self.ambient = 0.2
        self.cameraSelection = 0
        self.lightSelection = 0

        # setting up shader
        ape.render().setShaderInput('light', self.LCam)
        ape.render().setShaderInput('Ldepthmap', Ldepthmap)
        ape.render().setShaderInput('ambient', (self.ambient, 0, 0, 1.0))
        ape.render().setShaderInput('texDisable', (0, 0, 0, 0))
        ape.render().setShaderInput('scale', (1, 1, 1, 1))

        # Put a shader on the Light camera.
        lci = p3dc.NodePath(p3dc.PandaNode("Light Camera Initializer"))
        lci.setShader(ape.loader().loadShader('shadows_caster.sha'))
        self.LCam.node().setInitialState(lci.getState())

        # Put a shader on the Main camera.
        # Some video cards have special hardware for shadow maps.
        # If the card has that, use it.  If not, use a different
        # shader that does not require hardware support.

        mci = p3dc.NodePath(p3dc.PandaNode("Main Camera Initializer"))
        if ape.base().win.getGsg().getSupportsShadowFilter():
            mci.setShader(ape.loader().loadShader('shadows_shadow.sha'))
        else:
            mci.setShader(
                ape.loader().loadShader('shadows_shadow-nosupport.sha'))
        ape.base().cam.node().setInitialState(mci.getState())

        self.incrementCameraPosition(0)
        self.incrementLightPosition(0)
        self.adjustPushBias(1.0)