Minimap with destinations
This commit is contained in:
parent
4477ef7fbe
commit
c47f823c83
1 changed files with 506 additions and 25 deletions
|
|
@ -3,7 +3,7 @@
|
|||
//=============================================================================
|
||||
|
||||
/*:
|
||||
* @plugindesc Adds a minimap/zoom-out feature. Press M to toggle a zoomed-out view of the entire map.
|
||||
* @plugindesc Adds a minimap/zoom-out feature with exit labels, zoom and pan controls.
|
||||
* @author Dazed Translations
|
||||
*
|
||||
* @param Toggle Key
|
||||
|
|
@ -14,7 +14,17 @@
|
|||
* Press the M key while on the map to toggle a zoomed-out minimap view.
|
||||
* Shows the entire map scaled to fit the screen.
|
||||
* Character sprites are hidden, and a marker shows your position.
|
||||
* Press M again to return to normal view.
|
||||
*
|
||||
* Controls:
|
||||
* - M: Close minimap
|
||||
* - Mouse Wheel / Shift / Ctrl: Zoom in/out
|
||||
* - Arrow Keys / WASD / Mouse Drag: Pan the map
|
||||
* - R: Reset zoom and pan
|
||||
*
|
||||
* Features:
|
||||
* - Exit locations are numbered and show destination names in a legend
|
||||
* - Nearby exits to the same location are grouped together
|
||||
* - Zoom and pan for easier viewing of large maps
|
||||
*/
|
||||
|
||||
(function() {
|
||||
|
|
@ -28,6 +38,25 @@
|
|||
// Track minimap state
|
||||
let minimapActive = false;
|
||||
|
||||
// Zoom and pan state
|
||||
let minimapZoom = 1.0;
|
||||
let minimapPanX = 0;
|
||||
let minimapPanY = 0;
|
||||
const MIN_ZOOM = 0.5;
|
||||
const MAX_ZOOM = 3.0;
|
||||
const ZOOM_STEP = 0.1;
|
||||
const PAN_SPEED = 15;
|
||||
|
||||
// Mouse drag state
|
||||
let isDragging = false;
|
||||
let dragStartX = 0;
|
||||
let dragStartY = 0;
|
||||
let dragStartPanX = 0;
|
||||
let dragStartPanY = 0;
|
||||
|
||||
// Exit location data
|
||||
let exitLocations = [];
|
||||
|
||||
// Export minimap state for other plugins/systems to check
|
||||
window.isMinimapActive = function() {
|
||||
return minimapActive;
|
||||
|
|
@ -43,10 +72,17 @@
|
|||
};
|
||||
|
||||
//=========================================================================
|
||||
// Input - Add minimap key
|
||||
// Input - Add minimap key and zoom/pan keys
|
||||
//=========================================================================
|
||||
|
||||
Input.keyMapper[toggleKeyCode] = 'minimap';
|
||||
Input.keyMapper[82] = 'minimapReset'; // R key
|
||||
Input.keyMapper[16] = 'minimapZoomIn'; // Shift key
|
||||
Input.keyMapper[17] = 'minimapZoomOut'; // Ctrl key
|
||||
Input.keyMapper[87] = 'minimapUp'; // W key
|
||||
Input.keyMapper[65] = 'minimapLeft'; // A key
|
||||
Input.keyMapper[83] = 'minimapDown'; // S key
|
||||
Input.keyMapper[68] = 'minimapRight'; // D key
|
||||
|
||||
//=========================================================================
|
||||
// Auto-close minimap when any event starts
|
||||
|
|
@ -91,6 +127,9 @@
|
|||
|
||||
// Update player marker position and atmospheric effects if minimap is active
|
||||
if (minimapActive) {
|
||||
// Handle zoom and pan controls
|
||||
this.updateMinimapZoomPan();
|
||||
|
||||
if (this._minimapPlayerMarker) {
|
||||
this.updateMinimapPlayerMarker();
|
||||
}
|
||||
|
|
@ -98,6 +137,237 @@
|
|||
}
|
||||
};
|
||||
|
||||
Scene_Map.prototype.collectExitLocations = function() {
|
||||
exitLocations = [];
|
||||
const rawExits = [];
|
||||
|
||||
// Collect all transfer events
|
||||
for (const event of $gameMap.events()) {
|
||||
if (!event) continue;
|
||||
|
||||
const eventData = event.event();
|
||||
if (!eventData) continue;
|
||||
|
||||
// Check all pages for Transfer Player command
|
||||
for (const page of eventData.pages) {
|
||||
if (!page || !page.list) continue;
|
||||
|
||||
for (const cmd of page.list) {
|
||||
if (cmd.code === 201) { // Transfer Player command
|
||||
const params = cmd.parameters;
|
||||
if (params[0] === 0) { // Direct designation (not variable)
|
||||
const targetMapId = params[1];
|
||||
const mapName = this.getMapName(targetMapId);
|
||||
|
||||
rawExits.push({
|
||||
x: event.x,
|
||||
y: event.y,
|
||||
mapId: targetMapId,
|
||||
mapName: mapName
|
||||
});
|
||||
}
|
||||
break; // Only need first transfer per page
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
// Group nearby exits going to the same destination
|
||||
const GROUPING_DISTANCE = 3; // Tiles within this distance get grouped
|
||||
const grouped = [];
|
||||
const used = new Set();
|
||||
|
||||
for (let i = 0; i < rawExits.length; i++) {
|
||||
if (used.has(i)) continue;
|
||||
|
||||
const exit = rawExits[i];
|
||||
const group = {
|
||||
positions: [{x: exit.x, y: exit.y}],
|
||||
mapId: exit.mapId,
|
||||
mapName: exit.mapName
|
||||
};
|
||||
used.add(i);
|
||||
|
||||
// Find nearby exits to same destination
|
||||
for (let j = i + 1; j < rawExits.length; j++) {
|
||||
if (used.has(j)) continue;
|
||||
const other = rawExits[j];
|
||||
|
||||
if (other.mapId === exit.mapId) {
|
||||
// Check if any position in group is close enough
|
||||
let isNearby = false;
|
||||
for (const pos of group.positions) {
|
||||
const dx = Math.abs(other.x - pos.x);
|
||||
const dy = Math.abs(other.y - pos.y);
|
||||
if (dx <= GROUPING_DISTANCE && dy <= GROUPING_DISTANCE) {
|
||||
isNearby = true;
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
if (isNearby) {
|
||||
group.positions.push({x: other.x, y: other.y});
|
||||
used.add(j);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
// Calculate center position for the group
|
||||
let sumX = 0, sumY = 0;
|
||||
for (const pos of group.positions) {
|
||||
sumX += pos.x;
|
||||
sumY += pos.y;
|
||||
}
|
||||
group.centerX = sumX / group.positions.length;
|
||||
group.centerY = sumY / group.positions.length;
|
||||
|
||||
grouped.push(group);
|
||||
}
|
||||
|
||||
// Assign numbers to grouped exits
|
||||
let exitNumber = 1;
|
||||
for (const group of grouped) {
|
||||
group.number = exitNumber++;
|
||||
exitLocations.push(group);
|
||||
}
|
||||
};
|
||||
|
||||
Scene_Map.prototype.getMapName = function(mapId) {
|
||||
// Try to get map name from $dataMapInfos
|
||||
if ($dataMapInfos && $dataMapInfos[mapId]) {
|
||||
return $dataMapInfos[mapId].name || 'Unknown';
|
||||
}
|
||||
return 'Map ' + mapId;
|
||||
};
|
||||
|
||||
Scene_Map.prototype.updateMinimapZoomPan = function() {
|
||||
let zoomChanged = false;
|
||||
let panChanged = false;
|
||||
|
||||
// Zoom controls
|
||||
if (Input.isTriggered('minimapZoomIn') || Input.isRepeated('minimapZoomIn')) {
|
||||
minimapZoom = Math.min(MAX_ZOOM, minimapZoom + ZOOM_STEP);
|
||||
zoomChanged = true;
|
||||
}
|
||||
if (Input.isTriggered('minimapZoomOut') || Input.isRepeated('minimapZoomOut')) {
|
||||
minimapZoom = Math.max(MIN_ZOOM, minimapZoom - ZOOM_STEP);
|
||||
zoomChanged = true;
|
||||
}
|
||||
|
||||
// Pan controls (arrow keys and WASD)
|
||||
if (Input.isPressed('up') || Input.isPressed('minimapUp')) {
|
||||
minimapPanY += PAN_SPEED;
|
||||
panChanged = true;
|
||||
}
|
||||
if (Input.isPressed('down') || Input.isPressed('minimapDown')) {
|
||||
minimapPanY -= PAN_SPEED;
|
||||
panChanged = true;
|
||||
}
|
||||
if (Input.isPressed('left') || Input.isPressed('minimapLeft')) {
|
||||
minimapPanX += PAN_SPEED;
|
||||
panChanged = true;
|
||||
}
|
||||
if (Input.isPressed('right') || Input.isPressed('minimapRight')) {
|
||||
minimapPanX -= PAN_SPEED;
|
||||
panChanged = true;
|
||||
}
|
||||
|
||||
// Reset controls
|
||||
if (Input.isTriggered('minimapReset')) {
|
||||
minimapZoom = 1.0;
|
||||
minimapPanX = 0;
|
||||
minimapPanY = 0;
|
||||
zoomChanged = true;
|
||||
panChanged = true;
|
||||
SoundManager.playCursor();
|
||||
}
|
||||
|
||||
// Mouse wheel zoom
|
||||
if (this._minimapContent) {
|
||||
const wheelY = TouchInput.wheelY;
|
||||
if (wheelY !== 0) {
|
||||
if (wheelY < 0) {
|
||||
minimapZoom = Math.min(MAX_ZOOM, minimapZoom + ZOOM_STEP);
|
||||
} else {
|
||||
minimapZoom = Math.max(MIN_ZOOM, minimapZoom - ZOOM_STEP);
|
||||
}
|
||||
zoomChanged = true;
|
||||
}
|
||||
}
|
||||
|
||||
// Mouse drag pan
|
||||
if (TouchInput.isPressed()) {
|
||||
if (!isDragging) {
|
||||
isDragging = true;
|
||||
dragStartX = TouchInput.x;
|
||||
dragStartY = TouchInput.y;
|
||||
dragStartPanX = minimapPanX;
|
||||
dragStartPanY = minimapPanY;
|
||||
} else {
|
||||
minimapPanX = dragStartPanX + (TouchInput.x - dragStartX);
|
||||
minimapPanY = dragStartPanY + (TouchInput.y - dragStartY);
|
||||
panChanged = true;
|
||||
}
|
||||
} else {
|
||||
isDragging = false;
|
||||
}
|
||||
|
||||
// Apply zoom and pan to content
|
||||
if ((zoomChanged || panChanged) && this._minimapContent) {
|
||||
this.applyMinimapTransform();
|
||||
}
|
||||
};
|
||||
|
||||
Scene_Map.prototype.applyMinimapTransform = function() {
|
||||
if (!this._minimapContent) return;
|
||||
|
||||
// Calculate the center point for zooming
|
||||
const centerX = Graphics.width / 2;
|
||||
const centerY = Graphics.height / 2;
|
||||
|
||||
// Apply scale
|
||||
this._minimapContent.scale.x = this._minimapScale * minimapZoom;
|
||||
this._minimapContent.scale.y = this._minimapScale * minimapZoom;
|
||||
|
||||
// Calculate new offset to keep centered
|
||||
const mapWidth = $gameMap.width() * this._minimapTileWidth;
|
||||
const mapHeight = $gameMap.height() * this._minimapTileHeight;
|
||||
const scaledWidth = mapWidth * this._minimapScale * minimapZoom;
|
||||
const scaledHeight = mapHeight * this._minimapScale * minimapZoom;
|
||||
|
||||
const baseOffsetX = (Graphics.width - scaledWidth) / 2;
|
||||
const baseOffsetY = (Graphics.height - scaledHeight) / 2;
|
||||
|
||||
this._minimapContent.x = baseOffsetX + minimapPanX;
|
||||
this._minimapContent.y = baseOffsetY + minimapPanY;
|
||||
|
||||
// Update border to match content
|
||||
if (this._minimapBorder) {
|
||||
this._minimapBorder.scale.x = this._minimapScale * minimapZoom;
|
||||
this._minimapBorder.scale.y = this._minimapScale * minimapZoom;
|
||||
this._minimapBorder.x = baseOffsetX + minimapPanX - this._borderPadding * this._minimapScale * minimapZoom;
|
||||
this._minimapBorder.y = baseOffsetY + minimapPanY - this._borderPadding * this._minimapScale * minimapZoom;
|
||||
}
|
||||
|
||||
// Update exit destinations panel to stay next to map
|
||||
if (this._exitDestinationsPanel) {
|
||||
this._exitDestinationsPanel.scale.x = minimapZoom;
|
||||
this._exitDestinationsPanel.scale.y = minimapZoom;
|
||||
this._exitDestinationsPanel.x = baseOffsetX + minimapPanX + scaledWidth + this._exitPanelOffset * minimapZoom;
|
||||
this._exitDestinationsPanel.y = baseOffsetY + minimapPanY;
|
||||
}
|
||||
|
||||
// Store current offsets for marker positioning
|
||||
this._currentOffsetX = this._minimapContent.x;
|
||||
this._currentOffsetY = this._minimapContent.y;
|
||||
this._currentScale = this._minimapScale * minimapZoom;
|
||||
|
||||
// Update exit markers positions
|
||||
if (this._exitMarkers) {
|
||||
this.updateExitMarkerPositions();
|
||||
}
|
||||
};
|
||||
|
||||
Scene_Map.prototype.updateMinimapAtmosphere = function() {
|
||||
// Subtle flicker effect on the map content to simulate candlelight
|
||||
if (this._minimapContent) {
|
||||
|
|
@ -122,6 +392,15 @@
|
|||
Scene_Map.prototype.showMinimap = function() {
|
||||
if (!this._spriteset) return;
|
||||
|
||||
// Reset zoom and pan when opening
|
||||
minimapZoom = 1.0;
|
||||
minimapPanX = 0;
|
||||
minimapPanY = 0;
|
||||
isDragging = false;
|
||||
|
||||
// Collect exit location data
|
||||
this.collectExitLocations();
|
||||
|
||||
// Hide the normal spriteset
|
||||
this._spriteset.visible = false;
|
||||
|
||||
|
|
@ -191,8 +470,8 @@
|
|||
// Render the tilemap to a bitmap
|
||||
this.renderMinimapTiles();
|
||||
|
||||
// Draw ornate border around map
|
||||
this.drawOrnateBorder(offsetX, offsetY, scaledWidth, scaledHeight);
|
||||
// Create border as separate sprite that moves with content
|
||||
this.createMinimapBorder(mapPixelWidth, mapPixelHeight);
|
||||
|
||||
// Add title text with gothic styling
|
||||
this._minimapOverlay.bitmap.fontFace = 'GameFont';
|
||||
|
|
@ -211,16 +490,29 @@
|
|||
// Smaller instruction text
|
||||
this._minimapOverlay.bitmap.fontSize = 14;
|
||||
this._minimapOverlay.bitmap.textColor = '#8b7355';
|
||||
this._minimapOverlay.bitmap.drawText('Press M to close', 0, Graphics.height - 18, Graphics.width, 20, 'center');
|
||||
this._minimapOverlay.bitmap.drawText('M: Close | Arrows/WASD: Pan | Shift/Ctrl/Scroll: Zoom | R: Reset', 0, Graphics.height - 18, Graphics.width, 20, 'center');
|
||||
|
||||
// Draw legend
|
||||
this.drawMinimapLegend();
|
||||
|
||||
this.addChild(this._minimapOverlay);
|
||||
this.addChild(this._minimapBorder);
|
||||
this.addChild(this._minimapContent);
|
||||
|
||||
// Create exit destinations panel (moves with map)
|
||||
this.createExitDestinationsPanel(mapPixelWidth, mapPixelHeight);
|
||||
|
||||
// Create exit markers (as separate sprites for positioning with zoom/pan)
|
||||
this.createExitMarkers();
|
||||
|
||||
// Create player marker
|
||||
this.createMinimapPlayerMarker();
|
||||
|
||||
// Initialize current transform values and position all elements correctly
|
||||
this._currentOffsetX = offsetX;
|
||||
this._currentOffsetY = offsetY;
|
||||
this._currentScale = scale;
|
||||
this.applyMinimapTransform();
|
||||
};
|
||||
|
||||
Scene_Map.prototype.drawAtmosphericBackground = function() {
|
||||
|
|
@ -252,9 +544,21 @@
|
|||
ctx.fillRect(0, 0, w, h);
|
||||
};
|
||||
|
||||
Scene_Map.prototype.drawOrnateBorder = function(x, y, width, height) {
|
||||
const ctx = this._minimapOverlay.bitmap.context;
|
||||
Scene_Map.prototype.createMinimapBorder = function(mapPixelWidth, mapPixelHeight) {
|
||||
const borderSize = 6;
|
||||
const padding = 20; // Extra padding for the border sprite
|
||||
|
||||
// Create border sprite sized to fit around the map
|
||||
this._minimapBorder = new Sprite();
|
||||
const borderWidth = mapPixelWidth + padding * 2;
|
||||
const borderHeight = mapPixelHeight + padding * 2;
|
||||
this._minimapBorder.bitmap = new Bitmap(borderWidth, borderHeight);
|
||||
|
||||
const ctx = this._minimapBorder.bitmap.context;
|
||||
const x = padding;
|
||||
const y = padding;
|
||||
const width = mapPixelWidth;
|
||||
const height = mapPixelHeight;
|
||||
|
||||
// Outer dark border
|
||||
ctx.strokeStyle = '#0d0805';
|
||||
|
|
@ -310,6 +614,20 @@
|
|||
ctx.beginPath();
|
||||
ctx.arc(x + width, y + height, innerDot/2, 0, Math.PI * 2);
|
||||
ctx.fill();
|
||||
|
||||
// Store the padding offset for positioning
|
||||
this._borderPadding = padding;
|
||||
|
||||
// Position and scale to match content
|
||||
this._minimapBorder.x = this._minimapOffsetX - padding * this._minimapScale;
|
||||
this._minimapBorder.y = this._minimapOffsetY - padding * this._minimapScale;
|
||||
this._minimapBorder.scale.x = this._minimapScale;
|
||||
this._minimapBorder.scale.y = this._minimapScale;
|
||||
};
|
||||
|
||||
// Keep old function for compatibility but it does nothing now
|
||||
Scene_Map.prototype.drawOrnateBorder = function(x, y, width, height) {
|
||||
// Border is now drawn as a separate sprite in createMinimapBorder
|
||||
};
|
||||
|
||||
Scene_Map.prototype.drawMinimapLegend = function() {
|
||||
|
|
@ -377,6 +695,159 @@
|
|||
bitmap.drawText('Passage', legendX + dotSize + 10, legendY + lineHeight * 4 + 5, 150, 18, 'left');
|
||||
};
|
||||
|
||||
Scene_Map.prototype.createExitDestinationsPanel = function(mapPixelWidth, mapPixelHeight) {
|
||||
if (exitLocations.length === 0) return;
|
||||
|
||||
const lineHeight = 20;
|
||||
const padding = 15;
|
||||
const panelWidth = 280;
|
||||
const panelHeight = 35 + exitLocations.length * lineHeight + padding;
|
||||
|
||||
// Create panel sprite
|
||||
this._exitDestinationsPanel = new Sprite();
|
||||
this._exitDestinationsPanel.bitmap = new Bitmap(panelWidth, panelHeight);
|
||||
|
||||
const bitmap = this._exitDestinationsPanel.bitmap;
|
||||
const ctx = bitmap.context;
|
||||
|
||||
// Draw background panel
|
||||
ctx.fillStyle = 'rgba(26, 20, 16, 0.9)';
|
||||
ctx.fillRect(0, 0, panelWidth, panelHeight);
|
||||
ctx.strokeStyle = '#8b7355';
|
||||
ctx.lineWidth = 2;
|
||||
ctx.strokeRect(0, 0, panelWidth, panelHeight);
|
||||
|
||||
// Inner border
|
||||
ctx.strokeStyle = '#c9a959';
|
||||
ctx.lineWidth = 1;
|
||||
ctx.strokeRect(3, 3, panelWidth - 6, panelHeight - 6);
|
||||
|
||||
bitmap.fontFace = 'GameFont';
|
||||
bitmap.fontSize = 14;
|
||||
bitmap.textColor = '#d4af37';
|
||||
bitmap.outlineColor = '#1a0a00';
|
||||
bitmap.outlineWidth = 3;
|
||||
|
||||
// Title
|
||||
const titleY = 8;
|
||||
bitmap.drawText('~ Destinations ~', 0, titleY, panelWidth, 18, 'center');
|
||||
|
||||
// Underline
|
||||
ctx.strokeStyle = '#8b7355';
|
||||
ctx.lineWidth = 1;
|
||||
ctx.beginPath();
|
||||
ctx.moveTo(padding, titleY + 22);
|
||||
ctx.lineTo(panelWidth - padding, titleY + 22);
|
||||
ctx.stroke();
|
||||
|
||||
bitmap.fontSize = 12;
|
||||
bitmap.textColor = '#c9a959';
|
||||
|
||||
// Draw each exit destination (no limit now)
|
||||
for (let i = 0; i < exitLocations.length; i++) {
|
||||
const exit = exitLocations[i];
|
||||
const y = 32 + i * lineHeight;
|
||||
|
||||
// Draw number circle
|
||||
const circleX = padding + 10;
|
||||
const circleY = y + 9;
|
||||
ctx.fillStyle = '#7cfc00';
|
||||
ctx.shadowColor = '#7cfc00';
|
||||
ctx.shadowBlur = 3;
|
||||
ctx.beginPath();
|
||||
ctx.arc(circleX, circleY, 8, 0, Math.PI * 2);
|
||||
ctx.fill();
|
||||
ctx.shadowBlur = 0;
|
||||
ctx.strokeStyle = '#2a4a00';
|
||||
ctx.lineWidth = 1;
|
||||
ctx.stroke();
|
||||
|
||||
// Draw number
|
||||
ctx.fillStyle = '#1a0a00';
|
||||
ctx.font = 'bold 10px GameFont';
|
||||
ctx.textAlign = 'center';
|
||||
ctx.textBaseline = 'middle';
|
||||
ctx.fillText(exit.number.toString(), circleX, circleY);
|
||||
ctx.textAlign = 'left';
|
||||
|
||||
// Draw destination name (full name, no truncation)
|
||||
bitmap.drawText(exit.mapName, padding + 25, y, panelWidth - padding - 30, 18, 'left');
|
||||
}
|
||||
|
||||
// Position panel to the right of the map
|
||||
this._exitPanelOffset = 20; // Gap between map and panel
|
||||
this._exitDestinationsPanel.x = this._minimapOffsetX + mapPixelWidth * this._minimapScale + this._exitPanelOffset;
|
||||
this._exitDestinationsPanel.y = this._minimapOffsetY;
|
||||
|
||||
this.addChild(this._exitDestinationsPanel);
|
||||
};
|
||||
|
||||
// Keep old function for compatibility but redirect to new one
|
||||
Scene_Map.prototype.drawExitLegend = function() {
|
||||
// Now handled by createExitDestinationsPanel
|
||||
};
|
||||
|
||||
Scene_Map.prototype.createExitMarkers = function() {
|
||||
this._exitMarkers = [];
|
||||
|
||||
for (const exit of exitLocations) {
|
||||
const marker = new Sprite();
|
||||
marker.bitmap = new Bitmap(24, 24);
|
||||
|
||||
const ctx = marker.bitmap.context;
|
||||
const cx = 12, cy = 12;
|
||||
|
||||
// Draw green circle
|
||||
ctx.fillStyle = '#7cfc00';
|
||||
ctx.shadowColor = '#7cfc00';
|
||||
ctx.shadowBlur = 4;
|
||||
ctx.beginPath();
|
||||
ctx.arc(cx, cy, 10, 0, Math.PI * 2);
|
||||
ctx.fill();
|
||||
ctx.shadowBlur = 0;
|
||||
ctx.strokeStyle = '#2a4a00';
|
||||
ctx.lineWidth = 2;
|
||||
ctx.stroke();
|
||||
|
||||
// Draw number
|
||||
ctx.fillStyle = '#1a0a00';
|
||||
ctx.font = 'bold 12px GameFont';
|
||||
ctx.textAlign = 'center';
|
||||
ctx.textBaseline = 'middle';
|
||||
ctx.fillText(exit.number.toString(), cx, cy);
|
||||
|
||||
marker.anchor.x = 0.5;
|
||||
marker.anchor.y = 0.5;
|
||||
|
||||
// Store exit data on marker for positioning
|
||||
marker._exitData = exit;
|
||||
|
||||
this._exitMarkers.push(marker);
|
||||
this.addChild(marker);
|
||||
}
|
||||
|
||||
this.updateExitMarkerPositions();
|
||||
};
|
||||
|
||||
Scene_Map.prototype.updateExitMarkerPositions = function() {
|
||||
if (!this._exitMarkers) return;
|
||||
|
||||
const offsetX = this._currentOffsetX || this._minimapOffsetX;
|
||||
const offsetY = this._currentOffsetY || this._minimapOffsetY;
|
||||
const scale = this._currentScale || this._minimapScale;
|
||||
|
||||
for (const marker of this._exitMarkers) {
|
||||
const exit = marker._exitData;
|
||||
const markerX = offsetX + (exit.centerX + 0.5) * this._minimapTileWidth * scale;
|
||||
const markerY = offsetY + (exit.centerY + 0.5) * this._minimapTileHeight * scale;
|
||||
|
||||
marker.x = markerX;
|
||||
marker.y = markerY;
|
||||
marker.scale.x = Math.max(0.5, minimapZoom * 0.8);
|
||||
marker.scale.y = Math.max(0.5, minimapZoom * 0.8);
|
||||
}
|
||||
};
|
||||
|
||||
Scene_Map.prototype.renderMinimapTiles = function() {
|
||||
const mapWidth = $gameMap.width();
|
||||
const mapHeight = $gameMap.height();
|
||||
|
|
@ -520,7 +991,7 @@
|
|||
}
|
||||
}
|
||||
|
||||
// Draw important events as markers
|
||||
// Draw important events as markers (except transfers - those are drawn as numbered markers separately)
|
||||
for (const event of $gameMap.events()) {
|
||||
if (!event) continue;
|
||||
|
||||
|
|
@ -543,17 +1014,7 @@
|
|||
ctx.lineWidth = 2;
|
||||
ctx.stroke();
|
||||
} else if (this.isMapTransfer(event)) {
|
||||
// Draw exit/entrance marker (eerie green glow)
|
||||
ctx.fillStyle = '#7cfc00';
|
||||
ctx.shadowColor = '#7cfc00';
|
||||
ctx.shadowBlur = 6;
|
||||
ctx.beginPath();
|
||||
ctx.arc(ex, ey, markerSize, 0, Math.PI * 2);
|
||||
ctx.fill();
|
||||
ctx.shadowBlur = 0;
|
||||
ctx.strokeStyle = '#2a4a00';
|
||||
ctx.lineWidth = 2;
|
||||
ctx.stroke();
|
||||
// Skip - transfers are drawn as numbered markers by createExitMarkers()
|
||||
} else if (this.isImportantEvent(event)) {
|
||||
// Draw NPC marker (warm gold)
|
||||
ctx.fillStyle = '#daa520';
|
||||
|
|
@ -828,17 +1289,23 @@
|
|||
const playerX = $gamePlayer.x;
|
||||
const playerY = $gamePlayer.y;
|
||||
|
||||
// Use current transform offsets for zoom/pan support
|
||||
const offsetX = this._currentOffsetX || this._minimapOffsetX;
|
||||
const offsetY = this._currentOffsetY || this._minimapOffsetY;
|
||||
const scale = this._currentScale || this._minimapScale;
|
||||
|
||||
// Calculate marker position
|
||||
const markerX = this._minimapOffsetX + (playerX + 0.5) * this._minimapTileWidth * this._minimapScale;
|
||||
const markerY = this._minimapOffsetY + (playerY + 0.5) * this._minimapTileHeight * this._minimapScale;
|
||||
const markerX = offsetX + (playerX + 0.5) * this._minimapTileWidth * scale;
|
||||
const markerY = offsetY + (playerY + 0.5) * this._minimapTileHeight * scale;
|
||||
|
||||
this._minimapPlayerMarker.x = markerX;
|
||||
this._minimapPlayerMarker.y = markerY;
|
||||
|
||||
// Pulse effect
|
||||
// Pulse effect with zoom scaling
|
||||
const pulse = Math.sin(Graphics.frameCount * 0.1) * 0.2 + 1;
|
||||
this._minimapPlayerMarker.scale.x = pulse;
|
||||
this._minimapPlayerMarker.scale.y = pulse;
|
||||
const zoomScale = Math.max(0.5, minimapZoom * 0.8);
|
||||
this._minimapPlayerMarker.scale.x = pulse * zoomScale;
|
||||
this._minimapPlayerMarker.scale.y = pulse * zoomScale;
|
||||
};
|
||||
|
||||
Scene_Map.prototype.removeMinimapOverlay = function() {
|
||||
|
|
@ -846,6 +1313,10 @@
|
|||
this.removeChild(this._minimapOverlay);
|
||||
this._minimapOverlay = null;
|
||||
}
|
||||
if (this._minimapBorder) {
|
||||
this.removeChild(this._minimapBorder);
|
||||
this._minimapBorder = null;
|
||||
}
|
||||
if (this._minimapContent) {
|
||||
this.removeChild(this._minimapContent);
|
||||
this._minimapContent = null;
|
||||
|
|
@ -854,6 +1325,16 @@
|
|||
this.removeChild(this._minimapPlayerMarker);
|
||||
this._minimapPlayerMarker = null;
|
||||
}
|
||||
if (this._exitMarkers) {
|
||||
for (const marker of this._exitMarkers) {
|
||||
this.removeChild(marker);
|
||||
}
|
||||
this._exitMarkers = null;
|
||||
}
|
||||
if (this._exitDestinationsPanel) {
|
||||
this.removeChild(this._exitDestinationsPanel);
|
||||
this._exitDestinationsPanel = null;
|
||||
}
|
||||
};
|
||||
|
||||
//=========================================================================
|
||||
|
|
|
|||
Loading…
Reference in a new issue