Authors: Heretic
Version: 1.2
Type: Misc Add-on
Introduction
This script will allow you to create a Magic Compass that points at either a Map Coordinates or an Event. Its called a Magic Compass because normal compasses only point North. This one points at a location Magically!
Features
- Very easy to Install and Use
Should have a very high degree of compatability
Can point the Compass at any set of X and Y coordinates
Can point the Compass at an Event, even while it is moving around
Compass won't point at an Event that is Erased or doesn't have an Active Page
Can point at a set of X and Y coordinates that are off the current Map
Doesn't glitch when you go to Menu, unlike other Compass Scripts or Event Solutions
Uses a Background and Needle Image and positions these things for you!
Configuration Options can be altered during Gameplay
Limburger Cheese is really stinky but very tasty
Does anyone read this stuff?
No dependancies on other Scripts
Screenshots

The compass is in the Bottom Right corner. It updates dynamically as you move about.
Demo
http://downloads.chaos-project.com/here ... ssDemo.exe
Script
Place above Main and below Scene_Debug. Anywhere else should be fine in theory. If there are any problems, try moving this script closer to Main as some scripts replace methods that are aliased in this script.
I wrote a Looping Maps script, which is up over at chaos-project.com, and if you use that Script, place Magic Compass below Looping Maps.
Code:
#===============================================================================
#
# HERETIC'S MAGIC COMPASS [XP]
# Version 1.2
# Wednesday, May 6th, 2015
#
#===============================================================================
#
# ----- Overview -----
#
# This script will allow you to create a Magic Compass that points at either
# a Map Coordinates or an Event. Its called a Magic Compass because normal
# compasses only point North. This one points at a location Magically!
#
#
# ----- Features -----
#
# - Very easy to install and use
# - Should be highly compatible
# - No dependancies on other Scripts
# - Can point the Compass at any set of X and Y coordinates
# - Can point the Compass at an Event, even while it is moving around
# - Can point at a set of X and Y coordinates that are off the current Map
# - Doesn't glitch when you go to Menu, unlike other Compass Scripts
# - Uses a Background and Needle Image and positions these things for you
# - Configuration Options can be altered during gameplay
# - Limburger Cheese is really stinky but tasty
# - Does anyone read this stuff?
#
#
# ----- Version History -----
#
#
# Version 1.2 - Wednesday, May 6th, 2015
# - Fixed a bug where Tone did not match Screen Tone on Initialize
# Version 1.1 - Thursday, April 30th, 2015
# - Updated to work with Looping Maps
# * Compass will point at the closest possible distance to a Target
# Version 1.0 - Friday, December 26th, 2014
# - Initial Release
#
# ----- Instructions -----
#
# There are a few very simple script calls. Put these in Event -> Script
#
# $game_system.enable_compass = true / false
# * set to true or false to Show or Hide the Compass
#
# set_compass_map_target(x, y)
# * Sets the Compass to point at a Map X and Y Location (off map is a-okay)
#
# set_compass_event_target(target)
# * Sets the Compass to point at an Event or Event ID (either is fine)
#
# clear_compass_target
# * Clears Map Location and Target Event and causes Needle to float to North
#
#
# ----- Conditional Branch Scripts -----
#
# Put these in Event -> Conditional Branch -> Script
#
# enable_compass?
# * returns True or False if the Compass is Enabled
#
# can_point_compass?
# * returns True or False if the Compass will Point at a Target
# * returns False if an Event is Erased or doesn't have an Active Page or
# the Compass doesn't have a Map Target
#
# valid_compass_target?
# * NOTE: This must be run on an Event (recommended for Advanced Users)
# * $game_map.events[@event_id].valid_compass_target?
# * returns True or False if the Event ID is not Erased and Page is Active
#
#
# ----- Usage -----
#
# Once you have a Compass displayed on your screen, it will remain there
# until you call "enable_compass = false".
#
# The Compass Target will be erased when you change maps. Transfer Player
# on the same map will not erase the Compass Target however.
#
# If you set a Compass Target to an Event, the Event can not be erased
# and must have an active Page. For example, you have an Event with
# just one Page, and that Page has a Page Condition that is not met, such
# as a Game Switch that is not set to On, then the Compass will not
# point at that Event.
#
# If an Event is Erased or Page Conditions are not met while your Compass
# is displaying, the Compass will simply slowly float back to Due North.
#
#
# ----- Limitations -----
#
# The only Limitation I can think of is that this script in its current state
# probably won't work with Looping Map Scripts. I may take a crack at
# changing this if I ever get around to working on a Looping Map Script
# for RPG Maker XP.
#
# This has been fixed in Version 1.1 so the compass will consider the size
# of the map and point the shortest distance to your Compass Target.
#
#
# ----- Legal -----
#
# You may use this script in commercial products without permission, provided
# that I am credited for the usage of this script. You may redistribute this
# script on any websites. You may translate this script, provided that I am
# retained as the original author. You may make reasonable alterations
# to this script to suit your needs.
#
# You may NOT sell this script.
#
# You may NOT claim this script to be your property or intellectual work.
#
#
# ----- Layman Legal -----
#
# This script is supposed to be free. Just credit me if you use it in
# any sort of commercial stuff.
#
#
# ----- Configuration Options -----
#
# There are a number of Configuration Options so that you can customize this
# script to suit your needs. The Configuration Options establish default
# values, and can be changed during gameplay. Recommended for advanced
# users, but basically, all the Configuration Options are stored in
# your $game_system.
#
# COMPASS_X and COMPASS_Y are the On Screen Position for your Compass
#
# COMPASS_ZOOM will resize an image without the need to edit the images you
# use in an editor. I've found that zooming out looks just a bit better
# than 100% sized images while rotating.
#
# COMPASS_BACK_OPACITY allows you to make the Compass Background Image
# slightly transparent so it does not fully obstruct a Player's view
# of the current Map.
#
# COMPASS_HUD_Z is used to put the Compass on top of other Pictures or
# put the Compass below other Pictures. Up to you.
#
# COMPASS_SCREEN_TONE is used to match the Tone of the Compass Images
# to the Screen Tone. This is useful if you fade to black and still have
# the Compass displayed during a Map Change. If you want the compass
# to display even when the screen changes Tone, then set this value
# to False.
# Compass Background Graphic for Player's Compass (Use "" for No Picture)
COMPASS_BACK_GRAPHIC = "Compass Back.png"
# Compass Graphic for Player's Compass (Use "" for No Picture)
COMPASS_NEEDLE_GRAPHIC = "Compass Needle.png"
# Screen Position of Compass (this will change depening on Picture Size)
COMPASS_X = 525
COMPASS_Y = 365
# Adjust Compass Size for both Graphics (Smaller Grpahics rotate a bit better)
COMPASS_ZOOM = 75.0
# Makes the Background Image of the Compass Transparent
COMPASS_BACK_OPACITY = 160.0
# Compass Hud Z-Index - Use -1 for below Pictures and 100+ for above Pictures
COMPASS_HUD_Z = -1
# Make the Compass have a tone Consistent with the Game Screen (true / false)
COMPASS_SCREEN_TONE = true
#==============================================================================
# ** Game_System
#==============================================================================
class Game_System
#--------------------------------------------------------------------------
# * Public Instance Variables - Game_System
#--------------------------------------------------------------------------
attr_reader :enable_compass # Display On Screen Compass
attr_accessor :compass_back # Compass Back Graphic Default
attr_accessor :compass_needle # Compass Needle Graphic Default
attr_accessor :compass_x # Compass Screen X Position
attr_accessor :compass_y # Compass Screen Y Position
attr_accessor :compass_zoom # Zoom of Compass Pictures
attr_accessor :compass_screen_tone # Match Compass Tone to Screen Tone
attr_accessor :compass_back_opacity # Opacity of Compass Background
attr_accessor :compass_target_x # Map X Target Location
attr_accessor :compass_target_y # Map Y Target Location
attr_accessor :compass_target_event_id # Map Target Event
#--------------------------------------------------------------------------
# * Game System Initialization - Game_System
# - Default Values for when Compass is changed to Enabled
# - Adjusting values in Game System will not affect an existing Compass
#--------------------------------------------------------------------------
alias compass_game_system_initialize initialize unless $@
def initialize
# Call Original or other Aliases
compass_game_system_initialize
# Enable or Disable display of Compass
@enable_compass = false
# Compass Image Filenames (from Pictures folder)
@compass_back = COMPASS_BACK_GRAPHIC
@compass_needle = COMPASS_NEEDLE_GRAPHIC
# Default Screen Position of Compass Graphics
@compass_x = COMPASS_X
@compass_y = COMPASS_Y
# Default Zoom Level of Compass Graphics
@compass_zoom = COMPASS_ZOOM
# Default Opacity of a Compass Background Picture
@compass_back_opacity = COMPASS_BACK_OPACITY
# Default Match the two Compass Pictures Tone to the Screen Tone for Effect
@compass_screen_tone = COMPASS_SCREEN_TONE
# Map Coordinates for Compass to point at
@compass_target_x = nil
@compass_target_y = nil
# Event for Compass to point at dynamically
@compass_target_event_id = nil
end
#--------------------------------------------------------------------------
# * Enable Compass= (Setter Method) - Game_System
# - Enables the Compass and creates if needed
# - If called from a Common Event while in a Menu or other Scene, then
# the Compass Graphics will be created when you return to the Map.
#--------------------------------------------------------------------------
def enable_compass=(value)
# Check Value
return unless [true, false].include?(value)
# If True
if value == true
# If the Player's Compass doesn't exist and not a Common Event to change
if not $game_player.compass
# Create new Compass Object for Player
$game_player.compass = Game_Compass.new
# Position the Compass Object on the Screen
$game_player.compass.position_compass
end
end
# Store the Value
@enable_compass = value
end
#--------------------------------------------------------------------------
# * Set Compass Map Target - Game_System
# - Sets the Target of the Compass to Map Coordinates, even off map
# x : x-coordinate of Map
# y : y-coordinate of Map
#--------------------------------------------------------------------------
def set_compass_map_target(x, y)
# Clears Event Target ID
@compass_target_event_id = nil
# Sets a Map Location as a Target
@compass_target_x = x
@compass_target_y = y
end
#--------------------------------------------------------------------------
# * Set Compass Event Target - Game_System
# - Sets the Target of the Compass to an Event
# target : Event or Number
#--------------------------------------------------------------------------
def set_compass_event_target(target)
# Clears Map Location as a Target
@compass_target_x = nil
@compass_target_y = nil
# If Target is a Character
if target.is_a?(Game_Event)
# Just use the Event's ID
@compass_target_event_id = target.id
# Elsif the Target is a Number
elsif target.is_a?(Numeric)
# Set the Numeric Value of Target
@compass_target_event_id = target
end
end
#--------------------------------------------------------------------------
# * Clear Compass Target - Game_System
# - Clears the Compass Target
#--------------------------------------------------------------------------
def clear_compass_target
# Clears Needle Angle of Picture
$game_player.compass.needle_angle = nil if $game_player.compass
# Clears Map Location as a Target
@compass_target_x = nil
@compass_target_y = nil
# Clears Event Target ID
@compass_target_event_id = nil
end
end
#==============================================================================
# ** Game_Map
#==============================================================================
class Game_Map
#--------------------------------------------------------------------------
# * Setup - Game_Map
# - Clears Compass Targets on Map Change
# - Transferring the Player on the same Map will retain Targets
# map_id : map ID
#--------------------------------------------------------------------------
alias compass_map_setup setup unless $@
def setup(map_id)
# If a Compass is being dislayed and Target is an Event
if $game_system.enable_compass and $game_system.compass_target_event_id or
($game_system.compass_target_x and $game_system.compass_target_y)
# If Map Change
if @map and @map_id > 0 and @map_id != map_id
# Clear Compass Target (Event and Map Location)
$game_system.clear_compass_target
end
end
# Call Original or other Aliases
compass_map_setup(map_id)
end
end
#==============================================================================
# ** Compass_Picture
#==============================================================================
class Compass_Picture < Game_Picture
#--------------------------------------------------------------------------
# * Public Instance Variables - Compass_Picture
#--------------------------------------------------------------------------
attr_accessor :number # Picture Number and Z-Index
attr_accessor :name # Picture Filename in Pictures Folder
attr_accessor :origin # 0 Top Left - 1 Center (Default)
attr_accessor :x # x-coordinate
attr_accessor :y # y-coordinate
attr_accessor :zoom_x # x directional zoom rate
attr_accessor :zoom_y # y directional zoom rate
attr_accessor :opacity # opacity level
attr_accessor :blend_type # blend method
attr_accessor :tone # color tone
attr_accessor :angle # rotation angle
attr_accessor :angle_target # target of angle rotation
attr_accessor :angle_duration # duration of angle rotation
attr_accessor :rotate_speed # repeating rotation
#--------------------------------------------------------------------------
# * Object Initialization - Compass_Picture
# number : picture number
# type : background or needle
# - Creates the Pictures used for the Compass to add to Spriteset Map
# - Uses stored values from Game System to allow change during Gameplay
# - Changes to Game System do not affect existing Compass
# - Other methods available to Game_Picture are still available
#--------------------------------------------------------------------------
def initialize(number, type)
@number = number
@name = ""
@type = type
@origin = 1
@x = 0.0
@y = 0.0
@zoom_x = $game_system.compass_zoom
@zoom_y = $game_system.compass_zoom
@opacity = (type == :back) ? $game_system.compass_back_opacity : 255.0
@blend_type = 0
@duration = 0
@target_x = @x
@target_y = @y
@target_zoom_x = @zoom_x
@target_zoom_y = @zoom_y
@target_opacity = @opacity
# If Config to match Screen Tone
if $game_system.compass_screen_tone
# Set Picture Tone to the Tone of the Screen
@tone = $game_screen.tone
else
# Default Tone
@tone = Tone.new(0, 0, 0, 0)
end
@tone_target = @tone.clone
@tone_duration = 0
@angle = 0
@angle_target = @angle
@angle_duration = 0
@rotate_speed = 0
end
#--------------------------------------------------------------------------
# * Frame Update - Compass_Picture
# - Replaces Game_Picture Update of Super Class so only updates Rotation
# - Updates Transitions for X, Y, Zoom_X, Zoom_Y, Opacity, and Tone
# - Updates Transition for Angle
# - Similar to Game_Picture Update method but allows Rotation Transition
#--------------------------------------------------------------------------
def update
if @duration >= 1
d = @duration
@x = (@x * (d - 1) + @target_x) / d
@y = (@y * (d - 1) + @target_y) / d
@zoom_x = (@zoom_x * (d - 1) + @target_zoom_x) / d
@zoom_y = (@zoom_y * (d - 1) + @target_zoom_y) / d
@opacity = (@opacity * (d - 1) + @target_opacity) / d
@duration -= 1
end
if @tone_duration >= 1
d = @tone_duration
@tone.red = (@tone.red * (d - 1) + @tone_target.red) / d
@tone.green = (@tone.green * (d - 1) + @tone_target.green) / d
@tone.blue = (@tone.blue * (d - 1) + @tone_target.blue) / d
@tone.gray = (@tone.gray * (d - 1) + @tone_target.gray) / d
@tone_duration -= 1
end
if @angle_duration == 0 and @rotate_speed != 0
@angle += @rotate_speed / 2.0
elsif @angle_duration >= 1
d = @angle_duration
@angle = (@angle * (d - 1) + @angle_target) / d
@angle_duration -= 1
end
if @angle < 0 or @angle > 360
while @angle < 0 or @angle > 360
@angle += (@angle < 360 ? 360 : -360)
end
@angle %= 360
end
end
end
#==============================================================================
# ** Scene_Map
#==============================================================================
class Scene_Map
#--------------------------------------------------------------------------
# * Compass Map Spriteset - Scene_Map
# - Just returns the Spriteset Map
#--------------------------------------------------------------------------
def compass_map_spriteset
@spriteset
end
end
#==============================================================================
# ** Spriteset_Map
#==============================================================================
class Spriteset_Map
#--------------------------------------------------------------------------
# * Public Instance Variables - Spriteset_Map
#--------------------------------------------------------------------------
attr_reader :compass_back_picture # Compass Picture for Background
attr_reader :compass_needle_picture # Compass Picture for Needle
attr_reader :compass_back_sprite # Picture Sprite for Compass
attr_reader :compass_needle_sprite # Picture Sprite for Compass
#--------------------------------------------------------------------------
# * Add Compass - Spriteset_Map
# compass : Game_Compass
# - Uses number as a way to control the Z-Index
#--------------------------------------------------------------------------
def add_compass
# If the Compass Background Sprite does not already exist
if @compass_back_sprite.nil?
# Set the HUD's Z-Index as number from the Constant in Config
number = COMPASS_HUD_Z
# Create a Compass Picture for the Compass Background (type = :back)
@compass_back_picture = Compass_Picture.new(number, :back)
# Set the Picture Name from the Compass Object (refer to $game_system)
@compass_back_picture.name = $game_system.compass_back
# Shorthand
b = @compass_back_picture
# Create the Sprite for the Compass Background Picture
@compass_back_sprite = Sprite_Picture.new(@viewport2, b)
end
# If the Compass Needle Sprite does not already exist
if @compass_needle_sprite.nil?
# Set the HUD's Z-Index as number from the Constant in Config
number = COMPASS_HUD_Z
# Create a Compass Picture for the Compass Needle
@compass_needle_picture = Compass_Picture.new(number, :needle)
# If the Compass has a stored Needle Angle
if not $game_player.compass.needle_angle.nil?
# Set the Needle Angle before setting the Name or creating Sprite
@compass_needle_picture.angle = $game_player.compass.needle_angle
end
# Set the Picture Name from the Compass Object (refer to $game_system)
@compass_needle_picture.name = $game_system.compass_needle
# Shorthand
n = @compass_needle_picture
# Create the Sprite for the Compass Needle Picture
@compass_needle_sprite = Sprite_Picture.new(@viewport2, n)
end
# Position Compass Internally
position_compass
end
#--------------------------------------------------------------------------
# * Position Compass - Spriteset_Map
# - Positions the Compass Pictures and Sprites internally
#--------------------------------------------------------------------------
def position_compass
# Shorthand - Same as Position Compass called Internally
back_picture = @compass_back_picture
needle_picture = @compass_needle_picture
back_sprite = @compass_back_sprite
needle_sprite = @compass_needle_sprite
# Determine X Value as 1/2 of Larger Sprite
if back_sprite.bitmap.width > needle_sprite.bitmap.width
# Use the Centered Bitmap Width of the Background Sprite
sprite_x = back_sprite.bitmap.width / 2
else
# Use the Centered Bitmap Width of the Needle Sprite
sprite_x = needle_sprite.bitmap.width / 2
end
# Determine Y Value as 1/2 of Larger Sprite
if back_sprite.bitmap.height > needle_sprite.bitmap.height
# Use the Centered Bitmap Height of the Background Sprite
sprite_y = back_sprite.bitmap.height / 2
else
# Use the Centered Bitmap Height of the Needle Sprite
sprite_y = needle_sprite.bitmap.height / 2
end
# Position the Background Picture
back_picture.x = $game_player.compass.x + sprite_x
back_picture.y = $game_player.compass.y + sprite_y
# Position the Needle Picture
needle_picture.x = $game_player.compass.x + sprite_x
needle_picture.y = $game_player.compass.y + sprite_y
end
#--------------------------------------------------------------------------
# * Compass Sprite Update - Spriteset_Map
# - Alias of Main Sprite Update Method
# - Checks for Missing Compass Sprites on Scene Change (Menu)
#--------------------------------------------------------------------------
alias compass_sprite_update update unless $@
def update
# If the Compass Option is Enabled
if $game_system.enable_compass
# If the Compass Background or Compass Needle Sprites dont exist
if @compass_back_sprite.nil? or @compass_back_picture.nil?
# Create new Compass Object for Player unless it exists
$game_player.compass = Game_Compass.new unless $game_player.compass
# Add the Pictures and Sprites to Spriteset Map Object
add_compass
end
# Update the Compass Pictures
@compass_back_picture.update
@compass_needle_picture.update
# Update the Compass Sprites with values from Pictures
@compass_back_sprite.update
@compass_needle_sprite.update
elsif @compass_back_sprite
# Dispose of the Sprite and set the object to nil
@compass_back_sprite.dispose
@compass_back_sprite = nil
# If Needle Sprite exists
if @compass_needle_sprite
# Dispose of Needle Sprite and set the object to nil
@compass_needle_sprite.dispose
@compass_needle_sprite = nil
end
# Dispose of the Pictures
@compass_back_picture = nil
@compass_needle_picture = nil
end
# Call Original or other Aliases
compass_sprite_update
end
#--------------------------------------------------------------------------
# * Dispose - Spriteset Map
# - Disposes of Compass Images and Sprites for their Bitmaps (memory leak)
#--------------------------------------------------------------------------
alias compass_spriteset_dispose dispose
def dispose
# Dispose of the Sprites and Bitmaps
@compass_back_sprite.dispose if @compass_back_sprite
@compass_needle_sprite.dispose if @compass_needle_sprite
# Set Values to nil
@compass_back_sprite = nil if @compass_back_sprite
@compass_needle_sprite = nil if @compass_needle_sprite
# Call Original or other Aliases
compass_spriteset_dispose
end
end
#==============================================================================
# ** Game_Character
#==============================================================================
class Game_Character
#--------------------------------------------------------------------------
# * Object Initialization - Game_Character
# - Add Values before calling Original or other Aliases before Update
#--------------------------------------------------------------------------
alias compass_character_initialize initialize unless $@
def initialize
# If Player is Initialized by the Character Class (Super)
if self.is_a?(Game_Player)
# Placeholder for Game_Compass Object as a Picture
@compass = nil
end
# Call Original or other Aliases
compass_character_initialize
end
end
#==============================================================================
# ** Game_Compass
#==============================================================================
class Game_Compass
#--------------------------------------------------------------------------
# * Public Instance Variables - Game_Compass
#--------------------------------------------------------------------------
attr_accessor :x # Position of Compass on Screen
attr_accessor :y # Position of Compass on Screen
attr_accessor :needle_angle # Angle of Compass Needle
#--------------------------------------------------------------------------
# * Object Initialization - Game_Compass
# - Container in Game_Player for the Pictures
#--------------------------------------------------------------------------
def initialize
# Position of Compass on Screen
@x = $game_system.compass_x
@y = $game_system.compass_y
# Angle of the Compass Needle
@needle_angle = nil
end
#--------------------------------------------------------------------------
# * Back Sprite - Game_Compass
# - Returns the Spriteset Map Compass Background Sprite
#--------------------------------------------------------------------------
def back_sprite
$scene.compass_map_spriteset.compass_back_sprite
end
#--------------------------------------------------------------------------
# * Needle Sprite - Game_Compass
# - Returns the Spriteset Map Compass Background Sprite
#--------------------------------------------------------------------------
def needle_sprite
$scene.compass_map_spriteset.compass_needle_sprite
end
#--------------------------------------------------------------------------
# * Back Picture - Game_Compass
# - Returns the Spriteset Map Compass Background Picture
#--------------------------------------------------------------------------
def back_picture
$scene.compass_map_spriteset.compass_back_picture
end
#--------------------------------------------------------------------------
# * Needle Picture - Game_Compass
# - Returns the Spriteset Map Compass Needle Picture
#--------------------------------------------------------------------------
def needle_picture
$scene.compass_map_spriteset.compass_needle_picture
end
#--------------------------------------------------------------------------
# * Compass Target Distance - Game_Compass
# - Returns Array of Distances between Player and Target Coordinates
# - Made into a Method because this is where Looping Map Scripts will
# become Incompatible, so one method to fix things hopefully.
# target_x : Map Target X Coordinate
# target_y : Map Target Y Coordinate
#--------------------------------------------------------------------------
def compass_target_distance(target_x, target_y)
# Distance in Real Values between Player and Target
x_dist = (target_x - $game_player.real_x) * 1.0
y_dist = (target_y - $game_player.real_y) * 1.0
# Return the X and Y Distances as an Array
return [x_dist, y_dist]
end
# If Heretic's Loop Maps is installed
if Game_Map.method_defined?(:map_loop_passable?)
#--------------------------------------------------------------------------
# * Compass Target Distance - Game_Compass (for Loop Maps)
# - Required by Trig function to determine Radian Tangent value for Angle
# - Returns Array of Distances between Player and Target Coordinates
# - Made into a Method because this is where Looping Map Scripts will
# become Incompatible, so one method to fix things hopefully.
# target_x : Map Target X Coordinate
# target_y : Map Target Y Coordinate
#--------------------------------------------------------------------------
alias loop_map_compass_target_distance compass_target_distance unless $@
def compass_target_distance(target_x, target_y)
# Get difference in target coordinates from original method
dx, dy = loop_map_compass_target_distance(target_x, target_y)
# If Map Loops Horizontal and Distance is more than Half the Map (128 / 2)
if $game_map.loop_horizontal? and dx.abs > $game_map.width * 64
# Adjust X Distance for Horizontal Looping Map
dx += (dx < 0) ? $game_map.width * 128 : -$game_map.width * 128
end
# If Map Loops Vertical and Distance is more than Half the Map (128 / 2)
if $game_map.loop_vertical? and dy.abs > $game_map.height * 64
# Adjust X Distance for Vertical Looping Map
dy += (dy < 0) ? $game_map.height * 128 : -$game_map.height * 128
end
# Return Adjusted Difference X and Y values as Array for Looping Maps
return [dx, dy]
end
end # End Optional Alias Definition
#--------------------------------------------------------------------------
# * Update (frame) - Game_Compass
# - Points the Compass at Target Location or Event
#--------------------------------------------------------------------------
def update
# If Option to keep the Compass Tone same as the Screen
if $game_system.compass_screen_tone
# Set the Tone for the Two Images if visible
back_picture.tone = $game_screen.tone if back_picture.name != ""
needle_picture.tone = $game_screen.tone if needle_picture.name != ""
end
# Shorthand
target_id = $game_system.compass_target_event_id
# If Compass is set to use an Event as a Target and Target is Valid
if target_id and $game_map.events[target_id] and
$game_map.events[target_id].valid_compass_target?
# Get the Event from the Game Map
target_event = $game_map.events[$game_system.compass_target_event_id]
# Set Target X and Y
target_x = target_event.real_x * 1.0
target_y = target_event.real_y * 1.0
# If Target Coordinates are a Map Location
elsif $game_system.compass_target_x and $game_system.compass_target_y
# Set the Target Coordintates for Real X and Y values
target_x = $game_system.compass_target_x * 128.0
target_y = $game_system.compass_target_y * 128.0
end
# If Target Coordinates for Compass
if target_x and target_y
# X and Y Distance between the Player and Target
x, y = compass_target_distance(target_x, target_y)
# Clear Angle Transitions
needle_picture.angle_target = 0
needle_picture.angle_duration = 0
# If Coordinate Match and not Rotating
if x == 0 and y == 0 and needle_picture.rotate_speed == 0
# Spin the Needle
needle_picture.rotate(needle_picture.angle > 180 ? -30 : 30)
end
# If Same X Position
if x == 0 and y != 0
# Clear repeating Rotation
needle_picture.rotate(0)
# Set Needle Picture to Up or Down
#needle_picture.angle = (target_y < $game_player.real_y ? 0 : 180)
needle_picture.angle = (y < 0 ? 0 : 180)
# If Same Y Position
elsif y == 0 and x != 0
# Clear repeating Rotation
needle_picture.rotate(0)
# Set Needle Picture to Left or Right
needle_picture.angle = (x < 0 ? 90 : 270)
# Use Trig to determine Angle of Sprite
elsif x != 0 and y != 0
# Clear repeating Rotation
needle_picture.rotate(0)
# Trig to determine Angle (-180 used to point with the top of picture)
needle_picture.angle = (Math::atan2(x,y)*180.0/Math::PI).round - 180
end
# Store the Needle Angle for Scene Changes (Menu)
@needle_angle = needle_picture.angle
# No Compass Target
elsif needle_picture.angle != 0 and needle_picture.angle_duration == 0
# Clear repeating Rotation
needle_picture.rotate(0)
# Set the Needle Angle between 0 and 360
if needle_picture.angle < 0 or needle_picture.angle > 360
while needle_picture.angle < 0 or needle_picture.angle > 360
needle_picture.angle += (needle_picture.angle < 360 ? 360 : -360)
end
needle_picture.angle %= 360
end
# Angle
a = needle_picture.angle
# Use a Transition to move the Needle to 0 at 0.5 Degrees per Frame
needle_picture.angle_target = (a > 180 ? 360.0 : 0.0)
needle_picture.angle_duration = (a > 180 ? (a - 180) * 2 : a * 2)
end
end
#--------------------------------------------------------------------------
# * Position Compass - Game_Compass
# - Positions the Compass on the Screen and centers the Compass Images
# within this Container
#--------------------------------------------------------------------------
def position_compass
# Make sure the Sprites for the Compass exist in Spriteset Map
$scene.compass_map_spriteset.add_compass
# Determine X Value as 1/2 of Larger Sprite
if back_sprite.bitmap.width > needle_sprite.bitmap.width
# Use the Centered Bitmap Width of the Background Sprite
@sprite_x = back_sprite.bitmap.width / 2
else
# Use the Centered Bitmap Width of the Needle Sprite
@sprite_x = needle_sprite.bitmap.width / 2
end
# Determine Y Value as 1/2 of Larger Sprite
if back_sprite.bitmap.height > needle_sprite.bitmap.height
# Use the Centered Bitmap Height of the Background Sprite
@sprite_y = back_sprite.bitmap.height / 2
else
# Use the Centered Bitmap Height of the Needle Sprite
@sprite_y = needle_sprite.bitmap.height / 2
end
# Position the Background Picture
back_picture.x = @x + @sprite_x
back_picture.y = @y + @sprite_y
# Position the Needle Picture
needle_picture.x = @x + @sprite_x
needle_picture.y = @y + @sprite_y
end
end
#==============================================================================
# ** Game_Player
#==============================================================================
class Game_Player < Game_Character
#--------------------------------------------------------------------------
# * Public Instance Variables - Game_Player
#--------------------------------------------------------------------------
attr_accessor :compass # Compass Object for Player
#--------------------------------------------------------------------------
# * Update - Game_Player
# - Updates the Player's Compass
#--------------------------------------------------------------------------
alias player_compass_update update unless $@
def update
# Call Original or other Aliases
player_compass_update
# If Player has a Compass
if $game_system.enable_compass and $scene.is_a?(Scene_Map)
# If the Compass Picture doesn't exist
if @compass.nil?
# Create the new Game Compass
@compass = Game_Compass.new
# Position the Compass on the Screen
@compass.position_compass
end
# Update the Compass Picture Sprites from within the Object
@compass.update
# Compass is Disabled but Compass exists
elsif @compass
# Clear the Compass ojbect
@compass = nil
end
end
end
#==============================================================================
# ** Game_Event
#==============================================================================
class Game_Event < Game_Character
#--------------------------------------------------------------------------
# * Valid Compass Target? - Game_Event
# - Valid Compass Targets should have an Active Page and are not Erased
#--------------------------------------------------------------------------
def valid_compass_target?
return (not @erased and not @page.nil?)
end
end
#==============================================================================
# ** Interpreter
#==============================================================================
class Interpreter
#--------------------------------------------------------------------------
# * Set Compass Map Target - Interpreter
# - Sets the Target of the Compass to Map Coordinates, even off map
# x : x-coordinate of Map
# y : y-coordinate of Map
#--------------------------------------------------------------------------
def set_compass_map_target(x, y)
# Pass the Arguments along to the Game System method
$game_system.set_compass_map_target(x, y)
end
#--------------------------------------------------------------------------
# * Set Compass Event Target - Interpreter
# - Sets the Target of the Compass to an Event
# target : Event or Event ID
#--------------------------------------------------------------------------
def set_compass_event_target(target)
# Pass the Arguments along to the Game System method
$game_system.set_compass_event_target(target)
end
#--------------------------------------------------------------------------
# * Clear Compass Target - Interpreter
# - Clears the Compass Target
#--------------------------------------------------------------------------
def clear_compass_target
# Call the method in Game System
$game_system.clear_compass_target
end
#--------------------------------------------------------------------------
# * Enable Compass? - Interpreter (Setter Method)
# - Returns True or False from the Game System
#--------------------------------------------------------------------------
def enable_compass?
return ($game_system.enable_compass == true)
end
#--------------------------------------------------------------------------
# * Can Point Compass? - Interpreter
# - Checks if the Compass has a Target that will cause it to Point
#--------------------------------------------------------------------------
def can_point_compass?
# Shorthand for Game System
s = $game_system
# If Compass has a Target
if (s.compass_target_x and s.compass_target_y) or
(s.compass_target_event_id and
$game_map.events[s.compass_target_event_id] and
$game_map.events[s.compass_target_event_id].valid_compass_target?)
# Compass will point at a Target
return true
end
# Default - Needed for Event Conditional Branch -> Script Evaluation
return false
end
end
#==============================================================================
# ** Scene_Load
#==============================================================================
class Scene_Load < Scene_File
#--------------------------------------------------------------------------
# * Read Save Data - Scene_Load
# file : file object for reading (opened)
# - Checks for Uninitialized Values that Crash Savegames
#--------------------------------------------------------------------------
alias compass_read_save_data read_save_data unless $@
def read_save_data(file)
# Call Original or other Aliases
compass_read_save_data(file)
# Set Game System Compass to False for later Evaluation in Script Calls
$game_system.enable_compass = false if $game_system.enable_compass.nil?
# If Game System Compass Filenames are nil
if $game_system.compass_back.nil?
# Initialize from the Constant Value
$game_system.compass_back = COMPASS_BACK_GRAPHIC
end
# If Game System Compass Filenames are nil
if $game_system.compass_needle.nil?
# Initialize from the Constant Value
$game_system.compass_needle = COMPASS_NEEDLE_GRAPHIC
end
# If Game System Compass Background Opacity is
if $game_system.compass_back_opacity.nil?
# Initialize from the Constant Value
$game_system.compass_back_opacity = COMPASS_BACK_OPACITY
end
# If Game System Compass Screen Tone value not set
if $game_system.compass_screen_tone.nil?
# Initialize from the Constant Value
$game_system.compass_screen_tone = (COMPASS_SCREEN_TONE) ? true : false
end
# If Game System Zoom is nil?
$game_system.compass_zoom = COMPASS_ZOOM if $game_system.compass_zoom.nil?
# If Game System Compass X or Y are nil?
$game_system.compass_x = COMPASS_X if $game_system.compass_x.nil?
$game_system.compass_y = COMPASS_Y if $game_system.compass_y.nil?
end
end
Instructions
This script is quite easy to use.
Once installed somewhere above main, you can mess with the Options if you'd like.
To display the Compass, run a Script $game_system.enable_compass = true
To hide the Compass, run a Script $game_system.enable_compass = false
NOTE: I ran into some issues with the game hanging because of an Interpreter Bug. You can use Zeriab's command_355 fix to take care of the issue, or put another line in your script that says "return true". The command_355 fix is really the way to go.
Now that your Compass is shown, it needs a Target to point at! Just three important script calls.
- set_compass_map_target(x, y) # Use for a Map Location (offscreen is fine)
- set_compass_event_target(event_id) # Use to point the Compass at an existing Event
- clear_compass_target() # Clears Compass Targets
There are more commands and features available, described in documentation.
Compatibility
May not be compatible with any Looping Map Scripts at this time.
Credits and Thanks
I'd like to thank the Meteor that wiped out the Dinosaurs 65 million years ago.
Without that Meteor, we wouldn't be here today and I might be all scaley and have dry skin.
Author's Notes
The point of Scripts is to make things easy for others. It is possible to create a Compass purely out of Events, however, Event solutions have drawbacks as well as they may require more work than is necessary to pull off. Just try the Demo. It's small and will show you why this script is superior.
Edit: Redacted. This script was updated to version 1.1 for compatability with my Looping Maps script.