Skip to content

Instantly share code, notes, and snippets.

@nandakoryaaa
Created June 23, 2025 11:00
Show Gist options
  • Save nandakoryaaa/85b39a678d59cb6e089d91a4483b70ce to your computer and use it in GitHub Desktop.
Save nandakoryaaa/85b39a678d59cb6e089d91a4483b70ce to your computer and use it in GitHub Desktop.
Implementing display object list, drawabe & behaviour traits for abstract game in Rust
#[derive (Copy, Clone)]
struct Rect {
w: u32,
h: i32
}
struct Renderer {
canvas: u32 // not used
}
impl Renderer {
fn drawBitmap(&mut self, handle: u32) {
println!("drawing Bitmap {}", handle);
}
fn drawRect(&mut self, rect: Rect) {
println!("drawing Rect {}x{}", rect.w, rect.h);
}
}
trait Drawable {
fn draw(&self, renderer: &mut Renderer);
}
struct DrawableBitmap {
handle: u32
}
struct DrawableRect {
rect: Rect
}
impl Drawable for DrawableBitmap {
fn draw(&self, renderer: &mut Renderer) {
renderer.drawBitmap(self.handle);
}
}
impl Drawable for DrawableRect {
fn draw(&self, renderer: &mut Renderer) {
renderer.drawRect(self.rect);
}
}
trait Behaviour {
fn update(&mut self, gmo_data: &mut GMOData);
}
struct BehaviourMove {
speed: i32
}
struct BehaviourWait {
count: i32
}
impl Behaviour for BehaviourMove {
fn update(&mut self, gmo_data: &mut GMOData) {
gmo_data.x += self.speed;
println!("behaviour: Speed {}", gmo_data.x);
}
}
impl Behaviour for BehaviourWait {
fn update(&mut self, gmo_data: &mut GMOData) {
self.count += 1;
println!("behaviour: Wait {}", self.count);
}
}
#[derive (Copy, Clone)]
struct StageObject<'a> {
x: i32,
y: i32,
drawable: &'a dyn Drawable,
}
struct GMOData {
x: i32,
y: i32
}
struct GameObject<'a> {
data: GMOData,
sto_index: usize,
behaviour: &'a mut dyn Behaviour
}
struct STOEntry<'a> {
prev: usize,
next: usize,
sto: StageObject<'a>
}
struct STOList<'a> {
used_list: Vec<STOEntry<'a>>,
free_list: Vec<usize>,
capacity: usize,
cnt: usize,
first: usize,
last: usize
}
impl<'a> STOList<'a> {
fn create(capacity: usize) -> Self {
STOList {
used_list: Vec::with_capacity(capacity),
free_list: Vec::with_capacity(capacity),
capacity: capacity,
cnt: 0,
first: 0,
last: 0
}
}
fn add(&mut self, sto: StageObject<'a>) -> usize {
let mut index: usize = self.used_list.len();
let mut stoe = STOEntry {
prev: self.last,
next: index,
sto: sto
};
if self.free_list.len() == 0 {
if (index >= self.capacity) {
return index;
}
self.used_list.push(stoe);
} else {
if let Some(val) = self.free_list.pop() {
index = val;
stoe.next = index;
self.used_list[index] = stoe;
}
}
self.used_list[self.last].next = index;
self.last = index;
self.cnt += 1;
index
}
fn del(&mut self, index: usize) {
if index >= self.used_list.len() {
return;
}
let prev = self.used_list[index].prev;
let next = self.used_list[index].next;
if index == self.first {
self.first = next;
} else {
self.used_list[prev].next = next;
}
if index == self.last {
self.last = prev;
} else {
self.used_list[next].prev = prev;
}
self.free_list.push(index);
self.cnt -= 1;
}
}
struct Stage<'a> {
w: u32,
h: u32,
sto_list: STOList<'a>
}
impl<'a> Stage<'a> {
fn add_child(&mut self, sto: StageObject<'a>) -> usize {
return self.sto_list.add(sto);
}
fn remove_child(&mut self, index: usize) {
self.sto_list.del(index);
}
fn draw(&self, renderer: &mut Renderer) {
if self.sto_list.cnt == 0 {
return;
}
let mut index = self.sto_list.first;
while (true) {
let sto = self.sto_list.used_list[index].sto;
sto.drawable.draw(renderer);
if index == self.sto_list.last {
break;
}
index = self.sto_list.used_list[index].next;
}
}
}
fn process_game_objects(game_objects: &mut [GameObject]) {
for gmo in game_objects.iter_mut() {
gmo.behaviour.update(&mut gmo.data);
}
}
pub fn main()
{
let mut renderer = Renderer { canvas: 0 /* not used */};
// testing Stage
let mut stage = Stage {
w: 800,
h: 600,
sto_list: STOList::create(128)
};
let sto_bitmap = stage.add_child(
StageObject { x: 0, y: 0, drawable: &DrawableBitmap { handle: 5 }}
);
let sto_rect = stage.add_child(
StageObject { x: 0, y: 0, drawable: &DrawableRect { rect: Rect { w:10, h:10 }}}
);
stage.draw(&mut renderer);
// testing game objects
let mut game_objects: [GameObject; 2] = [
GameObject { data: GMOData { x: 0, y: 0}, sto_index: sto_bitmap, behaviour: &mut BehaviourMove { speed: 10 } },
GameObject { data: GMOData { x: 0, y: 0}, sto_index: sto_rect, behaviour: &mut BehaviourWait { count: 0 } }
];
process_game_objects(
&mut game_objects
);
}
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment