Как я могу определить размер экрана программно,
в единицах, используемых событиями касания
и Просмотр измерения/компоновки?
Другими словами, мне нужны координаты
в правом нижнем углу экрана,
в системе координат, используемой сенсорными событиями "
getRawX()/getRawY()
и View.getLocationOnScreen()
.
Я не решаюсь вызывать нужные единицы измерения/просмотра "пикселей" поскольку, очевидно, существует несколько понятий "пикселей" , на моем телефоне в различных режимах, и они не дополняют последовательную историю.
Я вижу, что это было задано и много ответили на stackoverflow и в других местах, но ни один из ответов не работает на моем телефоне (droid 4, android 4.1.2) во всех режимах:
- Могу ли я узнать ширину экрана программно в приложении Android?
- Как я могу получить ScreenSize программно в android
- Android set Просмотр видимости программно на основе размера экрана
- Как получить высоту экрана в Android?
- Получить высоту экрана в Android
- https://groups.google.com/forum/#!topic/android-developers/IpxnfvDFrpc
- http://shuklaxyz.blogspot.com/2012/02/how-to-programmatically-figure-out.html
- http://coderock.net/how-to-determine-screen-resolution-programmatically/
- http://www.codeproject.com/Tips/313848/Get-actual-screen-size-for-the-application-layout
- Android и установка ширины и высоты программно в единицах dp
- http://www.simplecodestuffs.com/how-to-get-screen-dimensions-programmatically-in-android/
- http://www.androidsnippets.com/get-size-and-orientation-of-the-screen
- http://grokbase.com/t/gg/android-developers/127aatfqb6/how-to-determine-screen-resolution-programmatically
(вау!)
Это код библиотеки, который должен работать независимо от того, находится ли приложение в режиме совместимости с экраном, (т.е. targetSdkVersion <= 10 в манифесте) или нет, и я также не хочу делать никаких предположений о позиции, размере или наличии строки состояния или любые другие подобные декорации экрана.
Вот факты:
-
мой телефон (дроид 4 работает андроид 4.1.2) имеет 540x960 физических пикселей, то есть маленькие цветные светящиеся точки.
-
размер экрана в желаемых единицах, от просмотра событий касания и просмотра измерений, является 360x640, когда приложение находится в режиме сопоставления экрана, 540x960, когда приложение не находится в режиме сопоставления экрана. Это числа, которые мне нужно найти программно, без отбрасывания событиями касания или представлениями, чтобы найти их, но мне очень сложно найти какой-либо API которые вернут эти числа.
-
Полученные объекты Display и DisplayMetrics в разных отношениях все утверждают, что размер экрана 540x960 "пикселей" (в режиме сопоставления экрана или нет). Чтобы быть конкретным, все говорят 540x960 все время: DisplayMetrics. {Ширина, высота} Пиксели, Display.getSize(), Display.getRealSize(), Display.get {ширина, высота}(),
-
Объекты конфигурации, полученные различными способами все говорят экран {Ширина, Высота} Dp = 360x614 (в режиме сопоставления экрана или нет). Я не считаю, что это весь экран, так как соотношение сторон неверно. (Я думаю, что весь экран минус строка состояния; Мне нужен весь экран.) Я думаю, что можно с уверенностью сказать, что весь экран 360x640 dp, хотя я не знаю API, который возвращает это 640.
-
DisplayMetrics, полученный различными способами скажем, "плотность" 1.0f, когда в режиме сопоставления экрана, 1.5f, если не в режиме сопоставления экрана.
-
Деятельность
getWindow().getAttributes().{width,height}
не является полезным, поскольку он обычно содержитMATCH_PARENT
а не фактические размеры. Но я, видимо, могу получить желаемый ответ отgetWindow().getDecorView().getMeasured{Width,Height}()
(что на самом деле удивительно, поскольку окно активности decorView не похоже, что он занимает весь экран; похоже, что он занимает экран минус строка состояния). Но я не хочу полагаться на это, потому что если окно когда-либо будет изменено (появляется мягкая клавиатура? кто-то вызывает window.setAttributes()? или, может быть, я вообще не занимаюсь деятельностью), это, очевидно, будет неправильным.
Я понимаю, что предполагается следующая формула: пикселей = плотность dp * Это, похоже, согласуется со всеми представленными числами ((3), (4), (5) выше) если не в режиме совместимости с экраном: 540x960 = 360x640 * 1,5 Но в режиме совместимости с экраном он не складывается: 540x960!= 360x640 * 1 Итак, что-то не так.
Простейшее объяснение, я думаю, заключается в том, что методы, перечисленные в (3) выше просто дают неправильный ответ для "пикселей" , когда в режиме сопоставления экрана, то есть они были предназначены для возврата 360x640 "пикселей" , но они ошибочно возвращают 540x960 вместо этого. Но могут быть и другие способы взглянуть на это.
В любом случае, получение желаемых номеров независимо от режима, из вышеупомянутых кусочков головоломки, безусловно, сложная головоломка. Я нашел способ, который, кажется, работает на моем телефоне в обоих режимах, но это очень круто, и он полагается на два предположения, которые по-прежнему кажутся довольно шаткими (как описано в комментариях кода ниже).
Вот мой рецепт:
/** get screen size in "pixels", i.e. touchevent/view units.
* on my droid 4, this is 360x640 or 540x960
* depending on whether the app is in screen compatibility mode
* (i.e. targetSdkVersion<=10 in the manifest) or not. */
public void getScreenSizePixels(int widthHeightInPixels[/*2*/])
{
Resources resources = getResources();
Configuration config = resources.getConfiguration();
DisplayMetrics dm = resources.getDisplayMetrics();
// Note, screenHeightDp isn't reliable
// (it seems to be too small by the height of the status bar),
// but we assume screenWidthDp is reliable.
// Note also, dm.widthPixels,dm.heightPixels aren't reliably pixels
// (they get confused when in screen compatibility mode, it seems),
// but we assume their ratio is correct.
double screenWidthInPixels = (double)config.screenWidthDp * dm.density;
double screenHeightInPixels = screenWidthInPixels * dm.heightPixels / dm.widthPixels;
widthHeightInPixels[0] = (int)(screenWidthInPixels + .5);
widthHeightInPixels[1] = (int)(screenHeightInPixels + .5);
}
Есть ли лучший/чистый способ найти размер экрана?