![]() |
|
Purple Martians update |
Michael Weiss
Member #223
April 2000
|
Hi all, I have been working on cleaning up and documenting my Purple Martians project. I wrote some HTML pages of detailed code descriptions. I was planning on hosting then on allegro.cc, but I don't have a members.allegro.cc account. I have been a member for almost 20 years, but never have signed up for the free web site. I requested one from Matt a few months ago, but I guess he rarely makes an appearance here anymore. So sad. I hope this doesn't mean that allegro.cc is going the way of the dodo. Anyway, if anyone would like to look at my detailed code descriptions and give any feedback, I would be most grateful. I have attached them to this post in a zip file, but they are also available with the rest of my project on https://github.com/mweiss001/purple_martians Of particular note, I am most proud of the netgame code, followed by the dynamic screen resizing while the game is running. The use of splines in the logo is neat too. The code is almost all straight C, at one point I was going to convert it all to C++, but gave up due to to sheer enormity of the task. I break some good programming styles, mostly with my use of global variables, but I honestly can't see a way around it that isn't more complicated and non-intuitive. I always try to minimize my use of globals, but some variables just need to be visible in lots of different scopes. I'm setting programming aside for now to switch back to my other creative outlet, writing and recording music. I took almost a year of all my spare time fixing up and polishing this project. I have to call an end to it at some time. There is no end to what I could add, change, redo, etc. But as it stands now, I am proud of what I have been able to accomplish. The one thing I like most about allegro is that it is a game programming library, not a game engine. You are free to implement your game however you want. I looked into Unity once, and even though it is very impressive and you could do some amazing things with it, you have to do things their way. For me, most of the enjoyment comes from figuring out from scratch, how to do things my way. This is mostly a vanity project. I did it because I wanted to. I wanted to prove to myself that I could do it. I would be just icing on the cake if other people liked it too. I also write and record original music, and there are many parallels between that creative endeavor and programming. I create something that did not exist before. I give it away for free. I do it mostly for me, but would love it if others appreciated it also. So please have a look at the detailed code descriptions and tell me your thoughts. Good, bad, ugly, whatever. Thanks everyone! Michael Weiss my email: Download Purple Martians from itch.io: Purple Martians project page on allegro.cc: Github repository for my project: My youtube channel with game videos and original music:
|
Frank Drebin
Member #2,987
December 2002
![]() |
WOW Now this is what I call a documentation! I took a look and there's nothing I can tell to do better. In fact it is so well documented that I feel it's rather like a tutorial for someone (or for yourself) to understand the structure of your source code I like how the screen resizing works in the game though sometimes I think that screen can go off-center (see attached screenshot). |
Michael Weiss
Member #223
April 2000
|
Thanks Frank, I tried to make the documentation very thorough, especially for the complicated parts. As far as the centering thing goes, I know what you mean, I am not 100% satisfied with that myself. The player is not supposed to be in the exact center anyways. I originally had it that way, but later changed it to a method with a hysteresis rectangle in the center of the screen that the player was free to move in without causing the level to scroll. Its size is customizable in the code: 1
2void get_new_screen_buffer(void)
3{
4 al_set_target_backbuffer(display);
5 al_clear_to_color(al_map_rgb(0,0,0));
6
7 int alp = active_local_player;
8 int c = players[alp].color;
9
10 // draw frame in local player's color
11 for (int x = 0; x < BORDER_WIDTH; x++)
12 al_draw_rectangle(x+0.5f, x+0.5f, (SCREEN_W-1-x)+0.5f, (SCREEN_H-1-x)+0.5f, palette_color[c + (x * 16)], 1);
13
14 // default place and size to draw on screen_buffer
15 int bw = BORDER_WIDTH;
16 int sbx = bw;
17 int sby = bw;
18 int sbw = SCREEN_W-bw*2;
19 int sbh = SCREEN_H-bw*2;
20
21 // how big is the entire level after scale factor is applied?
22 int sls = (int) ((float)2000 * scale_factor_current); // sls = scaled level size
23
24 // is the entire level smaller than the screen buffer width?
25 if (sls < sbw)
26 {
27 int a = sbw - sls; // how much smaller?
28 sbw = sls; // new screen_buffer blit width = sls
29 sbx += a/2; // new screen_buffer blit xpos
30 }
31
32 // is the entire level smaller than the screen buffer height?
33 if (sls < sbh)
34 {
35 int a = sbh - sls; // how much smaller?
36 sbh = sls; // new screen_buffer blit height = sls
37 sby += a/2; // new screen_buffer blit ypos
38 }
39
40 // find the size of the source screen from actual screen size and scaler
41 int SW = (int)( (float)(SCREEN_W - bw *2) / scale_factor_current);
42 int SH = (int)( (float)(SCREEN_H - bw *2) / scale_factor_current);
43 if (SW > 2000) SW = 2000;
44 if (SH > 2000) SH = 2000;
45
46 // find where to grab the source screen from based on the players position
47 int PX = al_fixtoi(players[alp].PX) + 10;
48 int PY = al_fixtoi(players[alp].PY) + 10;
49
50 // this method always has the player in the middle of the screen
51 //int WX = PX - SW/2 -10; // set window from PX, PY
52 //int WY = PY - SH/2 -10;
53
54 // set the scroll hysteresis (a rectangle in the middle of the screen where there is no scroll)
55 int x_size = SW / 8; // larger number is smaller window
56 int y_size = SH / 12;
57
58 if (WX < PX - SW/2 - x_size) WX = PX - SW/2 - x_size; // hit right edge
59 if (WX > PX - SW/2 + x_size) WX = PX - SW/2 + x_size; // hit left edge
60 if (WY < PY - SH/2 - y_size) WY = PY - SH/2 - y_size; // hit bottom edge
61 if (WY > PY - SH/2 + y_size) WY = PY - SH/2 + y_size; // hit top edge
62
63 // correct for edges
64 if (WX < 0) WX = 0;
65 if (WY < 0) WY = 0;
66 if (WX > (2000 - SW)) WX = 2000 - SW;
67 if (WY > (2000 - SH)) WY = 2000 - SH;
68
69 // used by get_new_background to only get what is needed
70 level_display_region_x = WX;
71 level_display_region_y = WY;
72 level_display_region_w = SW;
73 level_display_region_h = SH;
74
75 // this is what all the previous calculation have been building up to:
76 al_draw_scaled_bitmap(level_buffer, WX, WY, SW, SH, sbx, sby, sbw, sbh, 0);
77
78 #ifdef SHOW_HYSTERESIS_WINDOW
79 float hx1 = SCREEN_W/2 - x_size * scale_factor_current;
80 float hx2 = SCREEN_W/2 + x_size * scale_factor_current;
81 float hy1 = SCREEN_H/2 - y_size * scale_factor_current;
82 float hy2 = SCREEN_H/2 + y_size * scale_factor_current;
83 al_draw_rectangle(hx1, hy1, hx2, hy2, palette_color[10], 2);
84 #endif
85
86}
It seems to works pretty good, except when changing screen size, the player gets pushed up against the edge of the hysteresis window. I've noticed it myself, but couldn't think of a way to do anything about it. What did you think about the netgame code? PS I checked out Brutalo Deluxe back when you released v3.30 and liked it. Thanks for the feedback...
|
Frank Drebin
Member #2,987
December 2002
![]() |
The netcode looks reasonable, however, I didn't set up a net game to test the functionality by myself. Are you using TCP or UDP? Well I think I am using pretty much the same game loop like all the Allegro 5 tutorials suggest and the same one you are using in the 'Events'-section of your documentation - so nothing secret here... BTW: When porting a game from Allegro 4 to Allegro 5 I found this article quite useful - most of what I had to do is mentioned here. |
Edgar Reynaldo
Major Reynaldo
May 2007
![]() |
It would do you some good to add some organization to your data. Use structs to group data that belongs together. Globals ARE bad. If every file needs to access every piece of data throughout the program, it means your code is not modular. Wrap your data in a struct, and then pass a pointer to that struct. Voila, you now have access to everything you did before, but you don't need to share it with every module you have. To be honest, your code suffers from what I call "Urban Sprawl". My old Spiraloid program looked like that. There were dirty hacks all over the place, and functions were way too long. Your documentation is awesome, but hard to find in your repo. I applaud your work. You've made quite the awesome little game. If you were to rewrite the game from scratch, I'm sure the code would look completely different, but there's no really no point doing that when you have something that already works. Michael Weiss said: I was planning on hosting then on allegro.cc, but I don't have a members.allegro.cc account. I have been a member for almost 20 years, but never have signed up for the free web site. I requested one from Matt a few months ago, but I guess he rarely makes an appearance here anymore. So sad. I hope this doesn't mean that allegro.cc is going the way of the dodo. The best way to reach Matthew is by email, or PM. matthew@allegro.cc
My Website! | EAGLE GUI Library Demos | My Deviant Art Gallery | Spiraloid Preview | A4 FontMaker | Skyline! (Missile Defense) Eagle and Allegro 5 binaries | Older Allegro 4 and 5 binaries | Allegro 5 compile guide |
|