From 8ca77a1b73612ae293fcc6c4a967a99f0a600897 Mon Sep 17 00:00:00 2001 From: Duy Tran Khanh Date: Mon, 31 Oct 2022 11:13:03 +0700 Subject: [PATCH] Support resizable for iPadOS Stage Manager On iPadOS, PojavLauncher can be launched in portrait mode Declare controller support in Info.plist Sync LWJGL changes from Android repo --- .../src/main/java/org/lwjgl/glfw/GLFW.java | 4 +- .../main/java/org/lwjgl/opengl/Display.java | 21 ++-- .../src/main/java/org/lwjgl/opengl/Sync.java | 61 +++++++----- Natives/AboutLauncherViewController.m | 95 +++++++------------ Natives/CustomControlsViewController.m | 26 ++++- Natives/Info.plist | 15 ++- Natives/JavaGUIViewController.m | 32 ++++++- Natives/JavaLauncher.m | 1 + Natives/LauncherFAQViewController.m | 73 ++++++-------- Natives/LauncherPreferencesViewController2.m | 7 +- Natives/LoginViewController.m | 27 +++--- Natives/SurfaceViewController+LogView.m | 25 +++-- Natives/SurfaceViewController+Navigation.m | 28 +++--- Natives/SurfaceViewController.h | 8 ++ Natives/SurfaceViewController.m | 64 +++++++++++-- Natives/input_bridge_v3.m | 3 +- Natives/main_hook.m | 3 - 17 files changed, 295 insertions(+), 198 deletions(-) diff --git a/JavaApp/src/main/java/org/lwjgl/glfw/GLFW.java b/JavaApp/src/main/java/org/lwjgl/glfw/GLFW.java index 32f760b9..b3a8a7c3 100644 --- a/JavaApp/src/main/java/org/lwjgl/glfw/GLFW.java +++ b/JavaApp/src/main/java/org/lwjgl/glfw/GLFW.java @@ -998,6 +998,7 @@ public class GLFW public static void glfwSetWindowSize(long window, int width, int height) { try { + internalChangeMonitorSize(width, height); internalGetWindow(window).width = width; internalGetWindow(window).height = height; System.out.println("GLFW: Set size for window " + window + ", width=" + width + ", height=" + height); @@ -1090,8 +1091,7 @@ public class GLFW break; case CallbackBridge.EVENT_TYPE_FRAMEBUFFER_SIZE: case CallbackBridge.EVENT_TYPE_WINDOW_SIZE: - internalChangeMonitorSize((int)dataArr[1], (int)dataArr[2]); - glfwSetWindowSize(ptr, Tools.mGLFWWindowWidth, Tools.mGLFWWindowHeight); + glfwSetWindowSize(ptr, (int)dataArr[1], (int)dataArr[2]); if ((int)dataArr[0] == CallbackBridge.EVENT_TYPE_FRAMEBUFFER_SIZE && mGLFWFramebufferSizeCallback != null) { mGLFWFramebufferSizeCallback.invoke(ptr, Tools.mGLFWWindowWidth, Tools.mGLFWWindowHeight); } else if ((int)dataArr[0] == CallbackBridge.EVENT_TYPE_WINDOW_SIZE && mGLFWWindowSizeCallback != null) { diff --git a/JavaApp/src/main/java/org/lwjgl/opengl/Display.java b/JavaApp/src/main/java/org/lwjgl/opengl/Display.java index b761cd78..16d95640 100644 --- a/JavaApp/src/main/java/org/lwjgl/opengl/Display.java +++ b/JavaApp/src/main/java/org/lwjgl/opengl/Display.java @@ -82,12 +82,6 @@ public class Display { mode = desktopDisplayMode = new DisplayMode(monitorWidth, monitorHeight, monitorBitPerPixel, monitorRefreshRate); LWJGLUtil.log("Initial mode: " + desktopDisplayMode); - - // additional code workaround not called yet! - LWJGLUtil.log("Calling Display.create()"); - try { - create(); - } catch (LWJGLException e) {throw new RuntimeException(e);} } public static void setSwapInterval(int value) { @@ -342,6 +336,7 @@ public class Display { latestWidth = width; latestHeight = height; + //System.out.println("Window size callback"); if(parent != null) parent.setSize(width, height); } }; @@ -419,7 +414,7 @@ public class Display { Display.drawable = drawable; context = org.lwjgl.opengl.GLContext.createFromCurrent(); - glfwSwapInterval(0); + //glfwSwapInterval(0); glfwShowWindow(Window.handle); Mouse.create(); @@ -767,6 +762,7 @@ public class Display { public static void setVSyncEnabled(boolean sync) { vsyncEnabled = sync; + glfwSwapInterval(vsyncEnabled ? 1 : 0); } public static long getWindow() { @@ -857,7 +853,7 @@ public class Display { public static void setDisplayMode(DisplayMode dm) throws LWJGLException { mode = dm; - GLFW.glfwSetWindowSize(Window.handle, dm.getWidth(), dm.getHeight()); + if(isCreated) GLFW.glfwSetWindowSize(Window.handle, dm.getWidth(), dm.getHeight()); } public static DisplayMode getDisplayMode() { @@ -1029,6 +1025,10 @@ public class Display { } } + public static void setDisplayConfiguration(float gamma, float brightness, float contrast) throws LWJGLException { + // ignore call, this is required for a1.1.1 + } + public static java.lang.String getAdapter() { // TODO return "GeNotSupportedAdapter"; @@ -1047,8 +1047,9 @@ public class Display { * - the desired frame rate, in frames per second */ public static void sync(int fps) { - if (vsyncEnabled) - Sync.sync(fps); + /*if (vsyncEnabled) + Sync.sync(60); + else*/ Sync.sync(fps); } public static Drawable getDrawable() { diff --git a/JavaApp/src/main/java/org/lwjgl/opengl/Sync.java b/JavaApp/src/main/java/org/lwjgl/opengl/Sync.java index f8f7b075..dbc13655 100644 --- a/JavaApp/src/main/java/org/lwjgl/opengl/Sync.java +++ b/JavaApp/src/main/java/org/lwjgl/opengl/Sync.java @@ -48,6 +48,10 @@ class Sync { /** The time to sleep/yield until the next frame */ private static long nextFrame = 0; + /** The time since last frame **/ + private static long lastFrameTime = 0; + private static long lastDelay = 0; + /** whether the initialisation code has run */ private static boolean initialised = false; @@ -67,6 +71,38 @@ class Sync { public static void sync(int fps) { if (fps <= 0) return; + + preciseSync(fps); + } + + /** Fast, more cpu friendly way of syncing, although can be off the mark at times */ + private static void fastSync(int fps){ + if (!initialised){ + initialised = true; + lastFrameTime = getTime(); + } + + // Dumbass implementation I guess + long currentFrameTime = getTime(); + long deltaMs = (currentFrameTime - lastFrameTime)/1000000; + long deltaFrame = 1000/fps; + if(deltaMs < deltaFrame){ // skip the Thread sleep if the opportunity is available + try { + Thread.sleep(Math.min((deltaFrame - deltaMs) + lastDelay, deltaFrame)); + } catch (InterruptedException e) { + e.printStackTrace(); + } + lastDelay = 0; + }else{ + // Store how late the device is I guess + lastDelay = deltaMs - deltaFrame; + } + + lastFrameTime = getTime(); + } + + /** Precise, more cpu intensive way of syncing */ + private static void preciseSync(int fps){ if (!initialised) initialise(); @@ -76,7 +112,7 @@ class Sync { for (long t0 = getTime(), t1; (nextFrame - t0) > sleepDurations.avg(); t0 = t1) { Thread.sleep(1); sleepDurations.add((t1 = getTime()) - t0); // update average - // sleep time + // sleep time } // slowly dampen sleep average if too high to avoid yielding too @@ -88,7 +124,7 @@ class Sync { for (long t0 = getTime(), t1; (nextFrame - t0) > yieldDurations.avg(); t0 = t1) { Thread.yield(); yieldDurations.add((t1 = getTime()) - t0); // update average - // yield time + // yield time } } catch (InterruptedException e) { @@ -111,27 +147,6 @@ class Sync { yieldDurations.init((int) (-(getTime() - getTime()) * 1.333)); nextFrame = getTime(); - - String osName = System.getProperty("os.name"); - - if (osName.startsWith("Win")) { - // On windows the sleep functions can be highly inaccurate by - // over 10ms making in unusable. However it can be forced to - // be a bit more accurate by running a separate sleeping daemon - // thread. - Thread timerAccuracyThread = new Thread(new Runnable() { - public void run() { - try { - Thread.sleep(Long.MAX_VALUE); - } catch (Exception e) { - } - } - }); - - timerAccuracyThread.setName("LWJGL Timer"); - timerAccuracyThread.setDaemon(true); - timerAccuracyThread.start(); - } } /** diff --git a/Natives/AboutLauncherViewController.m b/Natives/AboutLauncherViewController.m index 09836dfd..0073074f 100644 --- a/Natives/AboutLauncherViewController.m +++ b/Natives/AboutLauncherViewController.m @@ -6,11 +6,9 @@ #import @interface AboutLauncherViewController() -@property (nonatomic, strong) UIActivityViewController *activityViewController; @end @implementation AboutLauncherViewController -@synthesize activityViewController; - (void)viewDidLoad { @@ -18,87 +16,64 @@ setViewBackgroundColor(self.view); [self setTitle:NSLocalizedString(@"login.menu.about", nil)]; - CGRect screenBounds = [[UIScreen mainScreen] bounds]; - CGFloat screenScale = [[UIScreen mainScreen] scale]; - - int width = (int) roundf(screenBounds.size.width); - int height = (int) roundf(screenBounds.size.height) - self.navigationController.navigationBar.frame.size.height; - int rawHeight = (int) roundf(screenBounds.size.height); - - UIScrollView *scrollView = [[UIScrollView alloc] initWithFrame:CGRectMake(0, self.navigationController.navigationBar.frame.size.height + 5, width, height)]; - [self.view addSubview:scrollView]; - scrollView.autoresizingMask = UIViewAutoresizingFlexibleHeight | UIViewAutoresizingFlexibleWidth; - // TODO: Move this into utils? struct utsname systemInfo; uname(&systemInfo); NSString *deviceModel = [NSString stringWithCString:systemInfo.machine encoding:NSUTF8StringEncoding]; NSString *currSysVer = [[UIDevice currentDevice] systemVersion]; - UILabel *logoVerView = [[UILabel alloc] initWithFrame:CGRectMake(4, 0, width - 8, 30)]; - logoVerView.text = [NSString stringWithFormat:@"version 2.1 %s (%s - %s) on %@ with iOS %@", CONFIG_TYPE, CONFIG_BRANCH, CONFIG_COMMIT, deviceModel, currSysVer]; - logoVerView.lineBreakMode = NSLineBreakByWordWrapping; - logoVerView.numberOfLines = 0; - [scrollView addSubview:logoVerView]; - [logoVerView setFont:[UIFont boldSystemFontOfSize:20]]; - - CGFloat logoNoteViewOriginY; if(@available (iOS 14.0, *)) { // UIMenu on the main screen - logoNoteViewOriginY = logoVerView.frame.origin.y + logoVerView.frame.size.height + 5; } else { - self.navigationItem.rightBarButtonItem = [[UIBarButtonItem alloc] initWithTitle:@"Send your logs" style:UIBarButtonItemStyleDone target:self action:@selector(latestLogShare)]; - UIButton *updateHistoryButton = [UIButton buttonWithType:UIButtonTypeRoundedRect]; - [updateHistoryButton setTitle:@"See the recent changelog." forState:UIControlStateNormal]; - updateHistoryButton.frame = CGRectMake(4, logoVerView.frame.origin.y + logoVerView.frame.size.height + 5, width - 8, 25.0); - updateHistoryButton.contentHorizontalAlignment = UIControlContentHorizontalAlignmentLeft; - [updateHistoryButton addTarget:self action:@selector(updateHistory) forControlEvents:UIControlEventTouchUpInside]; - [scrollView addSubview:updateHistoryButton]; - logoNoteViewOriginY = logoVerView.frame.origin.y + logoVerView.frame.size.height + updateHistoryButton.frame.size.height + 9; + self.navigationItem.rightBarButtonItems = @[ + [[UIBarButtonItem alloc] initWithTitle:NSLocalizedString(@"login.menu.sendlogs", nil) style:UIBarButtonItemStyleDone target:self action:@selector(latestLogShare)], + [[UIBarButtonItem alloc] initWithTitle:NSLocalizedString(@"login.menu.updates", nil) style:UIBarButtonItemStyleDone target:self action:@selector(updateHistory)] + ]; } - UILabel *logoNoteView = [[UILabel alloc] initWithFrame:CGRectMake(4.0, logoNoteViewOriginY, width - 8, 700)]; - logoNoteView.text = @"Created by PojavLauncherTeam in 2022. We do not exist on TikTok. No one from the dev team makes TikTok videos."; - logoNoteView.lineBreakMode = NSLineBreakByWordWrapping; - logoNoteView.numberOfLines = 0; - [logoNoteView sizeToFit]; - [scrollView addSubview:logoNoteView]; + UITextView *textView = [[UITextView alloc] initWithFrame:self.view.frame]; + textView.autoresizingMask = UIViewAutoresizingFlexibleHeight | UIViewAutoresizingFlexibleWidth; + textView.dataDetectorTypes = UIDataDetectorTypeLink; + textView.editable = NO; + [self.view addSubview:textView]; - UITextView *linkTextView = [[UITextView alloc] initWithFrame:CGRectMake(-1, logoNoteView.frame.origin.y + logoNoteView.frame.size.height + 9, width - 8, 84)]; - linkTextView.text = @"Discord: https://discord.gg/x5pxnANzbX\nSubreddit: https://reddit.com/r/PojavLauncher\nWiki: https://pojavlauncherteam.github.io"; - linkTextView.editable = NO; - linkTextView.dataDetectorTypes = UIDataDetectorTypeAll; - [scrollView addSubview:linkTextView]; - [linkTextView setFont:[UIFont systemFontOfSize:17]]; - - UILabel *safetyNoteView = [[UILabel alloc] initWithFrame:CGRectMake(4, linkTextView.frame.origin.y + linkTextView.frame.size.height - 2, width - 8, 700)]; - safetyNoteView.text = @"Stay safe when jailbroken. Make sure to install PojavLauncher from the official repositories to prevent the risk of malware."; - safetyNoteView.lineBreakMode = NSLineBreakByWordWrapping; - safetyNoteView.numberOfLines = 0; - [safetyNoteView sizeToFit]; - [scrollView addSubview:safetyNoteView]; + textView.text = [NSString stringWithFormat:@"version 2.1 %s (%s - %s) on %@ with iOS %@\n\n", CONFIG_TYPE, CONFIG_BRANCH, CONFIG_COMMIT, deviceModel, currSysVer]; + + [textView insertText: + @"Created by PojavLauncherTeam in 2022.\n" + @"Discord: https://discord.gg/x5pxnANzbX\n" + @"Subreddit: https://reddit.com/r/PojavLauncher\n" + @"TikTok: unavailable, we do not make videos on TikTok\n" + @"Wiki: https://pojavlauncherteam.github.io\n" + ]; + + if (getenv("POJAV_DETECTEDJB")) { + [textView insertText:@"Stay safe when jailbroken. "]; + } + [textView insertText:@"Make sure to install PojavLauncher from the official repositories to prevent the risk of malware.\n\n"]; NSDateFormatter *dateFormatter=[[NSDateFormatter alloc] init]; [dateFormatter setDateFormat:@"MM-dd"]; NSString* date = [dateFormatter stringFromDate:[NSDate date]]; if([date isEqualToString:@"06-29"] || [date isEqualToString:@"06-30"] || [date isEqualToString:@"07-01"]) { - UILabel *technoDay = [[UILabel alloc] initWithFrame:CGRectMake(4, safetyNoteView.frame.origin.y + safetyNoteView.frame.size.height + 9, width - 8, 700)]; - technoDay.text = @"May you rest in peace, Technoblade. The Minecraft community will always remember you."; - technoDay.lineBreakMode = NSLineBreakByWordWrapping; - technoDay.numberOfLines = 0; - [technoDay sizeToFit]; - [scrollView addSubview:technoDay]; - scrollView.contentSize = CGSizeMake(scrollView.frame.size.width, technoDay.frame.origin.y + technoDay.frame.size.height + 0); - } else { - scrollView.contentSize = CGSizeMake(scrollView.frame.size.width, safetyNoteView.frame.origin.y + safetyNoteView.frame.size.height + 0); + [textView insertText:@"May you rest in peace, Technoblade. The Minecraft community will always remember you."]; + } + + NSMutableAttributedString *newString = [[NSMutableAttributedString alloc] initWithString:textView.text]; + [newString addAttribute:NSFontAttributeName value:[UIFont systemFontOfSize:16] range:NSMakeRange(0, newString.length)]; + [newString addAttribute:NSFontAttributeName value:[UIFont boldSystemFontOfSize:20] range:NSMakeRange(0, [textView.text rangeOfString:@"\n"].location)]; + textView.attributedText = newString; + + if (@available(iOS 13.0, *)) { + textView.textColor = UIColor.labelColor; } } -(void)latestLogShare { NSString *latestlogPath = [NSString stringWithFormat:@"file://%s/latestlog.old.txt", getenv("HOME")]; - activityViewController = [[UIActivityViewController alloc] initWithActivityItems:@[@"latestlog.txt", [NSURL URLWithString:latestlogPath]] applicationActivities:nil]; - + UIActivityViewController *activityViewController = [[UIActivityViewController alloc] initWithActivityItems:@[@"latestlog.txt", [NSURL URLWithString:latestlogPath]] applicationActivities:nil]; + activityViewController.popoverPresentationController.barButtonItem = self.navigationItem.rightBarButtonItems[0]; [self presentViewController:activityViewController animated:YES completion:nil]; } diff --git a/Natives/CustomControlsViewController.m b/Natives/CustomControlsViewController.m index 7d18020f..0ea95767 100644 --- a/Natives/CustomControlsViewController.m +++ b/Natives/CustomControlsViewController.m @@ -82,6 +82,7 @@ NSMutableArray *keyCodeMap, *keyValueMap; UIEdgeInsets insets = UIApplication.sharedApplication.windows.firstObject.safeAreaInsets; self.ctrlView = [[ControlLayout alloc] initWithFrame:CGRectFromString(getPreference(@"control_safe_area"))]; + self.ctrlView.autoresizingMask = UIViewAutoresizingFlexibleWidth | UIViewAutoresizingFlexibleWidth; if (@available(iOS 13.0, *)) { self.ctrlView.layer.borderColor = UIColor.labelColor.CGColor; } else { @@ -99,6 +100,7 @@ NSMutableArray *keyCodeMap, *keyValueMap; navigationItem.leftBarButtonItem = [[UIBarButtonItem alloc] initWithBarButtonSystemItem:UIBarButtonSystemItemCancel target:self action:@selector(actionMenuSafeAreaCancel)]; navigationItem.rightBarButtonItem = [[UIBarButtonItem alloc] initWithBarButtonSystemItem:UIBarButtonSystemItemDone target:self action:@selector(actionMenuSafeAreaDone)]; self.navigationBar = [[UINavigationBar alloc] initWithFrame:CGRectMake(0, 0, self.view.frame.size.width, 44.0)]; + self.navigationBar.autoresizingMask = UIViewAutoresizingFlexibleWidth; self.navigationBar.hidden = YES; self.navigationBar.items = @[navigationItem]; self.navigationBar.translucent = YES; @@ -205,6 +207,24 @@ NSMutableArray *keyCodeMap, *keyValueMap; }); } +- (void)viewDidLayoutSubviews { + CGRect ctrlFrame = CGRectFromString(getPreference(@"control_safe_area")); + if ((ctrlFrame.size.width > ctrlFrame.size.height) != (self.view.frame.size.width > self.view.frame.size.height)) { + CGFloat tmpHeight = ctrlFrame.size.width; + ctrlFrame.size.width = ctrlFrame.size.height; + ctrlFrame.size.height = tmpHeight; + self.ctrlView.frame = ctrlFrame; + setPreference(@"control_safe_area", NSStringFromCGRect(ctrlFrame)); + } + + // Update dynamic position for each view + for (UIView *view in self.ctrlView.subviews) { + if ([view isKindOfClass:[ControlButton class]]) { + [(ControlButton *)view update]; + } + } +} + - (void)changeSafeAreaSelection:(UISegmentedControl *)sender { switch (sender.selectedSegmentIndex) { case 0: @@ -516,7 +536,11 @@ NSMutableArray *keyCodeMap, *keyValueMap; } - (BOOL)prefersHomeIndicatorAutoHidden { - return NO; + return YES; +} + +- (BOOL)prefersStatusBarHidden { + return YES; } - (void)onTouch:(UIPanGestureRecognizer *)sender { diff --git a/Natives/Info.plist b/Natives/Info.plist index cfa8d52f..d6e8efe8 100644 --- a/Natives/Info.plist +++ b/Natives/Info.plist @@ -60,6 +60,15 @@ CFBundleVersion 2 + GCSupportsControllerUserInteraction + + GCSupportedGameControllers + + + ProfileName + ExtendedGamepad + + LSApplicationQueriesSchemes filza @@ -105,8 +114,6 @@ arm64 metal - UIRequiresFullScreen - UIStatusBarHidden UISupportedInterfaceOrientations @@ -116,11 +123,13 @@ UISupportedInterfaceOrientations~ipad + UIInterfaceOrientationPortrait + UIInterfaceOrientationPortraitUpsideDown UIInterfaceOrientationLandscapeLeft UIInterfaceOrientationLandscapeRight UIViewControllerBasedStatusBarAppearance - + UISupportsDocumentBrowser diff --git a/Natives/JavaGUIViewController.m b/Natives/JavaGUIViewController.m index 9581ec0f..4eb8305e 100644 --- a/Natives/JavaGUIViewController.m +++ b/Natives/JavaGUIViewController.m @@ -27,7 +27,7 @@ JNIEXPORT void JNICALL Java_net_kdt_pojavlaunch_uikit_UIKit_refreshAWTBuffer(JNI @implementation SurfaceView const void * _CGDataProviderGetBytePointerCallbackAWT(void *info) { - return (const void *)rgbArray; + return (const void *)rgbArray; } - (void)displayLayer { @@ -60,7 +60,9 @@ const void * _CGDataProviderGetBytePointerCallbackAWT(void *info) { @interface JavaGUIViewController () { } -// - (void)method +@property BOOL virtualMouseEnabled; +@property CGRect virtualMouseFrame; +@property UIImageView* mousePointerView; @end @@ -74,7 +76,7 @@ const void * _CGDataProviderGetBytePointerCallbackAWT(void *info) { [self setNeedsUpdateOfScreenEdgesDeferringSystemGestures]; [self setNeedsUpdateOfHomeIndicatorAutoHidden]; - CGRect screenBounds = [[UIScreen mainScreen] bounds]; + CGRect screenBounds = self.view.bounds; CGFloat screenScale = [[UIScreen mainScreen] scale]; int width = (int) roundf(screenBounds.size.width); @@ -85,6 +87,7 @@ const void * _CGDataProviderGetBytePointerCallbackAWT(void *info) { windowHeight = roundf(height * screenScale * resolution); UIScrollView *scrollView = [[UIScrollView alloc] initWithFrame:self.view.frame]; + scrollView.autoresizingMask = UIViewAutoresizingFlexibleHeight | UIViewAutoresizingFlexibleWidth; scrollView.delegate = self; scrollView.minimumZoomScale = 1; scrollView.maximumZoomScale = 5; @@ -95,6 +98,18 @@ const void * _CGDataProviderGetBytePointerCallbackAWT(void *info) { [self.view addSubview:scrollView]; +// TODO +/* + self.virtualMouseEnabled = [getPreference(@"virtmouse_enable") boolValue]; + scrollView.bounces = !self.virtualMouseEnabled; + self.virtualMouseFrame = CGRectMake(screenBounds.size.width / 2, screenBounds.size.height / 2, 18, 27); + self.mousePointerView = [[UIImageView alloc] initWithFrame:self.virtualMouseFrame]; + self.mousePointerView.hidden = !self.virtualMouseEnabled; + self.mousePointerView.image = [UIImage imageNamed:@"mouse_pointer.png"]; + self.mousePointerView.userInteractionEnabled = NO; + [self.view addSubview:self.mousePointerView]; +*/ + UITapGestureRecognizer *tapGesture = [[UITapGestureRecognizer alloc] initWithTarget:self action:@selector(surfaceOnClick:)]; tapGesture.delegate = self; @@ -153,6 +168,17 @@ const void * _CGDataProviderGetBytePointerCallbackAWT(void *info) { } } +/* +- (void)scrollViewDidScroll:(UIScrollView *)scrollView { + if (scrollView.contentOffset.x == 0) { + + } + if (scrollView.contentOffset.y == 0) { + + } +} +*/ + - (UIView *)viewForZoomingInScrollView:(UIScrollView *)scrollView { return surfaceView; } diff --git a/Natives/JavaLauncher.m b/Natives/JavaLauncher.m index c12069d2..4f94a1ee 100644 --- a/Natives/JavaLauncher.m +++ b/Natives/JavaLauncher.m @@ -175,6 +175,7 @@ int launchJVM(NSString *username, id launchTarget, int width, int height, int mi } else { allocmem = [getPreference(@"allocated_memory") intValue]; } + NSLog(@"[JavaLauncher] Max RAM allocation is set to %d MB", allocmem); // "/Applications/PojavLauncher.app/libs/launcher.jar:/Applications/PojavLauncher.app/libs/ExagearApacheCommons.jar:/Applications/PojavLauncher.app/libs/gson-2.8.6.jar:/Applications/PojavLauncher.app/libs/jsr305.jar:/Applications/PojavLauncher.app/libs/lwjgl3-minecraft.jar"; diff --git a/Natives/LauncherFAQViewController.m b/Natives/LauncherFAQViewController.m index ba919ffb..1d51a107 100644 --- a/Natives/LauncherFAQViewController.m +++ b/Natives/LauncherFAQViewController.m @@ -2,11 +2,6 @@ #include "utils.h" -@interface LauncherFAQViewController () { -} --(UILabel *)faqContent:(bool)isHeading text:(NSString *)text width:(int)width; -@end - @implementation LauncherFAQViewController CGFloat faqcurrY = 4.0; - (void)viewDidLoad @@ -15,50 +10,36 @@ CGFloat faqcurrY = 4.0; setViewBackgroundColor(self.view); [self setTitle:NSLocalizedString(@"FAQ", nil)]; - CGRect screenBounds = [[UIScreen mainScreen] bounds]; - CGFloat screenScale = [[UIScreen mainScreen] scale]; - - int width = (int) roundf(screenBounds.size.width); - int height = (int) roundf(screenBounds.size.height) - self.navigationController.navigationBar.frame.size.height; - - UIScrollView *scrollView = [[UIScrollView alloc] initWithFrame:self.view.frame]; - [self.view addSubview:scrollView]; - scrollView.autoresizingMask = UIViewAutoresizingFlexibleHeight | UIViewAutoresizingFlexibleWidth; + NSMutableAttributedString *faqString = NSMutableAttributedString.new; - NSString *snapheadingtext = @"Vanilla versions after 21w08b"; - - faqcurrY = 4.0; - - [scrollView addSubview:[self faqContent:true text:@"Notice about older devices" width:width]]; - [scrollView addSubview:[self faqContent:false text:@"If you're using a device with less than 2GB of memory, you may not be able to play PojavLauncher with a good experience, if at all." width:width]]; - [scrollView addSubview:[self faqContent:true text:@"Modded versions before 1.16" width:width]]; - [scrollView addSubview:[self faqContent:false text:@"In order to use these versions, you need to install openjdk-8-jre from Doregon's Repo and change Java home in Preferences to 'Java 8'." width:width]]; - [scrollView addSubview:[self faqContent:true text:@"Vanilla versions after 21w10b" width:width]]; - [scrollView addSubview:[self faqContent:false text:@"In order to use these versions, you need to install openjdk-16-jre and change the Renderer in Preferences to tinygl4angle." width:width]]; - [scrollView addSubview:[self faqContent:true text:@"Vanilla versions after 21w37a" width:width]]; - [scrollView addSubview:[self faqContent:false text:@"In order to use these versions, you need to install openjdk-17-jre and change the Renderer in Preferences to tinygl4angle. If you are using unc0ver/checkra1n, switch to or wait for a Procursus jailbreak." width:width]]; - [scrollView addSubview:[self faqContent:true text:@"Sodium versions for 1.17 and higher" width:width]]; - [scrollView addSubview:[self faqContent:false text:@"Sodium is currently broken with 1.17 and higher, due to the workaround required to get these versions to launch." width:width]]; - [scrollView addSubview:[self faqContent:true text:@"Jetsam crashing" width:width]]; - [scrollView addSubview:[self faqContent:false text:@"Even though PojavLauncher only allocates 1/4 of the system's total memory, jetsam can still kill the game. A solution is described on the PojavLauncher website (iOS Wiki > Going further > overb0arding)" width:width]]; - [scrollView addSubview:[self faqContent:true text:@"Cosmetica capes" width:width]]; - [scrollView addSubview:[self faqContent:false text:@"To get started with Cosmetica capes, install OptiFine or the Cosmetica Mod, and visit login.cosmetica.cc to link with your Minecraft account." width:width]]; - - scrollView.contentSize = CGSizeMake(scrollView.frame.size.width, faqcurrY); + [faqString appendAttributedString:[self makeItem:@"Notice about older devices\nIf you're using a device with less than 2GB of memory, you may not be able to play PojavLauncher with a good experience, if at all.\n\n"]]; + + [faqString appendAttributedString:[self makeItem:@"Modded versions before 1.16\nIn order to use these versions, you need to install openjdk-8-jre(*) and change Java home in Preferences to 'Java 8'.\n\n"]]; + + [faqString appendAttributedString:[self makeItem:@"Vanilla versions after 21w10b\nIn order to use these versions, you need to install openjdk-17-jre(*) and change the Renderer in Preferences to Auto.\n\n"]]; + + [faqString appendAttributedString:[self makeItem:@"(*)\nInstalling external Java is not needed, as .ipa build has already included both Java versions in order to work without jailbreak.\n\n"]]; + + [faqString appendAttributedString:[self makeItem:@"Sodium versions for 1.17 and higher\nSodium is currently broken with 1.17 and higher, due to the workaround required to get these versions to launch.\n\n"]]; + + [faqString appendAttributedString:[self makeItem:@"Cosmetica capes\nTo get started with Cosmetica capes, install OptiFine or the Cosmetica Mod, and visit https://login.cosmetica.cc to link with your Minecraft account."]]; + + UITextView *textView = [[UITextView alloc] initWithFrame:self.view.frame]; + textView.autoresizingMask = UIViewAutoresizingFlexibleHeight | UIViewAutoresizingFlexibleWidth; + textView.attributedText = faqString; + textView.dataDetectorTypes = UIDataDetectorTypeLink; + textView.editable = NO; + if (@available(iOS 13.0, *)) { + textView.textColor = UIColor.labelColor; + } + [self.view addSubview:textView]; } --(UILabel *)faqContent:(bool)isHeading text:(NSString *)text width:(int)width { - UILabel *label = [[UILabel alloc] initWithFrame:CGRectMake(4.0, faqcurrY, width - 40, 30.0)]; - label.text = text; - label.lineBreakMode = NSLineBreakByWordWrapping; - label.numberOfLines = 0; - if(isHeading) { - [label setFont:[UIFont boldSystemFontOfSize:20]]; - } else { - [label sizeToFit]; - } - faqcurrY+=label.frame.size.height; - return label; +- (NSAttributedString *)makeItem:(NSString *)string { + NSMutableAttributedString *newString = [[NSMutableAttributedString alloc] initWithString:string]; + [newString addAttribute:NSFontAttributeName value:[UIFont systemFontOfSize:16] range:NSMakeRange(0, string.length)]; + [newString addAttribute:NSFontAttributeName value:[UIFont boldSystemFontOfSize:20] range:NSMakeRange(0, [string rangeOfString:@"\n"].location)]; + return newString; } @end diff --git a/Natives/LauncherPreferencesViewController2.m b/Natives/LauncherPreferencesViewController2.m index 721560f0..1197b1dc 100644 --- a/Natives/LauncherPreferencesViewController2.m +++ b/Natives/LauncherPreferencesViewController2.m @@ -385,7 +385,12 @@ typedef void(^CreateView)(UITableViewCell *, NSString *, NSDictionary *); picker.delegate = weakSelf; picker.dataSource = weakSelf; [picker reloadAllComponents]; - [picker selectRow:[item[@"pickKeys"] indexOfObject:getPreference(key)] inComponent:0 animated:NO]; + + NSInteger index = [item[@"pickKeys"] indexOfObject:getPreference(key)]; + if (index != NSNotFound) { + [picker selectRow:index inComponent:0 animated:NO]; + } + UIToolbar *toolbar = [[UIToolbar alloc] initWithFrame:CGRectMake(0.0, 0.0, weakSelf.view.frame.size.width, 44.0)]; UIBarButtonItem *flexibleSpace = [[UIBarButtonItem alloc] initWithBarButtonSystemItem:UIBarButtonSystemItemFlexibleSpace target:nil action:nil]; UIBarButtonItem *doneButton = [[UIBarButtonItem alloc] initWithBarButtonSystemItem:UIBarButtonSystemItemDone target:view action:@selector(resignFirstResponder)]; diff --git a/Natives/LoginViewController.m b/Natives/LoginViewController.m index f6ae631a..28051129 100644 --- a/Natives/LoginViewController.m +++ b/Natives/LoginViewController.m @@ -17,6 +17,9 @@ #import "ios_uikit_bridge.h" #import "utils.h" +#define AUTORESIZE_BTN UIViewAutoresizingFlexibleWidth | UIViewAutoresizingFlexibleLeftMargin | UIViewAutoresizingFlexibleTopMargin | UIViewAutoresizingFlexibleRightMargin +#define AUTORESIZE AUTORESIZE_BTN | UIViewAutoresizingFlexibleBottomMargin + #define TYPE_SELECTACC 0 #define TYPE_MICROSOFT 1 #define TYPE_OFFLINE 2 @@ -38,16 +41,10 @@ extern NSMutableDictionary *prefDict; [[NSNotificationCenter defaultCenter] addObserver:self selector:@selector(msaLoginCallback:) name:@"MSALoginCallback" object:nil]; - CGRect screenBounds = UIScreen.mainScreen.bounds; + CGFloat width = self.view.frame.size.width; + CGFloat height = self.view.frame.size.height; // - self.navigationController.navigationBar.frame.size.height; + CGFloat rawHeight = self.view.frame.size.height; - CGFloat width = screenBounds.size.width; - CGFloat height = screenBounds.size.height - self.navigationController.navigationBar.frame.size.height; - CGFloat rawHeight = screenBounds.size.height; - - UIScrollView *scrollView = [[UIScrollView alloc] initWithFrame:self.view.frame]; - scrollView.autoresizingMask = UIViewAutoresizingFlexibleHeight | UIViewAutoresizingFlexibleWidth; - [self.view addSubview:scrollView]; - if(roundf([[NSProcessInfo processInfo] physicalMemory] / 1048576) < 1900 && [getPreference(@"unsupported_warn_counter") intValue] == 0) { UIAlertController *RAMAlert = [UIAlertController alertControllerWithTitle:NSLocalizedString(@"login.warn.title.a7", nil) message:NSLocalizedString(@"login.warn.message.a7", nil) preferredStyle:UIAlertControllerStyleAlert]; UIAlertAction *ok = [UIAlertAction actionWithTitle:NSLocalizedString(@"OK", nil) style:UIAlertActionStyleCancel handler:nil]; @@ -76,6 +73,7 @@ extern NSMutableDictionary *prefDict; UIImageView *logoView = [[UIImageView alloc] initWithImage:[UIImage imageNamed:@"AppLogo"]]; logoView.frame = CGRectMake(0, (rawHeight / 2) - 35, width, 70); [logoView setContentMode:UIViewContentModeScaleAspectFit]; + logoView.autoresizingMask = AUTORESIZE; [self.view addSubview:logoView]; NSDateFormatter *dateFormatter=[[NSDateFormatter alloc] init]; @@ -102,6 +100,7 @@ extern NSMutableDictionary *prefDict; UIButton *button_faq = [UIButton buttonWithType:UIButtonTypeSystem]; setButtonPointerInteraction(button_faq); [button_faq setTitle:NSLocalizedString(@"FAQ", @"Frequently asked questions") forState:UIControlStateNormal]; + button_faq.autoresizingMask = AUTORESIZE_BTN; button_faq.frame = CGRectMake(widthSplit2 - (((width - widthSplit * 2.0) / 2) / 2), (height - 80.0), (width - widthSplit * 2.0) / 2, 40.0); if([date isEqualToString:@"06-29"] || [date isEqualToString:@"06-30"] || [date isEqualToString:@"07-01"]) { button_faq.backgroundColor = [UIColor colorWithRed:67/255.0 green:0/255.0 blue:8/255.0 alpha:1.0]; @@ -116,11 +115,12 @@ extern NSMutableDictionary *prefDict; [button_faq setTintColor:UIColor.whiteColor]; [button_faq setImage:button_faq.imageView.image forState:UIControlStateNormal]; } - [scrollView addSubview:button_faq]; + [self.view addSubview:button_faq]; UIButton *button_login = [UIButton buttonWithType:UIButtonTypeSystem]; setButtonPointerInteraction(button_login); [button_login setTitle:NSLocalizedString(@"Sign in", nil) forState:UIControlStateNormal]; + button_login.autoresizingMask = AUTORESIZE_BTN; button_login.frame = CGRectMake(button_faq.frame.origin.x - button_faq.frame.size.width - 20, (height - 80.0), (width - widthSplit * 2.0) / 2, 40.0); if([date isEqualToString:@"06-29"] || [date isEqualToString:@"06-30"] || [date isEqualToString:@"07-01"]) { button_login.backgroundColor = [UIColor colorWithRed:67/255.0 green:0/255.0 blue:8/255.0 alpha:1.0]; @@ -147,11 +147,12 @@ extern NSMutableDictionary *prefDict; [button_login setTintColor:UIColor.whiteColor]; [button_login setImage:button_login.imageView.image forState:UIControlStateNormal]; } - [scrollView addSubview:button_login]; + [self.view addSubview:button_login]; UIButton *button_accounts = [UIButton buttonWithType:UIButtonTypeSystem]; setButtonPointerInteraction(button_accounts); [button_accounts setTitle:NSLocalizedString(@"Accounts", nil) forState:UIControlStateNormal]; + button_accounts.autoresizingMask = AUTORESIZE_BTN; button_accounts.frame = CGRectMake(button_faq.frame.origin.x + button_faq.frame.size.width + 20, (height - 80.0), (width - widthSplit * 2.0) / 2, 40.0); if([date isEqualToString:@"06-29"] || [date isEqualToString:@"06-30"] || [date isEqualToString:@"07-01"]) { button_accounts.backgroundColor = [UIColor colorWithRed:67/255.0 green:0/255.0 blue:8/255.0 alpha:1.0]; @@ -166,7 +167,7 @@ extern NSMutableDictionary *prefDict; [button_accounts setTintColor:UIColor.whiteColor]; [button_accounts setImage:button_accounts.imageView.image forState:UIControlStateNormal]; } - [scrollView addSubview:button_accounts]; + [self.view addSubview:button_accounts]; if([date isEqualToString:@"06-29"] || [date isEqualToString:@"06-30"] || [date isEqualToString:@"07-01"]) { UILabel *technoNote = [[UILabel alloc] initWithFrame:CGRectMake(0, 15, width, 40.0)]; @@ -175,7 +176,7 @@ extern NSMutableDictionary *prefDict; technoNote.numberOfLines = 1; [technoNote setFont:[UIFont boldSystemFontOfSize:10]]; technoNote.textAlignment = NSTextAlignmentCenter; - [scrollView addSubview:technoNote]; + [self.view addSubview:technoNote]; } if (!getEntitlementValue(@"dynamic-codesigning")) { diff --git a/Natives/SurfaceViewController+LogView.m b/Natives/SurfaceViewController+LogView.m index 0259dc8e..6c49e219 100644 --- a/Natives/SurfaceViewController+LogView.m +++ b/Natives/SurfaceViewController+LogView.m @@ -48,7 +48,7 @@ static NSMutableArray* logLines; alert.popoverPresentationController.sourceView = cell; alert.popoverPresentationController.sourceRect = cell.bounds; UIAlertAction *share = [UIAlertAction actionWithTitle:NSLocalizedString(NSLocalizedString(@"Share", nil), nil) style:UIAlertActionStyleDefault handler:^(UIAlertAction * _Nonnull action) { - UIView *navigationBar = vc.logOutputView.subviews[0]; + UIView *navigationBar = vc.logOutputView.subviews[1]; UIActivityViewController *activityVC = [[UIActivityViewController alloc] initWithActivityItems:@[line] applicationActivities:nil]; activityVC.popoverPresentationController.sourceView = navigationBar; activityVC.popoverPresentationController.sourceRect = navigationBar.bounds; @@ -86,15 +86,14 @@ static int logCharPerLine; navigationBar.items = @[navigationItem]; navigationBar.topItem.title = NSLocalizedString(@"game.menu.log_output", nil); [navigationBar sizeToFit]; - [self.logOutputView addSubview:navigationBar]; - canAppendToLog = YES; - [self actionStartStopLogOutput]; + navigationBar.autoresizingMask = UIViewAutoresizingFlexibleWidth; - self.logTableView = [[UITableView alloc] initWithFrame: - CGRectMake(0, navigationBar.frame.size.height, self.view.frame.size.width, self.view.frame.size.height - navigationBar.frame.size.height)]; + self.logTableView = [[UITableView alloc] initWithFrame:self.view.frame]; logDelegate = [[LogDelegate alloc] init]; //self.logTableView.allowsSelection = NO; + self.logTableView.autoresizingMask = UIViewAutoresizingFlexibleHeight | UIViewAutoresizingFlexibleWidth; self.logTableView.backgroundColor = UIColor.clearColor; + self.logTableView.contentInset = UIEdgeInsetsMake(navigationBar.frame.size.height, 0, 0, 0); self.logTableView.dataSource = logDelegate; self.logTableView.delegate = logDelegate; self.logTableView.layoutMargins = UIEdgeInsetsZero; @@ -102,9 +101,11 @@ static int logCharPerLine; self.logTableView.separatorInset = UIEdgeInsetsZero; self.logTableView.separatorStyle = UITableViewCellSeparatorStyleNone; [self.logOutputView addSubview:self.logTableView]; + [self.logOutputView addSubview:navigationBar]; [self.rootView addSubview:self.logOutputView]; - //canAppendToLog = YES; + canAppendToLog = YES; + [self actionStartStopLogOutput]; } - (void)actionClearLogOutput { @@ -113,7 +114,7 @@ static int logCharPerLine; } - (void)actionShareLatestlog { - UINavigationBar *navigationBar = self.logOutputView.subviews[0]; + UINavigationBar *navigationBar = self.logOutputView.subviews[1]; NSString *latestlogPath = [NSString stringWithFormat:@"file://%s/latestlog.txt", getenv("POJAV_HOME")]; UIActivityViewController *activityVC = [[UIActivityViewController alloc] initWithActivityItems:@[@"latestlog.txt", [NSURL URLWithString:latestlogPath]] applicationActivities:nil]; @@ -124,7 +125,7 @@ static int logCharPerLine; - (void)actionStartStopLogOutput { canAppendToLog = !canAppendToLog; - UINavigationItem* item = ((UINavigationBar *)self.logOutputView.subviews[0]).items[0]; + UINavigationItem* item = ((UINavigationBar *)self.logOutputView.subviews[1]).items[0]; item.leftBarButtonItem = [[UIBarButtonItem alloc] initWithBarButtonSystemItem: canAppendToLog ? UIBarButtonSystemItemPause : UIBarButtonSystemItemPlay @@ -186,7 +187,7 @@ static int logCharPerLine; [instance actionToggleLogOutput]; } // Cleanup navigation bar - UINavigationBar *navigationBar = instance.logOutputView.subviews[0]; + UINavigationBar *navigationBar = instance.logOutputView.subviews[1]; navigationBar.topItem.title = [NSString stringWithFormat: NSLocalizedString(@"game.title.exit_code", nil), code]; navigationBar.items[0].leftBarButtonItem = [[UIBarButtonItem alloc] @@ -218,4 +219,8 @@ static int logCharPerLine; }); } +- (void)viewWillTransitionToSize_LogView:(CGRect)frame { + self.logOutputView.frame = frame; +} + @end diff --git a/Natives/SurfaceViewController+Navigation.m b/Natives/SurfaceViewController+Navigation.m index 3bd67f62..1e9ae6af 100644 --- a/Natives/SurfaceViewController+Navigation.m +++ b/Natives/SurfaceViewController+Navigation.m @@ -1,21 +1,21 @@ #import "LauncherPreferencesViewController2.h" #import "SurfaceViewController.h" -@interface SurfaceViewController(Navigation) - -@end - @implementation SurfaceViewController(Navigation) + +static UIView *menuSwipeView; - (void)initCategory_Navigation { UIPanGestureRecognizer *menuPanGesture = [[UIPanGestureRecognizer alloc] initWithTarget:self action:@selector(handleRightEdge:)]; menuPanGesture.delegate = self; UIView *menuSwipeLineView = [[UIView alloc] initWithFrame:CGRectMake(11.0, self.view.frame.size.height/2 - 100.0, 8.0, 200.0)]; + menuSwipeLineView.autoresizingMask = UIViewAutoresizingFlexibleTopMargin | UIViewAutoresizingFlexibleBottomMargin; menuSwipeLineView.backgroundColor = UIColor.whiteColor; menuSwipeLineView.layer.cornerRadius = 4; menuSwipeLineView.userInteractionEnabled = NO; UIView *menuSwipeView = [[UIView alloc] initWithFrame:CGRectMake(self.view.frame.size.width, 0, 30.0, self.view.frame.size.height)]; + menuSwipeView.autoresizingMask = UIViewAutoresizingFlexibleHeight | UIViewAutoresizingFlexibleLeftMargin; menuSwipeView.backgroundColor = [UIColor colorWithRed:0 green:0 blue:0 alpha:0.1]; [menuSwipeView addGestureRecognizer:menuPanGesture]; [menuSwipeView addSubview:menuSwipeLineView]; @@ -47,11 +47,6 @@ static CGPoint lastCenterPoint; if (lastCenterPoint.y == 0) { lastCenterPoint.x = self.rootView.center.x; lastCenterPoint.y = 1; - - // Set the height to fit the content - CGRect menuFrame = self.menuView.frame; - menuFrame.size.height = MIN(self.view.frame.size.height, self.menuView.contentSize.height); - self.menuView.frame = menuFrame; } CGFloat centerX = self.rootView.bounds.size.width / 2; @@ -66,7 +61,7 @@ static CGPoint lastCenterPoint; CGFloat scale = MAX(0.7, self.rootView.center.x / centerX); self.rootView.transform = CGAffineTransformScale(CGAffineTransformIdentity, scale, scale); - self.menuView.frame = CGRectMake(self.rootView.frame.size.width, self.rootView.frame.origin.y, self.menuView.frame.size.width, self.menuView.frame.size.height); + self.menuView.frame = CGRectMake(self.rootView.frame.size.width, self.rootView.frame.origin.y, self.menuView.frame.size.width, self.menuView.contentSize.height); // scale is in range of 0.7-1 // 1.1 - scale produces in range of 0.4-0.1 // result in transform scale range of 1-0.25 @@ -86,7 +81,7 @@ static CGPoint lastCenterPoint; self.rootView.center = CGPointMake(lastCenterPoint.x, centerY); self.rootView.transform = CGAffineTransformScale(CGAffineTransformIdentity, scale, scale); self.menuView.transform = CGAffineTransformScale(CGAffineTransformIdentity, (1.1-scale)*2.5, (1.1-scale)*2.5); - self.menuView.frame = CGRectMake(self.rootView.frame.size.width, self.rootView.frame.origin.y, self.menuView.frame.size.width, self.menuView.frame.size.height); + self.menuView.frame = CGRectMake(self.rootView.frame.size.width, self.rootView.frame.origin.y, self.menuView.frame.size.width, self.menuView.contentSize.height); } completion:^(BOOL finished) { self.menuView.hidden = scale == 1.0; }]; @@ -155,4 +150,15 @@ static CGPoint lastCenterPoint; } } +- (void)viewWillTransitionToSize_Navigation:(CGRect)frame { + if (self.rootView.transform.a != 0) { + CGFloat centerX = self.rootView.bounds.size.width / 2; + CGFloat centerY = self.rootView.bounds.size.height / 2; + self.rootView.center = lastCenterPoint = CGPointMake(centerX * self.rootView.transform.a, centerY); + } + + self.menuView.frame = CGRectMake(self.rootView.frame.size.width, self.rootView.frame.origin.y, + frame.size.width * 0.3 - 21.0, self.menuView.contentSize.height); +} + @end diff --git a/Natives/SurfaceViewController.h b/Natives/SurfaceViewController.h index facb1443..29cba0e7 100644 --- a/Natives/SurfaceViewController.h +++ b/Natives/SurfaceViewController.h @@ -34,4 +34,12 @@ CGPoint lastVirtualMousePoint; + (void)appendToLog:(NSString *)line; + (void)handleExitCode:(int)code; +- (void)viewWillTransitionToSize_LogView:(CGRect)frame; + +@end + +@interface SurfaceViewController(Navigation) + +- (void)viewWillTransitionToSize_Navigation:(CGRect)frame; + @end diff --git a/Natives/SurfaceViewController.m b/Natives/SurfaceViewController.m index be63d50b..68a6e211 100644 --- a/Natives/SurfaceViewController.m +++ b/Natives/SurfaceViewController.m @@ -84,13 +84,10 @@ BOOL slideableHotbar; } [displayLink addToRunLoop:NSRunLoop.currentRunLoop forMode:NSRunLoopCommonModes]; - CGRect screenBounds = [[UIScreen mainScreen] bounds]; - CGFloat screenScale = [[UIScreen mainScreen] scale]; + CGFloat screenScale = UIScreen.mainScreen.scale; resolutionScale = ((NSNumber *)getPreference(@"resolution")).floatValue / 100.0; - physicalWidth = roundf(screenBounds.size.width * screenScale); - physicalHeight = roundf(screenBounds.size.height * screenScale); [self updateSavedResolution]; self.rootView = [[UIView alloc] initWithFrame:CGRectMake(0, 0, self.view.frame.size.width + 30.0, self.view.frame.size.height)]; @@ -156,8 +153,9 @@ BOOL slideableHotbar; // Virtual mouse virtualMouseEnabled = [getPreference(@"virtmouse_enable") boolValue]; - virtualMouseFrame = CGRectMake(screenBounds.size.width / 2, screenBounds.size.height / 2, 18, 27); + virtualMouseFrame = CGRectMake(self.view.frame.size.width / 2, self.view.frame.size.height / 2, 18, 27); self.mousePointerView = [[UIImageView alloc] initWithFrame:virtualMouseFrame]; + self.mousePointerView.autoresizingMask = UIViewAutoresizingFlexibleLeftMargin | UIViewAutoresizingFlexibleTopMargin | UIViewAutoresizingFlexibleRightMargin |UIViewAutoresizingFlexibleBottomMargin; self.mousePointerView.hidden = !virtualMouseEnabled; self.mousePointerView.image = [UIImage imageNamed:@"mouse_pointer.png"]; self.mousePointerView.userInteractionEnabled = NO; @@ -218,7 +216,6 @@ BOOL slideableHotbar; [self.rootView addSubview:self.inputTextField]; - [self performSelector:@selector(initCategory_LogView)]; // [self setPreferredFramesPerSecond:1000]; @@ -256,27 +253,34 @@ BOOL slideableHotbar; virtualMouseEnabled = [getPreference(@"virtmouse_enable") boolValue]; self.mousePointerView.hidden = isGrabbing || !virtualMouseEnabled; - CGRect screenBounds = UIScreen.mainScreen.bounds; CGFloat screenScale = UIScreen.mainScreen.scale; // Update virtual mouse scale CGFloat mouseScale = [getPreference(@"mouse_scale") floatValue] / 100.0; - virtualMouseFrame = CGRectMake(screenBounds.size.width / 2, screenBounds.size.height / 2, 18.0 * mouseScale, 27 * mouseScale); + virtualMouseFrame = CGRectMake(self.view.frame.size.width / 2, self.view.frame.size.height / 2, 18.0 * mouseScale, 27 * mouseScale); self.mousePointerView.frame = virtualMouseFrame; self.longpressGesture.minimumPressDuration = [getPreference(@"press_duration") floatValue] / 1000.0; - self.ctrlView.frame = CGRectFromString(getPreference(@"control_safe_area")); + CGRect ctrlFrame = CGRectFromString(getPreference(@"control_safe_area")); + if ((ctrlFrame.size.width > ctrlFrame.size.height) != (self.view.frame.size.width > self.view.frame.size.height)) { + CGFloat tmpHeight = ctrlFrame.size.width; + ctrlFrame.size.width = ctrlFrame.size.height; + ctrlFrame.size.height = tmpHeight; + } + self.ctrlView.frame = ctrlFrame; [self loadCustomControls]; // Update resolution resolutionScale = [getPreference(@"resolution") floatValue] / 100.0; self.surfaceView.layer.contentsScale = screenScale * resolutionScale; [self updateSavedResolution]; - CallbackBridge_nativeSendScreenSize(windowWidth, windowHeight); } - (void)updateSavedResolution { + CGFloat screenScale = UIScreen.mainScreen.scale; + physicalWidth = roundf(self.view.frame.size.width * screenScale); + physicalHeight = roundf(self.view.frame.size.height * screenScale); windowWidth = roundf(physicalWidth * resolutionScale); windowHeight = roundf(physicalHeight * resolutionScale); // Resolution should not be odd @@ -286,6 +290,7 @@ BOOL slideableHotbar; if ((windowHeight % 2) != 0) { --windowHeight; } + CallbackBridge_nativeSendScreenSize(windowWidth, windowHeight); } - (void)launchMinecraft { @@ -349,6 +354,45 @@ BOOL slideableHotbar; return YES; } +- (BOOL)prefersStatusBarHidden { + return YES; +} +/* +- (void)viewDidLayoutSubviews { + if (self.ignoreLayoutSubviews) { + return; + } +*/ +- (void)viewWillTransitionToSize:(CGSize)size withTransitionCoordinator:(id)coordinator +{ + [coordinator animateAlongsideTransition:^(id _Nonnull context) { + self.rootView.bounds = CGRectMake(0, 0, size.width + 30.0, size.height); + + CGRect frame = self.view.frame; + frame.size = size; + self.surfaceView.frame = frame; + self.inputTextField.frame = CGRectMake(0, -32.0, size.width, 30.0); + [self viewWillTransitionToSize_LogView:frame]; + [self viewWillTransitionToSize_Navigation:frame]; + + CGRect ctrlFrame = CGRectFromString(getPreference(@"control_safe_area")); + if ((ctrlFrame.size.width > ctrlFrame.size.height) != (size.width > size.height)) { + CGFloat tmpHeight = ctrlFrame.size.width; + ctrlFrame.size.width = ctrlFrame.size.height; + ctrlFrame.size.height = tmpHeight; + } + self.ctrlView.frame = ctrlFrame; + for (UIView *view in self.ctrlView.subviews) { + if ([view isKindOfClass:[ControlButton class]]) { + [(ControlButton *)view update]; + } + } + } completion:^(id _Nonnull context) { + [self updateSavedResolution]; + }]; + [super viewWillTransitionToSize:size withTransitionCoordinator:coordinator]; +} + #pragma mark - Input: send touch utilities - (BOOL)isTouchInactive:(UITouch *)touch { diff --git a/Natives/input_bridge_v3.m b/Natives/input_bridge_v3.m index fb6c700f..2e814221 100644 --- a/Natives/input_bridge_v3.m +++ b/Natives/input_bridge_v3.m @@ -165,7 +165,7 @@ ADD_CALLBACK_WWIN(WindowPos); #undef ADD_CALLBACK_WWIN void sendData(int type, CGFloat i1, CGFloat i2, int i3, int i4) { - debugLog("Debug: Send data, jnienv.isNull=%d, bridgeClass.isNull=%d\n", runtimeJNIEnvPtr == NULL, inputBridgeClass_ANDROID == NULL); + //debugLog("Debug: Send data, jnienv.isNull=%d, bridgeClass.isNull=%d\n", runtimeJNIEnvPtr == NULL, inputBridgeClass_ANDROID == NULL); if (runtimeJNIEnvPtr == NULL) { (*runtimeJavaVMPtr)->AttachCurrentThread(runtimeJavaVMPtr, &runtimeJNIEnvPtr, NULL); } @@ -428,7 +428,6 @@ void CallbackBridge_nativeSendScreenSize(int width, int height) { GLFW_invoke_FramebufferSize((void*) showingWindow, width, height); } } - if (GLFW_invoke_WindowSize) { if (isUseStackQueueCall) { sendData(EVENT_TYPE_WINDOW_SIZE, width, height, 0, 0); diff --git a/Natives/main_hook.m b/Natives/main_hook.m index aec4d5d9..89b9f10f 100644 --- a/Natives/main_hook.m +++ b/Natives/main_hook.m @@ -3,9 +3,6 @@ #include "external/fishhook/fishhook.h" -// used to handle exit() hook if != 0 -extern float resolutionScale; - static void* (*orig_dlopen)(const char* path, int mode); static void (*orig_exit)(int code); static int (*orig_open)(const char *path, int oflag, ...);