mirror of
https://github.com/panda3d/panda3d.git
synced 2025-10-04 02:42:49 -04:00
Preliminary stencil buffer code.
This commit is contained in:
parent
1a8b8f1756
commit
682065a3e8
@ -31,7 +31,8 @@
|
||||
lru.h \
|
||||
parasiteBuffer.I parasiteBuffer.h \
|
||||
windowProperties.I windowProperties.h \
|
||||
renderBuffer.h
|
||||
renderBuffer.h \
|
||||
stencilRenderStates.h
|
||||
|
||||
#define INCLUDED_SOURCES \
|
||||
standardMunger.cxx \
|
||||
@ -50,7 +51,8 @@
|
||||
graphicsDevice.cxx \
|
||||
parasiteBuffer.cxx \
|
||||
windowProperties.cxx \
|
||||
lru.cxx
|
||||
lru.cxx \
|
||||
stencilRenderStates.cxx
|
||||
|
||||
#define INSTALL_HEADERS \
|
||||
standardMunger.I standardMunger.h \
|
||||
@ -72,7 +74,8 @@
|
||||
lru.h \
|
||||
parasiteBuffer.I parasiteBuffer.h \
|
||||
windowProperties.I windowProperties.h \
|
||||
renderBuffer.h
|
||||
renderBuffer.h \
|
||||
stencilRenderStates.h
|
||||
|
||||
#define IGATESCAN all
|
||||
|
||||
|
@ -9,3 +9,4 @@
|
||||
#include "graphicsOutput.cxx"
|
||||
#include "parasiteBuffer.cxx"
|
||||
#include "lru.cxx"
|
||||
#include "stencilRenderStates.cxx"
|
||||
|
@ -538,6 +538,17 @@ get_supports_basic_shaders() const {
|
||||
return _supports_basic_shaders;
|
||||
}
|
||||
|
||||
////////////////////////////////////////////////////////////////////
|
||||
// Function: GraphicsStateGuardian::get_supports_two_sided_stencil
|
||||
// Access: Published
|
||||
// Description: Returns true if this particular GSG supports
|
||||
// two sided stencil.
|
||||
////////////////////////////////////////////////////////////////////
|
||||
INLINE bool GraphicsStateGuardian::
|
||||
get_supports_two_sided_stencil() const {
|
||||
return _supports_two_sided_stencil;
|
||||
}
|
||||
|
||||
////////////////////////////////////////////////////////////////////
|
||||
// Function: GraphicsStateGuardian::get_color_scale_via_lighting
|
||||
// Access: Published
|
||||
@ -739,3 +750,23 @@ set_current_properties(FrameBufferProperties *prop) {
|
||||
_current_properties = prop;
|
||||
}
|
||||
|
||||
////////////////////////////////////////////////////////////////////
|
||||
// Function: GraphicsStateGuardian::set_stencil_clear_value
|
||||
// Access: Public
|
||||
// Description: Set current stencil clear value.
|
||||
////////////////////////////////////////////////////////////////////
|
||||
INLINE void GraphicsStateGuardian::
|
||||
set_stencil_clear_value(unsigned int stencil_clear_value) {
|
||||
_stencil_clear_value = stencil_clear_value;
|
||||
}
|
||||
|
||||
////////////////////////////////////////////////////////////////////
|
||||
// Function: GraphicsStateGuardian::get_stencil_clear_value
|
||||
// Access: Public
|
||||
// Description: Get current stencil clear value.
|
||||
////////////////////////////////////////////////////////////////////
|
||||
INLINE unsigned int GraphicsStateGuardian::
|
||||
get_stencil_clear_value() {
|
||||
return _stencil_clear_value;
|
||||
}
|
||||
|
||||
|
@ -85,7 +85,7 @@ GraphicsStateGuardian(const FrameBufferProperties &properties,
|
||||
{
|
||||
_coordinate_system = CS_invalid;
|
||||
_internal_transform = TransformState::make_identity();
|
||||
|
||||
|
||||
set_coordinate_system(get_default_coordinate_system());
|
||||
|
||||
_data_reader = (GeomVertexDataPipelineReader *)NULL;
|
||||
@ -94,7 +94,7 @@ GraphicsStateGuardian(const FrameBufferProperties &properties,
|
||||
_current_lens = (Lens *)NULL;
|
||||
_projection_mat = TransformState::make_identity();
|
||||
_projection_mat_inv = TransformState::make_identity();
|
||||
|
||||
|
||||
_needs_reset = true;
|
||||
_is_valid = false;
|
||||
_current_properties = NULL;
|
||||
@ -130,7 +130,7 @@ GraphicsStateGuardian(const FrameBufferProperties &properties,
|
||||
_supports_compressed_texture = false;
|
||||
_compressed_texture_formats.clear();
|
||||
_compressed_texture_formats.set_bit(Texture::CM_off);
|
||||
|
||||
|
||||
// Assume no limits on number of lights or clip planes.
|
||||
_max_lights = -1;
|
||||
_max_clip_planes = -1;
|
||||
@ -152,12 +152,18 @@ GraphicsStateGuardian(const FrameBufferProperties &properties,
|
||||
_supports_depth_texture = false;
|
||||
_supports_shadow_filter = false;
|
||||
_supports_basic_shaders = false;
|
||||
|
||||
_supports_stencil_wrap = false;
|
||||
_supports_two_sided_stencil = false;
|
||||
|
||||
_supported_geom_rendering = 0;
|
||||
|
||||
// If this is true, then we can apply a color and/or color scale by
|
||||
// twiddling the material and/or ambient light (which could mean
|
||||
// enabling lighting even without a LightAttrib).
|
||||
_color_scale_via_lighting = color_scale_via_lighting;
|
||||
|
||||
_stencil_render_states = 0;
|
||||
}
|
||||
|
||||
////////////////////////////////////////////////////////////////////
|
||||
@ -170,6 +176,11 @@ GraphicsStateGuardian::
|
||||
if (_global_gsg == this) {
|
||||
_global_gsg = NULL;
|
||||
}
|
||||
|
||||
if (_stencil_render_states) {
|
||||
delete _stencil_render_states;
|
||||
_stencil_render_states = 0;
|
||||
}
|
||||
}
|
||||
|
||||
////////////////////////////////////////////////////////////////////
|
||||
@ -229,11 +240,11 @@ set_coordinate_system(CoordinateSystem cs) {
|
||||
_inv_cs_transform = TransformState::make_identity();
|
||||
|
||||
} else {
|
||||
_cs_transform =
|
||||
_cs_transform =
|
||||
TransformState::make_mat
|
||||
(LMatrix4f::convert_mat(_coordinate_system,
|
||||
_internal_coordinate_system));
|
||||
_inv_cs_transform =
|
||||
_inv_cs_transform =
|
||||
TransformState::make_mat
|
||||
(LMatrix4f::convert_mat(_internal_coordinate_system,
|
||||
_coordinate_system));
|
||||
@ -276,11 +287,11 @@ reset() {
|
||||
_internal_transform = _cs_transform;
|
||||
_scene_null = new SceneSetup;
|
||||
_scene_setup = _scene_null;
|
||||
|
||||
|
||||
_color_write_mask = ColorWriteAttrib::C_all;
|
||||
_color_clear_value.set(0.0f, 0.0f, 0.0f, 0.0f);
|
||||
_depth_clear_value = 1.0f;
|
||||
_stencil_clear_value = 0.0f;
|
||||
_stencil_clear_value = 0;
|
||||
_accum_clear_value.set(0.0f, 0.0f, 0.0f, 0.0f);
|
||||
|
||||
_has_scene_graph_color = false;
|
||||
@ -305,6 +316,12 @@ reset() {
|
||||
_last_max_stage_index = 0;
|
||||
|
||||
_is_valid = true;
|
||||
|
||||
if (_stencil_render_states) {
|
||||
delete _stencil_render_states;
|
||||
_stencil_render_states = 0;
|
||||
}
|
||||
_stencil_render_states = new StencilRenderStates (this);
|
||||
}
|
||||
|
||||
////////////////////////////////////////////////////////////////////
|
||||
@ -737,7 +754,7 @@ clear(DrawableRegion *clearable) {
|
||||
//
|
||||
// * window size
|
||||
// * texture coordinates of card center
|
||||
//
|
||||
//
|
||||
// This routine can fetch these values as well, by
|
||||
// shoehorning them into a matrix. In this way, we avoid
|
||||
// the need for a separate routine to fetch these values.
|
||||
@ -756,7 +773,7 @@ fetch_specified_value(ShaderContext::ShaderMatSpec &spec, bool altered) {
|
||||
const LMatrix4f *val2;
|
||||
static LMatrix4f t1;
|
||||
static LMatrix4f t2;
|
||||
|
||||
|
||||
switch(spec._func) {
|
||||
case ShaderContext::SMF_compose:
|
||||
val1 = fetch_specified_part(spec._part[0], spec._arg[0], t1);
|
||||
@ -881,6 +898,14 @@ fetch_specified_part(ShaderContext::ShaderMatInput part, InternalName *name, LMa
|
||||
}
|
||||
case ShaderContext::SMO_view_x_to_view: {
|
||||
const ShaderInput *input = _target._shader->get_shader_input(name);
|
||||
|
||||
if (input->get_nodepath().is_empty()) {
|
||||
gsg_cat.error()
|
||||
<< "SHADER INPUT ASSERT: "
|
||||
<< name
|
||||
<< "\n";
|
||||
}
|
||||
|
||||
nassertr(!input->get_nodepath().is_empty(), &LMatrix4f::ident_mat());
|
||||
t = input->get_nodepath().get_net_transform()->get_mat() *
|
||||
get_scene()->get_world_transform()->get_mat();
|
||||
@ -888,6 +913,14 @@ fetch_specified_part(ShaderContext::ShaderMatInput part, InternalName *name, LMa
|
||||
}
|
||||
case ShaderContext::SMO_view_to_view_x: {
|
||||
const ShaderInput *input = _target._shader->get_shader_input(name);
|
||||
|
||||
if (input->get_nodepath().is_empty()) {
|
||||
gsg_cat.error()
|
||||
<< "SHADER INPUT ASSERT: "
|
||||
<< name
|
||||
<< "\n";
|
||||
}
|
||||
|
||||
nassertr(!input->get_nodepath().is_empty(), &LMatrix4f::ident_mat());
|
||||
t = get_scene()->get_camera_transform()->get_mat() *
|
||||
invert(input->get_nodepath().get_net_transform()->get_mat());
|
||||
@ -1032,7 +1065,7 @@ begin_frame(Thread *current_thread) {
|
||||
// be accurately updated.
|
||||
_state_rs = 0;
|
||||
_state.clear_to_zero();
|
||||
|
||||
|
||||
return true;
|
||||
}
|
||||
|
||||
@ -1068,11 +1101,11 @@ begin_scene() {
|
||||
void GraphicsStateGuardian::
|
||||
end_scene() {
|
||||
// We should clear this pointer now, so that we don't keep unneeded
|
||||
// reference counts dangling. We keep around a "null" scene setup
|
||||
// reference counts dangling. We keep around a "null" scene setup
|
||||
// object instead of using a null pointer to avoid special-case code
|
||||
// in set_state_and_transform.
|
||||
_scene_setup = _scene_null;
|
||||
|
||||
|
||||
// Undo any lighting we had enabled last scene, to force the lights
|
||||
// to be reissued, in case their parameters or positions have
|
||||
// changed between scenes.
|
||||
@ -1255,7 +1288,7 @@ finish_decal() {
|
||||
// are ok, false to abort this group of primitives.
|
||||
////////////////////////////////////////////////////////////////////
|
||||
bool GraphicsStateGuardian::
|
||||
begin_draw_primitives(const GeomPipelineReader *geom_reader,
|
||||
begin_draw_primitives(const GeomPipelineReader *geom_reader,
|
||||
const GeomMunger *munger,
|
||||
const GeomVertexDataPipelineReader *data_reader) {
|
||||
_munger = munger;
|
||||
@ -1360,7 +1393,7 @@ do_issue_clip_plane() {
|
||||
for (i = 0; i < cur_max_planes; i++) {
|
||||
_clip_plane_info[i]._next_enabled = false;
|
||||
}
|
||||
|
||||
|
||||
CPT(ClipPlaneAttrib) new_attrib = attrib->filter_to_max(_max_clip_planes);
|
||||
|
||||
bool any_bound = false;
|
||||
@ -1391,7 +1424,7 @@ do_issue_clip_plane() {
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
// See if there are any unbound plane ids
|
||||
if (cur_plane_id == -1) {
|
||||
for (i = 0; i < cur_max_planes; i++) {
|
||||
@ -1402,7 +1435,7 @@ do_issue_clip_plane() {
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
// If there were no unbound plane ids, see if we can replace
|
||||
// a currently unused but previously bound id
|
||||
if (cur_plane_id == -1) {
|
||||
@ -1424,21 +1457,21 @@ do_issue_clip_plane() {
|
||||
nassertv(cur_max_planes == (int)_clip_plane_info.size());
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
if (cur_plane_id >= 0) {
|
||||
enable_clip_plane(cur_plane_id, true);
|
||||
_clip_plane_info[cur_plane_id]._enabled = true;
|
||||
_clip_plane_info[cur_plane_id]._next_enabled = true;
|
||||
|
||||
|
||||
if (!any_bound) {
|
||||
begin_bind_clip_planes();
|
||||
any_bound = true;
|
||||
}
|
||||
|
||||
|
||||
// This is the first time this frame that this plane has been
|
||||
// bound to this particular id.
|
||||
bind_clip_plane(plane, cur_plane_id);
|
||||
|
||||
|
||||
} else if (cur_plane_id == -1) {
|
||||
gsg_cat.warning()
|
||||
<< "Failed to bind " << plane << " to id.\n";
|
||||
@ -1523,7 +1556,7 @@ do_issue_color_scale() {
|
||||
const ColorScaleAttrib *attrib = _target._color_scale;
|
||||
_color_scale_enabled = attrib->has_scale();
|
||||
_current_color_scale = attrib->get_scale();
|
||||
|
||||
|
||||
if (_color_blend_involves_color_scale) {
|
||||
_state_rs = 0;
|
||||
_state._transparency = 0;
|
||||
@ -1583,19 +1616,19 @@ do_issue_light() {
|
||||
NodePath light = new_light->get_on_light(li);
|
||||
nassertv(!light.is_empty() && light.node()->as_light() != (Light *)NULL);
|
||||
Light *light_obj = light.node()->as_light();
|
||||
|
||||
|
||||
num_enabled++;
|
||||
|
||||
|
||||
// Lighting should be enabled before we apply any lights.
|
||||
enable_lighting(true);
|
||||
_lighting_enabled = true;
|
||||
_lighting_enabled_this_frame = true;
|
||||
|
||||
|
||||
if (light_obj->get_type() == AmbientLight::get_class_type()) {
|
||||
// Ambient lights don't require specific light ids; simply add
|
||||
// in the ambient contribution to the current total
|
||||
cur_ambient_light += light_obj->get_color();
|
||||
|
||||
|
||||
} else {
|
||||
// Check to see if this light has already been bound to an id
|
||||
int cur_light_id = -1;
|
||||
@ -1606,7 +1639,7 @@ do_issue_light() {
|
||||
enable_light(i, true);
|
||||
_light_info[i]._enabled = true;
|
||||
_light_info[i]._next_enabled = true;
|
||||
|
||||
|
||||
if (!any_bound) {
|
||||
begin_bind_lights();
|
||||
any_bound = true;
|
||||
@ -1615,7 +1648,7 @@ do_issue_light() {
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
// See if there are any unbound light ids
|
||||
if (cur_light_id == -1) {
|
||||
for (i = 0; i < cur_max_lights; i++) {
|
||||
@ -1626,7 +1659,7 @@ do_issue_light() {
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
// If there were no unbound light ids, see if we can replace
|
||||
// a currently unused but previously bound id
|
||||
if (cur_light_id == -1) {
|
||||
@ -1638,7 +1671,7 @@ do_issue_light() {
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
// If we *still* don't have a light id, slot a new one.
|
||||
if (cur_light_id == -1) {
|
||||
if (_max_lights < 0 || cur_max_lights < _max_lights) {
|
||||
@ -1648,21 +1681,21 @@ do_issue_light() {
|
||||
nassertv(cur_max_lights == (int)_light_info.size());
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
if (cur_light_id >= 0) {
|
||||
enable_light(cur_light_id, true);
|
||||
_light_info[cur_light_id]._enabled = true;
|
||||
_light_info[cur_light_id]._next_enabled = true;
|
||||
|
||||
|
||||
if (!any_bound) {
|
||||
begin_bind_lights();
|
||||
any_bound = true;
|
||||
}
|
||||
|
||||
|
||||
// This is the first time this frame that this light has been
|
||||
// bound to this particular id.
|
||||
light_obj->bind(this, light, cur_light_id);
|
||||
|
||||
|
||||
} else if (cur_light_id == -1) {
|
||||
gsg_cat.warning()
|
||||
<< "Failed to bind " << light << " to id.\n";
|
||||
@ -1670,7 +1703,7 @@ do_issue_light() {
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
// Disable all unused lights
|
||||
for (i = 0; i < cur_max_lights; i++) {
|
||||
if (!_light_info[i]._next_enabled) {
|
||||
@ -1973,7 +2006,7 @@ init_frame_pstats() {
|
||||
_data_transferred_pcollector.clear_level();
|
||||
_vertex_buffer_switch_pcollector.clear_level();
|
||||
_index_buffer_switch_pcollector.clear_level();
|
||||
|
||||
|
||||
_primitive_batches_pcollector.clear_level();
|
||||
_primitive_batches_tristrip_pcollector.clear_level();
|
||||
_primitive_batches_trifan_pcollector.clear_level();
|
||||
@ -1983,7 +2016,7 @@ init_frame_pstats() {
|
||||
_vertices_trifan_pcollector.clear_level();
|
||||
_vertices_tri_pcollector.clear_level();
|
||||
_vertices_other_pcollector.clear_level();
|
||||
|
||||
|
||||
_state_pcollector.clear_level();
|
||||
_transform_state_pcollector.clear_level();
|
||||
_texture_state_pcollector.clear_level();
|
||||
@ -1994,7 +2027,7 @@ init_frame_pstats() {
|
||||
////////////////////////////////////////////////////////////////////
|
||||
// Function: GraphicsStateGuardian::get_unlit_state
|
||||
// Access: Protected, Static
|
||||
// Description:
|
||||
// Description:
|
||||
////////////////////////////////////////////////////////////////////
|
||||
CPT(RenderState) GraphicsStateGuardian::
|
||||
get_unlit_state() {
|
||||
@ -2008,7 +2041,7 @@ get_unlit_state() {
|
||||
////////////////////////////////////////////////////////////////////
|
||||
// Function: GraphicsStateGuardian::get_unclipped_state
|
||||
// Access: Protected, Static
|
||||
// Description:
|
||||
// Description:
|
||||
////////////////////////////////////////////////////////////////////
|
||||
CPT(RenderState) GraphicsStateGuardian::
|
||||
get_unclipped_state() {
|
||||
@ -2022,7 +2055,7 @@ get_unclipped_state() {
|
||||
////////////////////////////////////////////////////////////////////
|
||||
// Function: GraphicsStateGuardian::get_untextured_state
|
||||
// Access: Protected, Static
|
||||
// Description:
|
||||
// Description:
|
||||
////////////////////////////////////////////////////////////////////
|
||||
CPT(RenderState) GraphicsStateGuardian::
|
||||
get_untextured_state() {
|
||||
@ -2043,7 +2076,7 @@ get_untextured_state() {
|
||||
void GraphicsStateGuardian::
|
||||
traverse_prepared_textures(bool (*pertex_callbackfn)(TextureContext *,void *),void *callback_arg) {
|
||||
PreparedGraphicsObjects::Textures::const_iterator ti;
|
||||
for (ti = _prepared_objects->_prepared_textures.begin();
|
||||
for (ti = _prepared_objects->_prepared_textures.begin();
|
||||
ti != _prepared_objects->_prepared_textures.end();
|
||||
++ti) {
|
||||
bool bResult=(*pertex_callbackfn)(*ti,callback_arg);
|
||||
@ -2068,7 +2101,7 @@ calc_projection_mat(const Lens *lens) {
|
||||
if (!lens->is_linear()) {
|
||||
return NULL;
|
||||
}
|
||||
|
||||
|
||||
return TransformState::make_identity();
|
||||
}
|
||||
|
||||
|
@ -47,6 +47,7 @@
|
||||
#include "bitMask.h"
|
||||
#include "texture.h"
|
||||
#include "occlusionQueryContext.h"
|
||||
#include "stencilRenderStates.h"
|
||||
|
||||
class DrawableRegion;
|
||||
class GraphicsEngine;
|
||||
@ -120,11 +121,12 @@ PUBLISHED:
|
||||
INLINE bool get_supports_depth_texture() const;
|
||||
INLINE bool get_supports_shadow_filter() const;
|
||||
INLINE bool get_supports_basic_shaders() const;
|
||||
|
||||
INLINE bool get_supports_two_sided_stencil() const;
|
||||
|
||||
virtual int get_supported_geom_rendering() const;
|
||||
|
||||
INLINE bool get_color_scale_via_lighting() const;
|
||||
|
||||
|
||||
void set_coordinate_system(CoordinateSystem cs);
|
||||
INLINE CoordinateSystem get_coordinate_system() const;
|
||||
virtual CoordinateSystem get_internal_coordinate_system() const;
|
||||
@ -147,7 +149,7 @@ public:
|
||||
|
||||
virtual ShaderContext *prepare_shader(ShaderExpansion *shader);
|
||||
virtual void release_shader(ShaderContext *sc);
|
||||
|
||||
|
||||
virtual VertexBufferContext *prepare_vertex_buffer(GeomVertexArrayData *data);
|
||||
virtual void release_vertex_buffer(VertexBufferContext *vbc);
|
||||
|
||||
@ -158,7 +160,7 @@ public:
|
||||
virtual void begin_occlusion_query();
|
||||
virtual PT(OcclusionQueryContext) end_occlusion_query();
|
||||
|
||||
virtual PT(GeomMunger) get_geom_munger(const RenderState *state,
|
||||
virtual PT(GeomMunger) get_geom_munger(const RenderState *state,
|
||||
Thread *current_thread);
|
||||
virtual PT(GeomMunger) make_geom_munger(const RenderState *state,
|
||||
Thread *current_thread);
|
||||
@ -176,7 +178,7 @@ public:
|
||||
|
||||
const LMatrix4f *fetch_specified_value(ShaderContext::ShaderMatSpec &spec, bool altered);
|
||||
const LMatrix4f *fetch_specified_part(ShaderContext::ShaderMatInput input, InternalName *name, LMatrix4f &t);
|
||||
|
||||
|
||||
virtual void prepare_display_region(DisplayRegionPipelineReader *dr,
|
||||
Lens::StereoChannel stereo_channel);
|
||||
|
||||
@ -189,14 +191,14 @@ public:
|
||||
virtual void end_frame(Thread *current_thread);
|
||||
|
||||
void set_current_properties(FrameBufferProperties *properties);
|
||||
|
||||
|
||||
virtual bool depth_offset_decals();
|
||||
virtual CPT(RenderState) begin_decal_base_first();
|
||||
virtual CPT(RenderState) begin_decal_nested();
|
||||
virtual CPT(RenderState) begin_decal_base_second();
|
||||
virtual void finish_decal();
|
||||
|
||||
virtual bool begin_draw_primitives(const GeomPipelineReader *geom_reader,
|
||||
virtual bool begin_draw_primitives(const GeomPipelineReader *geom_reader,
|
||||
const GeomMunger *munger,
|
||||
const GeomVertexDataPipelineReader *data_reader);
|
||||
virtual void draw_triangles(const GeomPrimitivePipelineReader *reader);
|
||||
@ -213,28 +215,31 @@ public:
|
||||
|
||||
INLINE CPT(TransformState) get_external_transform() const;
|
||||
INLINE CPT(TransformState) get_internal_transform() const;
|
||||
|
||||
|
||||
RenderBuffer get_render_buffer(int buffer_type, const FrameBufferProperties &prop);
|
||||
|
||||
|
||||
INLINE const DisplayRegion *get_current_display_region() const;
|
||||
INLINE Lens::StereoChannel get_current_stereo_channel() const;
|
||||
INLINE const Lens *get_current_lens() const;
|
||||
|
||||
virtual const TransformState *get_cs_transform() const;
|
||||
INLINE const TransformState *get_inv_cs_transform() const;
|
||||
|
||||
|
||||
void do_issue_clip_plane();
|
||||
void do_issue_color();
|
||||
void do_issue_color_scale();
|
||||
void do_issue_light();
|
||||
|
||||
virtual void bind_light(PointLight *light_obj, const NodePath &light,
|
||||
|
||||
virtual void bind_light(PointLight *light_obj, const NodePath &light,
|
||||
int light_id);
|
||||
virtual void bind_light(DirectionalLight *light_obj, const NodePath &light,
|
||||
int light_id);
|
||||
virtual void bind_light(Spotlight *light_obj, const NodePath &light,
|
||||
int light_id);
|
||||
|
||||
INLINE void set_stencil_clear_value(unsigned int stencil_clear_value);
|
||||
INLINE unsigned int get_stencil_clear_value();
|
||||
|
||||
protected:
|
||||
INLINE NodePath get_light(int light_id) const;
|
||||
virtual void enable_lighting(bool enable);
|
||||
@ -267,7 +272,7 @@ protected:
|
||||
protected:
|
||||
PT(SceneSetup) _scene_null;
|
||||
PT(SceneSetup) _scene_setup;
|
||||
|
||||
|
||||
AttribSlots _state;
|
||||
AttribSlots _target;
|
||||
CPT(RenderState) _state_rs;
|
||||
@ -282,7 +287,7 @@ protected:
|
||||
unsigned int _color_write_mask;
|
||||
Colorf _color_clear_value;
|
||||
float _depth_clear_value;
|
||||
bool _stencil_clear_value;
|
||||
unsigned int _stencil_clear_value;
|
||||
Colorf _accum_clear_value;
|
||||
|
||||
CPT(DisplayRegion) _current_display_region;
|
||||
@ -291,7 +296,7 @@ protected:
|
||||
CPT(TransformState) _projection_mat;
|
||||
CPT(TransformState) _projection_mat_inv;
|
||||
FrameBufferProperties *_current_properties;
|
||||
|
||||
|
||||
CoordinateSystem _coordinate_system;
|
||||
CoordinateSystem _internal_coordinate_system;
|
||||
CPT(TransformState) _cs_transform;
|
||||
@ -342,7 +347,7 @@ protected:
|
||||
|
||||
bool _supports_compressed_texture;
|
||||
BitMask32 _compressed_texture_formats;
|
||||
|
||||
|
||||
int _max_lights;
|
||||
int _max_clip_planes;
|
||||
|
||||
@ -359,11 +364,17 @@ protected:
|
||||
bool _supports_depth_texture;
|
||||
bool _supports_shadow_filter;
|
||||
bool _supports_basic_shaders;
|
||||
|
||||
bool _supports_stencil_wrap;
|
||||
bool _supports_two_sided_stencil;
|
||||
|
||||
int _supported_geom_rendering;
|
||||
bool _color_scale_via_lighting;
|
||||
|
||||
int _stereo_buffer_mask;
|
||||
|
||||
StencilRenderStates *_stencil_render_states;
|
||||
|
||||
public:
|
||||
// Statistics
|
||||
static PStatCollector _vertex_buffer_switch_pcollector;
|
||||
@ -384,7 +395,7 @@ public:
|
||||
static PStatCollector _vertices_tristrip_pcollector;
|
||||
static PStatCollector _vertices_trifan_pcollector;
|
||||
static PStatCollector _vertices_tri_pcollector;
|
||||
static PStatCollector _vertices_other_pcollector;
|
||||
static PStatCollector _vertices_other_pcollector;
|
||||
static PStatCollector _vertices_indexed_tristrip_pcollector;
|
||||
static PStatCollector _state_pcollector;
|
||||
static PStatCollector _transform_state_pcollector;
|
||||
|
85
panda/src/display/stencilRenderStates.cxx
Normal file
85
panda/src/display/stencilRenderStates.cxx
Normal file
@ -0,0 +1,85 @@
|
||||
// Filename: stencilRenderStates.cxx
|
||||
// Created by: aignacio (17May06)
|
||||
//
|
||||
////////////////////////////////////////////////////////////////////
|
||||
//
|
||||
// PANDA 3D SOFTWARE
|
||||
// Copyright (c) 2001 - 2006, Disney Enterprises, Inc. All rights reserved
|
||||
//
|
||||
// All use of this software is subject to the terms of the Panda 3d
|
||||
// Software license. You should have received a copy of this license
|
||||
// along with this source code; you will also find a current copy of
|
||||
// the license at http://etc.cmu.edu/panda3d/docs/license/ .
|
||||
//
|
||||
// To contact the maintainers of this program write to
|
||||
// panda3d-general@lists.sourceforge.net .
|
||||
//
|
||||
////////////////////////////////////////////////////////////////////
|
||||
|
||||
#include "graphicsStateGuardian.h"
|
||||
#include "stencilRenderStates.h"
|
||||
|
||||
StencilRenderStates::
|
||||
StencilRenderStates (GraphicsStateGuardian *gsg) {
|
||||
|
||||
int index;
|
||||
|
||||
// clear all
|
||||
for (index = 0; index < SRS_total; index++) {
|
||||
_stencil_render_state_array [index] = 0;
|
||||
_stencil_function_array [index] = 0;
|
||||
}
|
||||
|
||||
// set default render states
|
||||
set_stencil_render_state (false, SRS_clear_value, 0);
|
||||
|
||||
set_stencil_render_state (false, SRS_reference, 0);
|
||||
|
||||
set_stencil_render_state (false, SRS_read_mask, ~0);
|
||||
set_stencil_render_state (false, SRS_write_mask, ~0);
|
||||
|
||||
set_stencil_render_state (false, SRS_front_enable, 0);
|
||||
set_stencil_render_state (false, SRS_front_comparison_function, SCF_always);
|
||||
set_stencil_render_state (false, SRS_front_stencil_fail_operation, SO_keep);
|
||||
set_stencil_render_state (false, SRS_front_stencil_pass_z_fail_operation, SO_keep);
|
||||
set_stencil_render_state (false, SRS_front_stencil_pass_z_pass_operation, SO_keep);
|
||||
|
||||
set_stencil_render_state (false, SRS_back_enable, 0);
|
||||
set_stencil_render_state (false, SRS_back_comparison_function, SCF_always);
|
||||
set_stencil_render_state (false, SRS_back_stencil_fail_operation, SO_keep);
|
||||
set_stencil_render_state (false, SRS_back_stencil_pass_z_fail_operation, SO_keep);
|
||||
set_stencil_render_state (false, SRS_back_stencil_pass_z_pass_operation, SO_keep);
|
||||
|
||||
_gsg = gsg;
|
||||
}
|
||||
|
||||
StencilRenderStates::
|
||||
~StencilRenderStates (void) {
|
||||
|
||||
}
|
||||
|
||||
void StencilRenderStates::
|
||||
set_stencil_render_state (bool execute_function, StencilRenderStates::StencilRenderState stencil_render_state, StencilType value) {
|
||||
|
||||
_stencil_render_state_array [stencil_render_state] = value;
|
||||
|
||||
if (execute_function) {
|
||||
StencilFunction stencil_function;
|
||||
|
||||
stencil_function = _stencil_function_array [stencil_render_state];
|
||||
if (stencil_function) {
|
||||
stencil_function (stencil_render_state, this);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
StencilType StencilRenderStates::
|
||||
get_stencil_render_state (StencilRenderStates::StencilRenderState stencil_render_state) {
|
||||
return _stencil_render_state_array [stencil_render_state];
|
||||
}
|
||||
|
||||
void StencilRenderStates::
|
||||
set_stencil_function (StencilRenderStates::StencilRenderState stencil_render_state, StencilFunction stencil_function) {
|
||||
_stencil_function_array [stencil_render_state] = stencil_function;
|
||||
}
|
||||
|
102
panda/src/display/stencilRenderStates.h
Normal file
102
panda/src/display/stencilRenderStates.h
Normal file
@ -0,0 +1,102 @@
|
||||
// Filename: stencilRenderStates.h
|
||||
// Created by: aignacio (17May06)
|
||||
//
|
||||
////////////////////////////////////////////////////////////////////
|
||||
//
|
||||
// PANDA 3D SOFTWARE
|
||||
// Copyright (c) 2001 - 2006, Disney Enterprises, Inc. All rights reserved
|
||||
//
|
||||
// All use of this software is subject to the terms of the Panda 3d
|
||||
// Software license. You should have received a copy of this license
|
||||
// along with this source code; you will also find a current copy of
|
||||
// the license at http://etc.cmu.edu/panda3d/docs/license/ .
|
||||
//
|
||||
// To contact the maintainers of this program write to
|
||||
// panda3d-general@lists.sourceforge.net .
|
||||
//
|
||||
////////////////////////////////////////////////////////////////////
|
||||
|
||||
#ifndef STENCILRENDERSTATES_H
|
||||
#define STENCILRENDERSTATES_H
|
||||
|
||||
class GraphicsStateGuardian;
|
||||
typedef unsigned int StencilType;
|
||||
|
||||
////////////////////////////////////////////////////////////////////
|
||||
// Class : StencilRenderStates
|
||||
// Description : An abstract cross-platform class for stencil buffer
|
||||
// render states. Each gsg needs to create its own
|
||||
// low-level functions on how to set each render state.
|
||||
////////////////////////////////////////////////////////////////////
|
||||
class EXPCL_PANDA StencilRenderStates {
|
||||
|
||||
PUBLISHED:
|
||||
enum StencilRenderState
|
||||
{
|
||||
SRS_clear_value,
|
||||
|
||||
SRS_reference,
|
||||
|
||||
SRS_read_mask,
|
||||
SRS_write_mask,
|
||||
|
||||
SRS_front_enable,
|
||||
SRS_front_comparison_function,
|
||||
SRS_front_stencil_fail_operation,
|
||||
SRS_front_stencil_pass_z_fail_operation,
|
||||
SRS_front_stencil_pass_z_pass_operation,
|
||||
|
||||
SRS_back_enable,
|
||||
SRS_back_comparison_function,
|
||||
SRS_back_stencil_fail_operation,
|
||||
SRS_back_stencil_pass_z_fail_operation,
|
||||
SRS_back_stencil_pass_z_pass_operation,
|
||||
|
||||
SRS_total,
|
||||
|
||||
SRS_first = 0,
|
||||
};
|
||||
|
||||
enum StencilComparisonFunction
|
||||
{
|
||||
SCF_never,
|
||||
SCF_less_than,
|
||||
SCF_equal,
|
||||
SCF_less_than_or_equal,
|
||||
SCF_greater_than,
|
||||
SCF_not_equal,
|
||||
SCF_greater_than_or_equal,
|
||||
SCF_always,
|
||||
};
|
||||
|
||||
enum StencilOperation
|
||||
{
|
||||
SO_keep,
|
||||
SO_zero,
|
||||
SO_replace,
|
||||
SO_increment,
|
||||
SO_decrement,
|
||||
SO_invert,
|
||||
SO_increment_saturate,
|
||||
SO_decrement_saturate,
|
||||
};
|
||||
|
||||
public:
|
||||
typedef void (*StencilFunction) (StencilRenderStates::StencilRenderState stencil_render_state, StencilRenderStates *stencil_render_states);
|
||||
|
||||
StencilRenderStates (GraphicsStateGuardian *gsg);
|
||||
~StencilRenderStates (void);
|
||||
|
||||
void set_stencil_render_state (bool execute_function, StencilRenderStates::StencilRenderState stencil_render_state, StencilType value);
|
||||
StencilType get_stencil_render_state (StencilRenderStates::StencilRenderState stencil_render_state);
|
||||
|
||||
void set_stencil_function (StencilRenderStates::StencilRenderState stencil_render_state, StencilFunction stencil_function);
|
||||
|
||||
GraphicsStateGuardian *_gsg;
|
||||
|
||||
private:
|
||||
StencilType _stencil_render_state_array [SRS_total];
|
||||
StencilFunction _stencil_function_array [SRS_total];
|
||||
};
|
||||
|
||||
#endif
|
@ -178,6 +178,7 @@ DXGraphicsStateGuardian9::
|
||||
}
|
||||
#endif
|
||||
|
||||
GraphicsStateGuardian::~GraphicsStateGuardian();
|
||||
}
|
||||
|
||||
////////////////////////////////////////////////////////////////////
|
||||
@ -230,8 +231,7 @@ apply_texture(int i, TextureContext *tc) {
|
||||
|
||||
DXTextureContext9 *dtc = DCAST(DXTextureContext9, tc);
|
||||
|
||||
if (_lru)
|
||||
{
|
||||
if (_lru) {
|
||||
_lru -> access_page (dtc -> _lru_page);
|
||||
}
|
||||
|
||||
@ -2356,6 +2356,108 @@ void DXGraphicsStateGuardian9::reset_render_states (void)
|
||||
_last_fvf = 0;
|
||||
}
|
||||
|
||||
////////////////////////////////////////////////////////////////////
|
||||
// DX stencil code section
|
||||
////////////////////////////////////////////////////////////////////
|
||||
|
||||
static int dx_stencil_comparison_function_array [ ] =
|
||||
{
|
||||
D3DCMP_NEVER,
|
||||
D3DCMP_LESS,
|
||||
D3DCMP_EQUAL,
|
||||
D3DCMP_LESSEQUAL,
|
||||
D3DCMP_GREATER,
|
||||
D3DCMP_NOTEQUAL,
|
||||
D3DCMP_GREATEREQUAL,
|
||||
D3DCMP_ALWAYS,
|
||||
};
|
||||
|
||||
static int dx_stencil_operation_array [ ] =
|
||||
{
|
||||
D3DSTENCILOP_KEEP,
|
||||
D3DSTENCILOP_ZERO,
|
||||
D3DSTENCILOP_REPLACE,
|
||||
D3DSTENCILOP_INCR,
|
||||
D3DSTENCILOP_DECR,
|
||||
D3DSTENCILOP_INVERT,
|
||||
|
||||
D3DSTENCILOP_INCRSAT,
|
||||
D3DSTENCILOP_DECRSAT,
|
||||
};
|
||||
|
||||
void dx_stencil_function (StencilRenderStates::StencilRenderState stencil_render_state, StencilRenderStates *stencil_render_states) {
|
||||
StencilType render_state_value;
|
||||
|
||||
DXGraphicsStateGuardian9 *gsg;
|
||||
|
||||
gsg = (DXGraphicsStateGuardian9 *) stencil_render_states -> _gsg;
|
||||
|
||||
render_state_value = stencil_render_states -> get_stencil_render_state (stencil_render_state);
|
||||
switch (stencil_render_state)
|
||||
{
|
||||
case StencilRenderStates::SRS_clear_value:
|
||||
gsg -> set_stencil_clear_value (render_state_value);
|
||||
break;
|
||||
|
||||
case StencilRenderStates::SRS_reference:
|
||||
gsg -> set_render_state (D3DRS_STENCILREF, render_state_value);
|
||||
break;
|
||||
|
||||
case StencilRenderStates::SRS_read_mask:
|
||||
gsg -> set_render_state (D3DRS_STENCILMASK, render_state_value);
|
||||
break;
|
||||
case StencilRenderStates::SRS_write_mask:
|
||||
gsg -> set_render_state (D3DRS_STENCILWRITEMASK, render_state_value);
|
||||
break;
|
||||
|
||||
case StencilRenderStates::SRS_front_enable:
|
||||
gsg -> set_render_state (D3DRS_STENCILENABLE, render_state_value);
|
||||
break;
|
||||
case StencilRenderStates::SRS_front_comparison_function:
|
||||
gsg -> set_render_state (D3DRS_STENCILFUNC, dx_stencil_comparison_function_array [render_state_value]);
|
||||
break;
|
||||
|
||||
case StencilRenderStates::SRS_front_stencil_fail_operation:
|
||||
gsg -> set_render_state (D3DRS_STENCILFAIL, dx_stencil_operation_array [render_state_value]);
|
||||
break;
|
||||
case StencilRenderStates::SRS_front_stencil_pass_z_fail_operation:
|
||||
gsg -> set_render_state (D3DRS_STENCILZFAIL, dx_stencil_operation_array [render_state_value]);
|
||||
break;
|
||||
case StencilRenderStates::SRS_front_stencil_pass_z_pass_operation:
|
||||
gsg -> set_render_state (D3DRS_STENCILPASS, dx_stencil_operation_array [render_state_value]);
|
||||
break;
|
||||
|
||||
case StencilRenderStates::SRS_back_enable:
|
||||
gsg -> set_render_state (D3DRS_TWOSIDEDSTENCILMODE, render_state_value);
|
||||
break;
|
||||
case StencilRenderStates::SRS_back_comparison_function:
|
||||
gsg -> set_render_state (D3DRS_CCW_STENCILFUNC, dx_stencil_comparison_function_array [render_state_value]);
|
||||
break;
|
||||
case StencilRenderStates::SRS_back_stencil_fail_operation:
|
||||
gsg -> set_render_state (D3DRS_CCW_STENCILFAIL, dx_stencil_operation_array [render_state_value]);
|
||||
break;
|
||||
case StencilRenderStates::SRS_back_stencil_pass_z_fail_operation:
|
||||
gsg -> set_render_state (D3DRS_CCW_STENCILZFAIL, dx_stencil_operation_array [render_state_value]);
|
||||
break;
|
||||
case StencilRenderStates::SRS_back_stencil_pass_z_pass_operation:
|
||||
gsg -> set_render_state (D3DRS_CCW_STENCILPASS, dx_stencil_operation_array [render_state_value]);
|
||||
break;
|
||||
|
||||
default:
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
void dx_set_stencil_functions (StencilRenderStates *stencil_render_states) {
|
||||
if (stencil_render_states) {
|
||||
StencilRenderStates::StencilRenderState stencil_render_state;
|
||||
|
||||
for (stencil_render_state = StencilRenderStates::SRS_first; stencil_render_state < StencilRenderStates::SRS_total; stencil_render_state = (StencilRenderStates::StencilRenderState) ((int) stencil_render_state + 1)) {
|
||||
stencil_render_states -> set_stencil_function (stencil_render_state, dx_stencil_function);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
////////////////////////////////////////////////////////////////////
|
||||
// Function: DXGraphicsStateGuardian9::reset
|
||||
// Access: Public, Virtual
|
||||
@ -2400,6 +2502,9 @@ reset() {
|
||||
_screen->_supports_dynamic_textures = ((d3d_caps.Caps2 & D3DCAPS2_DYNAMICTEXTURES) != 0);
|
||||
_screen->_supports_automatic_mipmap_generation = ((d3d_caps.Caps2 & D3DCAPS2_CANAUTOGENMIPMAP) != 0);
|
||||
|
||||
_supports_stencil_wrap = (d3d_caps.StencilCaps & D3DSTENCILCAPS_INCR) && (d3d_caps.StencilCaps & D3DSTENCILCAPS_DECR);
|
||||
_supports_two_sided_stencil = ((d3d_caps.StencilCaps & D3DSTENCILCAPS_TWOSIDED) != 0);
|
||||
|
||||
if (dxgsg9_cat.is_debug()) {
|
||||
dxgsg9_cat.debug()
|
||||
<< "\nHwTransformAndLight = " << ((d3d_caps.DevCaps & D3DDEVCAPS_HWTRANSFORMANDLIGHT) != 0)
|
||||
@ -2428,6 +2533,8 @@ reset() {
|
||||
<< "\nsupports_stream_offset = " << _supports_stream_offset
|
||||
<< "\nsupports_dynamic_textures = " << _screen->_supports_dynamic_textures
|
||||
<< "\nsupports_automatic_mipmap_generation = " << _screen->_supports_automatic_mipmap_generation
|
||||
<< "\nsupports_stencil_wrap = " << _supports_stencil_wrap
|
||||
<< "\nsupports_two_sided_stencil = " << _supports_two_sided_stencil
|
||||
<< "\nMaxAnisotropy = " << d3d_caps.MaxAnisotropy
|
||||
<< "\nDirectX SDK version " DIRECTX_SDK_VERSION
|
||||
<< "\n";
|
||||
@ -2732,6 +2839,8 @@ reset() {
|
||||
_texture_binding_shader_context = (CLP(ShaderContext) *)NULL;
|
||||
|
||||
PRINT_REFCNT(dxgsg9, _d3d_device);
|
||||
|
||||
dx_set_stencil_functions (_stencil_render_states);
|
||||
}
|
||||
|
||||
////////////////////////////////////////////////////////////////////
|
||||
|
@ -52,6 +52,8 @@
|
||||
|
||||
#include <algorithm>
|
||||
|
||||
#define DEBUG_BUFFERS false
|
||||
|
||||
TypeHandle CLP(GraphicsStateGuardian)::_type_handle;
|
||||
|
||||
PStatCollector CLP(GraphicsStateGuardian)::_load_display_list_pcollector("Draw:Transfer data:Display lists");
|
||||
@ -271,6 +273,183 @@ CLP(GraphicsStateGuardian)(const FrameBufferProperties &properties) :
|
||||
CLP(GraphicsStateGuardian)::
|
||||
~CLP(GraphicsStateGuardian)() {
|
||||
close_gsg();
|
||||
|
||||
if (_stencil_render_states) {
|
||||
delete _stencil_render_states;
|
||||
_stencil_render_states = 0;
|
||||
}
|
||||
|
||||
GraphicsStateGuardian::~GraphicsStateGuardian();
|
||||
}
|
||||
|
||||
////////////////////////////////////////////////////////////////////
|
||||
// GL stencil code section
|
||||
////////////////////////////////////////////////////////////////////
|
||||
|
||||
static int gl_stencil_comparison_function_array [ ] =
|
||||
{
|
||||
GL_NEVER,
|
||||
GL_LESS,
|
||||
GL_EQUAL,
|
||||
GL_LEQUAL,
|
||||
GL_GREATER,
|
||||
GL_NOTEQUAL,
|
||||
GL_GEQUAL,
|
||||
GL_ALWAYS,
|
||||
};
|
||||
|
||||
static int gl_stencil_operations_array [ ] =
|
||||
{
|
||||
GL_KEEP,
|
||||
GL_ZERO,
|
||||
GL_REPLACE,
|
||||
GL_INCR_WRAP,
|
||||
GL_DECR_WRAP,
|
||||
GL_INVERT,
|
||||
|
||||
GL_INCR,
|
||||
GL_DECR,
|
||||
};
|
||||
|
||||
void __glActiveStencilFace (GraphicsStateGuardian *gsg, GLenum face) {
|
||||
CLP(GraphicsStateGuardian) *glgsg;
|
||||
|
||||
glgsg = (CLP(GraphicsStateGuardian) *) gsg;
|
||||
if (gsg -> get_supports_two_sided_stencil ( ) &&
|
||||
glgsg -> _glActiveStencilFaceEXT) {
|
||||
if (face == GL_FRONT) {
|
||||
// glActiveStencilFaceEXT (GL_FRONT);
|
||||
glgsg -> _glActiveStencilFaceEXT (GL_FRONT);
|
||||
}
|
||||
else {
|
||||
// glActiveStencilFaceEXT (GL_BACK);
|
||||
glgsg -> _glActiveStencilFaceEXT (GL_BACK);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
void gl_front_stencil_function (StencilRenderStates::StencilRenderState stencil_render_state, StencilRenderStates *stencil_render_states) {
|
||||
|
||||
__glActiveStencilFace (stencil_render_states -> _gsg, GL_FRONT);
|
||||
glStencilFunc
|
||||
(
|
||||
gl_stencil_comparison_function_array [stencil_render_states -> get_stencil_render_state (StencilRenderStates::SRS_front_comparison_function)],
|
||||
stencil_render_states -> get_stencil_render_state (StencilRenderStates::SRS_reference),
|
||||
stencil_render_states -> get_stencil_render_state (StencilRenderStates::SRS_read_mask)
|
||||
);
|
||||
}
|
||||
void gl_front_stencil_operation (StencilRenderStates::StencilRenderState stencil_render_state, StencilRenderStates *stencil_render_states) {
|
||||
__glActiveStencilFace (stencil_render_states -> _gsg, GL_FRONT);
|
||||
glStencilOp
|
||||
(
|
||||
gl_stencil_operations_array [stencil_render_states -> get_stencil_render_state (StencilRenderStates::SRS_front_stencil_fail_operation)],
|
||||
gl_stencil_operations_array [stencil_render_states -> get_stencil_render_state (StencilRenderStates::SRS_front_stencil_pass_z_fail_operation)],
|
||||
gl_stencil_operations_array [stencil_render_states -> get_stencil_render_state (StencilRenderStates::SRS_front_stencil_pass_z_pass_operation)]
|
||||
);
|
||||
}
|
||||
|
||||
void gl_back_stencil_function (StencilRenderStates::StencilRenderState stencil_render_state, StencilRenderStates *stencil_render_states) {
|
||||
|
||||
bool supports_two_sided_stencil;
|
||||
|
||||
supports_two_sided_stencil = stencil_render_states -> _gsg -> get_supports_two_sided_stencil ( );
|
||||
if (supports_two_sided_stencil) {
|
||||
__glActiveStencilFace (stencil_render_states -> _gsg, GL_BACK);
|
||||
glStencilFunc
|
||||
(
|
||||
gl_stencil_comparison_function_array [stencil_render_states -> get_stencil_render_state (StencilRenderStates::SRS_back_comparison_function)],
|
||||
stencil_render_states -> get_stencil_render_state (StencilRenderStates::SRS_reference),
|
||||
stencil_render_states -> get_stencil_render_state (StencilRenderStates::SRS_read_mask)
|
||||
);
|
||||
}
|
||||
}
|
||||
|
||||
void gl_back_stencil_operation (StencilRenderStates::StencilRenderState stencil_render_state, StencilRenderStates *stencil_render_states) {
|
||||
|
||||
bool supports_two_sided_stencil;
|
||||
|
||||
supports_two_sided_stencil = stencil_render_states -> _gsg -> get_supports_two_sided_stencil ( );
|
||||
if (supports_two_sided_stencil) {
|
||||
__glActiveStencilFace (stencil_render_states -> _gsg, GL_BACK);
|
||||
glStencilOp
|
||||
(
|
||||
gl_stencil_operations_array [stencil_render_states -> get_stencil_render_state (StencilRenderStates::SRS_back_stencil_fail_operation)],
|
||||
gl_stencil_operations_array [stencil_render_states -> get_stencil_render_state (StencilRenderStates::SRS_back_stencil_pass_z_fail_operation)],
|
||||
gl_stencil_operations_array [stencil_render_states -> get_stencil_render_state (StencilRenderStates::SRS_back_stencil_pass_z_pass_operation)]
|
||||
);
|
||||
}
|
||||
}
|
||||
|
||||
void gl_front_back_stencil_function (StencilRenderStates::StencilRenderState stencil_render_state, StencilRenderStates *stencil_render_states) {
|
||||
gl_front_stencil_function (stencil_render_state, stencil_render_states);
|
||||
gl_back_stencil_function (stencil_render_state, stencil_render_states);
|
||||
}
|
||||
|
||||
void gl_stencil_function (StencilRenderStates::StencilRenderState stencil_render_state, StencilRenderStates *stencil_render_states) {
|
||||
|
||||
StencilType render_state_value;
|
||||
bool supports_two_sided_stencil;
|
||||
|
||||
supports_two_sided_stencil = stencil_render_states -> _gsg -> get_supports_two_sided_stencil ( );
|
||||
|
||||
render_state_value = stencil_render_states -> get_stencil_render_state (stencil_render_state);
|
||||
switch (stencil_render_state)
|
||||
{
|
||||
case StencilRenderStates::SRS_clear_value:
|
||||
stencil_render_states -> _gsg -> set_stencil_clear_value (render_state_value);
|
||||
break;
|
||||
|
||||
case StencilRenderStates::SRS_write_mask:
|
||||
glStencilMask (render_state_value);
|
||||
break;
|
||||
case StencilRenderStates::SRS_front_enable:
|
||||
if (render_state_value) {
|
||||
glEnable (GL_STENCIL_TEST);
|
||||
}
|
||||
else {
|
||||
glDisable (GL_STENCIL_TEST);
|
||||
}
|
||||
break;
|
||||
case StencilRenderStates::SRS_back_enable:
|
||||
if (supports_two_sided_stencil) {
|
||||
if (render_state_value) {
|
||||
glEnable (GL_STENCIL_TEST_TWO_SIDE_EXT);
|
||||
}
|
||||
else {
|
||||
glDisable (GL_STENCIL_TEST_TWO_SIDE_EXT);
|
||||
}
|
||||
}
|
||||
break;
|
||||
|
||||
default:
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
void gl_set_stencil_functions (StencilRenderStates *stencil_render_states) {
|
||||
|
||||
if (stencil_render_states) {
|
||||
stencil_render_states -> set_stencil_function (StencilRenderStates::SRS_clear_value, gl_stencil_function);
|
||||
|
||||
// GL seems to support different read masks and/or reference values for front and back, but DX does not.
|
||||
// This needs to be cross-platform so do it the DX way by setting the same read mask and reference for both front and back.
|
||||
stencil_render_states -> set_stencil_function (StencilRenderStates::SRS_reference, gl_front_back_stencil_function);
|
||||
stencil_render_states -> set_stencil_function (StencilRenderStates::SRS_read_mask, gl_front_back_stencil_function);
|
||||
|
||||
stencil_render_states -> set_stencil_function (StencilRenderStates::SRS_write_mask, gl_stencil_function);
|
||||
|
||||
stencil_render_states -> set_stencil_function (StencilRenderStates::SRS_front_enable, gl_stencil_function);
|
||||
stencil_render_states -> set_stencil_function (StencilRenderStates::SRS_front_comparison_function, gl_front_stencil_function);
|
||||
stencil_render_states -> set_stencil_function (StencilRenderStates::SRS_front_stencil_fail_operation, gl_front_stencil_operation);
|
||||
stencil_render_states -> set_stencil_function (StencilRenderStates::SRS_front_stencil_pass_z_fail_operation, gl_front_stencil_operation);
|
||||
stencil_render_states -> set_stencil_function (StencilRenderStates::SRS_front_stencil_pass_z_pass_operation, gl_front_stencil_operation);
|
||||
|
||||
stencil_render_states -> set_stencil_function (StencilRenderStates::SRS_back_enable, gl_stencil_function);
|
||||
stencil_render_states -> set_stencil_function (StencilRenderStates::SRS_back_comparison_function, gl_back_stencil_function);
|
||||
stencil_render_states -> set_stencil_function (StencilRenderStates::SRS_back_stencil_fail_operation, gl_back_stencil_operation);
|
||||
stencil_render_states -> set_stencil_function (StencilRenderStates::SRS_back_stencil_pass_z_fail_operation, gl_back_stencil_operation);
|
||||
stencil_render_states -> set_stencil_function (StencilRenderStates::SRS_back_stencil_pass_z_pass_operation, gl_back_stencil_operation);
|
||||
}
|
||||
}
|
||||
|
||||
////////////////////////////////////////////////////////////////////
|
||||
@ -433,7 +612,7 @@ reset() {
|
||||
_glDrawRangeElements = null_glDrawRangeElements;
|
||||
}
|
||||
|
||||
_supports_depth_texture =
|
||||
_supports_depth_texture =
|
||||
has_extension("GL_ARB_depth_texture") || is_at_least_version(1, 4);
|
||||
|
||||
_supports_3d_texture = false;
|
||||
@ -505,13 +684,13 @@ reset() {
|
||||
}
|
||||
|
||||
if (_supports_compressed_texture) {
|
||||
if (_glCompressedTexImage1D == NULL ||
|
||||
_glCompressedTexImage2D == NULL ||
|
||||
_glCompressedTexImage3D == NULL ||
|
||||
_glCompressedTexSubImage1D == NULL ||
|
||||
_glCompressedTexSubImage2D == NULL ||
|
||||
_glCompressedTexSubImage3D == NULL ||
|
||||
_glGetCompressedTexImage == NULL) {
|
||||
if (_glCompressedTexImage1D == NULL ||
|
||||
_glCompressedTexImage2D == NULL ||
|
||||
_glCompressedTexImage3D == NULL ||
|
||||
_glCompressedTexSubImage1D == NULL ||
|
||||
_glCompressedTexSubImage2D == NULL ||
|
||||
_glCompressedTexSubImage3D == NULL ||
|
||||
_glGetCompressedTexImage == NULL) {
|
||||
GLCAT.warning()
|
||||
<< "Compressed textures advertised as supported by OpenGL runtime, but could not get pointers to extension functions.\n";
|
||||
_supports_compressed_texture = false;
|
||||
@ -568,7 +747,7 @@ reset() {
|
||||
|
||||
_supports_tex_non_pow2 =
|
||||
has_extension("GL_ARB_texture_non_power_of_two");
|
||||
|
||||
|
||||
if (is_at_least_version(1, 3)) {
|
||||
_supports_multitexture = true;
|
||||
|
||||
@ -758,8 +937,8 @@ reset() {
|
||||
}
|
||||
}
|
||||
|
||||
if (_supports_occlusion_query &&
|
||||
(_glGenQueries == NULL || _glBeginQuery == NULL ||
|
||||
if (_supports_occlusion_query &&
|
||||
(_glGenQueries == NULL || _glBeginQuery == NULL ||
|
||||
_glEndQuery == NULL || _glDeleteQueries == NULL ||
|
||||
_glGetQueryObjectuiv == NULL)) {
|
||||
GLCAT.warning()
|
||||
@ -920,27 +1099,27 @@ reset() {
|
||||
case GL_COMPRESSED_RGB_S3TC_DXT1_EXT:
|
||||
GLCAT.debug(false) << " GL_COMPRESSED_RGB_S3TC_DXT1_EXT\n";
|
||||
break;
|
||||
|
||||
|
||||
case GL_COMPRESSED_RGBA_S3TC_DXT1_EXT:
|
||||
GLCAT.debug(false) << " GL_COMPRESSED_RGBA_S3TC_DXT1_EXT\n";
|
||||
break;
|
||||
|
||||
|
||||
case GL_COMPRESSED_RGBA_S3TC_DXT3_EXT:
|
||||
GLCAT.debug(false) << " GL_COMPRESSED_RGBA_S3TC_DXT3_EXT\n";
|
||||
break;
|
||||
|
||||
|
||||
case GL_COMPRESSED_RGBA_S3TC_DXT5_EXT:
|
||||
GLCAT.debug(false) << " GL_COMPRESSED_RGBA_S3TC_DXT5_EXT\n";
|
||||
break;
|
||||
|
||||
|
||||
case GL_COMPRESSED_RGB_FXT1_3DFX:
|
||||
GLCAT.debug(false) << " GL_COMPRESSED_RGB_FXT1_3DFX\n";
|
||||
break;
|
||||
|
||||
|
||||
case GL_COMPRESSED_RGBA_FXT1_3DFX:
|
||||
GLCAT.debug(false) << " GL_COMPRESSED_RGBA_FXT1_3DFX\n";
|
||||
break;
|
||||
|
||||
|
||||
default:
|
||||
GLCAT.debug(false)
|
||||
<< " Unknown compressed format 0x" << hex << formats[i]
|
||||
@ -954,6 +1133,16 @@ reset() {
|
||||
|
||||
report_my_gl_errors();
|
||||
|
||||
_supports_stencil_wrap = has_extension("GL_EXT_stencil_wrap");
|
||||
_supports_two_sided_stencil = has_extension("GL_EXT_stencil_two_side");
|
||||
if (_supports_two_sided_stencil) {
|
||||
_glActiveStencilFaceEXT = (PFNGLACTIVESTENCILFACEEXTPROC)
|
||||
get_extension_func(GLPREFIX_QUOTED, "ActiveStencilFaceEXT");
|
||||
}
|
||||
else {
|
||||
_glActiveStencilFaceEXT = 0;
|
||||
}
|
||||
|
||||
_auto_rescale_normal = false;
|
||||
|
||||
// If we don't have double-buffering, don't attempt to write to the
|
||||
@ -1074,6 +1263,8 @@ reset() {
|
||||
_error_count = 0;
|
||||
|
||||
report_my_gl_errors();
|
||||
|
||||
gl_set_stencil_functions (_stencil_render_states);
|
||||
}
|
||||
|
||||
|
||||
@ -1146,7 +1337,7 @@ do_clear(const RenderBuffer &buffer) {
|
||||
// scissor region and viewport)
|
||||
////////////////////////////////////////////////////////////////////
|
||||
void CLP(GraphicsStateGuardian)::
|
||||
prepare_display_region(DisplayRegionPipelineReader *dr,
|
||||
prepare_display_region(DisplayRegionPipelineReader *dr,
|
||||
Lens::StereoChannel stereo_channel) {
|
||||
nassertv(dr != (DisplayRegionPipelineReader *)NULL);
|
||||
GraphicsStateGuardian::prepare_display_region(dr, stereo_channel);
|
||||
@ -1165,7 +1356,7 @@ prepare_display_region(DisplayRegionPipelineReader *dr,
|
||||
enable_scissor(true);
|
||||
GLP(Scissor)(x, y, width, height);
|
||||
GLP(Viewport)(x, y, width, height);
|
||||
|
||||
|
||||
report_my_gl_errors();
|
||||
do_point_size();
|
||||
}
|
||||
@ -1287,7 +1478,7 @@ end_frame(Thread *current_thread) {
|
||||
if (PStatClient::is_connected()) {
|
||||
check_nonresident_texture(_prepared_objects->_texture_residency.get_inactive_resident());
|
||||
check_nonresident_texture(_prepared_objects->_texture_residency.get_active_resident());
|
||||
|
||||
|
||||
// OpenGL provides no methods for querying whether a buffer object
|
||||
// (vertex buffer) is resident. In fact, the API appears geared
|
||||
// towards the assumption that such buffers are always resident.
|
||||
@ -1346,7 +1537,7 @@ end_frame(Thread *current_thread) {
|
||||
|
||||
report_my_gl_errors();
|
||||
}
|
||||
|
||||
|
||||
|
||||
////////////////////////////////////////////////////////////////////
|
||||
// Function: GLGraphicsStateGuardian::begin_draw_primitives
|
||||
@ -2330,7 +2521,7 @@ extract_texture_data(Texture *tex) {
|
||||
Texture::ComponentType type = Texture::T_unsigned_byte;
|
||||
Texture::Format format = Texture::F_rgb;
|
||||
Texture::CompressionMode compression = Texture::CM_off;
|
||||
|
||||
|
||||
switch (internal_format) {
|
||||
case GL_COLOR_INDEX:
|
||||
format = Texture::F_color_index;
|
||||
@ -2464,8 +2655,8 @@ extract_texture_data(Texture *tex) {
|
||||
tex->set_wrap_u(get_panda_wrap_mode(wrap_u));
|
||||
tex->set_wrap_v(get_panda_wrap_mode(wrap_v));
|
||||
tex->set_wrap_w(get_panda_wrap_mode(wrap_w));
|
||||
tex->set_border_color(Colorf(border_color[0], border_color[1],
|
||||
border_color[2], border_color[3]));
|
||||
tex->set_border_color(Colorf(border_color[0], border_color[1],
|
||||
border_color[2], border_color[3]));
|
||||
|
||||
tex->set_minfilter(get_panda_filter_type(minfilter));
|
||||
// tex->set_magfilter(get_panda_filter_type(magfilter));
|
||||
@ -2474,10 +2665,10 @@ extract_texture_data(Texture *tex) {
|
||||
size_t page_size = 0;
|
||||
|
||||
if (!extract_texture_image(image, page_size, tex, target, page_target,
|
||||
type, compression, 0)) {
|
||||
type, compression, 0)) {
|
||||
return false;
|
||||
}
|
||||
|
||||
|
||||
tex->set_ram_image(image, compression, page_size);
|
||||
|
||||
if (tex->uses_mipmaps()) {
|
||||
@ -2488,8 +2679,8 @@ extract_texture_data(Texture *tex) {
|
||||
highest_level = min(highest_level, num_expected_levels);
|
||||
for (int n = 1; n <= highest_level; ++n) {
|
||||
if (!extract_texture_image(image, page_size, tex, target, page_target,
|
||||
type, compression, n)) {
|
||||
return false;
|
||||
type, compression, n)) {
|
||||
return false;
|
||||
}
|
||||
tex->set_ram_mipmap_image(n, image, page_size);
|
||||
}
|
||||
@ -2590,7 +2781,7 @@ prepare_vertex_buffer(GeomVertexArrayData *data) {
|
||||
CLP(VertexBufferContext) *gvbc = new CLP(VertexBufferContext)(_prepared_objects, data);
|
||||
_glGenBuffers(1, &gvbc->_index);
|
||||
|
||||
if (GLCAT.is_debug()) {
|
||||
if (DEBUG_BUFFERS && GLCAT.is_debug()) {
|
||||
GLCAT.debug()
|
||||
<< "creating vertex buffer " << gvbc->_index << ": "
|
||||
<< data->get_num_rows() << " vertices "
|
||||
@ -2669,7 +2860,7 @@ release_vertex_buffer(VertexBufferContext *vbc) {
|
||||
|
||||
CLP(VertexBufferContext) *gvbc = DCAST(CLP(VertexBufferContext), vbc);
|
||||
|
||||
if (GLCAT.is_debug()) {
|
||||
if (DEBUG_BUFFERS && GLCAT.is_debug()) {
|
||||
GLCAT.debug()
|
||||
<< "deleting vertex buffer " << gvbc->_index << "\n";
|
||||
}
|
||||
@ -2758,7 +2949,7 @@ prepare_index_buffer(GeomPrimitive *data) {
|
||||
CLP(IndexBufferContext) *gibc = new CLP(IndexBufferContext)(_prepared_objects, data);
|
||||
_glGenBuffers(1, &gibc->_index);
|
||||
|
||||
if (GLCAT.is_debug()) {
|
||||
if (DEBUG_BUFFERS && GLCAT.is_debug()) {
|
||||
GLCAT.debug()
|
||||
<< "creating index buffer " << gibc->_index << ": "
|
||||
<< data->get_num_vertices() << " indices ("
|
||||
@ -2837,7 +3028,7 @@ release_index_buffer(IndexBufferContext *ibc) {
|
||||
|
||||
CLP(IndexBufferContext) *gibc = DCAST(CLP(IndexBufferContext), ibc);
|
||||
|
||||
if (GLCAT.is_debug()) {
|
||||
if (DEBUG_BUFFERS && GLCAT.is_debug()) {
|
||||
GLCAT.debug()
|
||||
<< "deleting index buffer " << gibc->_index << "\n";
|
||||
}
|
||||
@ -2990,7 +3181,7 @@ framebuffer_copy_to_texture(Texture *tex, int z, const DisplayRegion *dr,
|
||||
tex->set_x_size(Texture::up_to_power_2(w));
|
||||
tex->set_y_size(Texture::up_to_power_2(h));
|
||||
}
|
||||
|
||||
|
||||
// Sanity check everything.
|
||||
if (z >= 0) {
|
||||
if (!_supports_cube_map) {
|
||||
@ -3681,7 +3872,7 @@ do_issue_blending() {
|
||||
// all the other blending-related stuff doesn't matter. If the
|
||||
// device doesn't support color-write, we use blending tricks
|
||||
// to effectively disable color write.
|
||||
unsigned int color_channels =
|
||||
unsigned int color_channels =
|
||||
_target._color_write->get_channels() & _color_write_mask;
|
||||
if (color_channels == ColorWriteAttrib::C_off) {
|
||||
if (_target._color_write != _state._color_write) {
|
||||
@ -4179,7 +4370,16 @@ report_extensions() const {
|
||||
////////////////////////////////////////////////////////////////////
|
||||
bool CLP(GraphicsStateGuardian)::
|
||||
has_extension(const string &extension) const {
|
||||
return (_extensions.find(extension) != _extensions.end());
|
||||
|
||||
bool state;
|
||||
|
||||
state = _extensions.find(extension) != _extensions.end();
|
||||
if (GLCAT.is_debug()) {
|
||||
GLCAT.debug()
|
||||
<< "HAS EXT " << extension << " " << state << "\n";
|
||||
}
|
||||
|
||||
return state;
|
||||
}
|
||||
|
||||
////////////////////////////////////////////////////////////////////
|
||||
@ -4254,39 +4454,39 @@ set_draw_buffer(const RenderBuffer &rb) {
|
||||
case RenderBuffer::T_front:
|
||||
GLP(DrawBuffer)(GL_FRONT);
|
||||
break;
|
||||
|
||||
|
||||
case RenderBuffer::T_back:
|
||||
GLP(DrawBuffer)(GL_BACK);
|
||||
break;
|
||||
|
||||
|
||||
case RenderBuffer::T_right:
|
||||
GLP(DrawBuffer)(GL_RIGHT);
|
||||
break;
|
||||
|
||||
|
||||
case RenderBuffer::T_left:
|
||||
GLP(DrawBuffer)(GL_LEFT);
|
||||
break;
|
||||
|
||||
|
||||
case RenderBuffer::T_front_right:
|
||||
nassertv(_current_properties->is_stereo());
|
||||
GLP(DrawBuffer)(GL_FRONT_RIGHT);
|
||||
break;
|
||||
|
||||
|
||||
case RenderBuffer::T_front_left:
|
||||
nassertv(_current_properties->is_stereo());
|
||||
GLP(DrawBuffer)(GL_FRONT_LEFT);
|
||||
break;
|
||||
|
||||
|
||||
case RenderBuffer::T_back_right:
|
||||
nassertv(_current_properties->is_stereo());
|
||||
GLP(DrawBuffer)(GL_BACK_RIGHT);
|
||||
break;
|
||||
|
||||
|
||||
case RenderBuffer::T_back_left:
|
||||
nassertv(_current_properties->is_stereo());
|
||||
GLP(DrawBuffer)(GL_BACK_LEFT);
|
||||
break;
|
||||
|
||||
|
||||
default:
|
||||
GLP(DrawBuffer)(GL_FRONT_AND_BACK);
|
||||
}
|
||||
@ -4297,7 +4497,7 @@ set_draw_buffer(const RenderBuffer &rb) {
|
||||
(_color_write_mask & ColorWriteAttrib::C_green) != 0,
|
||||
(_color_write_mask & ColorWriteAttrib::C_blue) != 0,
|
||||
(_color_write_mask & ColorWriteAttrib::C_alpha) != 0);
|
||||
|
||||
|
||||
report_my_gl_errors();
|
||||
}
|
||||
|
||||
@ -4342,40 +4542,40 @@ set_read_buffer(const RenderBuffer &rb) {
|
||||
case RenderBuffer::T_front:
|
||||
GLP(ReadBuffer)(GL_FRONT);
|
||||
break;
|
||||
|
||||
|
||||
case RenderBuffer::T_back:
|
||||
GLP(ReadBuffer)(GL_BACK);
|
||||
break;
|
||||
|
||||
|
||||
case RenderBuffer::T_right:
|
||||
GLP(ReadBuffer)(GL_RIGHT);
|
||||
break;
|
||||
|
||||
|
||||
case RenderBuffer::T_left:
|
||||
GLP(ReadBuffer)(GL_LEFT);
|
||||
break;
|
||||
|
||||
|
||||
case RenderBuffer::T_front_right:
|
||||
GLP(ReadBuffer)(GL_FRONT_RIGHT);
|
||||
break;
|
||||
|
||||
|
||||
case RenderBuffer::T_front_left:
|
||||
GLP(ReadBuffer)(GL_FRONT_LEFT);
|
||||
break;
|
||||
|
||||
|
||||
case RenderBuffer::T_back_right:
|
||||
GLP(ReadBuffer)(GL_BACK_RIGHT);
|
||||
break;
|
||||
|
||||
|
||||
case RenderBuffer::T_back_left:
|
||||
GLP(ReadBuffer)(GL_BACK_LEFT);
|
||||
break;
|
||||
|
||||
|
||||
default:
|
||||
GLP(ReadBuffer)(GL_FRONT_AND_BACK);
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
report_my_gl_errors();
|
||||
}
|
||||
|
||||
@ -4639,16 +4839,16 @@ get_external_image_format(Texture *tex) const {
|
||||
case Texture::F_color_index:
|
||||
case Texture::F_stencil_index:
|
||||
case Texture::F_depth_component:
|
||||
// This shouldn't be possible.
|
||||
nassertr(false, GL_RGB);
|
||||
break;
|
||||
// This shouldn't be possible.
|
||||
nassertr(false, GL_RGB);
|
||||
break;
|
||||
|
||||
case Texture::F_rgba:
|
||||
case Texture::F_rgbm:
|
||||
case Texture::F_rgba4:
|
||||
case Texture::F_rgba8:
|
||||
case Texture::F_rgba12:
|
||||
return GL_COMPRESSED_RGBA;
|
||||
return GL_COMPRESSED_RGBA;
|
||||
|
||||
case Texture::F_rgb:
|
||||
case Texture::F_rgb5:
|
||||
@ -4656,20 +4856,20 @@ get_external_image_format(Texture *tex) const {
|
||||
case Texture::F_rgb8:
|
||||
case Texture::F_rgb12:
|
||||
case Texture::F_rgb332:
|
||||
return GL_COMPRESSED_RGB;
|
||||
return GL_COMPRESSED_RGB;
|
||||
|
||||
case Texture::F_alpha:
|
||||
return GL_COMPRESSED_ALPHA;
|
||||
return GL_COMPRESSED_ALPHA;
|
||||
|
||||
case Texture::F_red:
|
||||
case Texture::F_green:
|
||||
case Texture::F_blue:
|
||||
case Texture::F_luminance:
|
||||
return GL_COMPRESSED_LUMINANCE;
|
||||
return GL_COMPRESSED_LUMINANCE;
|
||||
|
||||
case Texture::F_luminance_alpha:
|
||||
case Texture::F_luminance_alphamask:
|
||||
return GL_COMPRESSED_LUMINANCE_ALPHA;
|
||||
return GL_COMPRESSED_LUMINANCE_ALPHA;
|
||||
}
|
||||
break;
|
||||
|
||||
@ -4679,13 +4879,13 @@ get_external_image_format(Texture *tex) const {
|
||||
} else {
|
||||
return GL_COMPRESSED_RGB_S3TC_DXT1_EXT;
|
||||
}
|
||||
|
||||
|
||||
case Texture::CM_dxt3:
|
||||
return GL_COMPRESSED_RGBA_S3TC_DXT3_EXT;
|
||||
|
||||
|
||||
case Texture::CM_dxt5:
|
||||
return GL_COMPRESSED_RGBA_S3TC_DXT5_EXT;
|
||||
|
||||
|
||||
case Texture::CM_fxt1:
|
||||
if (Texture::has_alpha(tex->get_format())) {
|
||||
return GL_COMPRESSED_RGBA_FXT1_3DFX;
|
||||
@ -4772,37 +4972,37 @@ get_internal_image_format(Texture *tex) const {
|
||||
case Texture::F_color_index:
|
||||
case Texture::F_stencil_index:
|
||||
case Texture::F_depth_component:
|
||||
// Unsupported; fall through to below.
|
||||
break;
|
||||
// Unsupported; fall through to below.
|
||||
break;
|
||||
|
||||
case Texture::F_rgbm:
|
||||
if (get_supports_compressed_texture_format(Texture::CM_dxt1) && !is_3d) {
|
||||
return GL_COMPRESSED_RGBA_S3TC_DXT1_EXT;
|
||||
} else if (get_supports_compressed_texture_format(Texture::CM_fxt1) && !is_3d) {
|
||||
return GL_COMPRESSED_RGBA_FXT1_3DFX;
|
||||
} else {
|
||||
return GL_COMPRESSED_RGBA;
|
||||
}
|
||||
if (get_supports_compressed_texture_format(Texture::CM_dxt1) && !is_3d) {
|
||||
return GL_COMPRESSED_RGBA_S3TC_DXT1_EXT;
|
||||
} else if (get_supports_compressed_texture_format(Texture::CM_fxt1) && !is_3d) {
|
||||
return GL_COMPRESSED_RGBA_FXT1_3DFX;
|
||||
} else {
|
||||
return GL_COMPRESSED_RGBA;
|
||||
}
|
||||
|
||||
case Texture::F_rgba4:
|
||||
if (get_supports_compressed_texture_format(Texture::CM_dxt3) && !is_3d) {
|
||||
return GL_COMPRESSED_RGBA_S3TC_DXT3_EXT;
|
||||
} else if (get_supports_compressed_texture_format(Texture::CM_fxt1) && !is_3d) {
|
||||
return GL_COMPRESSED_RGBA_FXT1_3DFX;
|
||||
} else {
|
||||
return GL_COMPRESSED_RGBA;
|
||||
}
|
||||
if (get_supports_compressed_texture_format(Texture::CM_dxt3) && !is_3d) {
|
||||
return GL_COMPRESSED_RGBA_S3TC_DXT3_EXT;
|
||||
} else if (get_supports_compressed_texture_format(Texture::CM_fxt1) && !is_3d) {
|
||||
return GL_COMPRESSED_RGBA_FXT1_3DFX;
|
||||
} else {
|
||||
return GL_COMPRESSED_RGBA;
|
||||
}
|
||||
|
||||
case Texture::F_rgba:
|
||||
case Texture::F_rgba8:
|
||||
case Texture::F_rgba12:
|
||||
if (get_supports_compressed_texture_format(Texture::CM_dxt5) && !is_3d) {
|
||||
return GL_COMPRESSED_RGBA_S3TC_DXT5_EXT;
|
||||
} else if (get_supports_compressed_texture_format(Texture::CM_fxt1) && !is_3d) {
|
||||
return GL_COMPRESSED_RGBA_FXT1_3DFX;
|
||||
} else {
|
||||
return GL_COMPRESSED_RGBA;
|
||||
}
|
||||
if (get_supports_compressed_texture_format(Texture::CM_dxt5) && !is_3d) {
|
||||
return GL_COMPRESSED_RGBA_S3TC_DXT5_EXT;
|
||||
} else if (get_supports_compressed_texture_format(Texture::CM_fxt1) && !is_3d) {
|
||||
return GL_COMPRESSED_RGBA_FXT1_3DFX;
|
||||
} else {
|
||||
return GL_COMPRESSED_RGBA;
|
||||
}
|
||||
|
||||
case Texture::F_rgb:
|
||||
case Texture::F_rgb5:
|
||||
@ -4810,26 +5010,26 @@ get_internal_image_format(Texture *tex) const {
|
||||
case Texture::F_rgb8:
|
||||
case Texture::F_rgb12:
|
||||
case Texture::F_rgb332:
|
||||
if (get_supports_compressed_texture_format(Texture::CM_dxt1) && !is_3d) {
|
||||
return GL_COMPRESSED_RGB_S3TC_DXT1_EXT;
|
||||
} else if (get_supports_compressed_texture_format(Texture::CM_fxt1) && !is_3d) {
|
||||
return GL_COMPRESSED_RGB_FXT1_3DFX;
|
||||
} else {
|
||||
return GL_COMPRESSED_RGB;
|
||||
}
|
||||
if (get_supports_compressed_texture_format(Texture::CM_dxt1) && !is_3d) {
|
||||
return GL_COMPRESSED_RGB_S3TC_DXT1_EXT;
|
||||
} else if (get_supports_compressed_texture_format(Texture::CM_fxt1) && !is_3d) {
|
||||
return GL_COMPRESSED_RGB_FXT1_3DFX;
|
||||
} else {
|
||||
return GL_COMPRESSED_RGB;
|
||||
}
|
||||
|
||||
case Texture::F_alpha:
|
||||
return GL_COMPRESSED_ALPHA;
|
||||
return GL_COMPRESSED_ALPHA;
|
||||
|
||||
case Texture::F_red:
|
||||
case Texture::F_green:
|
||||
case Texture::F_blue:
|
||||
case Texture::F_luminance:
|
||||
return GL_COMPRESSED_LUMINANCE;
|
||||
return GL_COMPRESSED_LUMINANCE;
|
||||
|
||||
case Texture::F_luminance_alpha:
|
||||
case Texture::F_luminance_alphamask:
|
||||
return GL_COMPRESSED_LUMINANCE_ALPHA;
|
||||
return GL_COMPRESSED_LUMINANCE_ALPHA;
|
||||
}
|
||||
break;
|
||||
|
||||
@ -4839,20 +5039,20 @@ get_internal_image_format(Texture *tex) const {
|
||||
} else {
|
||||
return GL_COMPRESSED_RGB_S3TC_DXT1_EXT;
|
||||
}
|
||||
|
||||
|
||||
case Texture::CM_dxt3:
|
||||
return GL_COMPRESSED_RGBA_S3TC_DXT3_EXT;
|
||||
|
||||
|
||||
case Texture::CM_dxt5:
|
||||
return GL_COMPRESSED_RGBA_S3TC_DXT5_EXT;
|
||||
|
||||
|
||||
case Texture::CM_fxt1:
|
||||
if (Texture::has_alpha(tex->get_format())) {
|
||||
return GL_COMPRESSED_RGBA_FXT1_3DFX;
|
||||
} else {
|
||||
return GL_COMPRESSED_RGB_FXT1_3DFX;
|
||||
}
|
||||
|
||||
|
||||
case Texture::CM_default:
|
||||
case Texture::CM_off:
|
||||
case Texture::CM_dxt2:
|
||||
@ -6416,7 +6616,7 @@ upload_texture(CLP(TextureContext) *gtc) {
|
||||
} else {
|
||||
image_compression = tex->get_ram_image_compression();
|
||||
}
|
||||
|
||||
|
||||
int width = tex->get_x_size();
|
||||
int height = tex->get_y_size();
|
||||
int depth = tex->get_z_size();
|
||||
@ -6500,7 +6700,7 @@ upload_texture(CLP(TextureContext) *gtc) {
|
||||
depth = new_depth;
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
if (!_supports_bgr) {
|
||||
// If the GL doesn't claim to support BGR, we may have to reverse
|
||||
// the component ordering of the image.
|
||||
@ -6612,10 +6812,10 @@ upload_texture_image(CLP(TextureContext) *gtc,
|
||||
int width, int height, int depth,
|
||||
GLint external_format, GLenum component_type,
|
||||
bool one_page_only, int z,
|
||||
Texture::CompressionMode image_compression) {
|
||||
Texture::CompressionMode image_compression) {
|
||||
// Make sure the error stack is cleared out before we begin.
|
||||
report_my_gl_errors();
|
||||
|
||||
|
||||
if (target == GL_NONE) {
|
||||
// Unsupported target (e.g. 3-d texturing on GL 1.1).
|
||||
return false;
|
||||
@ -6631,10 +6831,10 @@ upload_texture_image(CLP(TextureContext) *gtc,
|
||||
if (GLCAT.is_debug()) {
|
||||
if (image_compression != Texture::CM_off) {
|
||||
GLCAT.debug()
|
||||
<< "loading pre-compressed texture " << tex->get_name() << "\n";
|
||||
<< "loading pre-compressed texture " << tex->get_name() << "\n";
|
||||
} else if (is_compressed_format(internal_format)) {
|
||||
GLCAT.debug()
|
||||
<< "compressing texture " << tex->get_name() << "\n";
|
||||
<< "compressing texture " << tex->get_name() << "\n";
|
||||
}
|
||||
}
|
||||
|
||||
@ -6655,17 +6855,17 @@ upload_texture_image(CLP(TextureContext) *gtc,
|
||||
num_ram_mipmap_levels = 1;
|
||||
if (uses_mipmaps) {
|
||||
num_ram_mipmap_levels = tex->get_num_ram_mipmap_images();
|
||||
|
||||
|
||||
if (num_ram_mipmap_levels == 1) {
|
||||
// No RAM mipmap levels available. Should we generate some?
|
||||
if (!_supports_generate_mipmap ||
|
||||
if (!_supports_generate_mipmap ||
|
||||
(!auto_generate_mipmaps && image_compression == Texture::CM_off)) {
|
||||
// Yes, the GL won't generate them, so we need to.
|
||||
tex->generate_ram_mipmap_images();
|
||||
num_ram_mipmap_levels = tex->get_num_ram_mipmap_images();
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
if (num_ram_mipmap_levels != 1) {
|
||||
// We will load the mipmap levels from RAM. Don't ask the GL to
|
||||
// generate them.
|
||||
@ -6673,7 +6873,7 @@ upload_texture_image(CLP(TextureContext) *gtc,
|
||||
GLP(TexParameteri)(target, GL_GENERATE_MIPMAP, false);
|
||||
}
|
||||
load_ram_mipmaps = true;
|
||||
|
||||
|
||||
} else {
|
||||
// We don't have mipmap levels in RAM. Ask the GL to generate
|
||||
// them if it can.
|
||||
@ -6687,10 +6887,10 @@ upload_texture_image(CLP(TextureContext) *gtc,
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
int highest_level = 0;
|
||||
|
||||
|
||||
|
||||
|
||||
if (!gtc->_already_applied ||
|
||||
gtc->_uses_mipmaps != uses_mipmaps ||
|
||||
gtc->_internal_format != internal_format ||
|
||||
@ -6716,7 +6916,7 @@ upload_texture_image(CLP(TextureContext) *gtc,
|
||||
external_format, GL_UNSIGNED_BYTE, blank_image);
|
||||
delete blank_image;
|
||||
}
|
||||
|
||||
|
||||
for (int n = 0; n < num_ram_mipmap_levels; ++n) {
|
||||
const unsigned char *image = tex->get_ram_mipmap_image(n);
|
||||
if (image == (const unsigned char *)NULL) {
|
||||
@ -6746,7 +6946,7 @@ upload_texture_image(CLP(TextureContext) *gtc,
|
||||
0, image_size, image);
|
||||
}
|
||||
break;
|
||||
|
||||
|
||||
case GL_TEXTURE_3D:
|
||||
if (_supports_3d_texture) {
|
||||
if (image_compression == Texture::CM_off) {
|
||||
@ -6754,7 +6954,7 @@ upload_texture_image(CLP(TextureContext) *gtc,
|
||||
width, height, depth, 0,
|
||||
external_format, component_type, image);
|
||||
} else {
|
||||
_glCompressedTexImage3D(target, n, external_format, width,
|
||||
_glCompressedTexImage3D(target, n, external_format, width,
|
||||
height, depth,
|
||||
0, image_size, image);
|
||||
}
|
||||
@ -6763,14 +6963,14 @@ upload_texture_image(CLP(TextureContext) *gtc,
|
||||
return false;
|
||||
}
|
||||
break;
|
||||
|
||||
|
||||
default:
|
||||
if (image_compression == Texture::CM_off) {
|
||||
GLP(TexImage2D)(target, n, internal_format,
|
||||
width, height, 0,
|
||||
external_format, component_type, image);
|
||||
} else {
|
||||
_glCompressedTexImage2D(target, n, external_format, width, height,
|
||||
_glCompressedTexImage2D(target, n, external_format, width, height,
|
||||
0, image_size, image);
|
||||
}
|
||||
}
|
||||
@ -6827,7 +7027,7 @@ upload_texture_image(CLP(TextureContext) *gtc,
|
||||
return false;
|
||||
}
|
||||
break;
|
||||
|
||||
|
||||
default:
|
||||
if (image_compression == Texture::CM_off) {
|
||||
GLP(TexSubImage2D)(target, n, 0, 0, width, height,
|
||||
@ -6905,15 +7105,15 @@ get_texture_memory_size(Texture *tex) {
|
||||
if (is_compressed_format(internal_format)) {
|
||||
// Try to get the compressed size.
|
||||
GLint image_size;
|
||||
GLP(GetTexLevelParameteriv)(page_target, 0,
|
||||
GLP(GetTexLevelParameteriv)(page_target, 0,
|
||||
GL_TEXTURE_COMPRESSED_IMAGE_SIZE, &image_size);
|
||||
|
||||
|
||||
GLenum error_code = GLP(GetError)();
|
||||
if (error_code != GL_NO_ERROR) {
|
||||
if (GLCAT.is_debug()) {
|
||||
GLCAT.debug()
|
||||
<< "Couldn't get compressed size for " << tex->get_name()
|
||||
<< " : " << get_error_string(error_code) << "\n";
|
||||
GLCAT.debug()
|
||||
<< "Couldn't get compressed size for " << tex->get_name()
|
||||
<< " : " << get_error_string(error_code) << "\n";
|
||||
}
|
||||
// Fall through to the noncompressed case.
|
||||
} else {
|
||||
@ -6922,26 +7122,26 @@ get_texture_memory_size(Texture *tex) {
|
||||
}
|
||||
|
||||
// OK, get the noncompressed size.
|
||||
GLint red_size, green_size, blue_size, alpha_size,
|
||||
GLint red_size, green_size, blue_size, alpha_size,
|
||||
luminance_size, intensity_size;
|
||||
GLint depth_size = 0;
|
||||
GLP(GetTexLevelParameteriv)(page_target, 0,
|
||||
GLP(GetTexLevelParameteriv)(page_target, 0,
|
||||
GL_TEXTURE_RED_SIZE, &red_size);
|
||||
GLP(GetTexLevelParameteriv)(page_target, 0,
|
||||
GLP(GetTexLevelParameteriv)(page_target, 0,
|
||||
GL_TEXTURE_GREEN_SIZE, &green_size);
|
||||
GLP(GetTexLevelParameteriv)(page_target, 0,
|
||||
GLP(GetTexLevelParameteriv)(page_target, 0,
|
||||
GL_TEXTURE_BLUE_SIZE, &blue_size);
|
||||
GLP(GetTexLevelParameteriv)(page_target, 0,
|
||||
GLP(GetTexLevelParameteriv)(page_target, 0,
|
||||
GL_TEXTURE_ALPHA_SIZE, &alpha_size);
|
||||
GLP(GetTexLevelParameteriv)(page_target, 0,
|
||||
GLP(GetTexLevelParameteriv)(page_target, 0,
|
||||
GL_TEXTURE_LUMINANCE_SIZE, &luminance_size);
|
||||
GLP(GetTexLevelParameteriv)(page_target, 0,
|
||||
GLP(GetTexLevelParameteriv)(page_target, 0,
|
||||
GL_TEXTURE_INTENSITY_SIZE, &intensity_size);
|
||||
if (_supports_depth_texture) {
|
||||
// Actually, this seems to cause problems on some Mesa versions,
|
||||
// even though they advertise GL_ARB_depth_texture. Who needs it.
|
||||
// GLP(GetTexLevelParameteriv)(page_target, 0,
|
||||
// GL_TEXTURE_DEPTH_SIZE, &depth_size);
|
||||
// GLP(GetTexLevelParameteriv)(page_target, 0,
|
||||
// GL_TEXTURE_DEPTH_SIZE, &depth_size);
|
||||
}
|
||||
|
||||
GLint width = 1, height = 1, depth = 1;
|
||||
@ -7013,9 +7213,9 @@ check_nonresident_texture(BufferContextChain &chain) {
|
||||
////////////////////////////////////////////////////////////////////
|
||||
bool CLP(GraphicsStateGuardian)::
|
||||
extract_texture_image(PTA_uchar &image, size_t &page_size,
|
||||
Texture *tex, GLenum target, GLenum page_target,
|
||||
Texture::ComponentType type,
|
||||
Texture::CompressionMode compression, int n) {
|
||||
Texture *tex, GLenum target, GLenum page_target,
|
||||
Texture::ComponentType type,
|
||||
Texture::CompressionMode compression, int n) {
|
||||
if (target == GL_TEXTURE_CUBE_MAP) {
|
||||
// A cube map, compressed or uncompressed. This we must extract
|
||||
// one page at a time.
|
||||
@ -7034,8 +7234,8 @@ extract_texture_image(PTA_uchar &image, size_t &page_size,
|
||||
|
||||
if (compression != Texture::CM_off) {
|
||||
GLint image_size;
|
||||
GLP(GetTexLevelParameteriv)(page_target, n,
|
||||
GL_TEXTURE_COMPRESSED_IMAGE_SIZE, &image_size);
|
||||
GLP(GetTexLevelParameteriv)(page_target, n,
|
||||
GL_TEXTURE_COMPRESSED_IMAGE_SIZE, &image_size);
|
||||
nassertr(image_size <= (int)page_size, false);
|
||||
page_size = image_size;
|
||||
}
|
||||
@ -7044,12 +7244,12 @@ extract_texture_image(PTA_uchar &image, size_t &page_size,
|
||||
|
||||
for (int z = 0; z < 6; ++z) {
|
||||
page_target = GL_TEXTURE_CUBE_MAP_POSITIVE_X + z;
|
||||
|
||||
|
||||
if (compression == Texture::CM_off) {
|
||||
GLP(GetTexImage)(page_target, n, external_format, pixel_type,
|
||||
image.p() + z * page_size);
|
||||
GLP(GetTexImage)(page_target, n, external_format, pixel_type,
|
||||
image.p() + z * page_size);
|
||||
} else {
|
||||
_glGetCompressedTexImage(page_target, 0, image.p() + z * page_size);
|
||||
_glGetCompressedTexImage(page_target, 0, image.p() + z * page_size);
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -78,6 +78,7 @@ typedef void (APIENTRYP PFNGLCOMPRESSEDTEXIMAGE1DPROC) (GLenum target, GLint lev
|
||||
typedef void (APIENTRYP PFNGLCOMPRESSEDTEXSUBIMAGE3DPROC) (GLenum target, GLint level, GLint xoffset, GLint yoffset, GLint zoffset, GLsizei width, GLsizei height, GLsizei depth, GLenum format, GLsizei imageSize, const GLvoid *data);
|
||||
typedef void (APIENTRYP PFNGLCOMPRESSEDTEXSUBIMAGE2DPROC) (GLenum target, GLint level, GLint xoffset, GLint yoffset, GLsizei width, GLsizei height, GLenum format, GLsizei imageSize, const GLvoid *data);
|
||||
typedef void (APIENTRYP PFNGLCOMPRESSEDTEXSUBIMAGE1DPROC) (GLenum target, GLint level, GLint xoffset, GLsizei width, GLenum format, GLsizei imageSize, const GLvoid *data);
|
||||
typedef void (APIENTRY * PFNGLACTIVESTENCILFACEEXTPROC) (GLenum face);
|
||||
#endif // __EDG__
|
||||
|
||||
////////////////////////////////////////////////////////////////////
|
||||
@ -90,12 +91,12 @@ class EXPCL_GL CLP(GraphicsStateGuardian) : public GraphicsStateGuardian {
|
||||
public:
|
||||
CLP(GraphicsStateGuardian)(const FrameBufferProperties &properties);
|
||||
virtual ~CLP(GraphicsStateGuardian)();
|
||||
|
||||
|
||||
virtual void reset();
|
||||
|
||||
virtual void do_clear(const RenderBuffer &buffer);
|
||||
|
||||
virtual void prepare_display_region(DisplayRegionPipelineReader *dr,
|
||||
virtual void prepare_display_region(DisplayRegionPipelineReader *dr,
|
||||
Lens::StereoChannel stereo_channel);
|
||||
virtual CPT(TransformState) calc_projection_mat(const Lens *lens);
|
||||
virtual bool prepare_lens();
|
||||
@ -103,7 +104,7 @@ public:
|
||||
virtual bool begin_frame(Thread *current_thread);
|
||||
virtual void end_frame(Thread *current_thread);
|
||||
|
||||
virtual bool begin_draw_primitives(const GeomPipelineReader *geom_reader,
|
||||
virtual bool begin_draw_primitives(const GeomPipelineReader *geom_reader,
|
||||
const GeomMunger *munger,
|
||||
const GeomVertexDataPipelineReader *data_reader);
|
||||
virtual void draw_triangles(const GeomPrimitivePipelineReader *reader);
|
||||
@ -125,7 +126,7 @@ public:
|
||||
|
||||
virtual ShaderContext *prepare_shader(ShaderExpansion *shader);
|
||||
virtual void release_shader(ShaderContext *sc);
|
||||
|
||||
|
||||
void record_deleted_display_list(GLuint index);
|
||||
|
||||
virtual VertexBufferContext *prepare_vertex_buffer(GeomVertexArrayData *data);
|
||||
@ -153,11 +154,11 @@ public:
|
||||
|
||||
void apply_fog(Fog *fog);
|
||||
|
||||
virtual void bind_light(PointLight *light_obj, const NodePath &light,
|
||||
virtual void bind_light(PointLight *light_obj, const NodePath &light,
|
||||
int light_id);
|
||||
virtual void bind_light(DirectionalLight *light_obj, const NodePath &light,
|
||||
virtual void bind_light(DirectionalLight *light_obj, const NodePath &light,
|
||||
int light_id);
|
||||
virtual void bind_light(Spotlight *light_obj, const NodePath &light,
|
||||
virtual void bind_light(Spotlight *light_obj, const NodePath &light,
|
||||
int light_id);
|
||||
|
||||
void print_gfx_visual();
|
||||
@ -186,7 +187,7 @@ public:
|
||||
const TransformState *transform);
|
||||
|
||||
void bind_fbo(GLuint fbo);
|
||||
|
||||
|
||||
protected:
|
||||
void do_issue_transform();
|
||||
void do_issue_render_mode();
|
||||
@ -207,7 +208,7 @@ protected:
|
||||
void do_issue_tex_gen();
|
||||
void do_issue_tex_matrix();
|
||||
|
||||
static bool report_errors_loop(int line, const char *source_file,
|
||||
static bool report_errors_loop(int line, const char *source_file,
|
||||
GLenum error_code, int &error_count);
|
||||
static string get_error_string(GLenum error_code);
|
||||
string show_gl_string(const string &name, GLenum id);
|
||||
@ -260,7 +261,7 @@ protected:
|
||||
GLenum get_texture_target(Texture::TextureType texture_type) const;
|
||||
GLenum get_texture_wrap_mode(Texture::WrapMode wm) const;
|
||||
static Texture::WrapMode get_panda_wrap_mode(GLenum wm);
|
||||
static GLenum get_texture_filter_type(Texture::FilterType ft,
|
||||
static GLenum get_texture_filter_type(Texture::FilterType ft,
|
||||
Texture::Format fmt, bool ignore_mipmaps);
|
||||
static Texture::FilterType get_panda_filter_type(GLenum ft);
|
||||
static GLenum get_component_type(Texture::ComponentType component_type);
|
||||
@ -271,7 +272,7 @@ protected:
|
||||
static GLint get_texture_apply_mode_type(TextureStage::Mode am);
|
||||
static GLint get_texture_combine_type(TextureStage::CombineMode cm);
|
||||
GLint get_texture_src_type(TextureStage::CombineSource cs,
|
||||
int last_stage, int last_saved_result,
|
||||
int last_stage, int last_saved_result,
|
||||
int this_stage) const;
|
||||
static GLint get_texture_operand_type(TextureStage::CombineOperand co);
|
||||
static GLenum get_fog_mode_type(Fog::Mode m);
|
||||
@ -288,19 +289,19 @@ protected:
|
||||
void specify_texture(Texture *tex);
|
||||
void apply_texture(TextureContext *tc);
|
||||
bool upload_texture(CLP(TextureContext) *gtc);
|
||||
bool upload_texture_image(CLP(TextureContext) *gtc, bool uses_mipmaps,
|
||||
GLenum target, GLint internal_format,
|
||||
bool upload_texture_image(CLP(TextureContext) *gtc, bool uses_mipmaps,
|
||||
GLenum target, GLint internal_format,
|
||||
int width, int height, int depth,
|
||||
GLint external_format, GLenum component_type,
|
||||
GLint external_format, GLenum component_type,
|
||||
bool one_page_only, int z,
|
||||
Texture::CompressionMode image_compression);
|
||||
Texture::CompressionMode image_compression);
|
||||
|
||||
size_t get_texture_memory_size(Texture *tex);
|
||||
void check_nonresident_texture(BufferContextChain &chain);
|
||||
bool extract_texture_image(PTA_uchar &image, size_t &page_size,
|
||||
Texture *tex, GLenum target, GLenum page_target,
|
||||
Texture::ComponentType type,
|
||||
Texture::CompressionMode compression, int n);
|
||||
Texture *tex, GLenum target, GLenum page_target,
|
||||
Texture::ComponentType type,
|
||||
Texture::CompressionMode compression, int n);
|
||||
|
||||
void do_point_size();
|
||||
|
||||
@ -329,7 +330,7 @@ protected:
|
||||
bool _polygon_offset_enabled;
|
||||
bool _flat_shade_model;
|
||||
int _decal_level;
|
||||
|
||||
|
||||
bool _dithering_enabled;
|
||||
|
||||
int _viewport_width;
|
||||
@ -339,14 +340,14 @@ protected:
|
||||
float _point_size;
|
||||
bool _point_perspective;
|
||||
bool _vertex_blending_enabled;
|
||||
|
||||
|
||||
PT(ShaderExpansion) _current_shader_expansion;
|
||||
CLP(ShaderContext) *_current_shader_context;
|
||||
PT(ShaderExpansion) _vertex_array_shader_expansion;
|
||||
CLP(ShaderContext) *_vertex_array_shader_context;
|
||||
PT(ShaderExpansion) _texture_binding_shader_expansion;
|
||||
CLP(ShaderContext) *_texture_binding_shader_context;
|
||||
|
||||
|
||||
#ifdef SUPPORT_IMMEDIATE_MODE
|
||||
CLP(ImmediateModeSender) _sender;
|
||||
bool _use_sender;
|
||||
@ -358,7 +359,7 @@ protected:
|
||||
GLuint _current_vbuffer_index;
|
||||
GLuint _current_ibuffer_index;
|
||||
GLuint _current_fbo;
|
||||
|
||||
|
||||
int _error_count;
|
||||
|
||||
string _gl_vendor;
|
||||
@ -435,7 +436,7 @@ public:
|
||||
PFNGLFRAMEBUFFERRENDERBUFFEREXTPROC _glFramebufferRenderbuffer;
|
||||
PFNGLGETFRAMEBUFFERATTACHMENTPARAMETERIVEXTPROC _glGetFramebufferAttachmentParameteriv;
|
||||
PFNGLGENERATEMIPMAPEXTPROC _glGenerateMipmap;
|
||||
|
||||
|
||||
PFNGLDRAWBUFFERSPROC _glDrawBuffers;
|
||||
|
||||
PFNGLGENQUERIESPROC _glGenQueries;
|
||||
@ -444,6 +445,8 @@ public:
|
||||
PFNGLDELETEQUERIESPROC _glDeleteQueries;
|
||||
PFNGLGETQUERYOBJECTUIVPROC _glGetQueryObjectuiv;
|
||||
|
||||
PFNGLACTIVESTENCILFACEEXTPROC _glActiveStencilFaceEXT;
|
||||
|
||||
GLenum _edge_clamp;
|
||||
GLenum _border_clamp;
|
||||
GLenum _mirror_repeat;
|
||||
|
@ -100,6 +100,7 @@
|
||||
showBoundsEffect.I showBoundsEffect.h \
|
||||
spotlight.I spotlight.h \
|
||||
stateMunger.I stateMunger.h \
|
||||
stencilAttrib.I stencilAttrib.h \
|
||||
switchNode.I switchNode.h \
|
||||
texMatrixAttrib.I texMatrixAttrib.h \
|
||||
texProjectorEffect.I texProjectorEffect.h \
|
||||
@ -202,6 +203,7 @@
|
||||
showBoundsEffect.cxx \
|
||||
spotlight.cxx \
|
||||
stateMunger.cxx \
|
||||
stencilAttrib.cxx \
|
||||
switchNode.cxx \
|
||||
texMatrixAttrib.cxx \
|
||||
texProjectorEffect.cxx \
|
||||
@ -301,6 +303,7 @@
|
||||
showBoundsEffect.I showBoundsEffect.h \
|
||||
spotlight.I spotlight.h \
|
||||
stateMunger.I stateMunger.h \
|
||||
stencilAttrib.I stencilAttrib.h \
|
||||
switchNode.I switchNode.h \
|
||||
texMatrixAttrib.I texMatrixAttrib.h \
|
||||
texProjectorEffect.I texProjectorEffect.h \
|
||||
|
@ -43,6 +43,7 @@ clear_to_zero() {
|
||||
_rescale_normal = NULL;
|
||||
_shade_model = NULL;
|
||||
_shader = NULL;
|
||||
_stencil = NULL;
|
||||
_tex_gen = NULL;
|
||||
_tex_matrix = NULL;
|
||||
_texture = NULL;
|
||||
|
@ -51,13 +51,14 @@ initialize_defvals() {
|
||||
_defvals._rescale_normal = DCAST(RescaleNormalAttrib,RescaleNormalAttrib::make_default());
|
||||
_defvals._shade_model = DCAST(ShadeModelAttrib,ShadeModelAttrib::make(ShadeModelAttrib::M_smooth));
|
||||
_defvals._shader = DCAST(ShaderAttrib,ShaderAttrib::make_off());
|
||||
_defvals._stencil = DCAST(StencilAttrib,StencilAttrib::make());
|
||||
_defvals._tex_gen = DCAST(TexGenAttrib,TexGenAttrib::make());
|
||||
_defvals._tex_matrix = DCAST(TexMatrixAttrib,TexMatrixAttrib::make());
|
||||
_defvals._texture = DCAST(TextureAttrib,TextureAttrib::make_all_off());
|
||||
_defvals._transparency = DCAST(TransparencyAttrib,TransparencyAttrib::make(TransparencyAttrib::M_none));
|
||||
|
||||
|
||||
// Step two. Replace each with make_default_impl.
|
||||
|
||||
|
||||
_defvals._alpha_test = DCAST(AlphaTestAttrib,_defvals._alpha_test->make_default());
|
||||
_defvals._antialias = DCAST(AntialiasAttrib,_defvals._antialias->make_default());
|
||||
_defvals._clip_plane = DCAST(ClipPlaneAttrib,_defvals._clip_plane->make_default());
|
||||
@ -77,6 +78,7 @@ initialize_defvals() {
|
||||
_defvals._rescale_normal = DCAST(RescaleNormalAttrib,_defvals._rescale_normal->make_default());
|
||||
_defvals._shade_model = DCAST(ShadeModelAttrib,_defvals._shade_model->make_default());
|
||||
_defvals._shader = DCAST(ShaderAttrib,_defvals._shader->make_default());
|
||||
_defvals._stencil = DCAST(StencilAttrib,_defvals._stencil->make_default());
|
||||
_defvals._tex_gen = DCAST(TexGenAttrib,_defvals._tex_gen->make_default());
|
||||
_defvals._tex_matrix = DCAST(TexMatrixAttrib,_defvals._tex_matrix->make_default());
|
||||
_defvals._texture = DCAST(TextureAttrib,_defvals._texture->make_default());
|
||||
@ -118,6 +120,7 @@ AttribSlots(const AttribSlots ©) :
|
||||
_rescale_normal(copy._rescale_normal),
|
||||
_shade_model(copy._shade_model),
|
||||
_shader(copy._shader),
|
||||
_stencil(copy._stencil),
|
||||
_tex_gen(copy._tex_gen),
|
||||
_tex_matrix(copy._tex_matrix),
|
||||
_texture(copy._texture),
|
||||
@ -151,6 +154,7 @@ operator =(const AttribSlots &src) {
|
||||
_rescale_normal = src._rescale_normal;
|
||||
_shade_model = src._shade_model;
|
||||
_shader = src._shader;
|
||||
_stencil = src._stencil;
|
||||
_tex_gen = src._tex_gen;
|
||||
_tex_matrix = src._tex_matrix;
|
||||
_texture = src._texture;
|
||||
@ -184,10 +188,11 @@ get_slot(int n) const {
|
||||
case 16: return DCAST(RenderAttrib, _rescale_normal);
|
||||
case 17: return DCAST(RenderAttrib, _shade_model);
|
||||
case 18: return DCAST(RenderAttrib, _shader);
|
||||
case 19: return DCAST(RenderAttrib, _tex_gen);
|
||||
case 20: return DCAST(RenderAttrib, _tex_matrix);
|
||||
case 21: return DCAST(RenderAttrib, _texture);
|
||||
case 22: return DCAST(RenderAttrib, _transparency);
|
||||
case 19: return DCAST(RenderAttrib, _stencil);
|
||||
case 20: return DCAST(RenderAttrib, _tex_gen);
|
||||
case 21: return DCAST(RenderAttrib, _tex_matrix);
|
||||
case 22: return DCAST(RenderAttrib, _texture);
|
||||
case 23: return DCAST(RenderAttrib, _transparency);
|
||||
default:
|
||||
nassertr(false, NULL);
|
||||
return NULL;
|
||||
@ -221,11 +226,11 @@ set_slot(int n, const RenderAttrib *val) {
|
||||
case 16: _rescale_normal = DCAST(RescaleNormalAttrib, val); break;
|
||||
case 17: _shade_model = DCAST(ShadeModelAttrib, val); break;
|
||||
case 18: _shader = DCAST(ShaderAttrib, val); break;
|
||||
case 19: _tex_gen = DCAST(TexGenAttrib, val); break;
|
||||
case 20: _tex_matrix = DCAST(TexMatrixAttrib, val); break;
|
||||
case 21: _texture = DCAST(TextureAttrib, val); break;
|
||||
case 22: _transparency = DCAST(TransparencyAttrib, val); break;
|
||||
case 19: _stencil = DCAST(StencilAttrib, val); break;
|
||||
case 20: _tex_gen = DCAST(TexGenAttrib, val); break;
|
||||
case 21: _tex_matrix = DCAST(TexMatrixAttrib, val); break;
|
||||
case 22: _texture = DCAST(TextureAttrib, val); break;
|
||||
case 23: _transparency = DCAST(TransparencyAttrib, val); break;
|
||||
default: nassertv(false);
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -43,6 +43,7 @@
|
||||
#include "rescaleNormalAttrib.h"
|
||||
#include "shadeModelAttrib.h"
|
||||
#include "shaderAttrib.h"
|
||||
#include "stencilAttrib.h"
|
||||
#include "texMatrixAttrib.h"
|
||||
#include "texGenAttrib.h"
|
||||
#include "textureAttrib.h"
|
||||
@ -76,11 +77,12 @@ class EXPCL_PANDA AttribSlots
|
||||
CPT(RescaleNormalAttrib) _rescale_normal;
|
||||
CPT(ShadeModelAttrib) _shade_model;
|
||||
CPT(ShaderAttrib) _shader;
|
||||
CPT(StencilAttrib) _stencil;
|
||||
CPT(TexGenAttrib) _tex_gen;
|
||||
CPT(TexMatrixAttrib) _tex_matrix;
|
||||
CPT(TextureAttrib) _texture;
|
||||
CPT(TransparencyAttrib) _transparency;
|
||||
|
||||
|
||||
public:
|
||||
AttribSlots();
|
||||
AttribSlots(const AttribSlots ©);
|
||||
@ -91,10 +93,10 @@ class EXPCL_PANDA AttribSlots
|
||||
|
||||
public:
|
||||
// Each "array" reference requires a switch and a DCAST, so it's not overly fast.
|
||||
enum { slot_count=23 };
|
||||
enum { slot_count=24 };
|
||||
const RenderAttrib *get_slot(int n) const;
|
||||
void set_slot(int n, const RenderAttrib *attrib);
|
||||
|
||||
|
||||
private:
|
||||
static AttribSlots _defvals;
|
||||
static void initialize_defvals();
|
||||
|
@ -247,8 +247,8 @@ ConfigVariableBool m_dual_transparent
|
||||
ConfigVariableBool m_dual_flash
|
||||
("m-dual-flash", false,
|
||||
PRC_DESC("Set this true to flash any objects that use M_dual, for debugging."));
|
||||
|
||||
|
||||
|
||||
|
||||
ConfigVariableBool asynchronous_loads
|
||||
("asynchronous-loads", false,
|
||||
PRC_DESC("Set this true to support actual asynchronous loads via the "
|
||||
@ -258,7 +258,7 @@ ConfigVariableBool asynchronous_loads
|
||||
"this false for now."));
|
||||
|
||||
ConfigVariableList load_file_type
|
||||
("load-file-type",
|
||||
("load-file-type",
|
||||
PRC_DESC("List the model loader modules that Panda will automatically "
|
||||
"import when a new, unknown model type is loaded. This may be "
|
||||
"either the name of a module, or a space-separate list of filename "
|
||||
@ -344,6 +344,7 @@ init_libpgraph() {
|
||||
ShowBoundsEffect::init_type();
|
||||
Spotlight::init_type();
|
||||
StateMunger::init_type();
|
||||
StencilAttrib::init_type();
|
||||
SwitchNode::init_type();
|
||||
TexMatrixAttrib::init_type();
|
||||
TexProjectorEffect::init_type();
|
||||
@ -385,7 +386,7 @@ init_libpgraph() {
|
||||
LensNode::register_with_read_factory();
|
||||
LightAttrib::register_with_read_factory();
|
||||
LODNode::register_with_read_factory();
|
||||
MaterialAttrib::register_with_read_factory();
|
||||
MaterialAttrib::register_with_read_factory();
|
||||
ModelNode::register_with_read_factory();
|
||||
ModelRoot::register_with_read_factory();
|
||||
PandaNode::register_with_read_factory();
|
||||
|
@ -16,6 +16,7 @@
|
||||
#include "showBoundsEffect.cxx"
|
||||
#include "spotlight.cxx"
|
||||
#include "stateMunger.cxx"
|
||||
#include "stencilAttrib.cxx"
|
||||
#include "switchNode.cxx"
|
||||
#include "texMatrixAttrib.cxx"
|
||||
#include "texProjectorEffect.cxx"
|
||||
|
70
panda/src/pgraph/stencilAttrib.I
Normal file
70
panda/src/pgraph/stencilAttrib.I
Normal file
@ -0,0 +1,70 @@
|
||||
// Filename: stencilAttrib.I
|
||||
// Created by: aignacio (18May06)
|
||||
//
|
||||
////////////////////////////////////////////////////////////////////
|
||||
//
|
||||
// PANDA 3D SOFTWARE
|
||||
// Copyright (c) 2001 - 2006, Disney Enterprises, Inc. All rights reserved
|
||||
//
|
||||
// All use of this software is subject to the terms of the Panda 3d
|
||||
// Software license. You should have received a copy of this license
|
||||
// along with this source code; you will also find a current copy of
|
||||
// the license at http://etc.cmu.edu/panda3d/docs/license/ .
|
||||
//
|
||||
// To contact the maintainers of this program write to
|
||||
// panda3d-general@lists.sourceforge.net .
|
||||
//
|
||||
////////////////////////////////////////////////////////////////////
|
||||
|
||||
|
||||
////////////////////////////////////////////////////////////////////
|
||||
// Function: StencilAttrib::Constructor
|
||||
// Access: Private
|
||||
// Description: Use StencilAttrib::make() to construct a new
|
||||
// StencilAttrib object.
|
||||
////////////////////////////////////////////////////////////////////
|
||||
INLINE StencilAttrib::
|
||||
StencilAttrib() {
|
||||
|
||||
_stencil_render_states [SRS_clear_value] = 0;
|
||||
|
||||
_stencil_render_states [SRS_reference] = 0;
|
||||
|
||||
_stencil_render_states [SRS_read_mask] = ~0;
|
||||
_stencil_render_states [SRS_write_mask] = ~0;
|
||||
|
||||
_stencil_render_states [SRS_front_enable] = 0;
|
||||
_stencil_render_states [SRS_front_comparison_function] = SCF_always;
|
||||
_stencil_render_states [SRS_front_stencil_fail_operation] = SO_keep;
|
||||
_stencil_render_states [SRS_front_stencil_pass_z_fail_operation] = SO_keep;
|
||||
_stencil_render_states [SRS_front_stencil_pass_z_pass_operation] = SO_keep;
|
||||
|
||||
_stencil_render_states [SRS_back_enable] = 0;
|
||||
_stencil_render_states [SRS_back_comparison_function] = SCF_always;
|
||||
_stencil_render_states [SRS_back_stencil_fail_operation] = SO_keep;
|
||||
_stencil_render_states [SRS_back_stencil_pass_z_fail_operation] = SO_keep;
|
||||
_stencil_render_states [SRS_back_stencil_pass_z_pass_operation] = SO_keep;
|
||||
|
||||
_default = true;
|
||||
}
|
||||
|
||||
////////////////////////////////////////////////////////////////////
|
||||
// Function: StencilAttrib::set_render_state
|
||||
// Access: Published
|
||||
// Description: Sets the render state.
|
||||
////////////////////////////////////////////////////////////////////
|
||||
INLINE void StencilAttrib::
|
||||
set_render_state(unsigned int render_state_identifier, unsigned int render_state) {
|
||||
_stencil_render_states [render_state_identifier] = render_state;
|
||||
_default = false;
|
||||
}
|
||||
|
||||
////////////////////////////////////////////////////////////////////
|
||||
// Function: StencilAttrib::get_render_state
|
||||
// Access: Published
|
||||
// Description: Returns render state.
|
||||
////////////////////////////////////////////////////////////////////
|
||||
INLINE unsigned int StencilAttrib::
|
||||
get_render_state(unsigned int render_state_identifier) const {
|
||||
return _stencil_render_states [render_state_identifier];
|
||||
}
|
186
panda/src/pgraph/stencilAttrib.cxx
Normal file
186
panda/src/pgraph/stencilAttrib.cxx
Normal file
@ -0,0 +1,186 @@
|
||||
// Filename: stencilAttrib.cxx
|
||||
// Created by: aignacio (18May06)
|
||||
//
|
||||
////////////////////////////////////////////////////////////////////
|
||||
//
|
||||
// PANDA 3D SOFTWARE
|
||||
// Copyright (c) 2001 - 2006, Disney Enterprises, Inc. All rights reserved
|
||||
//
|
||||
// All use of this software is subject to the terms of the Panda 3d
|
||||
// Software license. You should have received a copy of this license
|
||||
// along with this source code; you will also find a current copy of
|
||||
// the license at http://etc.cmu.edu/panda3d/docs/license/ .
|
||||
//
|
||||
// To contact the maintainers of this program write to
|
||||
// panda3d-general@lists.sourceforge.net .
|
||||
//
|
||||
////////////////////////////////////////////////////////////////////
|
||||
|
||||
#include "stencilAttrib.h"
|
||||
#include "attribSlots.h"
|
||||
#include "graphicsStateGuardianBase.h"
|
||||
#include "dcast.h"
|
||||
#include "bamReader.h"
|
||||
#include "bamWriter.h"
|
||||
#include "datagram.h"
|
||||
#include "datagramIterator.h"
|
||||
|
||||
TypeHandle StencilAttrib::_type_handle;
|
||||
|
||||
////////////////////////////////////////////////////////////////////
|
||||
// Function: StencilAttrib::make
|
||||
// Access: Published, Static
|
||||
// Description: Constructs a new StencilAttrib object.
|
||||
////////////////////////////////////////////////////////////////////
|
||||
CPT(RenderAttrib) StencilAttrib::
|
||||
make() {
|
||||
StencilAttrib *attrib = new StencilAttrib;
|
||||
return return_new(attrib);
|
||||
}
|
||||
|
||||
////////////////////////////////////////////////////////////////////
|
||||
// Function: StencilAttrib::output
|
||||
// Access: Public, Virtual
|
||||
// Description:
|
||||
////////////////////////////////////////////////////////////////////
|
||||
void StencilAttrib::
|
||||
output(ostream &out) const {
|
||||
int index;
|
||||
for (index = 0; index < SRS_total; index++) {
|
||||
out << "(" << index << "," << _stencil_render_states [index] << ")";
|
||||
}
|
||||
}
|
||||
|
||||
////////////////////////////////////////////////////////////////////
|
||||
// Function: StencilAttrib::compare_to_impl
|
||||
// Access: Protected, Virtual
|
||||
// Description: Intended to be overridden by derived StencilAttrib
|
||||
// types to return a unique number indicating whether
|
||||
// this StencilAttrib is equivalent to the other one.
|
||||
//
|
||||
// This should return 0 if the two StencilAttrib objects
|
||||
// are equivalent, a number less than zero if this one
|
||||
// should be sorted before the other one, and a number
|
||||
// greater than zero otherwise.
|
||||
//
|
||||
// This will only be called with two StencilAttrib
|
||||
// objects whose get_type() functions return the same.
|
||||
////////////////////////////////////////////////////////////////////
|
||||
int StencilAttrib::
|
||||
compare_to_impl(const RenderAttrib *other) const {
|
||||
const StencilAttrib *sa;
|
||||
DCAST_INTO_R(sa, other, 0);
|
||||
|
||||
int compare_result = 0;
|
||||
|
||||
// quick test to see if both are default states
|
||||
// which should be the most common case
|
||||
if (_default && (_default == sa -> _default)) {
|
||||
|
||||
}
|
||||
else {
|
||||
int index;
|
||||
for (index = 0; index < SRS_total; index++) {
|
||||
if (_stencil_render_states [index] - sa -> _stencil_render_states [index]) {
|
||||
|
||||
// ?????
|
||||
compare_result = -(index + 1);
|
||||
break;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
return compare_result;
|
||||
}
|
||||
|
||||
////////////////////////////////////////////////////////////////////
|
||||
// Function: StencilAttrib::make_default_impl
|
||||
// Access: Protected, Virtual
|
||||
// Description: Intended to be overridden by derived StencilAttrib
|
||||
// types to specify what the default property for a
|
||||
// StencilAttrib of this type should be.
|
||||
//
|
||||
// This should return a newly-allocated StencilAttrib of
|
||||
// the same type that corresponds to whatever the
|
||||
// standard default for this kind of StencilAttrib is.
|
||||
////////////////////////////////////////////////////////////////////
|
||||
RenderAttrib *StencilAttrib::
|
||||
make_default_impl() const {
|
||||
return new StencilAttrib;
|
||||
}
|
||||
|
||||
////////////////////////////////////////////////////////////////////
|
||||
// Function: StencilAttrib::store_into_slot
|
||||
// Access: Public, Virtual
|
||||
// Description: Stores this attrib into the appropriate slot of
|
||||
// an object of class AttribSlots.
|
||||
////////////////////////////////////////////////////////////////////
|
||||
void StencilAttrib::
|
||||
store_into_slot(AttribSlots *slots) const {
|
||||
slots->_stencil = this;
|
||||
}
|
||||
|
||||
////////////////////////////////////////////////////////////////////
|
||||
// Function: StencilAttrib::register_with_read_factory
|
||||
// Access: Public, Static
|
||||
// Description: Tells the BamReader how to create objects of type
|
||||
// StencilAttrib.
|
||||
////////////////////////////////////////////////////////////////////
|
||||
void StencilAttrib::
|
||||
register_with_read_factory() {
|
||||
BamReader::get_factory()->register_factory(get_class_type(), make_from_bam);
|
||||
}
|
||||
|
||||
////////////////////////////////////////////////////////////////////
|
||||
// Function: StencilAttrib::write_datagram
|
||||
// Access: Public, Virtual
|
||||
// Description: Writes the contents of this object to the datagram
|
||||
// for shipping out to a Bam file.
|
||||
////////////////////////////////////////////////////////////////////
|
||||
void StencilAttrib::
|
||||
write_datagram(BamWriter *manager, Datagram &dg) {
|
||||
RenderAttrib::write_datagram(manager, dg);
|
||||
|
||||
int index;
|
||||
for (index = 0; index < SRS_total; index++) {
|
||||
dg.add_int32(_stencil_render_states [index]);
|
||||
}
|
||||
}
|
||||
|
||||
////////////////////////////////////////////////////////////////////
|
||||
// Function: StencilAttrib::make_from_bam
|
||||
// Access: Protected, Static
|
||||
// Description: This function is called by the BamReader's factory
|
||||
// when a new object of type StencilAttrib is encountered
|
||||
// in the Bam file. It should create the StencilAttrib
|
||||
// and extract its information from the file.
|
||||
////////////////////////////////////////////////////////////////////
|
||||
TypedWritable *StencilAttrib::
|
||||
make_from_bam(const FactoryParams ¶ms) {
|
||||
StencilAttrib *attrib = new StencilAttrib;
|
||||
DatagramIterator scan;
|
||||
BamReader *manager;
|
||||
|
||||
parse_params(params, scan, manager);
|
||||
attrib->fillin(scan, manager);
|
||||
|
||||
return attrib;
|
||||
}
|
||||
|
||||
////////////////////////////////////////////////////////////////////
|
||||
// Function: StencilAttrib::fillin
|
||||
// Access: Protected
|
||||
// Description: This internal function is called by make_from_bam to
|
||||
// read in all of the relevant data from the BamFile for
|
||||
// the new StencilAttrib.
|
||||
////////////////////////////////////////////////////////////////////
|
||||
void StencilAttrib::
|
||||
fillin(DatagramIterator &scan, BamReader *manager) {
|
||||
RenderAttrib::fillin(scan, manager);
|
||||
|
||||
int index;
|
||||
for (index = 0; index < SRS_total; index++) {
|
||||
_stencil_render_states [index] = scan.get_int32();
|
||||
}
|
||||
_default = false;
|
||||
}
|
134
panda/src/pgraph/stencilAttrib.h
Normal file
134
panda/src/pgraph/stencilAttrib.h
Normal file
@ -0,0 +1,134 @@
|
||||
// Filename: stencilAttrib.h
|
||||
// Created by: aignacio (18May06)
|
||||
//
|
||||
////////////////////////////////////////////////////////////////////
|
||||
//
|
||||
// PANDA 3D SOFTWARE
|
||||
// Copyright (c) 2001 - 2006, Disney Enterprises, Inc. All rights reserved
|
||||
//
|
||||
// All use of this software is subject to the terms of the Panda 3d
|
||||
// Software license. You should have received a copy of this license
|
||||
// along with this source code; you will also find a current copy of
|
||||
// the license at http://etc.cmu.edu/panda3d/docs/license/ .
|
||||
//
|
||||
// To contact the maintainers of this program write to
|
||||
// panda3d-general@lists.sourceforge.net .
|
||||
//
|
||||
////////////////////////////////////////////////////////////////////
|
||||
|
||||
#ifndef STENCILATTRIB_H
|
||||
#define STENCILATTRIB_H
|
||||
|
||||
#include "pandabase.h"
|
||||
#include "renderAttrib.h"
|
||||
|
||||
class FactoryParams;
|
||||
|
||||
////////////////////////////////////////////////////////////////////
|
||||
// Class : StencilAttrib
|
||||
// Description : Enables or disables writing of pixel to framebuffer
|
||||
// based on its alpha value relative to a reference alpha value
|
||||
////////////////////////////////////////////////////////////////////
|
||||
class EXPCL_PANDA StencilAttrib : public RenderAttrib {
|
||||
private:
|
||||
INLINE StencilAttrib();
|
||||
|
||||
PUBLISHED:
|
||||
|
||||
// enums are duplicated here from class StencilRenderStates for use in Python
|
||||
enum StencilRenderState
|
||||
{
|
||||
SRS_clear_value,
|
||||
|
||||
SRS_reference,
|
||||
|
||||
SRS_read_mask,
|
||||
SRS_write_mask,
|
||||
|
||||
SRS_front_enable,
|
||||
SRS_front_comparison_function,
|
||||
SRS_front_stencil_fail_operation,
|
||||
SRS_front_stencil_pass_z_fail_operation,
|
||||
SRS_front_stencil_pass_z_pass_operation,
|
||||
|
||||
SRS_back_enable,
|
||||
SRS_back_comparison_function,
|
||||
SRS_back_stencil_fail_operation,
|
||||
SRS_back_stencil_pass_z_fail_operation,
|
||||
SRS_back_stencil_pass_z_pass_operation,
|
||||
|
||||
SRS_total,
|
||||
|
||||
SRS_first = 0,
|
||||
};
|
||||
|
||||
enum StencilComparisonFunction
|
||||
{
|
||||
SCF_never,
|
||||
SCF_less_than,
|
||||
SCF_equal,
|
||||
SCF_less_than_or_equal,
|
||||
SCF_greater_than,
|
||||
SCF_not_equal,
|
||||
SCF_greater_than_or_equal,
|
||||
SCF_always,
|
||||
};
|
||||
|
||||
enum StencilOperation
|
||||
{
|
||||
SO_keep,
|
||||
SO_zero,
|
||||
SO_replace,
|
||||
SO_increment,
|
||||
SO_decrement,
|
||||
SO_invert,
|
||||
SO_increment_saturate,
|
||||
SO_decrement_saturate,
|
||||
};
|
||||
|
||||
static CPT(RenderAttrib) make();
|
||||
INLINE void set_render_state (unsigned int render_state_identifier, unsigned int render_state);
|
||||
INLINE unsigned int get_render_state (unsigned int render_state_identifier) const;
|
||||
|
||||
public:
|
||||
virtual void output(ostream &out) const;
|
||||
virtual void store_into_slot(AttribSlots *slots) const;
|
||||
|
||||
protected:
|
||||
virtual int compare_to_impl(const RenderAttrib *other) const;
|
||||
virtual RenderAttrib *make_default_impl() const;
|
||||
|
||||
private:
|
||||
unsigned int _stencil_render_states [SRS_total];
|
||||
bool _default;
|
||||
|
||||
public:
|
||||
static void register_with_read_factory();
|
||||
virtual void write_datagram(BamWriter *manager, Datagram &dg);
|
||||
|
||||
protected:
|
||||
static TypedWritable *make_from_bam(const FactoryParams ¶ms);
|
||||
void fillin(DatagramIterator &scan, BamReader *manager);
|
||||
|
||||
public:
|
||||
static TypeHandle get_class_type() {
|
||||
return _type_handle;
|
||||
}
|
||||
static void init_type() {
|
||||
RenderAttrib::init_type();
|
||||
register_type(_type_handle, "StencilAttrib",
|
||||
RenderAttrib::get_class_type());
|
||||
}
|
||||
virtual TypeHandle get_type() const {
|
||||
return get_class_type();
|
||||
}
|
||||
virtual TypeHandle force_init_type() {init_type(); return get_class_type();}
|
||||
|
||||
private:
|
||||
static TypeHandle _type_handle;
|
||||
};
|
||||
|
||||
#include "stencilAttrib.I"
|
||||
|
||||
#endif
|
||||
|
Loading…
x
Reference in New Issue
Block a user