fix: graphics menu navigation, layout, render distance cap, skin anim speed

Rewire the SWF focus chain via Iggy so VSync, Fullscreen, and Render
Distance are reachable with keyboard/gamepad navigation.

Cap render distance slider at 16 chunks. Shift graphics menu layout
up 60px for better centering.

Fix skin preview walk/attack animations running too fast with VSync
off by scaling per-frame increments by delta time relative to 60fps.
This commit is contained in:
itsRevela
2026-04-01 03:43:28 -05:00
parent 2cc03476b3
commit a017579bc3
5 changed files with 86 additions and 1 deletions

View File

@@ -74,7 +74,7 @@ UIScene_SettingsGraphicsMenu::UIScene_SettingsGraphicsMenu(int iPad, void *initD
WCHAR TempString[256];
swprintf(TempString, 256, L"Render Distance: %d",app.GetGameSettings(m_iPad,eGameSetting_RenderDistance));
m_sliderRenderDistance.init(TempString,eControl_RenderDistance,0,5,DistanceToLevel(app.GetGameSettings(m_iPad,eGameSetting_RenderDistance)));
m_sliderRenderDistance.init(TempString,eControl_RenderDistance,0,3,DistanceToLevel(app.GetGameSettings(m_iPad,eGameSetting_RenderDistance)));
swprintf( TempString, 256, L"%ls: %d%%", app.GetString( IDS_SLIDER_GAMMA ),app.GetGameSettings(m_iPad,eGameSetting_Gamma));
m_sliderGamma.init(TempString,eControl_Gamma,0,100,app.GetGameSettings(m_iPad,eGameSetting_Gamma));
@@ -93,6 +93,24 @@ UIScene_SettingsGraphicsMenu::UIScene_SettingsGraphicsMenu(int iPad, void *initD
// VSync and Exclusive Fullscreen are only available on PC
removeControl(&m_checkboxVSync, true);
removeControl(&m_checkboxExclusiveFullscreen, true);
#else
// The SWF's original focus chain skips VSync, Fullscreen, and RenderDistance
// (CustomSkinAnim -> Gamma). Rewire the navigation so all controls are reachable:
// CustomSkinAnim -> VSync -> Fullscreen -> RenderDistance -> Gamma
{
IggyName navDown = registerFastName(L"m_objNavDown");
IggyName navUp = registerFastName(L"m_objNavUp");
IggyValueSetStringUTF8RS(m_checkboxCustomSkinAnim.getIggyValuePath(), navDown, nullptr, "VSync", -1);
IggyValueSetStringUTF8RS(m_checkboxVSync.getIggyValuePath(), navUp, nullptr, "CustomSkinAnim", -1);
IggyValueSetStringUTF8RS(m_checkboxVSync.getIggyValuePath(), navDown, nullptr, "ExclusiveFullscreen", -1);
IggyValueSetStringUTF8RS(m_checkboxExclusiveFullscreen.getIggyValuePath(), navUp, nullptr, "VSync", -1);
IggyValueSetStringUTF8RS(m_checkboxExclusiveFullscreen.getIggyValuePath(), navDown, nullptr, "RenderDistance", -1);
IggyValueSetStringUTF8RS(m_sliderRenderDistance.getIggyValuePath(), navUp, nullptr, "ExclusiveFullscreen", -1);
}
#endif
const bool bInGame=(Minecraft::GetInstance()->level!=nullptr);

View File

@@ -14,6 +14,12 @@ This project is based on source code of Minecraft Legacy Console Edition v1.6.05
## Latest:
### Graphics Settings Menu Fixes
- Fixed keyboard/gamepad navigation skipping VSync, Fullscreen, and Render Distance options. The SWF focus chain only linked the original console controls; added C++ post-init rewiring of `m_objNavDown`/`m_objNavUp` via Iggy so all controls are reachable
- Shifted the graphics menu layout up by 60 pixels for better vertical centering
- Fixed skin preview walking and attack animations running too fast with VSync off. The per-frame animation increments now scale by delta time relative to a 60fps baseline
### Async Autosave (Dedicated Server)
- Autosave no longer freezes the server. Previously, every autosave compressed the entire world save file with zlib synchronously on the main thread, blocking all game ticks for 2-6 seconds depending on world size

61
tools/ShiftMenuY.java Normal file
View File

@@ -0,0 +1,61 @@
import com.jpexs.decompiler.flash.SWF;
import com.jpexs.decompiler.flash.tags.Tag;
import com.jpexs.decompiler.flash.tags.base.PlaceObjectTypeTag;
import com.jpexs.decompiler.flash.types.MATRIX;
import java.io.*;
/**
* Shifts a named PlaceObject element's Y position in a SWF.
* Usage: ShiftMenuY <input.swf> <output.swf> <element_name> <y_offset_pixels>
*
* Positive offset = move down, negative = move up.
* SWF uses twips (1 pixel = 20 twips).
*/
public class ShiftMenuY {
public static void main(String[] args) throws Exception {
if (args.length < 3) {
System.out.println("Usage: ShiftMenuY <input.swf> <output.swf> <y_offset_pixels> [element_name]");
System.out.println(" Shifts all elements (or a named element) by the given pixel offset.");
System.out.println(" Negative values move up, positive move down.");
return;
}
String inputPath = args[0];
String outputPath = args[1];
int offsetPixels = Integer.parseInt(args[2]);
String targetName = args.length > 3 ? args[3] : null;
int offsetTwips = offsetPixels * 20;
SWF swf = new SWF(new FileInputStream(inputPath), false);
int modified = 0;
for (Tag tag : swf.getTags()) {
if (tag instanceof PlaceObjectTypeTag) {
PlaceObjectTypeTag po = (PlaceObjectTypeTag) tag;
String name = po.getInstanceName();
if (targetName != null && !targetName.equals(name)) continue;
MATRIX matrix = po.getMatrix();
if (matrix != null) {
int oldY = matrix.translateY;
matrix.translateY += offsetTwips;
System.out.printf(" %s: Y %d -> %d twips (%+d px)%n",
name != null ? name : "(unnamed)",
oldY, matrix.translateY, offsetPixels);
po.setModified(true);
modified++;
}
}
}
if (modified == 0) {
System.out.println("No elements modified.");
return;
}
System.out.printf("Modified %d element(s) by %+d pixels%n", modified, offsetPixels);
try (FileOutputStream fos = new FileOutputStream(outputPath)) {
swf.saveTo(fos);
}
System.out.println("Saved: " + outputPath);
}
}