android dp, px 해상도 변환
// PX ---> DP public static int getPixelToDp(Context context, int pixel) { float dp = 0; try { DisplayMetrics metrics = context.getResources().getDisplayMetrics(); dp = pixel / (metrics.densityDpi / 160f); } catch (Exception e) { } return (int) dp; } // DP ---> PX public static int getDpToPixel(Context context, int DP) { float px = 0; try { px = TypedValue.applyDimension(TypedValue.COMPLEX_UNIT_DIP, DP, context.getResources().getDisplayMetrics()); } catch (Exception e) { } return (int) px; } // DP ---> PX public static int getDpToPixel(Context context, float DP) { float px = 0; try { px = TypedValue.applyDimension(TypedValue.COMPLEX_UNIT_DIP, DP, context.getResources().getDisplayMetrics()); } catch (Exception e) { } return (int) px; }
안드로이드 폰 해상도 구하기
private void getDisplayInfo() { DisplayMetrics displayMetrics = new DisplayMetrics(); getWindowManager().getDefaultDisplay().getMetrics(displayMetrics); int deviceWidth = displayMetrics.widthPixels; int deviceHeight = displayMetrics.heightPixels; // 꼭 넣어 주어야 한다. 이렇게 해야 displayMetrics가 세팅이 된다. getWindowManager().getDefaultDisplay().getMetrics(displayMetrics); System.out.println("displayMetrics.density : " + displayMetrics.density); System.out.println("deviceWidth(px) : " + deviceWidth + ", deviceHeight(px) : " + deviceHeight); DisplayMetrics metrics = new DisplayMetrics(); ((WindowManager) mContext.getSystemService(Context.WINDOW_SERVICE)).getDefaultDisplay().getMetrics(metrics); // constant 값: DENSITY_LOW 120, DENSITY_MEDIUM 160, DENSITY_HIGH 240 int density = metrics.densityDpi; System.out.println("density : " + density); int dipWidth = (int) (deviceWidth / displayMetrics.density); int dipHeight = (int) (deviceHeight / displayMetrics.density); System.out.println("dipWidth(dp) : " + dipWidth + ", dipHeight(dp) : " + dipHeight); }
안드로이드 2013/01/15 19:11 http://javacan.tistory.com/233
안드로이드를 좀 더 잘 해 보기 위해 기초를 다지고 있는데, 그 중 첫 번째로 공부하고 있는 부분이 해상도 및 레이아웃과 관련된 내용이다.
안드로이드의 주요 단위
안드로이드 기기들이 해상도와 물리적인 크기가 저마다 다르기 때문에, UI 레이아웃을 기기별로 깨지지 않게 만들어주려면 주요 단위에 대한 이해가 필요하다. 다음은 안드로이드 개발시 알아야 하는 용어/단위를 정리한 것이다.
용어 및 단위 |
설명 |
Pixel |
화면상의 픽셀 |
해상도(Resolution) |
픽셀 단위의 화면 크기. 예를 들어, 갤럭시노트 10.1의 해상도는 1280*800인데, 이는 픽셀이 1280개 및 800개임을 의미한다. |
DPI (Dots Per Inch) / 밀도 |
물리적인 1 인치 당 포함되는 픽셀 개수. 예를 들어, 160 DPI는 1인당 픽셀이 160개 포함된다는 것을 의미한다. 주요 DPI는 다음과 같다. - LDPI (low) : 120 DPI - MDPI (medium) : 160 DPI - TVDPI : 213 DPI - HDPI (high) : 240 DPI - XHDPI (extra high) : 320 DPI |
스크린 크기 |
물리적인 크기의 종류를 나타낸다. 다음의 4종류가 존재한다. - X-Large: 주로 10.1 인치 이상의 디바이스 - Large: 주로 5인치 이상의 디바이스 - Normal: 3인치에서 5인치 미만의 사이의 디바이스 - Small: 3인치 미만의 디바이스 |
px |
픽셀 기반의 단위 |
dip (density-independent pixels) 또는 dp |
밀도 독립 단위로, 장치의 밀도에 상관없이 물리적으로 (거의) 동일한 크기를 갖는다. |
sp (scale-independent pixels) |
스케일 독립 픽셀 단위로 , dip와 유사하며, 글꼴 크기를 지정할 때 주로 사용된다. |
실제 테스트 해 볼 수 있는 기기별로 확인해보니 주요 값은 다음과 같았다.
|
갤럭시노트 10.1 |
옵LTE 2 |
넥서스7 |
옵Q |
해상도 (픽셀단위) |
800 x 1280 |
720 x 1280 |
800 x 1280 |
480 x 800 |
해상도 (DP 단위) |
800 x 1280 |
360 x 640 |
600 x 961 |
320 x 533 |
DPI |
160 DPI (mdpi) |
320 DPI (xhdpi) |
213 DPI |
240 DPI |
스크린 크기 |
xlarge |
normal |
large |
normal |
밀도 비율 (DPI / 160) |
1 |
2 |
1.331250 |
1.5 |
안드로이드의 기준 DPI는 중간 수준인 160 DPI이다. 160 DPI를 기준으로 DPI가 크면 밀도가 높아지고, DPI가 작으면 밀도가 낮아진다. 또한, 160 DPI인 경우 밀도독립 단위인 DP(DIP)와 픽셀이 같은 크기를 갖는다. 즉, 160 DPI에서 1 DP는 1 PX이 된다.
PX와 DP
옵LTE2와 넥서스7 그리고 갤럭시노트 10.1에서 트위터를 실행해보면, 기기의 크기는 다르지만, 상단 바 부분의 물리적 높이가 동일한 것을 확인할 수 있다. 또한, 글자 크기도 동일한 것을 확인할 수 있다.
[옵티머스LTE2(좌)와 넥서스7(우)에서 트위터를 실행한 화면. 상단 바와 메뉴의 높이가 (거의) 같다]
위 그림에서 두 기기의 높이 해상도는 1280이지만, 물리적인 크기는 넥서스7이 더 크다. 따라서, 위 그림에서 실제 px 단위의 높이 값은 좌측의 옵티머스LTE2가 넥서스7보다 커야 위와 같이 물리적으로 동일한 크기로 표시된다. 모든 기기마다 물리적으로 동일한 높이를 갖는 px 값을 구해서 계산한다는 것은 매우 힘든데, dp 단위를 사용하면 위 그림처럼 기기의 크기에 상관없이 물리적으로 동일한 크기로 레이아웃을 구성할 수 있다.
XML 레이아웃 설정 파일에서 dp 단위로 크기를 지정하면, 안드로이드는 내부적으로 알맞은 px 단위로 값을 변환해서 크기를 구성한다. 따라서, 개발자는 dp 단위를 사용해서 물리적으로 동일한 크기를 갖는 레이아웃을 구성할 수 있다.
코드에서 직접 크기를 설정하는 경우에는 픽셀 단위로 지정하게 되는데, 이 경우 다음의 공식을 이용해서 dp 단위의 값을 px 단위의 값으로 변환할 수 있다.
px = dp * (DPI / 160)
기기의 DPI 구하기
dp 단위의 값으로부터 px 단위의 값을 구하려면 기기의 DPI를 구해야 하는데, 다음의 코드를 이용하면 DPI를 구할 수 있다.
Display dis = ((WindowManager) getSystemService(WINDOW_SERVICE)).getDefaultDisplay();
DisplayMetrics metrics = new DisplayMetrics();
dis.getMetrics(metrics);
// 해상도: dis.getWidth() * dis.getHeight() / metrics.widthPixels * metrics.heightPixels
// DPI: metrics.densityDpi
// 밀도비율 (DPI / 160) : metrics.density
참고자료
- 기기별 DPI/해상도/크기 등: http://developer.android.com/tools/revisions/platforms.html
- Supporting Multiple Screens: http://developer.android.com/guide/practices/screens_support.html
'안드로이드 개발 팁' 카테고리의 다른 글
android 페이지 목록 동적으로 처리하기 (0) | 2014.05.29 |
---|---|
android textview setlayoutparams programmatically (0) | 2014.05.29 |
Android Custom Keyboard 예제2 (0) | 2014.05.20 |
Android Custom Keyboard 예제 (2) | 2014.05.19 |
android 색칠하기 알고리즘 (0) | 2014.05.13 |