Android에서 런타임에 dp 또는 dip로 화면 너비를 결정하는 방법은 무엇입니까?


194

dip / dp (Java 파일)를 사용하여 안드로이드 위젯의 레이아웃을 코딩해야합니다. 내가 코딩하면 런타임에

int pixel=this.getWindowManager().getDefaultDisplay().getWidth();

화면 너비를 픽셀 단위로 반환합니다 (px). 이것을 dp로 변환하려면 코딩했습니다.

int dp =pixel/(int)getResources().getDisplayMetrics().density ;

정답을 반환하지 않는 것 같습니다. 화면 해상도가 480 x 800 인 WVGA800의 에뮬레이터를 만들었습니다. 에뮬레이터를 실행하고 코드가 픽셀과 dp의 값을 인쇄하게하면 둘 다 320이되었습니다. 이 에뮬레이터는 240dpi이며 배율은 0.75입니다.

답변:


378

이 시도

Display display = getWindowManager().getDefaultDisplay();
DisplayMetrics outMetrics = new DisplayMetrics ();
display.getMetrics(outMetrics);

float density  = getResources().getDisplayMetrics().density;
float dpHeight = outMetrics.heightPixels / density;
float dpWidth  = outMetrics.widthPixels / density;

또는

감사합니다 @ Tomáš Hubálek

DisplayMetrics displayMetrics = context.getResources().getDisplayMetrics();    
float dpHeight = displayMetrics.heightPixels / displayMetrics.density;
float dpWidth = displayMetrics.widthPixels / displayMetrics.density;

91
왜 WindowManager를 호출해야합니까? 이 코드는 어떻습니까? DisplayMetrics displayMetrics = resources.getDisplayMetrics (); float screenWidthDp = displayMetrics.widthPixels / displayMetrics.density;
— Tomáš Hubálek

2
매우 높은 밀도의 화면을 사용하면 효과가 없었습니다. 마치 화면의 작은 부분 만있는 것처럼 보입니다. 이 솔루션은 저에게 효과적 이었습니다. stackoverflow.com/a/18712361/956975 Display display = getWindowManager (). getDefaultDisplay (); 포인트 크기 = new Point (); display.getSize (크기); int 너비 = size.x; int 높이 = size.y;
— marienke '12

1
@dsdsdsdsd : context는 Context 클래스의 인스턴스입니다. 특히 Activity는 Context의 하위 클래스이므로 Activity에서 이것을 사용하고 Fragment에서 getActivity ()를 사용하십시오. 응용 프로그램 및 서비스도 컨텍스트의 하위 클래스입니다.
— François POYER

112

Google 에서이 질문을 우연히 발견 한 후 나중에 API> = 13에 유효한 쉬운 솔루션을 찾았습니다.

향후 참조를 위해 :

Configuration configuration = yourActivity.getResources().getConfiguration();
int screenWidthDp = configuration.screenWidthDp; //The current width of the available screen space, in dp units, corresponding to screen width resource qualifier.
int smallestScreenWidthDp = configuration.smallestScreenWidthDp; //The smallest screen size an application will see in normal operation, corresponding to smallest screen width resource qualifier.

참조 구성 클래스 참조

편집 : Nick Baicoianu가 지적했듯이 화면 의 사용 가능한 너비 / 높이를 반환합니다 (대부분의 경우 흥미로운 것이어야 함). 실제 디스플레이 크기 가 필요한 경우 상단 답변에 충실하십시오.


23
Configuration의 screenWidthDp / screenHeightDp와 DisplayMetrics widthPixels / heightPixels를 사용하는 것의 중요한 차이점 중 하나는 Configuration에서 사용 가능한 디스플레이 크기 (상태 표시 줄 등을 뺀 값)를 반환하는 반면 DisplayMetrics는 전체 화면 크기를 반환한다는 것입니다.
— Nick Baicoianu

이것은 API 레벨 13 이상에만 해당됩니다
— ono

@NickBaicoianu의 설명에 추가하기 위해 getConfiguration () 및 getDisplayMetrics () 메소드는 다중 창 모드에서 작동합니다. 즉, 크기는 화면이 아닌 창의 크기를 반영합니다.
— nmw

7

기본 밀도 값 160이 누락되었습니다.

    2 px = 3 dip if dpi == 80(ldpi), 320x240 screen
    1 px = 1 dip if dpi == 160(mdpi), 480x320 screen
    3 px = 2 dip if dpi == 240(hdpi), 840x480 screen

즉, 세로 모드에서 너비가 160dip 인 레이아웃을 디자인하면 모든 ldpi / mdpi / hdpi 장치에서 화면의 절반이됩니다 (태블릿 제외).


당신이 대답 한 것은 내 질문의 논리적 인 추론입니다. 이해합니다. 런타임에 화면 해상도에 상관없이 올바른 dpi 너비가 코드에 의해 선택되도록 Java로 어떻게 코딩해야합니까?
— Khushboo

이번에 잘 이해하기를 바랍니다 :) DisplayMetrics outMetrics = null; getWindowManager().getDefaultDisplay().getMetrics(outMetrics);활동 내에서 사용하십시오 . 그런 outMetrics.density당신에게에 명시된 바와 같이 현재 장치의 규모 계수 줄 것이다 문서
— Mykhailo Gaidai

6

대신 이것을 사용하는 것은 어떻습니까?

final DisplayMetrics displayMetrics=getResources().getDisplayMetrics();
final float screenWidthInDp=displayMetrics.widthPixels/displayMetrics.density;
final float screenHeightInDp=displayMetrics.heightPixels/displayMetrics.density;

6
DisplayMetrics displayMetrics = new DisplayMetrics();

getWindowManager().getDefaultDisplay().getMetrics(displayMetrics);

int width_px = Resources.getSystem().getDisplayMetrics().widthPixels;

int height_px =Resources.getSystem().getDisplayMetrics().heightPixels;

int pixeldpi = Resources.getSystem().getDisplayMetrics().densityDpi;


int width_dp = (width_px/pixeldpi)*160;
int height_dp = (height_px/pixeldpi)*160;

8
설명을 고려해보십시오
— 큰 현상금

5

kotlin의 답변 :

  context?.let {
        val displayMetrics = it.resources.displayMetrics
        val dpHeight = displayMetrics.heightPixels / displayMetrics.density
        val dpWidth = displayMetrics.widthPixels / displayMetrics.density
    }

4

Kotlin을 위해 단순화 :

val widthDp = resources.displayMetrics.run { widthPixels / density }
val heightDp = resources.displayMetrics.run { heightPixels / density }

2

DP로 화면 너비와 높이를 얻으십시오.

1 단계 : 인터페이스 생성

public interface ScreenInterface {

   float getWidth();

   float getHeight();

}

2 단계 : 구현 자 클래스 작성

public class Screen implements ScreenInterface {
    private Activity activity;

    public Screen(Activity activity) {
        this.activity = activity;
    }

    private DisplayMetrics getScreenDimension(Activity activity) {
        DisplayMetrics displayMetrics = new DisplayMetrics();
        activity.getWindowManager().getDefaultDisplay().getMetrics(displayMetrics);
        return displayMetrics;
    }

    private float getScreenDensity(Activity activity) {
        return activity.getResources().getDisplayMetrics().density;
    }

    @Override
    public float getWidth() {
        DisplayMetrics displayMetrics = getScreenDimension(activity);
        return displayMetrics.widthPixels / getScreenDensity(activity);
    }

    @Override
    public float getHeight() {
        DisplayMetrics displayMetrics = getScreenDimension(activity);
        return displayMetrics.heightPixels / getScreenDensity(activity);
    }
} 

3 단계 : 활동에서 너비와 높이를 가져옵니다.

Screen screen = new Screen(this); // Setting Screen
screen.getWidth();
screen.getHeight();

높이 또는 너비를 픽셀 또는 dp로 반환합니까?
— Taslim Oseni

.density라고 불리는 이유는 그것이 DP에서 당신에게주는 이유입니다
— Ali Azaz Alam

간단한 작업을 해결하기 위해 앱에 코드 톤을 추가하는 것은 좋은 생각이 아닙니다.
— Ruslan Berozov

선생님은 클래스를 구현할 것인지 직접 코딩 할 것인지에 달려 있습니다. 정의 된 클래스에서 직접 구현할 코드를 쉽게 추출 할 수 있습니다.
— Ali Azaz Alam

0

화면 너비 만 알고 싶다면 개발자 옵션에서 "가장 작은 화면 너비"를 검색하면됩니다. 편집 할 수도 있습니다.


0

이 시도:

Display display   = getWindowManager().getDefaultDisplay();
Point displaySize = new Point();
display.getSize(displaySize);
int width  = displaySize.x;
int height = displaySize.y;

-5

문제는 float를 int로 캐스팅하여 정밀도를 잃는 것입니다. 또한 인자와 곱해야하며 나누지 않아야합니다.

이 작업을 수행:

int dp = (int)(pixel*getResources().getDisplayMetrics().density);

3
이 답변은 잘못되었습니다. 에서 developer.android.com/guide/practices/... , 화소 DP * 밀도 =.
— Vance-Turner
당사 사이트를 사용함과 동시에 당사의 쿠키 정책과 개인정보 보호정책을 읽고 이해하였음을 인정하는 것으로 간주합니다.
Licensed under cc by-sa 3.0 with attribution required.