|
11 | 11 |
|
12 | 12 | import javax.annotation.Nullable; |
13 | 13 |
|
| 14 | +import java.lang.reflect.InvocationTargetException; |
| 15 | +import java.lang.reflect.Method; |
14 | 16 | import java.util.Arrays; |
15 | 17 | import java.util.List; |
16 | 18 | import java.util.Map; |
17 | 19 |
|
| 20 | +import android.content.Context; |
| 21 | +import android.os.Build; |
18 | 22 | import android.util.DisplayMetrics; |
| 23 | +import android.view.Display; |
| 24 | +import android.view.WindowManager; |
19 | 25 |
|
20 | 26 | import com.facebook.csslayout.CSSLayoutContext; |
21 | 27 | import com.facebook.infer.annotation.Assertions; |
@@ -84,7 +90,9 @@ public UIManagerModule( |
84 | 90 | UIImplementation uiImplementation) { |
85 | 91 | super(reactContext); |
86 | 92 | mEventDispatcher = new EventDispatcher(reactContext); |
87 | | - DisplayMetrics displayMetrics = reactContext.getResources().getDisplayMetrics(); |
| 93 | + |
| 94 | + DisplayMetrics displayMetrics = getDisplayMetrics(); |
| 95 | + |
88 | 96 | DisplayMetricsHolder.setDisplayMetrics(displayMetrics); |
89 | 97 | mModuleConstants = createConstants(displayMetrics, viewManagerList); |
90 | 98 | mUIImplementation = uiImplementation; |
@@ -452,4 +460,39 @@ public EventDispatcher getEventDispatcher() { |
452 | 460 | public void sendAccessibilityEvent(int tag, int eventType) { |
453 | 461 | mUIImplementation.sendAccessibilityEvent(tag, eventType); |
454 | 462 | } |
| 463 | + |
| 464 | + private DisplayMetrics getDisplayMetrics() { |
| 465 | + Context context = getReactApplicationContext(); |
| 466 | + |
| 467 | + DisplayMetrics displayMetrics = context.getResources().getDisplayMetrics(); |
| 468 | + WindowManager wm = (WindowManager) context.getSystemService(Context.WINDOW_SERVICE); |
| 469 | + Display display = wm.getDefaultDisplay(); |
| 470 | + |
| 471 | + // Get the real display metrics if we are using API level 17 or higher. |
| 472 | + // The real metrics include system decor elements (e.g. soft menu bar). |
| 473 | + // |
| 474 | + // See: http://developer.android.com/reference/android/view/Display.html#getRealMetrics(android.util.DisplayMetrics) |
| 475 | + if (Build.VERSION.SDK_INT >= 17){ |
| 476 | + display.getRealMetrics(displayMetrics); |
| 477 | + |
| 478 | + } else { |
| 479 | + // For 14 <= API level <= 16, we need to invoke getRawHeight and getRawWidth to get the real dimensions. |
| 480 | + // Since react-native only supports API level 16+ we don't have to worry about other cases. |
| 481 | + // |
| 482 | + // Reflection exceptions are rethrown at runtime. |
| 483 | + // |
| 484 | + // See: http://stackoverflow.com/questions/14341041/how-to-get-real-screen-height-and-width/23861333#23861333 |
| 485 | + try { |
| 486 | + Method mGetRawH = Display.class.getMethod("getRawHeight"); |
| 487 | + Method mGetRawW = Display.class.getMethod("getRawWidth"); |
| 488 | + displayMetrics.widthPixels = (Integer) mGetRawW.invoke(display); |
| 489 | + displayMetrics.heightPixels = (Integer) mGetRawH.invoke(display); |
| 490 | + } catch (InvocationTargetException | IllegalAccessException | NoSuchMethodException e) { |
| 491 | + throw new RuntimeException("Error getting real dimensions for API level < 17", e); |
| 492 | + } |
| 493 | + } |
| 494 | + |
| 495 | + return displayMetrics; |
| 496 | + } |
| 497 | + |
455 | 498 | } |
0 commit comments