解像度がのPantechデバイス用にピクセル単位で指定された高さと幅でアプリケーションを作成しました480x800
。
G1デバイスの高さと幅を変換する必要があります。
それをdpに変換すると問題が解決し、両方のデバイスに同じ解決策が提供されると思いました。
ピクセルをdpに変換する簡単な方法はありますか?
助言がありますか?
解像度がのPantechデバイス用にピクセル単位で指定された高さと幅でアプリケーションを作成しました480x800
。
G1デバイスの高さと幅を変換する必要があります。
それをdpに変換すると問題が解決し、両方のデバイスに同じ解決策が提供されると思いました。
ピクセルをdpに変換する簡単な方法はありますか?
助言がありますか?
回答:
// Converts 14 dip into its equivalent px
float dip = 14f;
Resources r = getResources();
float px = TypedValue.applyDimension(
TypedValue.COMPLEX_UNIT_DIP,
dip,
r.getDisplayMetrics()
);
applyDimension
ですか?だけでもいいgetResource().getDisplayMetrics()
ですか、それとも他に何かありますか?
Context
オブジェクトにアクセスできない場合Resources.getSystem().getDisplayMetrics()
/**
* This method converts dp unit to equivalent pixels, depending on device density.
*
* @param dp A value in dp (density independent pixels) unit. Which we need to convert into pixels
* @param context Context to get resources and device specific display metrics
* @return A float value to represent px equivalent to dp depending on device density
*/
public static float convertDpToPixel(float dp, Context context){
return dp * ((float) context.getResources().getDisplayMetrics().densityDpi / DisplayMetrics.DENSITY_DEFAULT);
}
/**
* This method converts device specific pixels to density independent pixels.
*
* @param px A value in px (pixels) unit. Which we need to convert into db
* @param context Context to get resources and device specific display metrics
* @return A float value to represent dp equivalent to px value
*/
public static float convertPixelsToDp(float px, Context context){
return px / ((float) context.getResources().getDisplayMetrics().densityDpi / DisplayMetrics.DENSITY_DEFAULT);
}
Resource.getSystem()
強調鉱山)のドキュメントから:「システムリソースのみ(アプリケーションリソースなし)へのアクセスを提供し、現在の画面に対して構成されていない(ディメンション単位を使用できない、変更されない)グローバル共有リソースオブジェクトを返すオリエンテーションなどに基づく)。」
なるべくUtil.javaクラスに入れる
public static float dpFromPx(final Context context, final float px) {
return px / context.getResources().getDisplayMetrics().density;
}
public static float pxFromDp(final Context context, final float dp) {
return dp * context.getResources().getDisplayMetrics().density;
}
float density = context.getResources().getDisplayMetrics().density;
float px = someDpValue * density;
float dp = somePxValue / density;
density
等しい
.75
オンldpi
(120
dpi)1.0
オンmdpi
(160
dpi;ベースライン)1.5
オンhdpi
(240
dpi)2.0
オンxhdpi
(320
dpi)3.0
オンxxhdpi
(480
dpi)4.0
オンxxxhdpi
(640
dpi)このオンラインコンバーターを使用するをて、dpi値をいじってください。
編集:dpi
バケットとの間に1対1の関係はないようdensity
です。以下のように見えますNexus 5X
ビーイングがxxhdpi
持っているdensity
の値2.625
(の代わりに3
)。Device Metricsをご覧ください。
あなたはこれを使うことができます.. コンテキストなし
public static int pxToDp(int px) {
return (int) (px / Resources.getSystem().getDisplayMetrics().density);
}
public static int dpToPx(int dp) {
return (int) (dp * Resources.getSystem().getDisplayMetrics().density);
}
@Stanが述べたように、システムが密度を変更すると、このアプローチを使用すると問題が発生する可能性があります。そのことに注意してください!
個人的には、コンテキストを使用してそれを行っています。それは私があなたと共有したかったちょうど別のアプローチです
ディメンションXMLを使用できる場合、それは非常に簡単です。
あなたのres/values/dimens.xml
:
<?xml version="1.0" encoding="utf-8"?>
<resources>
<dimen name="thumbnail_height">120dp</dimen>
...
...
</resources>
次に、Javaで:
getResources().getDimensionPixelSize(R.dimen.thumbnail_height);
Android開発ガイドによると:
px = dp * (dpi / 160)
しかし、ピクセルで記述されたデザインを受け取ったときに、これを逆に実行したいことがよくあります。そう:
dp = px / (dpi / 160)
240dpiのデバイスを使用している場合、この比率は1.5(前述のとおり)であるため、60pxのアイコンはアプリケーションで40dpに相当します。
Context
エレガントな静的メソッドなし:
public static int dpToPx(int dp)
{
return (int) (dp * Resources.getSystem().getDisplayMetrics().density);
}
public static int pxToDp(int px)
{
return (int) (px / Resources.getSystem().getDisplayMetrics().density);
}
Resources.getSystem()
javadocは、「システムリソースのみ(アプリケーションリソースなし)へのアクセスを提供し、現在の画面に対して構成されていない(寸法単位を使用できない、方向に基づいて変更されないなど)グローバル共有リソースオブジェクトを返す」と述べています。これは、たとえそれが何らかの方法で機能したとしても、これを行うべきではないと言っています。
したがって、次の公式を使用して、dpで指定された次元から適切なピクセル数を計算できます。
public int convertToPx(int dp) {
// Get the screen's density scale
final float scale = getResources().getDisplayMetrics().density;
// Convert the dps to pixels, based on density scale
return (int) (dp * scale + 0.5f);
}
convertToDp
。
Kotlinを使用しているユーザー向け:
val Int.toPx: Int
get() = (this * Resources.getSystem().displayMetrics.density).toInt()
val Int.toDp: Int
get() = (this / Resources.getSystem().displayMetrics.density).toInt()
使用法:
64.toPx
32.toDp
Android SDKにはデフォルトのユーティリティがあります:http : //developer.android.com/reference/android/util/TypedValue.html
float resultPix = TypedValue.applyDimension(TypedValue.COMPLEX_UNIT_DIP,1,getResources().getDisplayMetrics())
resultPix
int型である必要があります。int resultPix = (int) TypedValue.applyDimension(TypedValue.COMPLEX_UNIT_DIP,1,getResources().getDisplayMetrics())
kotlin-extensionを使用すると、より良い
fun Int.toPx(context: Context): Int = (this * context.resources.displayMetrics.density).toInt()
fun Int.toDp(context: Context): Int = (this / context.resources.displayMetrics.density).toInt()
更新:
そのためのdisplayMetrics
の一部であるグローバル共有リソース、我々は使用することができますResources.getSystem()
fun Int.toPx(): Int = (this * Resources.getSystem().displayMetrics.density).toInt()
fun Int.toDp(): Int = (this / Resources.getSystem().displayMetrics.density).toInt()
fun convertDpToPixel(dp: Float, context: Context): Float {
return dp * (context.resources.displayMetrics.densityDpi.toFloat() / DisplayMetrics.DENSITY_DEFAULT)
}
fun convertPixelsToDp(px: Float, context: Context): Float {
return px / (context.resources.displayMetrics.densityDpi.toFloat() / DisplayMetrics.DENSITY_DEFAULT)
}
public static float convertDpToPixel(float dp, Context context) {
return dp * ((float) context.getResources().getDisplayMetrics().densityDpi / DisplayMetrics.DENSITY_DEFAULT);
}
public static float convertPixelsToDp(float px, Context context) {
return px / ((float) context.getResources().getDisplayMetrics().densityDpi / DisplayMetrics.DENSITY_DEFAULT);
}
おそらく値/ディメンション内にディメンションがある場合、おそらく最良の方法は、getDimension()メソッドから直接ディメンションを取得することです。これにより、ピクセル値に既に変換されたディメンションが返されます。
context.getResources().getDimension(R.dimen.my_dimension)
これをよりよく説明するために、
getDimension(int resourceId)
既にピクセルに変換された寸法をFLOATとして返します。
getDimensionPixelSize(int resourceId)
同じを返しますが、intに切り捨てられるため、AS AN INTEGERになります。
参照してくださいAndroidの参照を
public static int dp2px(Resources resource, int dp) {
return (int) TypedValue.applyDimension(TypedValue.COMPLEX_UNIT_DIP, dp,resource.getDisplayMetrics());
}
ピクセルをdpに変換します。
public static float px2dp(Resources resource, float px) {
return (float) TypedValue.applyDimension(TypedValue.COMPLEX_UNIT_PX, px,resource.getDisplayMetrics());
}
ここで、resourceはcontext.getResources()です。
このような:
public class ScreenUtils {
public static float dpToPx(Context context, float dp) {
if (context == null) {
return -1;
}
return dp * context.getResources().getDisplayMetrics().density;
}
public static float pxToDp(Context context, float px) {
if (context == null) {
return -1;
}
return px / context.getResources().getDisplayMetrics().density;
}
}
コンテキストに依存、浮動小数点値を返す、静的メソッド
から:https : //github.com/Trinea/android-common/blob/master/src/cn/trinea/android/common/util/ScreenUtils.java#L15
kotlinの拡張機能を使用したよりエレガントなアプローチ
/**
* Converts dp to pixel
*/
val Int.dpToPx: Int get() = (this * Resources.getSystem().displayMetrics.density).toInt()
/**
* Converts pixel to dp
*/
val Int.pxToDp: Int get() = (this / Resources.getSystem().displayMetrics.density).toInt()
使用法:
println("16 dp in pixel: ${16.dpToPx}")
println("16 px in dp: ${16.pxToDp}")
function name
」と読みますが、この場合は逆です。各関数の意図を明確にするために、関数の名前を更新して、それぞれdpToPxおよびpxToDpを読み取ることができます。
パフォーマンスが重要なアプリケーションを開発する場合は、次の最適化クラスを検討してください。
public final class DimensionUtils {
private static boolean isInitialised = false;
private static float pixelsPerOneDp;
// Suppress default constructor for noninstantiability.
private DimensionUtils() {
throw new AssertionError();
}
private static void initialise(View view) {
pixelsPerOneDp = view.getResources().getDisplayMetrics().densityDpi / 160f;
isInitialised = true;
}
public static float pxToDp(View view, float px) {
if (!isInitialised) {
initialise(view);
}
return px / pixelsPerOneDp;
}
public static float dpToPx(View view, float dp) {
if (!isInitialised) {
initialise(view);
}
return dp * pixelsPerOneDp;
}
}
ピクセルをdpに変換するには、TypedValueを使用します。
ドキュメントが言及したように:動的に型付けされたデータ値のコンテナ。
そしてapplyDimensionメソッドを使用します:
public static float applyDimension (int unit, float value, DisplayMetrics metrics)
次のように、次元を保持するアンパックされた複素数データ値を最終的な浮動小数点値に変換します。
Resources resource = getResources();
float dp = TypedValue.applyDimension(TypedValue.COMPLEX_UNIT_PX, 69, resource.getDisplayMetrics());
お役に立てれば幸いです。
これは私にとってそれがどのように機能するかです:
DisplayMetrics displaymetrics = new DisplayMetrics();
getWindowManager().getDefaultDisplay().getMetrics(displaymetrics);
int h = displaymetrics.heightPixels;
float d = displaymetrics.density;
int heightInPixels=(int) (h/d);
幅についても同じことができます。
ピクセルと同じようにdpを使用する必要があります。それだけです。独立したピクセルを表示します。中密度の画面と同じ数値を使用すると、高密度の画面でサイズが魔法のように正しくなります。
ただし、レイアウトデザインのfill_parentオプションが必要なようです。ビューまたはコントロールを親コンテナの残りのすべてのサイズに拡張する場合は、fill_parentを使用します。
PX
とDP
は異なりますが似ています。
DP
画面の物理サイズのみを考慮した場合の解像度です。使用DP
すると、レイアウトが他の同様のサイズの画面に異なるサイズで拡大縮小されますpixel
密度の。
pixels
ただし、実際に必要な場合もありますが、コードでディメンションを処理するときはpixels
、変換しない限り、常にrealを処理します。
Androidデバイスでは、通常のサイズのhdpi
画面800x480 is 533x320
でDP
(と思います)。に変換DP
しpixels /1.5
、元に戻し*1.5
ます。これは1画面サイズの場合のみで、dpi
デザインによって異なります。私たちのアーティストは私に与えてくれpixels
ます、そして私DP
は上の1.5
方程式で変換します。
Integer値が必要な場合は、Math.round()を使用すると、floatが最も近い整数に丸められます。
public static int pxFromDp(final float dp) {
return Math.round(dp * Resources.getSystem().getDisplayMetrics().density);
}
最良の答えは、Androidフレームワーク自体にあります。この等式を使用してください...
public static int dpToPixels(final DisplayMetrics display_metrics, final float dps) {
final float scale = display_metrics.density;
return (int) (dps * scale + 0.5f);
}
(dpをpxに変換)
これは私のために働きます(C#):
int pixels = (int)((dp) * Resources.System.DisplayMetrics.Density + 0.5f);
コトリン
fun spToPx(ctx: Context, sp: Float): Float {
return sp * ctx.resources.displayMetrics.scaledDensity
}
fun pxToDp(context: Context, px: Float): Float {
return px / context.resources.displayMetrics.density
}
fun dpToPx(context: Context, dp: Float): Float {
return dp * context.resources.displayMetrics.density
}
java
public static float spToPx(Context ctx,float sp){
return sp * ctx.getResources().getDisplayMetrics().scaledDensity;
}
public static float pxToDp(final Context context, final float px) {
return px / context.getResources().getDisplayMetrics().density;
}
public static float dpToPx(final Context context, final float dp) {
return dp * context.getResources().getDisplayMetrics().density;
}