mirror of
https://github.com/AntonioND/nitro-engine.git
synced 2025-06-18 16:45:33 -04:00
403 lines
16 KiB
C
403 lines
16 KiB
C
// SPDX-License-Identifier: MIT
|
|
//
|
|
// Copyright (c) 2008-2022 Antonio Niño Díaz
|
|
//
|
|
// This file is part of Nitro Engine
|
|
|
|
#ifndef NE_TEXTURE_H__
|
|
#define NE_TEXTURE_H__
|
|
|
|
#include <nds.h>
|
|
|
|
#include "NEPalette.h"
|
|
#include "NEPolygon.h"
|
|
|
|
/// @file NETexture.h
|
|
/// @brief Texture and material functions.
|
|
|
|
/// @defgroup material_system Material system
|
|
///
|
|
/// Material manipulation system. A material is composed of a texture and,
|
|
/// optionally, a palette. It also has diffuse, ambient, specular and emission
|
|
/// properties.
|
|
///
|
|
/// @{
|
|
|
|
#define NE_DEFAULT_TEXTURES 128 ///< Default max number of materials
|
|
|
|
#define NE_NO_PALETTE -1 ///< Value that represents not having a palette
|
|
|
|
/// Holds information of one material.
|
|
typedef struct {
|
|
int texindex; ///< Index to internal texture object
|
|
NE_Palette *palette; ///< Palette used by this material
|
|
u32 color; ///< Color of this material when lights aren't used
|
|
u32 diffuse_ambient; ///< Diffuse and ambient lighting material color
|
|
u32 specular_emission; ///< Specular and emission lighting material color
|
|
bool palette_autodelete; ///< Set to true for the palette to be deleted with the material.
|
|
} NE_Material;
|
|
|
|
/// Supported texture options
|
|
typedef enum {
|
|
NE_TEXTURE_WRAP_S = (1U << 16), ///< Wrap/repeat texture on S axis
|
|
NE_TEXTURE_WRAP_T = (1U << 17), ///< Wrap/repeat texture on T axis
|
|
NE_TEXTURE_FLIP_S = (1U << 18), ///< Flip texture on S axis when wrapping
|
|
NE_TEXTURE_FLIP_T = (1U << 19), ///< Flip texture on T axis when wrapping
|
|
NE_TEXTURE_COLOR0_TRANSPARENT = (1U << 29), ///< Make palette index 0 transparent
|
|
NE_TEXGEN_OFF = (0U << 30), ///< Don't modify texture coordinates
|
|
NE_TEXGEN_TEXCOORD = (1U << 30), ///< Multiply coordinates by texture matrix
|
|
NE_TEXGEN_NORMAL = (2U << 30), ///< Texcoords = Normal * texture matrix (spherical reflection)
|
|
NE_TEXGEN_POSITION = (3U << 30) ///< Texcoords = Vertex * texture matrix
|
|
} NE_TextureFlags;
|
|
|
|
/// Creates a new material object.
|
|
///
|
|
/// @return Pointer to the newly created material.
|
|
NE_Material *NE_MaterialCreate(void);
|
|
|
|
/// Applies a color to a material.
|
|
///
|
|
/// Note that the color will only be displayed if no normal commands are used.
|
|
/// Any model with normals will ignore this color.
|
|
///
|
|
/// @param tex Material.
|
|
/// @param color Color.
|
|
void NE_MaterialColorSet(NE_Material *tex, u32 color);
|
|
|
|
/// Removes the color of a material (sets it back to white).
|
|
///
|
|
/// @param tex Material.
|
|
void NE_MaterialColorDelete(NE_Material *tex);
|
|
|
|
/// Loads a texture from the filesystem and assigns it to a material object.
|
|
///
|
|
/// The height doesn't need to be a power of two, but he width must be a power
|
|
/// of two.
|
|
///
|
|
/// Textures with width that isn't a power of two need to be resized manually,
|
|
/// which is very slow, and they don't save any VRAM when loaded compared to a
|
|
/// texture with the full width. The only advantage is that they need less
|
|
/// storage space, but you can achieve the same effect by compressing them.
|
|
///
|
|
/// Textures with a height that isn't a power of two don't need to be resized,
|
|
/// and they actually save VRAM space (you tell the GPU that the texture is
|
|
/// bigger, but then you ignore the additional space, as it will be used by
|
|
/// other textures).
|
|
///
|
|
/// Textures with the 4x4 Texel format (NE_TEX4X4) are normally split into two
|
|
/// parts: one that goes into texture slots 0 or 2 and another one that goes
|
|
/// into texture slot 1. This function expects the two parts to be concatenated
|
|
/// (with the slot 1 part after the other part).
|
|
///
|
|
/// @param tex Material.
|
|
/// @param fmt Texture format.
|
|
/// @param sizeX (sizeX, sizeY) Texture size.
|
|
/// @param sizeY (sizeX, sizeY) Texture size.
|
|
/// @param flags Parameters of the texture.
|
|
/// @param path Path of the texture file.
|
|
/// @return It returns 1 on success, 0 on error.
|
|
int NE_MaterialTexLoadFAT(NE_Material *tex, NE_TextureFormat fmt,
|
|
int sizeX, int sizeY, NE_TextureFlags flags,
|
|
const char *path);
|
|
|
|
/// Loads a texture in Texel 4x4 format from the filesystem and assigns it to a
|
|
/// material object.
|
|
///
|
|
/// Width and height need to be powers of two.
|
|
///
|
|
/// @param tex Material.
|
|
/// @param sizeX (sizeX, sizeY) Texture size.
|
|
/// @param sizeY (sizeX, sizeY) Texture size.
|
|
/// @param flags Parameters of the texture.
|
|
/// @param path02 Path of the texture file (part that goes in slot 0/2).
|
|
/// @param path1 Path of the texture file (part that goes in slot 1).
|
|
/// @return It returns 1 on success, 0 on error.
|
|
int NE_MaterialTex4x4LoadFAT(NE_Material *tex, int sizeX, int sizeY,
|
|
NE_TextureFlags flags, const char *path02,
|
|
const char *path1);
|
|
|
|
/// Loads a texture in any format from a GRF file to a material and palette.
|
|
///
|
|
/// The size and format are obtained from the GRF header.
|
|
///
|
|
/// @param tex Material.
|
|
/// @param pal Palette. If the format is 16 bit, nothing will be loaded here.
|
|
/// @param flags Parameters of the texture.
|
|
/// @param path Path of the GRF file.
|
|
/// @return It returns 1 on success, 0 on error.
|
|
int NE_MaterialTexLoadGRF(NE_Material *tex, NE_Palette *pal,
|
|
NE_TextureFlags flags, const char *path);
|
|
|
|
/// Loads a texture from RAM and assigns it to a material object.
|
|
///
|
|
/// Textures with width that isn't a power of two need to be resized manually,
|
|
/// which is very slow, and they don't save any VRAM when loaded compared to a
|
|
/// texture with the full width. The only advantage is that they need less
|
|
/// storage space, but you can achieve the same effect by compressing them.
|
|
///
|
|
/// Textures with a height that isn't a power of two don't need to be resized,
|
|
/// and they actually save VRAM space (you tell the GPU that the texture is
|
|
/// bigger, but then you ignore the additional space, as it will be used by
|
|
/// other textures).
|
|
///
|
|
/// Textures with the 4x4 Texel format (NE_TEX4X4) are normally split into two
|
|
/// parts: one that goes into texture slots 0 or 2 and another one that goes
|
|
/// into texture slot 1. This function expects the two parts to be concatenated
|
|
/// (with the slot 1 part after the other part).
|
|
///
|
|
/// @param tex Material.
|
|
/// @param fmt Texture format.
|
|
/// @param sizeX (sizeX, sizeY) Texture size.
|
|
/// @param sizeY (sizeX, sizeY) Texture size.
|
|
/// @param flags Parameters of the texture.
|
|
/// @param texture Pointer to the texture data.
|
|
/// @return It returns 1 on success, 0 on error.
|
|
int NE_MaterialTexLoad(NE_Material *tex, NE_TextureFormat fmt,
|
|
int sizeX, int sizeY, NE_TextureFlags flags,
|
|
const void *texture);
|
|
|
|
/// Loads a texture from RAM and assigns it to a material object.
|
|
///
|
|
/// Width and height need to be powers of two.
|
|
///
|
|
/// @param tex Material.
|
|
/// @param sizeX (sizeX, sizeY) Texture size.
|
|
/// @param sizeY (sizeX, sizeY) Texture size.
|
|
/// @param flags Parameters of the texture.
|
|
/// @param texture02 Pointer to the texture data (part that goes in slot 0/2).
|
|
/// @param texture1 Pointer to the texture data (part that goes in slot 1).
|
|
/// @return It returns 1 on success, 0 on error.
|
|
int NE_MaterialTex4x4Load(NE_Material *tex, int sizeX, int sizeY,
|
|
NE_TextureFlags flags, const void *texture02,
|
|
const void *texture1);
|
|
|
|
/// Tell a material that it has to delete its palette on deletion.
|
|
///
|
|
/// Normally, when a material is deleted, the palette isn't deleted with it.
|
|
/// This function will tell the material to delete its palette when
|
|
/// NE_MaterialDelete() is called. This is helpful because it lets the developer
|
|
/// stop caring about the palette.
|
|
///
|
|
/// @param mat Material.
|
|
void NE_MaterialAutodeletePalette(NE_Material *mat);
|
|
|
|
/// Copies the texture of a material into another material.
|
|
///
|
|
/// Unlike with models, you can delete the source and destination materials as
|
|
/// desired. Nitro Engine will keep track of how many materials use any specific
|
|
/// texture and palette and it will remove them when no more materials are using
|
|
/// them.
|
|
///
|
|
/// @param source Source.
|
|
/// @param dest Destination.
|
|
void NE_MaterialClone(NE_Material *source, NE_Material *dest);
|
|
|
|
/// Alias of NE_MaterialClone
|
|
///
|
|
/// @deprecated This definition is only present for backwards compatibility and
|
|
/// it will be removed.
|
|
#define NE_MaterialTexClone NE_MaterialClone
|
|
|
|
/// Assigns a palette to a material.
|
|
///
|
|
/// @param tex Material.
|
|
/// @param pal Palette.
|
|
void NE_MaterialSetPalette(NE_Material *tex, NE_Palette *pal);
|
|
|
|
/// Alias of NE_MaterialSetPalette().
|
|
///
|
|
/// @deprecated This definition is only present for backwards compatibility and
|
|
/// it will be removed.
|
|
#define NE_MaterialTexSetPal NE_MaterialSetPalette
|
|
|
|
/// Set active material to use when drawing polygons.
|
|
///
|
|
/// If the pointer passed is NULL the function will disable textures and new
|
|
/// polygons won't be affected by them until this function is called again with
|
|
/// a valid material.
|
|
///
|
|
/// @param tex Material to be used.
|
|
void NE_MaterialUse(const NE_Material *tex);
|
|
|
|
/// Flags to choose which VRAM banks Nitro Engine can use to allocate textures.
|
|
typedef enum {
|
|
NE_VRAM_A = (1 << 0), ///< Bank A
|
|
NE_VRAM_B = (1 << 1), ///< Bank B
|
|
NE_VRAM_C = (1 << 2), ///< Bank C
|
|
NE_VRAM_D = (1 << 3), ///< Bank D
|
|
|
|
NE_VRAM_AB = NE_VRAM_A | NE_VRAM_B, ///< Banks A and B
|
|
NE_VRAM_AC = NE_VRAM_A | NE_VRAM_C, ///< Banks A and C
|
|
NE_VRAM_AD = NE_VRAM_A | NE_VRAM_D, ///< Banks A and D
|
|
NE_VRAM_BC = NE_VRAM_B | NE_VRAM_C, ///< Banks B and C
|
|
NE_VRAM_BD = NE_VRAM_B | NE_VRAM_D, ///< Banks B and D
|
|
NE_VRAM_CD = NE_VRAM_C | NE_VRAM_D, ///< Banks C and D
|
|
|
|
NE_VRAM_ABC = NE_VRAM_A | NE_VRAM_B | NE_VRAM_C, ///< Banks A, B and C
|
|
NE_VRAM_ABD = NE_VRAM_A | NE_VRAM_B | NE_VRAM_D, ///< Banks A, B and D
|
|
NE_VRAM_ACD = NE_VRAM_A | NE_VRAM_C | NE_VRAM_D, ///< Banks A, C and D
|
|
NE_VRAM_BCD = NE_VRAM_B | NE_VRAM_C | NE_VRAM_D, ///< Banks B, C and D
|
|
|
|
NE_VRAM_ABCD = NE_VRAM_A | NE_VRAM_B | NE_VRAM_C | NE_VRAM_D, ///< All main banks
|
|
} NE_VRAMBankFlags;
|
|
|
|
/// Resets the material system and sets the new max number of objects.
|
|
///
|
|
/// In Dual 3D mode, only VRAM A and B are available for textures.
|
|
///
|
|
/// If no VRAM banks are specified in this function, all VRAM banks A to D will
|
|
/// be used for textures (or just A and B in dual 3D mode).
|
|
///
|
|
/// @param max_textures Max number of textures. If lower than 1, it will
|
|
/// create space for NE_DEFAULT_TEXTURES.
|
|
/// @param max_palettes Max number of palettes. If lower than 1, it will
|
|
/// create space for NE_DEFAULT_PALETTES.
|
|
/// @param bank_flags VRAM banks where Nitro Engine can allocate textures.
|
|
/// @return Returns 0 on success.
|
|
int NE_TextureSystemReset(int max_textures, int max_palettes,
|
|
NE_VRAMBankFlags bank_flags);
|
|
|
|
/// Deletes a material object.
|
|
///
|
|
/// @param tex Pointer to the material object.
|
|
void NE_MaterialDelete(NE_Material *tex);
|
|
|
|
/// Returns the available free memory for textures.
|
|
///
|
|
/// Note that, even if it is all available, it may not be contiguous, so you may
|
|
/// not be able to load a texture because there isn't enough space in any free
|
|
/// gap.
|
|
///
|
|
/// @return Returns the available memory in bytes.
|
|
int NE_TextureFreeMem(void);
|
|
|
|
/// Returns the percentage of available free memory for textures.
|
|
///
|
|
/// @return Returns the percentage of available memory (0-100).
|
|
int NE_TextureFreeMemPercent(void);
|
|
|
|
/// Defragment memory used for textures.
|
|
///
|
|
/// WARNING: This function is currently not working.
|
|
void NE_TextureDefragMem(void);
|
|
|
|
/// End texture system and free all memory used by it.
|
|
void NE_TextureSystemEnd(void);
|
|
|
|
/// Returns the width of a texture.
|
|
///
|
|
/// This is the size given when the texture was loaded.
|
|
///
|
|
/// @param tex Material.
|
|
/// @return Returns the size in pixels.
|
|
int NE_TextureGetSizeX(const NE_Material *tex);
|
|
|
|
/// Returns the height of a texture.
|
|
///
|
|
/// This is the size given when the texture was loaded.
|
|
///
|
|
/// @param tex Material.
|
|
/// @return Returns the size in pixels.
|
|
int NE_TextureGetSizeY(const NE_Material *tex);
|
|
|
|
/// Returns the real width of a texture.
|
|
///
|
|
/// This is the internal size given to the GPU when the texture is used, not the
|
|
/// size used to load the texture, which may have been smaller.
|
|
///
|
|
/// @param tex Material.
|
|
/// @return Returns the size in pixels.
|
|
int NE_TextureGetRealSizeX(const NE_Material *tex);
|
|
|
|
/// Returns the real height size of a texture.
|
|
///
|
|
/// This is the internal size given to the GPU when the texture is used, not the
|
|
/// size used to load the texture, which may have been smaller.
|
|
///
|
|
/// @param tex Material.
|
|
/// @return Returns the size in pixels.
|
|
int NE_TextureGetRealSizeY(const NE_Material *tex);
|
|
|
|
/// Sets lighting properties of this material.
|
|
///
|
|
/// @param tex Material to modify.
|
|
/// @param diffuse Set diffuse color: lights that directly hits the polygon.
|
|
/// @param ambient Set ambient color: lights that indirectly hit the polygon
|
|
/// (reflections from the walls, etc).
|
|
/// @param specular Set specular color: lights reflected towards the camera,
|
|
/// like a mirror.
|
|
/// @param emission Set emission color: light emitted by the polygon.
|
|
/// @param vtxcolor If true, diffuse reflection will work as a color command.
|
|
/// @param useshininess If true, specular reflection will use the shininess
|
|
/// table.
|
|
void NE_MaterialSetProperties(NE_Material *tex, u32 diffuse, u32 ambient,
|
|
u32 specular, u32 emission, bool vtxcolor,
|
|
bool useshininess);
|
|
|
|
/// Alias of NE_MaterialSetProperties
|
|
///
|
|
/// @deprecated This definition is only present for backwards compatibility and
|
|
/// it will be removed.
|
|
#define NE_MaterialSetPropierties NE_MaterialSetProperties
|
|
|
|
/// Sets default lighting properties of materials when they are created.
|
|
///
|
|
/// @param diffuse Set diffuse color: lights that directly hits the polygon.
|
|
/// @param ambient Set ambient color: lights that indirectly hit the polygon
|
|
/// (reflections from the walls, etc).
|
|
/// @param specular Set specular color: lights reflected towards the camera,
|
|
/// like a mirror.
|
|
/// @param emission Set emission color: light emitted by the polygon.
|
|
/// @param vtxcolor If true, diffuse reflection will work as a color command.
|
|
/// @param useshininess If true, specular reflection will use the shininess
|
|
/// table.
|
|
void NE_MaterialSetDefaultProperties(u32 diffuse, u32 ambient, u32 specular,
|
|
u32 emission, bool vtxcolor,
|
|
bool useshininess);
|
|
|
|
/// Alias of NE_MaterialSetDefaultProperties
|
|
///
|
|
/// @deprecated This definition is only present for backwards compatibility and
|
|
/// it will be removed.
|
|
#define NE_MaterialSetDefaultPropierties NE_MaterialSetDefaultProperties
|
|
|
|
/// Enables modification of the specified texture.
|
|
///
|
|
/// Use this during VBL. Remember to use NE_TextureDrawingEnd() when you finish.
|
|
/// If you don't, the GPU won't be able to render textures to the screen.
|
|
///
|
|
/// @param tex Texture to modify.
|
|
/// @return Returns a pointer to the base address of the texture in VRAM.
|
|
void *NE_TextureDrawingStart(const NE_Material *tex);
|
|
|
|
/// Sets the specified pixel to the specified color.
|
|
///
|
|
/// This only works for textures in RGBA/RGB format.
|
|
///
|
|
/// Use this during VBL.
|
|
///
|
|
/// @param x (x, y) Pixel coordinates.
|
|
/// @param y (x, y) Pixel coordinates.
|
|
/// @param color Color in RGB15. Bit 15 must be set to make the pixel visible.
|
|
void NE_TexturePutPixelRGBA(u32 x, u32 y, u16 color);
|
|
|
|
/// Sets the specified pixel to the specified palette color index.
|
|
///
|
|
/// This only works for textures in RGB256 format.
|
|
///
|
|
/// Use this during VBL.
|
|
///
|
|
/// @param x (x,y) Pixel coordinates.
|
|
/// @param y (x,y) Pixel coordinates.
|
|
/// @param palettecolor New palette color index.
|
|
void NE_TexturePutPixelRGB256(u32 x, u32 y, u8 palettecolor);
|
|
|
|
/// Disables modification of textures.
|
|
///
|
|
/// Use this during VBL.
|
|
void NE_TextureDrawingEnd(void);
|
|
|
|
/// @}
|
|
|
|
#endif // NE_TEXTURE_H__
|