Skip to content

Commit

Permalink
points: support point texturing
Browse files Browse the repository at this point in the history
If the GL_COORD_REPLACE flag is set, then instead of the texture
coordinates found on the vertex, we should use a hardcoded (0, 0)
coordinate for the top left corner, and (1, 1) for the bottom right.
We do this by replacing the vertex array with the PointSpritesTexReader
class, whose reader method always returns (0, 0).

We also need to modify a few other places so that the array classes know
what is the primitive being drawn, because this swap must only be
applied when rendering points.
  • Loading branch information
mardy authored and WinterMute committed Nov 25, 2024
1 parent 618529a commit 60afb21
Show file tree
Hide file tree
Showing 5 changed files with 45 additions and 9 deletions.
29 changes: 28 additions & 1 deletion src/arrays.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -208,6 +208,13 @@ struct SphereMapTexReader: public GeneratedTexVertexReader {
}
};

struct PointSpritesTexReader: public GeneratedTexVertexReader {
using GeneratedTexVertexReader::GeneratedTexVertexReader;
void read_tex2f(int index, Tex2f tex) override {
tex[0] = tex[1] = 0.0f;
}
};

struct VertexReaderBase: public AbstractVertexReader {
VertexReaderBase(GxVertexFormat format, VboType vbo, const void *data,
int stride):
Expand Down Expand Up @@ -558,7 +565,8 @@ static inline VertexReaderBase *get_reader(OgxArrayReader *reader)
return reinterpret_cast<VertexReaderBase *>(reader);
}

void _ogx_arrays_setup_draw(bool has_normals, uint8_t num_colors,
void _ogx_arrays_setup_draw(uint8_t gxmode,
bool has_normals, uint8_t num_colors,
uint8_t tex_unit_mask)
{
GX_ClearVtxDesc();
Expand All @@ -584,6 +592,25 @@ void _ogx_arrays_setup_draw(bool has_normals, uint8_t num_colors,
for (int i = 0; i < MAX_TEXTURE_UNITS; i++) {
VertexReaderBase *r = get_reader(&glparamstate.texcoord_array[i]);
u8 unit_bit = 1 << i;

if (gxmode == GX_POINTS &&
glparamstate.point_sprites_enabled &&
glparamstate.point_sprites_coord_replace) {
if (tex_unit_mask & unit_bit) {
/* Don't pass the texture coordinates specified by the
* client, but a hardcoded (0, 0). */
GeneratedTexVertexReader *gr =
GeneratedTexVertexReader::create_at
<PointSpritesTexReader>(&glparamstate.texcoord_array[i]);
gr->setup_draw();
gr->set_tex_coord_source(GX_TG_TEX0 + sent_tex_arrays++);
s_tex_unit_mask |= unit_bit;
/* Do not process more units */
i = MAX_TEXTURE_UNITS;
}
continue;
}

if (glparamstate.texture_unit[i].gen_enabled) {
/* Some kinds of texture generation cannot be performed by the
* GPU, and we have to generate the texture coordinates in
Expand Down
3 changes: 2 additions & 1 deletion src/arrays.h
Original file line number Diff line number Diff line change
Expand Up @@ -48,7 +48,8 @@ void _ogx_array_reader_init(OgxArrayReader *reader,
uint8_t vertex_attribute,
const void *data,
int num_components, GLenum type, int stride);
void _ogx_arrays_setup_draw(bool has_normals, uint8_t num_colors,
void _ogx_arrays_setup_draw(uint8_t gxmode,
bool has_normals, uint8_t num_colors,
uint8_t tex_unit_mask);
/* Get the mask of units having texture coordinates. This is not necessarily
* the same as glparamstate.cs.texcoord_enabled, because we might have
Expand Down
4 changes: 3 additions & 1 deletion src/call_lists.c
Original file line number Diff line number Diff line change
Expand Up @@ -229,7 +229,9 @@ static void execute_draw_geometry_list(struct DrawGeometry *dg)
}
}

_ogx_arrays_setup_draw(dg->cs.normal_enabled,
DrawMode gxmode = _ogx_draw_mode(dg->mode);
_ogx_arrays_setup_draw(gxmode.mode,
dg->cs.normal_enabled,
dg->cs.color_enabled ? 2 : 0,
dg->cs.texcoord_enabled);
if (!dg->cs.normal_enabled) {
Expand Down
15 changes: 9 additions & 6 deletions src/gc_gl.c
Original file line number Diff line number Diff line change
Expand Up @@ -2309,7 +2309,8 @@ static void flat_draw_geometry(void *cb_data)
{
OgxDrawData *data = cb_data;

_ogx_arrays_setup_draw(false, /* no normals */
_ogx_arrays_setup_draw(data->gxmode.mode,
false, /* no normals */
false, /* no color */
false /* no texturing */);
/* TODO: we could use C++ templates here too, to build more effective
Expand Down Expand Up @@ -2348,7 +2349,8 @@ static void flat_draw_elements(void *cb_data)
{
OgxDrawElementsData *data = cb_data;

_ogx_arrays_setup_draw(false, /* no normals */
_ogx_arrays_setup_draw(data->gxmode.mode,
false, /* no normals */
false, /* no color */
false /* no texturing */);

Expand Down Expand Up @@ -2385,7 +2387,7 @@ void glArrayElement(GLint i)
}
}

static bool setup_draw()
static bool setup_draw(uint8_t gxmode)
{
_ogx_efb_set_content_type(OGX_EFB_SCENE);

Expand All @@ -2398,7 +2400,8 @@ static bool setup_draw()
else
color_provide = 1;
}
_ogx_arrays_setup_draw(glparamstate.cs.normal_enabled, color_provide, texen);
_ogx_arrays_setup_draw(gxmode,
glparamstate.cs.normal_enabled, color_provide, texen);

/* Note that _ogx_setup_render_stages() uses some information from the
* vertex arrays computed by _ogx_arrays_setup_draw(), so it must be called
Expand Down Expand Up @@ -2429,7 +2432,7 @@ void glDrawArrays(GLenum mode, GLint first, GLsizei count)

_ogx_gpu_resources_push();

bool should_draw = setup_draw();
bool should_draw = setup_draw(gxmode.mode);
if (should_draw) {
draw_arrays_general(gxmode, first, count);
glparamstate.draw_count++;
Expand Down Expand Up @@ -2459,7 +2462,7 @@ void glDrawElements(GLenum mode, GLsizei count, GLenum type, const GLvoid *indic

_ogx_gpu_resources_push();

bool should_draw = setup_draw();
bool should_draw = setup_draw(gxmode.mode);
if (should_draw) {
draw_elements_general(gxmode, count, type, indices);
glparamstate.draw_count++;
Expand Down
3 changes: 3 additions & 0 deletions src/texture_unit.c
Original file line number Diff line number Diff line change
Expand Up @@ -428,6 +428,9 @@ static void setup_texture_stage(const OgxTextureUnit *tu,
GX_TEVPREV);
}
GX_SetTevOrder(stage, tex_coord, tex_map, channel);
bool points_enabled = glparamstate.point_sprites_enabled &&
glparamstate.point_sprites_coord_replace;
GX_EnableTexOffsets(tex_coord, GX_DISABLE, points_enabled);
GX_LoadTexObj(&texture_list[tu->glcurtex].texobj, tex_map);
}

Expand Down

0 comments on commit 60afb21

Please sign in to comment.