Introduction

Day 1
GBA Hardware

Day 2
"Hello, World!"

Day 3
Input

Day 4
Backgrounds -
  Bitmapped Modes

Day 5
Sprites

Day 6
Backgrounds -
  Tile Modes

Day 7
Project 1 -
  Tetris

Quiz - Week 1

Day 8
Sprites #2 -
  Animation

Day 9
Maps

Day 10
Sprites #3 -
  Animation #2

Day 11
Backgrounds -
  Rotation

Day 12
Sprites #4 -
  Mosaic

Version History

Downloads

Books

Links

Graphics FAQ

GFX2GBA Readme

Games

Projects

Credits

Support

HAM Tutorial :: Day 12 :: Sprites #4 - Mosaic

 

I think it's time to learn one of those simple yet really cool effects: mosaic. Today we'll do mosaic on sprites, tomorrow we'll check it out for backgrounds. For the most part, today's code will be very similar to Day 8 and Day 10.

NOTE: I got the graphic for this example free from here.

Controls:
Up - Vertical mosaic increase
Down - Vertical mosaic decrease
Left - Horizontal mosaic decrease
Right - Horizontal mosaic increase
Start - Reset to no mosaic

// The Main HAM Library
#include "mygba.h"

// Graphics Includes
#include "gfx/background.pal.c" // Created from water.bmp
#include "gfx/object.pal.c" // Created from ship.bmp
#include
"gfx/ship.raw.c" // gfx2gba -D -fsrc -pobject.pal -t8 ship.bmp
#include
"gfx/water.map.c" // gfx2gba -fsrc -m -pbackground.pal
                                               -t8 water.bmp

#include
"gfx/water.raw.c"

// Global Variables
u8 ship[1]; // Sprite index for the ship
u8
new_frame = 0; // 0 = true, 1 = false
u16
curr_frame = 1; // Current frame
u8
mosaic_h = 0; // Mosaic horizontal amount
u8
mosaic_v = 0; // Mosaic vertical amount

// Function Prototypes
void
vblFunc(); // VBL function
void
query_keys(); // Query for input
void
redraw(); // Redraw sprites

// Main function
int
main()
{
  // Variables
  map_fragment_info_ptr bg_water; // Pointer to our background

  // Initialize HAMlib
  ham_Init();

  // Setup the background mode
  ham_SetBgMode(1);

  // Initialize the palettes
  ham_LoadBGPal(&background_Palette,256); // Background palette
  ham_LoadObjPal(&object_Palette, 256); // Sprite palette

  // Setup the tileset for our image
  ham_bg[0].ti = ham_InitTileSet(&water_Tiles,
                                                    SIZEOF_16BIT(water_Tiles),1,1);
  // Setup the map for our image
  ham_bg[0].mi = ham_InitMapEmptySet(3,0);
  bg_water = ham_InitMapFragment(&water_Map,30,20,0,0,30,20,0);
  ham_InsertMapFragment(bg_water,0,0,0);

  // Display the background
  ham_InitBg(0,1,0,0);

  // Setup the sprite ship[0] = ham_CreateObj(&ship_Bitmap,0,3,
                                               OBJ_MODE_NORMAL, 1,0,1,0,0,0,0,88,48);

  // Start the VBL interrupt handler   ham_StartIntHandler(INT_TYPE_VBL,&vblFunc);

  // Infinite loop to keep the program running
  while(1) {
    // First check if it's a new frame
    if (new_frame) {
       // Apply the mosaic
      M_MOSAIC_SET(0,0,mosaic_h,mosaic_v);
      // That's the end of the new frame
      new_frame = 0;
    }
  }

  return 0;
} // End of main()

// VBL Function
void
vblFunc()
{
  ham_CopyObjToOAM(); // Copy sprites to hardware
  new_frame = 1; // It's a new frame
  query_keys(); // Check for input
  return;
} // End of vblFunc()

// Query keys
void
query_keys()
{
  // UP
  if(F_CTRLINPUT_UP_PRESSED) {
    if (mosaic_v < 10) {
      ++mosaic_v;
    } else {
      mosaic_v = 0;
    }
  }

  // DOWN
  if(F_CTRLINPUT_DOWN_PRESSED) {
    if (mosaic_v == 0) {
      mosaic_v = 10;
    } else {
      --mosaic_v;
    }
  }

  // LEFT
  if(F_CTRLINPUT_LEFT_PRESSED) {
    if (mosaic_h == 0) {
      mosaic_h = 10;
    } else {
      --mosaic_h;
    }
  }

  // RIGHT
  if(F_CTRLINPUT_RIGHT_PRESSED) {
    if (mosaic_h < 10) {
      ++mosaic_h;
    } else {
      mosaic_h = 0;
    }
  }

  // START
  if (F_CTRLINPUT_START_PRESSED) {
    mosaic_v = 0;
    mosaic_h = 0;
  }

  return;
} // End of query_keys()

 

Code Explanation

// Global Variables

u8 new_frame = 0; // 0 = true, 1 = false
This should be easy to figure it. It is a variable used to make sure the effects are only applied once per frame.

u8 mosaic_h = 0; // Mosaic horizontal amount
u8 mosaic_v = 0; // Mosaic vertical amount
When you apply the mosaic effect, you have the option of doing it vertically and/or horizontally.

// Main function

// Setup the sprite
ship[0] = ham_CreateObj(...)

Notice that the seventh variable passed to the function is a 1, not a 0. Without this, mosaic won't work on the sprite created.

M_MOSAIC_SET(0,0,mosaic_h,mosaic_v);
This macro is found in mygba.h and looks like this:
#define M_MOSAIC_SET(bgh,bgv,objh,objv). As you can see, the first two parameters are for the background. For this example, we are just applying mosaic on the sprite.

The rest of the code should be trivial to figure out, but if you have questions, post them in the forum and I'll answer as soon as possible.

 

Download Code

NOTE: You may need to Right-click and choose Save As.

HAM Version 2.40 And Higher
Necessary for all HAM programs: makefile
Graphics: background.pal.c, object.pal.c, ship.raw.c, water.map.c,
               water.raw.c
Main source file: main.c
Compiled binary: hello.gba
VisualHAM project files: day12.vho, day12.vhw

Download All Files In One Zip: Day12_Sprites4_Mosaic.zip

View Demo Now (currently not working)

Discuss Day 12

 

<<

HOME

>>