Buckets:
NaTo1000/termux-app-bucket / termux-shared /src /main /java /com /termux /shared /view /ViewUtils.java
| package com.termux.shared.view; | |
| import android.app.Activity; | |
| import android.content.Context; | |
| import android.content.ContextWrapper; | |
| import android.content.res.Configuration; | |
| import android.graphics.Point; | |
| import android.graphics.Rect; | |
| import android.os.Build; | |
| import android.util.TypedValue; | |
| import android.view.View; | |
| import android.view.ViewGroup; | |
| import androidx.annotation.NonNull; | |
| import androidx.annotation.Nullable; | |
| import androidx.appcompat.app.ActionBar; | |
| import androidx.appcompat.app.AppCompatActivity; | |
| import com.termux.shared.logger.Logger; | |
| public class ViewUtils { | |
| /** Log root view events. */ | |
| public static boolean VIEW_UTILS_LOGGING_ENABLED = false; | |
| private static final String LOG_TAG = "ViewUtils"; | |
| /** | |
| * Sets whether view utils logging is enabled or not. | |
| * | |
| * @param value The boolean value that defines the state. | |
| */ | |
| public static void setIsViewUtilsLoggingEnabled(boolean value) { | |
| VIEW_UTILS_LOGGING_ENABLED = value; | |
| } | |
| /** | |
| * Check if a {@link View} is fully visible and not hidden or partially covered by another view. | |
| * | |
| * https://stackoverflow.com/a/51078418/14686958 | |
| * | |
| * @param view The {@link View} to check. | |
| * @param statusBarHeight The status bar height received by {@link View.OnApplyWindowInsetsListener}. | |
| * @return Returns {@code true} if view is fully visible. | |
| */ | |
| public static boolean isViewFullyVisible(View view, int statusBarHeight) { | |
| Rect[] windowAndViewRects = getWindowAndViewRects(view, statusBarHeight); | |
| if (windowAndViewRects == null) | |
| return false; | |
| return windowAndViewRects[0].contains(windowAndViewRects[1]); | |
| } | |
| /** | |
| * Get the {@link Rect} of a {@link View} and the {@link Rect} of the window inside which it | |
| * exists. | |
| * | |
| * https://stackoverflow.com/a/51078418/14686958 | |
| * | |
| * @param view The {@link View} inside the window whose {@link Rect} to get. | |
| * @param statusBarHeight The status bar height received by {@link View.OnApplyWindowInsetsListener}. | |
| * @return Returns {@link Rect[]} if view is visible where Rect[0] will contain window | |
| * {@link Rect} and Rect[1] will contain view {@link Rect}. This will be {@code null} | |
| * if view is not visible. | |
| */ | |
| public static Rect[] getWindowAndViewRects(View view, int statusBarHeight) { | |
| if (view == null || !view.isShown()) | |
| return null; | |
| boolean view_utils_logging_enabled = VIEW_UTILS_LOGGING_ENABLED; | |
| // windowRect - will hold available area where content remain visible to users | |
| // Takes into account screen decorations (e.g. statusbar) | |
| Rect windowRect = new Rect(); | |
| view.getWindowVisibleDisplayFrame(windowRect); | |
| // If there is actionbar, get his height | |
| int actionBarHeight = 0; | |
| boolean isInMultiWindowMode = false; | |
| Context context = view.getContext(); | |
| if (context instanceof AppCompatActivity) { | |
| ActionBar actionBar = ((AppCompatActivity) context).getSupportActionBar(); | |
| if (actionBar != null) actionBarHeight = actionBar.getHeight(); | |
| isInMultiWindowMode = (Build.VERSION.SDK_INT >= Build.VERSION_CODES.N) && ((AppCompatActivity) context).isInMultiWindowMode(); | |
| } else if (context instanceof Activity) { | |
| android.app.ActionBar actionBar = ((Activity) context).getActionBar(); | |
| if (actionBar != null) actionBarHeight = actionBar.getHeight(); | |
| isInMultiWindowMode = (Build.VERSION.SDK_INT >= Build.VERSION_CODES.N) && ((Activity) context).isInMultiWindowMode(); | |
| } | |
| int displayOrientation = getDisplayOrientation(context); | |
| // windowAvailableRect - takes into account actionbar and statusbar height | |
| Rect windowAvailableRect; | |
| windowAvailableRect = new Rect(windowRect.left, windowRect.top + actionBarHeight, windowRect.right, windowRect.bottom); | |
| // viewRect - holds position of the view in window | |
| // (methods as getGlobalVisibleRect, getHitRect, getDrawingRect can return different result, | |
| // when partialy visible) | |
| Rect viewRect; | |
| final int[] viewsLocationInWindow = new int[2]; | |
| view.getLocationInWindow(viewsLocationInWindow); | |
| int viewLeft = viewsLocationInWindow[0]; | |
| int viewTop = viewsLocationInWindow[1]; | |
| if (view_utils_logging_enabled) { | |
| Logger.logVerbose(LOG_TAG, "getWindowAndViewRects:"); | |
| Logger.logVerbose(LOG_TAG, "windowRect: " + toRectString(windowRect) + ", windowAvailableRect: " + toRectString(windowAvailableRect)); | |
| Logger.logVerbose(LOG_TAG, "viewsLocationInWindow: " + toPointString(new Point(viewLeft, viewTop))); | |
| Logger.logVerbose(LOG_TAG, "activitySize: " + toPointString(getDisplaySize(context, true)) + | |
| ", displaySize: " + toPointString(getDisplaySize(context, false)) + | |
| ", displayOrientation=" + displayOrientation); | |
| } | |
| if (isInMultiWindowMode) { | |
| if (displayOrientation == Configuration.ORIENTATION_PORTRAIT) { | |
| // The windowRect.top of the window at the of split screen mode should start right | |
| // below the status bar | |
| if (statusBarHeight != windowRect.top) { | |
| if (view_utils_logging_enabled) | |
| Logger.logVerbose(LOG_TAG, "Window top does not equal statusBarHeight " + statusBarHeight + " in multi-window portrait mode. Window is possibly bottom app in split screen mode. Adding windowRect.top " + windowRect.top + " to viewTop."); | |
| viewTop += windowRect.top; | |
| } else { | |
| if (view_utils_logging_enabled) | |
| Logger.logVerbose(LOG_TAG, "windowRect.top equals statusBarHeight " + statusBarHeight + " in multi-window portrait mode. Window is possibly top app in split screen mode."); | |
| } | |
| } else if (displayOrientation == Configuration.ORIENTATION_LANDSCAPE) { | |
| // If window is on the right in landscape mode of split screen, the viewLeft actually | |
| // starts at windowRect.left instead of 0 returned by getLocationInWindow | |
| viewLeft += windowRect.left; | |
| } | |
| } | |
| int viewRight = viewLeft + view.getWidth(); | |
| int viewBottom = viewTop + view.getHeight(); | |
| viewRect = new Rect(viewLeft, viewTop, viewRight, viewBottom); | |
| if (displayOrientation == Configuration.ORIENTATION_LANDSCAPE && viewRight > windowAvailableRect.right) { | |
| if (view_utils_logging_enabled) | |
| Logger.logVerbose(LOG_TAG, "viewRight " + viewRight + " is greater than windowAvailableRect.right " + windowAvailableRect.right + " in landscape mode. Setting windowAvailableRect.right to viewRight since it may not include navbar height."); | |
| windowAvailableRect.right = viewRight; | |
| } | |
| return new Rect[]{windowAvailableRect, viewRect}; | |
| } | |
| /** | |
| * Check if {@link Rect} r2 is above r2. An empty rectangle never contains another rectangle. | |
| * | |
| * @param r1 The base rectangle. | |
| * @param r2 The rectangle being tested that should be above. | |
| * @return Returns {@code true} if r2 is above r1. | |
| */ | |
| public static boolean isRectAbove( Rect r1, Rect r2) { | |
| // check for empty first | |
| return r1.left < r1.right && r1.top < r1.bottom | |
| // now check if above | |
| && r1.left <= r2.left && r1.bottom >= r2.bottom; | |
| } | |
| /** | |
| * Get device orientation. | |
| * | |
| * Related: https://stackoverflow.com/a/29392593/14686958 | |
| * | |
| * @param context The {@link Context} to check with. | |
| * @return {@link Configuration#ORIENTATION_PORTRAIT} or {@link Configuration#ORIENTATION_LANDSCAPE}. | |
| */ | |
| public static int getDisplayOrientation( Context context) { | |
| Point size = getDisplaySize(context, false); | |
| return (size.x < size.y) ? Configuration.ORIENTATION_PORTRAIT : Configuration.ORIENTATION_LANDSCAPE; | |
| } | |
| /** | |
| * Get device display size. | |
| * | |
| * @param context The {@link Context} to check with. It must be {@link Activity} context, otherwise | |
| * android will throw: | |
| * `java.lang.IllegalArgumentException: Used non-visual Context to obtain an instance of WindowManager. Please use an Activity or a ContextWrapper around one instead.` | |
| * @param activitySize The set to {@link true}, then size returned will be that of the activity | |
| * and can be smaller than physical display size in multi-window mode. | |
| * @return Returns the display size as {@link Point}. | |
| */ | |
| public static Point getDisplaySize( Context context, boolean activitySize) { | |
| // android.view.WindowManager.getDefaultDisplay() and Display.getSize() are deprecated in | |
| // API 30 and give wrong values in API 30 for activitySize=false in multi-window | |
| androidx.window.WindowManager windowManager = new androidx.window.WindowManager(context); | |
| androidx.window.WindowMetrics windowMetrics; | |
| if (activitySize) | |
| windowMetrics = windowManager.getCurrentWindowMetrics(); | |
| else | |
| windowMetrics = windowManager.getMaximumWindowMetrics(); | |
| return new Point(windowMetrics.getBounds().width(), windowMetrics.getBounds().height()); | |
| } | |
| /** Convert {@link Rect} to {@link String}. */ | |
| public static String toRectString(Rect rect) { | |
| if (rect == null) return "null"; | |
| return "(" + rect.left + "," + rect.top + "), (" + rect.right + "," + rect.bottom + ")"; | |
| } | |
| /** Convert {@link Point} to {@link String}. */ | |
| public static String toPointString(Point point) { | |
| if (point == null) return "null"; | |
| return "(" + point.x + "," + point.y + ")"; | |
| } | |
| /** Get the {@link Activity} associated with the {@link Context} if available. */ | |
| public static Activity getActivity(Context context) { | |
| while (context instanceof ContextWrapper) { | |
| if (context instanceof Activity) { | |
| return (Activity)context; | |
| } | |
| context = ((ContextWrapper)context).getBaseContext(); | |
| } | |
| return null; | |
| } | |
| /** Convert value in device independent pixels (dp) to pixels (px) units. */ | |
| public static float dpToPx(Context context, float dp) { | |
| return TypedValue.applyDimension(TypedValue.COMPLEX_UNIT_DIP, dp, context.getResources().getDisplayMetrics()); | |
| } | |
| /** Convert value in pixels (px) to device independent pixels (dp) units. */ | |
| public static float pxToDp(Context context, float px) { | |
| return px / context.getResources().getDisplayMetrics().density; | |
| } | |
| public static void setLayoutMarginsInDp( View view, int left, int top, int right, int bottom) { | |
| Context context = view.getContext(); | |
| setLayoutMarginsInPixels(view, (int) dpToPx(context, left), (int) dpToPx(context, top), | |
| (int) dpToPx(context, right), (int) dpToPx(context, bottom)); | |
| } | |
| public static void setLayoutMarginsInPixels( View view, int left, int top, int right, int bottom) { | |
| if (view.getLayoutParams() instanceof ViewGroup.MarginLayoutParams) { | |
| ViewGroup.MarginLayoutParams params = (ViewGroup.MarginLayoutParams) view.getLayoutParams(); | |
| params.setMargins(left, top, right, bottom); | |
| view.setLayoutParams(params); | |
| } | |
| } | |
| } | |
Xet Storage Details
- Size:
- 11.6 kB
- Xet hash:
- 2c4cef399ef145ed887431fbbe79d54e5f4803bda0d0e29aa4dc7266f68e4687
·
Xet efficiently stores files, intelligently splitting them into unique chunks and accelerating uploads and downloads. More info.