Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Rely on MaximizeUsingFullscreenGeometryHint flag to provide fullscreen experience on Android #5950

Merged
merged 1 commit into from
Jan 23, 2025
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
120 changes: 39 additions & 81 deletions platform/android/src/ch/opengis/qfield/QFieldActivity.java
Original file line number Diff line number Diff line change
Expand Up @@ -53,6 +53,7 @@ OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
import android.content.res.Configuration;
import android.content.res.Resources;
import android.graphics.Color;
import android.graphics.Insets;
import android.media.MediaScannerConnection;
import android.net.Uri;
import android.os.AsyncTask;
Expand Down Expand Up @@ -130,8 +131,6 @@ public class QFieldActivity extends QtActivity {
private boolean handleVolumeKeys = false;
private String pathsToExport;
private String projectPath;
private double sceneTopMargin = 0;
private double sceneBottomMargin = 0;

private static final int CAMERA_RESOURCE = 600;
private static final int GALLERY_RESOURCE = 601;
Expand All @@ -149,53 +148,6 @@ public class QFieldActivity extends QtActivity {
public void onCreate(Bundle savedInstanceState) {
prepareQtActivity();
super.onCreate(savedInstanceState);

if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.LOLLIPOP) {
int resourceId = getResources().getIdentifier("status_bar_height",
"dimen", "android");
if (resourceId > 0) {
sceneTopMargin = getResources().getDimension(resourceId);
}

if (sceneTopMargin <= 0) {
sceneTopMargin = Math.ceil(
(Build.VERSION.SDK_INT >= Build.VERSION_CODES.M ? 24 : 25) *
getResources().getDisplayMetrics().density);
}

Window window = getWindow();
window.addFlags(
WindowManager.LayoutParams.FLAG_DRAWS_SYSTEM_BAR_BACKGROUNDS);
window.getDecorView().setSystemUiVisibility(
View.SYSTEM_UI_FLAG_LAYOUT_FULLSCREEN);
window.setStatusBarColor(Color.TRANSPARENT);
View decor = window.getDecorView();
decor.setSystemUiVisibility(decor.getSystemUiVisibility() |
View.SYSTEM_UI_FLAG_LIGHT_STATUS_BAR);

resourceId = getResources().getIdentifier(
"config_navBarInteractionMode", "integer", "android");
if (resourceId > 0) {
// if the navigation bar is in gesture mode, draw under it
if (getResources().getInteger(resourceId) == 2) {
resourceId = getResources().getIdentifier(
"navigation_bar_height", "dimen", "android");
if (resourceId > 0) {
sceneBottomMargin =
getResources().getDimension(resourceId);

window.addFlags(WindowManager.LayoutParams
.FLAG_TRANSLUCENT_NAVIGATION);
window.setNavigationBarColor(Color.TRANSPARENT);
if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.O) {
decor.setSystemUiVisibility(
decor.getSystemUiVisibility() |
View.SYSTEM_UI_FLAG_LIGHT_NAVIGATION_BAR);
}
}
}
}
}
}

@Override
Expand Down Expand Up @@ -246,12 +198,8 @@ private boolean isDarkTheme() {

private void vibrate(int milliseconds) {
Vibrator v = (Vibrator)getSystemService(Context.VIBRATOR_SERVICE);
if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.O) {
v.vibrate(VibrationEffect.createOneShot(
milliseconds, VibrationEffect.DEFAULT_AMPLITUDE));
} else {
v.vibrate(milliseconds);
}
v.vibrate(VibrationEffect.createOneShot(
milliseconds, VibrationEffect.DEFAULT_AMPLITUDE));
}

private void processProjectIntent() {
Expand Down Expand Up @@ -287,8 +235,7 @@ public void run() {
new File(importProjectPath).mkdir();
}

if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.KITKAT &&
(scheme.compareTo(ContentResolver.SCHEME_CONTENT) == 0 ||
if ((scheme.compareTo(ContentResolver.SCHEME_CONTENT) == 0 ||
action.compareTo(Intent.ACTION_SEND) == 0) &&
importDatasetPath != "") {
DocumentFile documentFile =
Expand Down Expand Up @@ -396,36 +343,47 @@ public void run() {
});
}

private double statusBarMargin() {
double margin = sceneTopMargin;
if (margin > 0) {
int resourceId = getResources().getIdentifier("status_bar_height",
"dimen", "android");
if (resourceId > 0) {
double dimension = getResources().getDimension(resourceId);
if (dimension > 0) {
margin = dimension;
}
private Insets getSafeInsets() {
Copy link
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

A note on this function: we'll be able to get rid of this one altogether when we move to Qt >= 6.9, where we finally have a safeAreaMargins implementation for Android (see https://bugreports.qt.io/browse/QTBUG-131519). We already use QPlatformWindow's safeAreaMargins on iOS and it'll be nice to use it for Android too.

That said, this is for a much latter date. Just stating for the record :)

// TODO when updating to Qt >= 6.9, rely on safeAreaMargins
View decorView = getWindow().getDecorView();
WindowInsets insets = decorView.getRootWindowInsets();
Insets safeInsets;
if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.R) {
int types = WindowInsets.Type.displayCutout() |
WindowInsets.Type.systemBars();
safeInsets = insets.getInsets(types);
} else {
int left = 0;
int top = 0;
int right = 0;
int bottom = 0;
int visibility = decorView.getSystemUiVisibility();
if ((visibility & View.SYSTEM_UI_FLAG_FULLSCREEN) == 0) {
left = insets.getSystemWindowInsetLeft();
top = insets.getSystemWindowInsetTop();
right = insets.getSystemWindowInsetRight();
bottom = insets.getSystemWindowInsetBottom();
}

if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.P) {
DisplayCutout cutout = getWindow()
.getDecorView()
.getRootWindowInsets()
.getDisplayCutout();
if (cutout != null) {
int cutoutHeight = cutout.getSafeInsetTop();
if (cutoutHeight > margin) {
margin = cutoutHeight;
}
}
// Android 9 and 10 emulators don't seem to be able
// to handle this, but let's have the logic here anyway
DisplayCutout cutout = insets.getDisplayCutout();
if (cutout != null) {
left = Math.max(left, cutout.getSafeInsetLeft());
top = Math.max(top, cutout.getSafeInsetTop());
right = Math.max(right, cutout.getSafeInsetRight());
bottom = Math.max(bottom, cutout.getSafeInsetBottom());
}
safeInsets = Insets.of(left, top, right, bottom);
}
return margin;
return safeInsets;
}

private double statusBarMargin() {
return getSafeInsets().top;
}

private double navigationBarMargin() {
return sceneBottomMargin;
return getSafeInsets().bottom;
}

private void dimBrightness() {
Expand Down
4 changes: 1 addition & 3 deletions platform/android/src/ch/opengis/qfield/QFieldUtils.java
Original file line number Diff line number Diff line change
Expand Up @@ -483,11 +483,9 @@ public static String getExtensionFromMimeType(String type) {
// original script by SANJAY GUPTA
// (https://stackoverflow.com/questions/17546101/get-real-path-for-uri-android)
public static String getPathFromUri(final Context context, final Uri uri) {
final boolean isKitKat =
Build.VERSION.SDK_INT >= Build.VERSION_CODES.KITKAT;
String path = null;

if (isKitKat && DocumentsContract.isDocumentUri(context, uri)) {
if (DocumentsContract.isDocumentUri(context, uri)) {
// DocumentProvider
if (isExternalStorageDocument(uri)) {
// ExternalStorageProvider
Expand Down
2 changes: 1 addition & 1 deletion src/qml/qgismobileapp.qml
Original file line number Diff line number Diff line change
Expand Up @@ -41,7 +41,7 @@ ApplicationWindow {
id: mainWindow
objectName: 'mainWindow'
visible: true
flags: Qt.Window | Qt.WindowTitleHint | Qt.WindowSystemMenuHint | (sceneBorderless ? Qt.FramelessWindowHint : 0) | (Qt.platform.os === "ios" ? Qt.MaximizeUsingFullscreenGeometryHint : 0) | (Qt.platform.os !== "ios" && Qt.platform.os !== "android" ? Qt.WindowMinMaxButtonsHint | Qt.WindowCloseButtonHint : 0)
flags: Qt.Window | Qt.WindowTitleHint | Qt.WindowSystemMenuHint | (sceneBorderless ? Qt.FramelessWindowHint : 0) | (Qt.platform.os === "ios" || Qt.platform.os === "android" ? Qt.MaximizeUsingFullscreenGeometryHint : 0) | (Qt.platform.os !== "ios" && Qt.platform.os !== "android" ? Qt.WindowMinMaxButtonsHint | Qt.WindowCloseButtonHint : 0)

Material.theme: Theme.darkTheme ? "Dark" : "Light"
Material.accent: Theme.mainColor
Expand Down
Loading