int Map::PickTile(int x, int y)
{
/*static float offset;
static sfuMapTilePickingClosest data_new, data_old;
static Vector3 point_on_ray, ray_origin;
///this might be wrong
//first get the original ray coordinates (camera position + cursor offset)
/*if (x > 0)
offset = (2 * (x - e_engine->m_map_space[12])) / e_engine->wnd_size.x - 1;
else
offset = 0;
ray_origin.x = m_cam_coords->x + offset;
if (y > 0)
offset = (2 * (y - e_engine->m_map_space[13])) / e_engine->wnd_size.y - 1;
else
offset = 0;
ray_origin.y = m_cam_coords->y + offset;
ray_origin.z = m_cam_coords->z; //might need to inverse this?
///need to also store here the current angle of the camera
///could try and get away with using the radians m_angle thingy here
///could also pass that directly into the function
//then get the current rotation of the camera
///can just shove the first tile into data_old
/*data_old.dist = e_math_gl->ClosestPointOnRay(&point_on_ray, &ray_origin, m_cam_direction, &(m_tile_coords[(int)((m_cam_coords->y * m_width) + m_cam_coords->x)]));
data_old.tile = (int)((m_cam_coords->y * m_width) + m_cam_coords->x);
for (i = m_cam_coords->y; i < m_cam_view->x; i++)
{
for (o = m_cam_coords->x; o < m_cam_view->y; o++)
{
data_new.dist = e_math_gl->ClosestPointOnRay(&point_on_ray,
&ray_origin,
m_cam_direction,
&(m_tile_coords[(int)((i * m_width) + o)]));
if (data_new.dist < data_old.dist)
{
data_old.dist = data_new.dist;
data_old.tile = (int)((i * m_width) + o);
}
}
}*/
static Vector3 unit_ray, ray, pos, endray, point;
static float distance;
m_hover_bool_render = false;
//mainly just need the position could get the direction anyway, and that should be just
//x/y/z * w? but meh, could put the position at the center of the camera aswell, which is what we want anyway
//obv not doing this very good, remember ray is just the direction
/* get tile from cursor position via picking */
e_detect->GetPickRay(&pos, &unit_ray, x, y, e_camera->getFOV(), e_engine->wnd_size.x, e_engine->wnd_size.y);
memcpy(&ray, &unit_ray, sizeof(Vector3));
//need to get the length for the ray, (times by a scalar in this case distance)
e_math->MultiplyVectorByScalar(&ray, e_camera->getFar());
m_endpos.x = ray.x + pos.x;
m_endpos.y = ray.y + pos.y;
m_endpos.z = ray.z + pos.z;
#ifdef _DEBUG
memcpy(&m_startpos, &pos, sizeof(Vector3));
m_startpos.z -= 0.1f;
//debug/render pick ray
if (m_debug_first == true)
{
e_sb->Begin(GL_QUADS, 4, NULL);
/*e_sb->AddPos(4.0f, 4.0f, -1.0f);
e_sb->AddPos(4.1f, 4.0f, -1.0f);
e_sb->AddPos(4.1f, 8.0f, -1.0f);
e_sb->AddPos(4.0f, 8.0f, -1.0f);*/
///need to rotate these
e_sb->AddPos(m_startpos.x, m_startpos.y, m_startpos.z);
e_sb->AddPos(m_startpos.x + 0.1f, m_startpos.y, m_startpos.z);
e_sb->AddPos(m_endpos.x, m_endpos.y, m_endpos.z);
e_sb->AddPos(m_endpos.x + 0.1f, m_endpos.y, m_endpos.z);
m_debug_sb = e_sb->End();
m_debug_first = false;
}
else //modifying positions
{
e_sb->ReplacePos(m_debug_sb, 0, m_startpos.x, m_startpos.y, m_startpos.z);
e_sb->ReplacePos(m_debug_sb, 1, m_startpos.x + 0.1f, m_startpos.y, m_startpos.z);
e_sb->ReplacePos(m_debug_sb, 2, m_endpos.x, m_endpos.y, m_endpos.z);
e_sb->ReplacePos(m_debug_sb, 3, m_endpos.x + 0.1f, m_endpos.y, m_endpos.z);
}
#endif
static float t;
//check all map but filter later to the size
//or 1000 boxes
for (i = 0; i < m_length; i++)
{
//first get the closest point on ray then scale to that ray
/*memcpy(&point, &m_endpos, sizeof(Vector3));
t = e_math_gl->ClosestPointOnRay(&point, &pos, &unit_ray, &(m_bbox[i].min));
///would project to inside the box (might need max and get the middle to calculate)
//e_math_gl->ClosestRayOnRay(&endray, &pos, &unit_ray, &(m_bbox[i].min));
//t = e_math->DistanceSquared3(&pos, &(m_bbox[i].min));
memcpy(&endray, &unit_ray, sizeof(Vector3));
endray.x *= t;
endray.y *= t;
endray.z *= t;*/
//just need to see whether distance is correct?
//memcpy(&ray, &unit_ray, sizeof(Vector3));
//e_math->MultiplyVectorByScalar(&ray, e_camera->getFar());
//first to collide
if (e_detect->BoxIntersectRay(&(m_bbox[i].min), &(m_bbox[i].max), &pos, &unit_ray) == true)
{
// select this one
int type;
///the selection should be based on what we current have in the in tile, so need to keymap that and then set the highlight
/*switch (m_in_tile.sprite_type)
{
case FOXY_SPRITE_ACTOR:
type = i_actor->getType(m_in_tile.sprite_pos);
m_hover_width = m_keymap_actors[type].width;
m_hover_height = m_keymap_actors[type].height;
break;
case FOXY_SPRITE_BUILDING:
//type = i_building->getType(m_in_tile.sprite_pos);
m_hover_width = m_keymap_buildings[type].width;
m_hover_height = m_keymap_buildings[type].height;
break;
case FOXY_SPRITE_OBJECT:
//type = i_object->getType(m_in_tile.sprite_pos);
m_hover_width = m_keymap_objects[type].width;
m_hover_height = m_keymap_objects[type].height;
break;
}*/
m_hover_width = 1;
m_hover_height = 1;
//store records in hover tile for rendering puposes and return the tile
m_hover_tile_pos = i;
m_hover_bool_render = true;
return i;
}
}
//loose, no tile selected
return FOXY_INVALID;
}