Android设备存储与RAM信息展示:环形进度条实现求助
搞定垃圾清理APP的环形进度条问题
嘿,我来帮你解决这个环形进度条的实现难题!你需要展示存储和RAM的已用/可用空间,并且用环形进度条可视化,咱们一步步来搞定。
方案一:自定义环形进度条View(推荐,可控性强)
自定义View能让你完全掌控环形的样式、颜色、文本显示,完美匹配你的设计需求。
1. 创建自定义环形进度条类
新建CircleProgressBar.java,代码如下:
import android.content.Context; import android.graphics.Canvas; import android.graphics.Color; import android.graphics.Paint; import android.graphics.RectF; import android.util.AttributeSet; import android.view.View; public class CircleProgressBar extends View { // 画笔相关 private Paint mBgPaint; private Paint mProgressPaint; private Paint mTextPaint; // 进度相关 private int mProgress = 0; private int mMaxProgress = 100; // 尺寸相关 private int mWidth; private int mHeight; // 文本内容 private String mCenterText = ""; public CircleProgressBar(Context context) { super(context); init(); } public CircleProgressBar(Context context, AttributeSet attrs) { super(context, attrs); init(); } private void init() { // 初始化背景圆环画笔 mBgPaint = new Paint(); mBgPaint.setColor(Color.parseColor("#E0E0E0")); mBgPaint.setStyle(Paint.Style.STROKE); mBgPaint.setStrokeWidth(20); mBgPaint.setAntiAlias(true); // 初始化进度圆环画笔 mProgressPaint = new Paint(); mProgressPaint.setColor(Color.parseColor("#FF6D00")); mProgressPaint.setStyle(Paint.Style.STROKE); mProgressPaint.setStrokeWidth(20); mProgressPaint.setAntiAlias(true); mProgressPaint.setStrokeCap(Paint.Cap.ROUND); // 进度条两端圆角 // 初始化中心文本画笔 mTextPaint = new Paint(); mTextPaint.setColor(Color.parseColor("#333333")); mTextPaint.setTextSize(40); mTextPaint.setAntiAlias(true); mTextPaint.setTextAlign(Paint.Align.CENTER); } @Override protected void onMeasure(int widthMeasureSpec, int heightMeasureSpec) { super.onMeasure(widthMeasureSpec, heightMeasureSpec); mWidth = getMeasuredWidth(); mHeight = getMeasuredHeight(); // 确保是正方形 int size = Math.min(mWidth, mHeight); setMeasuredDimension(size, size); } @Override protected void onDraw(Canvas canvas) { super.onDraw(canvas); // 绘制背景圆环 RectF bgRect = new RectF(40, 40, mWidth - 40, mHeight - 40); canvas.drawArc(bgRect, 0, 360, false, mBgPaint); // 绘制进度圆环 float sweepAngle = (float) mProgress / mMaxProgress * 360; canvas.drawArc(bgRect, -90, sweepAngle, false, mProgressPaint); // 绘制中心文本 float textY = mHeight / 2 - (mTextPaint.descent() + mTextPaint.ascent()) / 2; canvas.drawText(mCenterText, mWidth / 2, textY, mTextPaint); } // 设置进度 public void setProgress(int progress) { mProgress = progress; invalidate(); } // 设置中心显示文本 public void setCenterText(String text) { mCenterText = text; invalidate(); } // 设置进度条颜色 public void setProgressColor(int color) { mProgressPaint.setColor(color); invalidate(); } }
2. 在布局文件中引用自定义View
修改你的activity_main.xml,添加两个环形进度条(一个用于存储,一个用于RAM):
<?xml version="1.0" encoding="utf-8"?> <LinearLayout xmlns:android="http://schemas.android.com/apk/res/android" android:layout_width="match_parent" android:layout_height="match_parent" android:orientation="vertical" android:padding="20dp" android:gravity="center"> <!-- 存储进度条 --> <com.yourpackage.CircleProgressBar android:id="@+id/storageProgressBar" android:layout_width="200dp" android:layout_height="200dp" android:layout_marginBottom="30dp"/> <!-- RAM进度条 --> <com.yourpackage.CircleProgressBar android:id="@+id/ramProgressBar" android:layout_width="200dp" android:layout_height="200dp"/> </LinearLayout>
记得把com.yourpackage替换成你的实际包名。
3. 在MainActivity中获取数据并设置进度
完善你的MainActivity.java,添加存储权限申请、存储和RAM数据获取逻辑:
import android.Manifest; import android.app.ActivityManager; import android.content.pm.PackageManager; import android.os.Build; import android.os.Bundle; import android.os.Environment; import android.widget.Toast; import androidx.appcompat.app.AppCompatActivity; import java.io.File; public class MainActivity extends AppCompatActivity { private CircleProgressBar mStorageProgressBar; private CircleProgressBar mRamProgressBar; private static final int STORAGE_PERMISSION_REQUEST_CODE = 100; @Override protected void onCreate(Bundle savedInstanceState) { super.onCreate(savedInstanceState); setContentView(R.layout.activity_main); mStorageProgressBar = findViewById(R.id.storageProgressBar); mRamProgressBar = findViewById(R.id.ramProgressBar); // 检查存储权限 if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.M) { if (checkSelfPermission(Manifest.permission.READ_EXTERNAL_STORAGE) != PackageManager.PERMISSION_GRANTED) { requestPermissions(new String[]{Manifest.permission.READ_EXTERNAL_STORAGE}, STORAGE_PERMISSION_REQUEST_CODE); } else { loadStorageInfo(); } } else { loadStorageInfo(); } // 加载RAM信息 loadRamInfo(); } // 获取并设置存储信息 private void loadStorageInfo() { File internalStorage = Environment.getDataDirectory(); long totalSpace = internalStorage.getTotalSpace(); long freeSpace = internalStorage.getFreeSpace(); long usedSpace = totalSpace - freeSpace; // 转换为GB单位(也可以用MB,根据需求调整) String totalStr = String.format("%.1f GB", totalSpace / (1024f * 1024f * 1024f)); String usedStr = String.format("%.1f GB", usedSpace / (1024f * 1024f * 1024f)); String freeStr = String.format("%.1f GB", freeSpace / (1024f * 1024f * 1024f)); // 计算进度(已用/总*100) int progress = (int) ((usedSpace * 100f) / totalSpace); // 设置进度和中心文本 mStorageProgressBar.setProgress(progress); mStorageProgressBar.setCenterText("存储\n" + usedStr + "/" + totalStr + "\n可用:" + freeStr); } // 获取并设置RAM信息 private void loadRamInfo() { ActivityManager activityManager = (ActivityManager) getSystemService(ACTIVITY_SERVICE); ActivityManager.MemoryInfo memoryInfo = new ActivityManager.MemoryInfo(); activityManager.getMemoryInfo(memoryInfo); long totalRam = memoryInfo.totalMem; long freeRam = memoryInfo.availMem; long usedRam = totalRam - freeRam; // 转换为GB单位 String totalStr = String.format("%.1f GB", totalRam / (1024f * 1024f * 1024f)); String usedStr = String.format("%.1f GB", usedRam / (1024f * 1024f * 1024f)); String freeStr = String.format("%.1f GB", freeRam / (1024f * 1024f * 1024f)); int progress = (int) ((usedRam * 100f) / totalRam); mRamProgressBar.setProgress(progress); mRamProgressBar.setCenterText("RAM\n" + usedStr + "/" + totalStr + "\n可用:" + freeStr); // 可以给RAM进度条换个颜色,区分存储 mRamProgressBar.setProgressColor(getResources().getColor(R.color.blue)); } @Override public void onRequestPermissionsResult(int requestCode, String[] permissions, int[] grantResults) { super.onRequestPermissionsResult(requestCode, permissions, grantResults); if (requestCode == STORAGE_PERMISSION_REQUEST_CODE) { if (grantResults.length > 0 && grantResults[0] == PackageManager.PERMISSION_GRANTED) { loadStorageInfo(); } else { Toast.makeText(this, "需要存储权限才能查看存储信息", Toast.LENGTH_SHORT).show(); } } } }
方案二:使用系统ProgressBar的环形样式(快速实现)
如果不想自定义View,也可以用系统自带的环形ProgressBar,然后在上方叠加TextView显示文本:
<RelativeLayout android:layout_width="200dp" android:layout_height="200dp"> <ProgressBar android:id="@+id/ramProgress" android:layout_width="match_parent" android:layout_height="match_parent" android:indeterminate="false" android:max="100" android:progress="60" style="?android:attr/progressBarStyleLarge"/> <TextView android:layout_width="wrap_content" android:layout_height="wrap_content" android:layout_centerInParent="true" android:text="RAM\n2.3/6.0GB\n可用:3.7GB" android:textAlignment="center"/> </RelativeLayout>
这种方式优点是快,但样式自定义程度低,适合快速原型开发。
注意事项
- 权限适配:Android 6.0+必须动态申请
READ_EXTERNAL_STORAGE权限才能获取存储信息; - 单位转换:记得把字节转换成用户易懂的GB/MB,避免显示超大数字;
- 样式调整:可以根据你的示例图片,修改自定义View中的颜色、线条宽度、文本大小等参数,完全匹配设计。
内容的提问来源于stack exchange,提问作者ZKhan
相关产品推荐
相关产品推荐

