Jump to content

Recommended Posts

Posted

Okay, been a while since I've posted. :) Anyways, lately I have been thinking about something I have been wanting to do but have got stuck on this part. My idea involves a grid.

 

In the grid, each little cell contains something, maybe in image, who knows. This grid of course would have to be displayed to the web browser in one of different forms but that doesn't really matter here. Now here comes the hard part. I want to be able to store the grid in a single variable. Something that could look like this:

 

>xxxxxxxxTxB
xxxTxxxxxxB
xxxxxxTxxxB
xxTxxxxxxxB
xxxxxxxxTxB
xxxxxxxxTxB
xxxTxxxxxxB
xxxxxxTxxxB
xxTxxxxxxxB
xxxxxxxxTx

 

That's a 10x10 grid. I need to find a way to have php scan that variable, and do something depending on the certain letter it sees. Say for every "x" it sees, it needs to make a green cell and for every "T" it sees, it needs to make a brown tile. And for every "B" it sees, it starts a new row. Is there any function that I can use in order to scan it and perform an action depending on what letter it encounters?

 

There might be a really simple way to do this I haven't been able to find, or I'll need to define my own function to do it. >.<

Posted

(I may be missing some of your meaning... but here goes)

 

I'd use an array. That's not technically a variable, but sounds like the tool to use. If you need the array in a variable, serialize() the array.

Posted (edited)

I have started using arrays but it's quite inconvenient. x.x Here is what I have so far:

 

>// Store the map into the variable...
$area1 = 'x x x x x x x x x x x x x x x x x x x x x x x x x x x x x xB
x x x x x x x x x x x x x x x x x x x x x x x x x x x x x xB
x x x x x x x x x x x x x x x x x x x x x x x x x x x x x xB
x x x x x x x x x x x x x x x x x x x x x x x x x x x x x xB
x x x x x x x x x x x x x x x x x x x x x x x x x x x x x xB
x x x x x x x x x x x x x x x x x x x x x x x x x x x x x xB
x x x x x x x x x x x x x x x x x x x x x x x x x x x x x xB
x x x x x x x x x x x x x x x x x x x x x x x x x x x x x xB
x x x x x x x x x x x x x x x x x x x x x x x x x x x x x xB
x x x x x x x x x x x x x x x x x x x x x x x x x x x x x xB
x x x x x x x x x x x x x x x x x x x x x x x x x x x x x xB
x x x x x x x x x x x x x x x x x x x x x x x x x x x x x xB
x x x x x x x x x x x x x x x x x x x x x x x x x x x x x xB
x x x x x x x x x x x x x x x x x x x x x x x x x x x x x xB
x x x x x x x x x x x x x x x x x x x x x x x x x x x x x xB
x x x x x x x x x x x x x x x x x x x x x x x x x x x x x xB
x x x x x x x x x x x x x x x x x x x x x x x x x x x x x xB
x x x x x x x x x x x x x x x x x x x x x x x x x x x x x xB
x x x x x x x x x x x x x x x x x x x x x x x x x x x x x xB
x x x x x x x x x x x x x x x x x x x x x x x x x x x x x xB
x x x x x x x x x x x x x x x x x x x x x x x x x x x x x xB
x x x x x x x x x x x x x x x x x x x x x x x x x x x x x xB
x x x x x x x x x x x x x x x x x x x x x x x x x x x x x xB
x x x x x x x x x x x x x x x x x x x x x x x x x x x x x xB
x x x x x x x x x x x x x x x x x x x x x x x x x x x x x xB
x x x x x x x x x x x x x x x x x x x x x x x x x x x x x xB
x x x x x x x x x x x x x x x x x x x x x x x x x x x x x xB
x x x x x x x x x x x x x x x x x x x x x x x x x x x x x xB
x x x x x x x x x x x x x x x x x x x x x x x x x x x x x xB
x x x x x x x x x x x x x x x x x x x x x x x x x x x x x x';

// Get it all on one one line...
$area1 = explode ("\n", $area1);
$area1 = implode ('', $area1);

// Explode the string to store the rows into an array...
$area1 = explode ('B', $area1);

// Explode again to store each character into a nested array...
for ($i = 0; $i < 30; $i++) {
   $area1[$i] = explode (' ', $area1[$i]);
}

From there I could recall any one of the x's by using $area[row][column]. I have run into another problem. I need it to be $area[column][row], heh... Sorry about all the questions, I only know the basics of php.

 

Also a couple other minor things... I'm not sure or not if there's a function to put a variable all on one line or not...

Edited by D.Slatk
Posted

You've described the tree, can you give me a view of the forest? What's the big picture thing you're trying to accomplish?

Posted (edited)

Okay I managed to get something done. Sorry for not being very clear. I'm trying to have a big "map" of letters that are used to output a table. Each letter represents something in the table, whether it's a cell with a certain color or a </tr><tr> to start a new row.

 

One problem I was having was when I was trying to explode that string so I could each each letter into its own array. I couldn't just explode with '' (explode things that have nothing between them), which I was trying to do to accomplish that. So I looked at php.net and after a bit of looking found a function called chunk_split()! So I used that to place a colon after every letter, then used substr() to take off the last colon, and then exploded it by the colon so each letter was in it's own key as I wanted. :P

 

Here is the working code:

 

>echo '<html><head><title>Test</title><style type="text/css"><!-- body,table {font-size:11px;} --></style></head><body>';

// Store the map into the variable...
$area1 = 'xxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxx
xxxxxxxxxxxxxxLxxxxxxxxxxxxxxxxx
xxxxxxxxxxxxxLLxxxLLLxxxxxxxxxxx
xxxxxxxLLxxLxxxxxxLLxxxxxxxxxxxx
xxxxxxLLLxxxxLLxxxxxxLLLLLxxxxxx
xxxxxxxxxxxxxxxxxxLLLLLLLLLLxxxx
xxxLLLLLLLLLLLLLLLLLLLLLLLLLLxxx
xxLLLLLLLLLLLLLLLLLLLLLLLLLLLLxx
xxLLLLLLLLLLLLLLLLLLLLLLLLLLLLxx
xxxLLLLLLLLLLLLLLLLLLLLLLLLLLLxx
xxxxLLLLLLLLLLLLLLLLLLLLLLLLLLxx
xxxLLLLLLLLLLLLLLLLLLLLLLLLLLLxx
xxLLLLLLLLLLLLLLLLLLLLLLLLLLLLxx
xLLLLLLLLLLLLLLLLLLLLLLLLLLLLLxx
xLLLLLLLLLLLLLLLLLLLLLLLLLLLLLxx
xLLLLLLLLLLLLLLLLLLLLLLLLLLLLxxx
xLLLLLLLLLLLxxxxxxxLxLLLLLxxxxxx
xLLLLLLLLLxxxxxxxxxxxxxxxxxxxxxx
xLLLLLLLxxxxxxxxxxxxxxxxxxxxxxxx
xLLLLLLLxxxxxxxxxxxxxxxxxxxxxxxx
xLLLLLLLLLxxxxxxxxxxxxxxxxxxxxxx
xxLLLLLLLLLLLLLLLLLLLLxxxxxxxxxx
xxxLLLLLLLLLLLLLLLLLLLLxxxxxxxxx
xxxxLLLLLLLLLLLLLLLLLLLLxxxxxxxx
xxxxxLLLLLLLLLLLLLLLLLLLLxxxxxxx
xxxxxxLLLLLLLLLLLLLLLLLLLxxxxxxx
xxxxxxxLLLLLLLLLLLLLLLLLxxxxxxxx
xxLLxxxxxxxxxxxxxxLLLxxxxxxxxxxx
xxxxxxxLLLxxxLxxxxxxxxxxxxxxxxxx
xxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxx';

// Separate the letters with a colon...
$area1 = chunk_split($area1, 1, ':');
$area1 = substr ($area1, 0, (strlen($area1)-1));

// Put each tile into a key of the array...
$area1 = explode (':', $area1);

// Generate the table and it's tiles depending on the contents of each key...
echo '<table border="0" cellpadding="0" cellspacing="0" align="center"><tr>';
for ($i = 0; isset($area1[$i]); $i++) {
   switch ($area1[$i]) {
   case 'x':
       echo '<td width="16" height="16" bgcolor="#89CBF3"> </td>';
       break;
   case 'L':
       echo '<td width="16" height="16" bgcolor="#19CF00"> </td>';
       break;
   case "\n":
       echo '</tr><tr>';
       break;
   default:
       echo '<td width="16" height="16" bgcolor="#FFFFFF"> </td>';
   }
}
echo '</tr></table>';

echo '</body></html>';

 

You can see it in action at http://test.talonz.com/enginetest.php :D

 

However I am still looking for ways to make the script more clean. Thanks for telling me about the serialize() function, that way it'd be easy to store this into a mysql record. :) Okay, and the big forest thing. I want to be able to have a very large map. In order to reduce speeds of requests to the table I'd have several maps, with each record having some way of identifying where it is in relationship to the other maps.

 

Then the big goal is I want to be able to recall say a 10x10 area for starters anywhere on that big map (all of the records put together forms the big map)... It's confusing I think but right now I just want to make sure I can get those records stored and recalled in a nice clean way. :P

Edited by D.Slatk
Posted

If I understand you correctly you want the states in a single string so that you can easily store the states in a database.

 

If you want to access the strings states directly without exploding the string into an array just use the string index operator

 

$str = "hello";

echo $str{0}; // outputs 'h'

echo $str{1}; // outputs 'e'

 

since your array is 10,10 you would have a string of length 100.

to calculate the 1d index from a 2d co-ordinate you just do the following:

 

$rowLength = 10;

$numRows = 10;

$stringIndex = ($rowIndex * $rowLength) + $colIndex;

echo $str{$stringIndex};

 

so if you want to access the character in the string at row 0, column 5.. $stringIndex would be (0 * 10) + 5 = 5. Row 2 at column 3 would be (2 * 10) + 3 = 23;

 

hope this helps

Posted (edited)

That is a very good idea, thanks! :dance: One thing before I try it though, I looked for documentation on php.net so I could find more information out about it but couldn't find any... Do you have a link to it there?

 

edit

Nevermind, foud some, it was way down though:

http://us2.php.net/manual/en/language.types.string.php

 

Going to go try it now.

 

edit

 

Yay, works. :dance: All I had to do was take out the code that converted the string into an array, and then replace each instance if $area1[$i] with $area1{$1}. Any more ideas on how to make this run faster / make the code more clean would be greatly appreciated!

 

http://test.talonz.com/enginetest.php <- Ignore the trees, was testing something.

Edited by D.Slatk
Posted

Glad to help.

 

Sorry.. I cant think of any way to make it faster.

 

Depending on your application you might be able to cache the output table if page requests for the same info are common, but I don't know how dynamic your data is.

Posted

hehe, That's okay. My next step is probably going to have to be to store several areas (smaller map chunks of the big map) in a database and somehow assign attributes to organize how they should be arranged on the big map as a whole. I think I am going to use an area id for the primary key, two numbers for the area location (x and y), then the map string for that area. I'd need to write a function that requests a portion of the map depending on for numbers (x1, y1, x2, y2) and those four numbers being two "global" coordinates. An area's global coordinates are determined by the area location. :dance:

 

That is the best idea I can think of in order to reduce stress. See I could just make one HUGE map, but since when people request, they only request (normally) a 21x21 chunk of it, that creates a lot of stress on the server. They'd be requesting a huge data entry and only using just a small portion of it. With my idea in the first paragraph, they'll only be request up to four max areas at a time which is stitched together to show them the portion they're supposed to see.

 

This is all just theorizing. :dance: No idea how I'll get it done but all you need is an ambition. If anybody has any other ideas that would work better, prove to be less stress on the server, or make the output'ed source code smaller again please share! hehe.

Posted (edited)

Just off the top of my head you could just do a replace on the string. (Sorry if this got mentioned before but I only scanned the thread).

 

>function generate_map($str) {
  $str = str_replace('x', '<td class="g1"> </td>', $str);
  $str = str_replace('T', '<td class="g2"> </td>', $str);
  $str = str_replace('L', '<td class="w1"> </td>', $str);
  $str = str_replace("\n", "</tr>\n<tr>\n", $str);
  return $str;
}

 

Or use preg_replace. Could even make an array of each letter and what it represents then use a foreach loop.

 

>$tiles = array('x' => '<td class="g1"> </td>', 'T' => '<td class="g2"> </td>', '\n' => '</tr>\n<tr>\n');

foreach ($tiles as $key => $value) {
  str_replace($key, $value, $mapstring);
}

Edited by carbonize
Posted

That's a really cool function, but it's very hard to get actual things inside of the cells such as the trees that are in the link... it is more easy for me to output the map piece by piece (td by td, and run conditionals to check if they need the images inside and if so then place them) until they all put together the actual map...

Posted

Sounds like you are on the correct track using a 2d primary key as coords.

Personally I think I would use a multi keyed primary id being the upper left hand coordinates of the system. If you keep the x,y separate you should be able to do queries in ranges. IE: all maps with x coordinates < b but greater than a and with y coordiants > c but less then d.

 

You may even play around with letting some client side scripting display the actual data and grab just the map string from the site. This could let you do fast scrolling around your map without refreshing the page.

 

JP

Posted

Hehe, I am not actually using a primary key as the coords. Each "area" would have its own primary key of course, but it'd just be its id. Rather, each area has an identification associated with it, mainly its coords with all the other areas. Say you have 9 areas that are put next to eachother to form the large map.

 

>[Area 0x0] [Area 0x1] [Area 0x2]
[Area 1x0] [Area 1x1] [Area 1x2]
[Area 2x0] [Area 2x1] [Area 2x2]

 

That's how they'd be next to eachother on the actual map. To calculate the global top-left coordinate of an area, that'd be done depending on the sizes of the areas. Right now I'm thinking each size will be 32x32, but that isn't final yet. So the top left of area 1x2 would be (32, 64). ;)

 

So basically the top-left global coords of an area are based on the area coords... Because if I need to edit it, I can, but I can't edit a primary key. :P

Posted

I believe you are mistaken about not being able to modify a primary key. At least using mysql you can. Primary keys just have to be unique. Since presumably you would have no overlapping areas in your db, you should be able to guarantee uniqueness without an additional id.

 

The following does work as long as 1,1 is not already in the db.

 

CREATE TABLE `test` (

`x` int(10) unsigned NOT NULL default '0',

`y` int(10) unsigned NOT NULL default '0',

`data` varchar(255) NOT NULL default '',

PRIMARY KEY (`x`,`y`)

) TYPE=MyISAM COMMENT='test';

 

INSERT INTO `test` VALUES (1, 2, 'testdata');

UPDATE `test` SET `y` = '1' WHERE `x` =1 AND `y` =2;

Posted

Oh okay, I see what you mean there, now. I didn't know that you could assign primary keys to two columns! Changin will work unless I need to use foreign keys, which I don't think I would need to do yet, really. This should save a column for several tables, thanks. :(

 

By the way, if you try to change the value of a primary key into a value that already exists in the column, will it bring up an error?

Posted
Changin will work unless I need to use foreign keys

You can still do it, you just need a 2 field foreign key.

 

By the way, if you try to change the value of a primary key into a value that already exists in the column, will it bring up an error?

 

Yes it will throw error #1062 - Duplicate entry

 

BTW what is the acutal purpose of your app. How is it going to be used? (If you don't mind me asking)

Posted (edited)
You can still do it, you just need a 2 field foreign key.

Yes it will throw error #1062 - Duplicate entry

 

BTW what is the acutal purpose of your app.  How is it going to be used? (If you don't mind me asking)

Wow that really adds a lot more possibilities than I had imagined, making a primary key depend on two columns' values. Okay good about the error thing, when the php interfaces with the database I'll get caught if I'm doing anything stupid!

 

You certainly know a lot about about mysql. Thanks for all the help by the way. I'll post why I'm building it in the morning as it will take some time to type up. It is a bit late here in california. :xmas:

Edited by D.Slatk
Posted (edited)

Okay, basically I am trying to build the first steps of a game. :) I've got an idea and so i'm going with it. Since it involves things on a visual map, I think that's where I need to start. Each tile on the map has certain things associated with it.

 

Maybe you'll run into a monster, maybe you'll get teleported to a different location, maybe it'll trigger a conversation with a computer-controlled character. I have most of the details of how to get it done, I just need to keep reading this book and then actually write the rest of the code for it. :clapping:

 

If you are interested in how the tables are going to be structured feel free to PM me and I'll give you more details!

Edited by D.Slatk

Join the conversation

You can post now and register later. If you have an account, sign in now to post with your account.

Guest
Unfortunately, your content contains terms that we do not allow. Please edit your content to remove the highlighted words below.
Reply to this topic...

×   Pasted as rich text.   Paste as plain text instead

  Only 75 emoji are allowed.

×   Your link has been automatically embedded.   Display as a link instead

×   Your previous content has been restored.   Clear editor

×   You cannot paste images directly. Upload or insert images from URL.

×
×
  • Create New...