I have a simple game project i'm working on to learn/improve my C knowledge. At the moment i have an array that contains a 'map' of my terrain, it also contains items and enemies. This is working fine, but to improve it, i'm trying to have two arrays that overlap, so i never put item's on the terrain, but in a separate item array which overlaps the terrain.
I've approached it in the way below;
void items(int * terrainMap, int itemCount, int * itemMap){
int newx = getRand(0, xsize);
int newy = getRand(0, ysize);
int count = 0;
while (count < itemCount){
if (getCell(newx, newy, terrainMap) == corridoor|| getCell(newx, newy, terrainMap) == floor){
setCell(newx, newy, chest, itemMap);
count++;
}
else {
newx = getRand(0, xsize);
newy = getRand(0, ysize);
}
}
}
Both arrays are initialized, terrain is mapped out, items is set to empty tiles. What i'm trying to do is in the if conditions, check if the terrain is passable (corridor or floor) and if so, place a chest- but place it in the item array, not on the terrain. The above code work if i place a chest on terrain, but only ever seems to place one chest in the item array.
Can someone please over me some assistance as to where i'm going wrong? Or suggest some improvements to this method? Thanks very much in advance - i'm very new to C and coding so any advice is great.
You don't modify newx and newy after adding the chest (you aren't hitting the else), so you end up adding the chest to the same position itemCount times.
You can fix this by moving your assignment of newx and newy outside of the else (to update them every time you enter the loop). You might also want to check if there isn't already a chest at that position to guarantee you get that many chests.
Related
EDIT #1.
Now i see that my functions doesnt work with this game so please forget them.
Still haven't found a solution, saw some documentation about Queue's as fjf2002 mentioned but it's way too complex to me at this momment. Tried to make a snake[20] array to store coordinates by 2 {1, 1, 1, 2} would be: Head (1,1) Tail (1,2) on the map. Still can't figure how to move it around the map and make the tail follow the head. My mind is blank after trying everything and getting frustrated by my lack of experience. Im not allowed to use anything beyond two-dimensional arrays. Meaning that no structs, no queues, no stacks... This is supposed to be done without using those and profesor says that is more easier than i think. (Dont post that i should ask him for the solution as he keeps saying the same without answering my questions). Any idea would help me greatly...------------------------------------------------------------------------------------------------------------------------------------
im using VisualStudio 2013 and programming in C language.
Was looking for a solution in the past 2 days and found nothing over internet to help me. Saw dozens of different snake games in english and spanish but i can't understand them due to zero explaining of their programs or due to my lack of experience.
Tried everything of my knowledge without success and i can't really come up with a solution by my own.
I have:
-Function to generate the map.
-Function to move the snake:
COORD cxy;
#define posicion(x,y) {(cxy.X)= (x);(cxy.Y)= (y); SetConsoleCursorPosition((GetStdHandle(STD_OUTPUT_HANDLE)), (cxy) );}
int tablero[20][20], posx = 0, posy = 0;
void movimientoSnake(){
int m = 1, k = 0, tail = 3;
char dir = 'd';
do{
if (kbhit()){
dir = getch();
if (dir == 'w'){
m = 0;
k = -1;
}
if(dir == 's'){
m = 0;
k = 1;
}
if (dir == 'a'){
m = -1;
k = 0;
}
if (dir == 'd'){
m = 1;
k = 0;
}
}
else{
Sleep(500);
posicion(posx += m, posy += k);
printf("%d", 1);
posicion(posx - tail, posy);
printf("%d", 0);
}
} while (2 > 1);
*The snake moves OK according to wasd keys, and it leaves a trail with 1's (map is full of 0's).
*It moves based on position: position(x,y) of the map (moves there) printf("%d", 1); (prints an 1). for example
The main problem is when i want to delete the trail when i move down, delete the last position while at the same time im printing the new one ahead.
If possible i would like a solution without too much complex (using too many libraries) as by now i only know:
#include <stdio.h>
#include <Windows.h>
#include <stdlib.h>
I tried to store coordinates on arrays as i saw in almost 90% of snake games out there but i dont understand the concept so i ended up with a bunch of tries without success.
Any ideas?
Thank you very much in advance.
So let us summarize:
Knowing only the coordinates of the head of the snake, how to determine the coordinates of the tail?
Since the snake may have several turns, there is no straight forward way.
I tried to store coordinates on arrays as i saw in almost 90% of snake games out there
Seems to be the only solution.
but i dont understand the concept
You should store the positions occupied by the snake in an array. You have to keep track which array elements are currently occupied, where the head and where the tail is stored.
Or you use the above as an already implemented product: a data structure that allows easy access to first and last element. Read
about http://en.wikipedia.org/wiki/FIFO , http://www.cplusplus.com/reference/queue/queue/ .
I have been trying to write an FPS in C/X11/OpenGL, but the issue that I have encountered is with calculating where the bullet hits. I have used a horrible technique, and it only sometimes works:
pos size, p;
size.x = 0.1;
size.z = 0.1; // Since the game is technically top-down (but in a 3D perspective)
// Positions are in X/Z, no Y
float f; // Counter
float d = FIRE_MAX + 1 /* Shortest Distance */, d1 /* Distance being calculated */;
x = 0; // Index of object to hit
for (f = 0.0; f < FIRE_MAX; f += .01) {
// Go forwards
p.x = player->pos.x + f * sin(toRadians(player->rot.x));
p.z = player->pos.z - f * cos(toRadians(player->rot.x));
// Get all objects that collide with the current position of the bullet
short* objs = _colDetectGetObjects(p, size, objects);
for (i = 0; i < MAX_OBJECTS; i++) {
if (objs[i] == -1) {
continue;
}
// Check the distance between the object and the player
d1 = sqrt(
pow((objects[i].pos.x - player->pos.x), 2)
+ pow((objects[i].pos.z - player->pos.z),
2));
// If it's closer, set it as the object to hit
if (d1 < d) {
x = i;
d = d1;
}
}
// If there was an object, hit it
if (x > 0) {
hit(&objects[x], FIRE_DAMAGE, explosions, currtime);
break;
}
}
It just works by making a for-loop and calculating any objects that might collide with where the bullet currently is. This, of course, is very slow, and sometimes doesn't even work.
What would be the preferred way to calculate where the bullet hits? I have thought of making a line and seeing if any objects collide with that line, but I have no idea how to do that kind of collision detection.
EDIT: I guess my question is this: How do I calculate the nearest object colliding in a line (that might not be a straight 45/90 degree angle)? Or are there any simpler methods of calculating where the bullet hits? The bullet is sort of like a laser, in the sense that gravity does not affect it (writing an old-school game, so I don't want it to be too realistic)
For every object you want to be hit-able, define a bounding object.
Simple examples would be a sphere or a box.
Then you have to implement a ray-sphere or ray-box intersection.
For exaple have a look at line-sphere intersection.
For boxes, you can either test aginast the four bounding lines, but there are algorithms optimsed for axis aligned boxes.
With this, proceed as you already do. For every object in the scene, check for intersection, if intersects, compare distance to previous intersected objects, take the one that is hit first.
The intersection algorithems give you the ray parameter as a result (the value t for which hit_position = ray_origin + t * ray_direction) which you can use to compare the distances.
You can organise all scene objects in the BSP tree then hit\collide detection will be pretty easy to implement. Also you can use BSP to detect invisible objects and discard them before rendering.
I am making a simple test application in C that is supposed to generate three dimensional dice. I am going to use OpenGL to do the actual drawing, but I cannot figure out how to actually generate the vertices. Of course, the whole point of this test was to see if my algorithm worked, but I found a major logic error that I cannot fix. Can somebody please point me to an article, website, or something that explains the concept? If not, although I would prefer to do the actual implementation myself, the C code is acceptable.
Basically, this is what I did before I forgot what I was doing for the algorithm:
void calculateVertices(int sides) {
BOOL isDone = FALSE;
int vectorsPerSide = 3;
VDVector3f *vertices = malloc((sizeof(VDVector3f) * (sides + 1)));
VDVector3f *normals = malloc((sizeof(VDVector3f) * (sides + 1)));
while (!isDone) {
// Start by positioning the first vertex.
vertices[0] = VDVector3fMake(0.0, 0.0, 1.0);
for (int index = 1; index <= sides; index ++) {
}
// Not a match, increase the number of vectors
vectorsPerSide ++;
}
}
Basically, it loops until a match is found. This sounds inefficient to me, but I had no other idea as to how to do this. The first vertex will actually be removed from the array at the end; I was going to use it to create the first side, which would have been used to properly position the others.
My main goal here is to be able to pass number (like 30) to it, and have it set the vertices automatically. I will not have protections against making one sided and two sided dice, because I have something special in mind. I will have those vertices entered elsewhere.
Thanks in advance for the help!
By the way, I have an algorithm that can normalize the completed vertex array. You don't have to bother helping with that.
I don't think this is possible to generalize this. How, for example would you make a fair 5 or 9 sided die? I don't think I have ever seen such a thing. A quick search on wikipedia suggests platonic solids may be what you are after. http://en.wikipedia.org/wiki/Platonic_solid
This is for a Terrain Generation and rendering program.
I have a loop that looks like this:
x = -MAX_SIGHT_DISTANCE;
y = -MAX_SIGHT_WIDTH;
while (x < MAX_SIGHT_DISTANCE)
{
while (y < MAX_SIGHT_WIDTH)
{
value = noise2d(x+camera.x, y+camera.y);
if (pointInFrustum(x-camera.x, y-camera.y, value, direction, FOV, MAX_SIGHT_DISTANCE) == 1)
{
// TODO: STORE VALUE TO AN ARRAY....SOMEHOW...
}
dz = value-camera.z;
distance = sqrt(x*x + y*y + (dz)*(dz));
x += DISTANCE_FUNCTION(distance);
y += DISTANCE_FUNCTION(distance);
}
}
It's supposed to find a semi-random height value at different resolutions: Much higher resolution up close, and lower resolution farther away.
Later,
for x
{
glBegin(GL_TRIANGLE_STRIP);
for y
{
glVertex(x, y);
glVertex(x+1, y);
}
glEnd();
}
This is supposed to be the rendering code (in pseudo-code, of course).
I have to specify the coordinates of each point. I'd really like to use triangle strips here, so I need to have all points in one strip following each other.
Comes my question: How do I store these points? In python I'd create a list, and then just render everything in the list.
Problem is this is in C, arrays aren't dynamic. So I need a size. How can I know that size? How can I loop through it in an intelligent way (since it has variable widths)? And how can I prevent stuff like the end of one row joining with the beginning of another row?
Or am I doing the whole thing wrong?
How about you use a dynamic data structure like a stack of linked-lists?
Each linked list would hold the points for each triangle strip.
The stack would contain the a linked list for each triange strip.
Linked list would suit your problem because you dont really need to index your elements.
Basically I've got some structs of type Ship which are going to go on a board which can have a variable width and height. The information about the ships is read in from a file, and I just need to know the best way to make sure that none of the ships overlap.
Here is the structure of Ship:
int x // x position of first part of ship
int y // y position of first part of ship
char dir // direction of the ship, either 'N','S','E' or 'W'
int length // length of the ship
Also, what would be a good way to handle the directions. Something cleaner than using a switch statement and using a different condition for each direction.
Any help would be greatly appreciated!
You could keep a boolean array of the entire grid, initially initialized to "false." For each ship, for each location the ship covers, check if the location is "false." If it is,
set it to "true". If not, then some other ship is on the location.
This algorithm is linear in the total area of all the ships, but also requires extra space
proportional to the number of locations on the board.
This is the same thing as a test whether rectangles intersect, I think your code would be simpler if you don't think of these ships as a point,length, and direction but as a rectangle.
So convert this
int x // x position of first part of ship
int y // y position of first part of ship
char dir // direction of the ship, either 'N','S','E' or 'W'
int length // length of the ship
to this (allow negative cx & cy to get N,S,E,W)
int x // x position of first part of ship
int y // y position of first part of ship
int cx // length of the ship in X
int cy // length of the ship in Y
or this
int left // x position of Eastern part of the ship
int top // y position of Northernmost part of ship
int right // x position of Westernmost part of the ship
int bottom // y position of Southernmost part of ship
bool orientation; // so we can tell East from West or North from South.
Then a simple function can determine if two ships intersect.
bool DoShipsIntersect(Ship * a, Ship * b)
{
if ((a->right < b->left) || (b->right < a->left))
return false;
if ((a->bottom < b->top) || (b->bottom < a->top))
return false;
return true;
}
A brute force compare of every ship to every other ship should be quite fast as long as you don't have thousands of ships.
Unless you have a lot of ships then just use a simple brute force algorithm, which will be two nested loops, i.e. O(n^2).
Keep a bitmap of the board where each bit indicates whether there's a ship occupying that tile. For each ship mark the tiles it occupies on the board, and check out if you mark the same bit twice.
(Battleship?)
Make a 2D array ("board") which contains the ID of the ship when one is present. Therefore, when you add the ship you can check in O(length) time whether a space is occupied or not.
O(n * length) time, O(N^2) space.
One way of representing a direction is as a unit vector. This can be 2 integers: dirX and dirY. Eg. dirX=1 for East; or dirY=1 for South.
You can then iterate over all positions occupied by a ship with:
int cx = x;
int cy = y;
for(int i = 0; i < length; i++) {
cx += dirX;
cy += dirY;
}
Or get a bounding-box based on these values:
x
y
x + dirX * (length - 1)
y + dirY * (length - 1)
You might want to use an enum type for your direction. In terms of finding overlaps, create a two dimensional array of booleans initialized to false for your board. Then, for each ship, finding the corresponding entries in the array and, if they are already true, you have an overlap. Otherwise, set those entries to true. If you have placed all your ships and didn't encounter an already true entry, then there is no overlap.