Alphish / gm-community-toolbox

A collection of utility functions for GameMaker.
MIT License
34 stars 6 forks source link

Room coordinates to GUI layer coordinates. #57

Open jon-mil-92 opened 1 year ago

jon-mil-92 commented 1 year ago

I have implemented a function that takes in the coordinates of a point in the room, along with the camera index for the current camera, and it returns the GUI layer coordinates in an array. I found this useful for making hud elements follow an object in the room when it enters the camera view.

/// @func rm_coord_to_gui_coord(_rm_x, _rm_y, _cam_index)
/// @desc This function translates the given room coordinates to GUI layer coordinates that are
/// contained in an array. GUI X coordinate is index 0, and GUI Y coordinate is index 1.
/// @arg {Real} _rm_x The X coordinate for the point in the room.
/// @arg {Real} _rm_y The Y coordinate for the point in the room.
/// @arg {Real} _cam_index The index of the camera that is currently being used.
/// @returns {Array<Real>} GUI layer coordinates array. Index 0 is the X coordinate, and index 1
/// is the Y coordinate.
function rm_coord_to_gui_coord(_rm_x, _rm_y, _cam_index) {
    // The room coordinates for the center of the given camera view index.
    var _view_center_x = camera_get_view_x(view_camera[_cam_index])
            + (camera_get_view_width(view_camera[_cam_index]) / 2);
    var _view_center_y = camera_get_view_y(view_camera[_cam_index])
            + (camera_get_view_height(view_camera[_cam_index]) / 2);

    // The amount the camera is zoomed into the room.
    var _zoom = view_wport[_cam_index] / camera_get_view_width(view_camera[_cam_index]);

    // The distance the point is from the center of the camera view.
    var _dist_from_center = point_distance(_view_center_x, _view_center_y, _rm_x, _rm_y) * _zoom;

    // The direction the point is from the center of the camera view.
    var _dir_from_center = point_direction(_view_center_x, _view_center_y, _rm_x, _rm_y)
            + camera_get_view_angle(view_camera[_cam_index]);

    // GUI layer cooridates for the given room coordinates.
    var _gui_x = (view_wport[_cam_index] / 2) + lengthdir_x(_dist_from_center, _dir_from_center);
    var _gui_y = (view_hport[_cam_index] / 2) + lengthdir_y(_dist_from_center, _dir_from_center);

    return [_gui_x, _gui_y];
}
AtlaStar commented 12 months ago

Is this necessary though? Iirc, drawing things in a GUI draw allows you to just draw directly to the back buffer, meaning that drawing at (0,0) will always be the top left corner.

Grisgram commented 4 months ago

Is this necessary though? Iirc, drawing things in a GUI draw allows you to just draw directly to the back buffer, meaning that drawing at (0,0) will always be the top left corner.

that's not the purpose of this function. like the op said, "a hud following an object in the room". it shall render on ui layer (above everything else), but on the coordinates in the room of any object. so he needs a translation between ui and room coordinates. i have also a set of these in place (both directions, world_to_ui and ui_to_world). things like that also help if you want to launch a particle effect on some ui element, as the particle_system is always in world coordinates but your ui is on the ui layer.

JujuAdams commented 2 months ago

See Input's source for a different approach. I would also recommend a GUI -> room function as well as this is occasionally useful.