Showing posts with label projectoh. Show all posts
Showing posts with label projectoh. Show all posts

7/01/2009

More than 1 year of Ocean Horizons SourceForge project

It has been more than 1 year since I uploaded the worthless Ocean Horizons svn dump to Sourceforge project site.

I did make some major progress but the development is slowed down to a crawl now, for the retarded overcomplicated GUI system built on top of guichan and lack of GFX sprites.

I tried to learn blender to create simple ship models to make create ship sprites easier, but I find blender is just not for me, I find the interface utterly confusing and unusable, maybe it's just me too stupid to figure out their proper usage and functionalities, I followed the blender noob-to-pro guide carefully to create a simple model, but as soon as I apply the subsurf modifier to smoothe the model everything is messed up.

I guess I will forget about blender for now and stick to gimp for the sprites, hopefully the development will be back on track soon.

11/04/2008

Implementing Multiplayer

At the moment I am plugging SDL_Net into Ocean Horizons, the newly added basic AI and movement states need to send/receive requests to/from server game in multiplayer game, there are also tons of things needed to be addressed in network/SDL_Net/server game in general:


Message Struct:
Ocean Horizons needs an universal serialized header format to identify a message's type, length and possibly a timestamp indicating the birth of such message in game time.


Serializing Game Objects over Network:
Generally sending a whole object over network is a big nono in most applications. However, in a game like Ocean Horizons, such thing is unavoidable. Probably I will just copy-paste the save to file serialization functions and replace FILE/OFSTREAM buffer with a char* buffer =D Reusable codes *cough*


Sending AI order/action changes events over Network:
AI Order/Action are the fundamentals of a simple "state-machine" AI used in pretty much every game genre, sometimes they are also referred as "Goals" in games have relatively higher level intelligence, e.g:FPS bots.
An Order/Action should be as simple and as small in size as possible, since they change alot in a game, and every object that has AI has at least 1 instance of both.
For example, when sending an attack-some-target order, you will need:
1.The attacker
2.The target
3.IF in range THEN attack ELSE move-to-attack
4.IF move-to-attack THEN get-target-position

The order 'ATTACK' is just an enum or constant that is probably only 1 byte if you have less than 255 order types(well if you have more than 255 order types, you fail at making a game =o), while the attacker and the target are probably multiple bytes objects, to minimize the network overhead you will need an unique id for every object in game, sending Unique Id(usually 4-8 bytes, depends on how you handle Unique Id and how many objects your game has) is much more efficient than serializing the 2 objects, both in time and in space.

In Server Client model Ocean Horizons will be using the overhead of Sending AI order/action will be significant on server, basically one AI order/action message will need to be send [number of players] times by the server, so having slim AI order/action messages will be critical.


Synchronization over Network:
Synchronization is a bit tricky in a game with tons of objects, if you synchronize all objects every few second, you will probably run out of bandwidth. Though if you don't synchronize them frequently enough, desynchronization will happen, which is bad because one or more players might be playing an entirely different game from others..
Server Client model should minimize desynchronization, but it does come at a price:the reduced responsiveness when you are issuing orders, executing commands as non-server player. Basically you have to do:

1.Someone needs to issue order 'move to X' for my ship with id 123
2.Send Request TYPE:SHIP_ORDER_MOVE SOURCE:123 TARGETX:0 TARGETY:0 to server
3.Server receives Request and Process, if it's a valid order then send granted Request to all connected players
4.The original Request Sender being one of the connected players, so he receives granted Request and his ship begins to move to X eventually..


In-game join:
To join in game you probably need to download the last server game save and synchronize with all server's game states. I think there is no other simple and efficient way to do this..


Handling Dropped Player/Player X has left:
The best way of doing this I have seen is openttd's: when one player drops/leaves his units/buildings remain intact but got taken over by AI, other player or the dropped/left player may join to regain control over his old assets later.

I typed too much again =/

9/29/2008

Pathfinding and Map Wrapping rants 2

I forgot that Planet Earth is a sphere...so the map wrap for Y coords is wrong, the intersection of equator and prime meridian divides meridian projection(tile map) into 4 "areas" like this:

Y Max
[NW][NE]
[SW][SE]
Y Min

So when your whatever moving object hits Y Max in [NW] area, your ship should reappear at [NE] area with Y Max minus 1..Hitting is Y Min in [SW] is similar except it's Y Min plus 1, also X coords is mirrored when your hit Y Max or Y Min:

X Min[NW][NE]X Max
X Min[SW][SE]X Max

Lets say we have a ship at X(100), Y(MAX-1) on 1000x1000 map(starting index 0):
[NW]'s X coords range would be 0-499
[NE]'s X coords range would be 500-999

When ship moves towards Y axis positively(north) by one, the ship reappears at X(999 - 100), Y(MAX-1)...It's very confusing, even on papers, in game the renderer needs to flip all tiles that have been "Y wrapped"(the "wrapped" tiles are on the other side of the sphere, so they are upside down and mirrored.It needs to draw from right to left and swap point 1,2 with 3,4 on quads...)

Though i will ignore this issue for now, since it's tolerable and in 1500's no ship could reach max Y(northpole) or min Y(southpole) intact... =o

9/05/2008

Pathfinding and Map Wrapping rants

Okay, here is the rants about Pathfinding and Map Wrapping in Ocean Horizons,they are royal pains really, why? Let me explain:

Pathfinding on HUGE tiles map:
Initially I naively thought a decent pathfinding algorithm will solve the problem, so I ripped borrowed A* Array implementation codes from an excellent pathfinding example program called PathFinder2D, but soon I realized pathfinding on a HUGE tile map will be a CPU hog, not to mention the enormous overhead of memory used by PathPlanner to store tile information like block status, open/closed flag, terrain type and stuff.

I have to make a simple and stupid pathplanner that only plans next node to move towards, basically it loops through 8 directions and find the one that is closest to the destination, it sucks but works.Probably a last-node needs to be passed to that function to avoid lock between 2 tiles.

Additionally a navigation graph needs to be incorporated into pathfinding system, once the graph is contructed, the routes between nodes are trusted, which means there is no obstruction between 2 linked nodes in graph, so pathfinding is not needed when doing long distance traverse.

Map Wrapping:
What is Map Wrapping?You may wonder, Map Wrapping is wrapping the coords when reaching map edges, it's a must because planet Earth is not flat, at least in our game. So whenever the map reaches edges(MAX_WIDTH or MAX_HEIGHT), the map needs to be wrapped to X-0 Y-0 again, this sounds easy enough, but there is tons of stuff that need to take Map Wrapping into consideration:

When units move to a coordination that is larger than max x, max y, you will need to cap it.
When screen draws tiles x, y bigger than max x, max y, you will need to draw the wrapped ones.
Distance between tiles calculation must checkwhether the distance is greater than 1/2 of map height or width, because distance between X-1023 and X-1 is actually 2 on a 1024 width map, but you might get broken result 1023-1 if you don't..

Hopefully I will be able to resolve these headaches gracefully. =D

5/09/2008

Source available at sourceforge svn

You can check out the source code via sourceforge svn now:

https://projectoh.svn.sourceforge.net/svnroot/projectoh

Or browse my hacks magick via sourceforge viewvc:

Browse SVN

Currently it's far from playable,though I would like to make the development more transparent to others.

4/08/2008

Progress on pre-alpha part 3

I am having a problem with map at the moment,I will need to either store mover objects pointers in map tile or make collision-test on all objects every frame,apparently the latter sounds a bit stupid,but pointers-in-maptile has its own problem:

In Ocean Horizons,each tile is 32 by 32 pixels big,so in order to represent the 'world' at an acceptable size,I will need tons of them,more precisely 1024x1024+ of them,in a worst case scenario,there might be few hundreds objects overlapping each other in one tile at a time,let's say 200,then there will need to be 1024x1024x200 pointers,in 32bit it's 1024x1024x200x4 bytes or 800MB,in 64bit it's 1024x1024x200x8 bytes or 1.6 GIGABYTE!Now this sounds even more stupid than the collision-test on all objects every frame idea.

Perhaps I should allocate them dynamically,but a pointer pointing to array of pointers on each tile doesn't sound like a good solution either.Hopefully I will get this problem sorted out soon.

2/25/2008

Progress on pre-alpha part 2

I was mainly working on Opengl renderer,the SDL blit speed is simply not good enough for 32bit color tiles,with 800x600/32x32 tiles and 256 Guichan image buttons,an optimized windows/linux release build linked against release version of SDL(provided by SDL site/distro,assuming they are O2) runs at approximately 10fps,while a debug one runs at about 5fps on windows/3fps on linux.
Now Opengl renderer is working and it has much better performance than SDL,but it will require a 3D card that supports 1.1 version of opengl.
Data loading via GM is sorta working,I can load info of different ship parts from .gm files.Current goal is to make a working ship sprite with 8 directions(45 degree per frame),so I could test the mobile object class I wrote earlier.Another goal is keeping both texture size and texture amount as low as possible,my goal is keeping total amount under 32MB.

32MB = 32 * 1024 * 1024 B = 32 * 512 * 512 * 4 B = roughly 32 512x512 32bit bitmap's

Wow that's a lot,now I should really stop talking to myself on this lifeless blog and get back to coding. =)

2/10/2008

Progress on pre-alpha

I registered and created a project on sourceforge.net(and they approved my project,thanks sourceforge.net).I will import local svn repository on my harddisk into sourceforge.net as soon as test data is relatively complete and compile-able on both windows and linux.
Actually I have been working on this project for more than half a year now,but due to other projects draining most of my spare time,it did not progress very well =(

Renderer:
I wrote a simple tile drawer using SDL_Blit functions,but it's more 3d orientated than 2d orientated,so the performance is a bit unacceptable with 32bit per pixel.I might consider using OGL to do the pixel fill instead.

Current renderer features:
  • Draw background layer(draw an image before anything else)
  • Draw grids(a hack to draw 4 (1*TileWidth) rect to resemble grids around a tile)
  • Draw tiles
  • Per pixel scrolling
Despite all the crappyness,I still considered my renderer an improvement compare to the original game's render,because the old one was 1994 and it did not even support per pixel scrolling if memory serves me right.

Input:
Current Input system uses SDL input events,I added some basic features such as doubleclick and hold.

Features:
  • SDL input based input
  • double-click handling
  • hold handling with duration
GUI:
GUI uses guichan library,which is probably the best and the most versatile GUI library available,its forums and its author are also very helpful,for a list of features it supports please refer to guichan's site: http://guichan.sourceforge.net

Scripting:
I use gamemonkey(GM) script,which is an underrated/unpopular scripting language designed specifically for games.GM supports universal table(any element in any table can be any data type) like LUA but GM is more powerful than LUA for games.

Currently GM is only used for data loading and storage.

Sound and Network:
No time has been spent on them yet,they have the least priority in my todo list. =)

That's all for now.