我正在尝试实现一个ProgressBar,这样当我的应用程序变得稍微空闲时(从尝试计算一个包含大量内容的方法),它应该显示该方法的完成进度,它是一个布尔值应该在最后返回true的方法 所以现在我很困惑如何监控进度(作为整数值),当它不是一个整数返回类型的方法
我尝试了很多不同的事情,但是当我使用处理程序时,我不知道如何将其编码为:
..当这个带有进度条处理程序的线程完成时,method = true,显示数据
即使我的逻辑可能现在不顺利,我也会展示我在做什么
private ProgressDialog progressBar;
private int percentageStatus = 0;
private Handler progressBarHandler = new Handler();
Thread loadingBar = new Thread(new Runnable() {
public void run() {
while(percentageStatus <= 100)
{
percentageStatus++;
try
{
Thread.sleep(20);
}
catch (InterruptedException e)
{
e.printStackTrace();
}
progressBarHandler.post(new Runnable() {
public void run()
{
progressBar.setProgress(percentageStatus);
Log.i("TESTS", "check..." + percentageStatus);
}
});
}
if (percentageStatus >= 100)
{
try
{
Thread.sleep(100);
}
catch (InterruptedException e) {
e.printStackTrace();
}
// close the progress bar dialog
//progressBar.dismiss();
progressBar.cancel();
}
}
});
@Override
public void onCreate(Bundle savedInstanceState){
super.onCreate(savedInstanceState);
progressBar = new ProgressDialog(this);
progressBar.setCancelable(true);
progressBar.setMessage("Loading...");
progressBar.setProgressStyle(ProgressDialog.STYLE_HORIZONTAL);
progressBar.setProgress(0);
progressBar.setMax(100);
progressBar.show();
loadingBar.start();
while(doWaitTask() < 100)
{
doWaitTask();
}
programCreated = true;
if(programCreated == true)
{
data = (TextView)findViewById(R.id.debug);
MyAsyncTask task = new MyAsyncTask();
task.execute(); //this is an async task which just appends some text to a TextView
}
}
public int doWaitTask() {
while (loadingValue <= 10000) {
loadingValue++;
}
return 100;
}
&#34; doWaitTask()&#34;这只是我模拟正在完成的一些工作的方法(用于SSSCCEE目的)
总结一下:当progressBar正在显示和更新进度时,我试图让屏幕为空而没有文字,一旦进度完成,它应该在进度完成后显示屏幕(所以我试图让它有点像加载栏)
使用异步任务会更好吗?以及在这种情况下如何?
答案 0 :(得分:0)
我要求你使用AsyncTask。您可以在下面找到我们如何使用它的示例:
首先我们需要创建活动的界面(在我的例子中,我们将使用Button和ProgressBar):
<?xml version="1.0" encoding="utf-8"?>
<RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android"
android:id="@+id/myLayout"
android:layout_width="match_parent"
android:layout_height="match_parent" >
<Button
android:id="@+id/btDoTask"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_alignParentLeft="true"
android:layout_alignParentTop="true"
android:layout_marginLeft="102dp"
android:layout_marginTop="24dp"
android:text="Do Async Task" />
<ProgressBar
android:id="@+id/pbAsyncBackgroundTraitement"
style="?android:attr/progressBarStyleHorizontal"
android:layout_width="fill_parent"
android:layout_height="wrap_content"
android:layout_alignParentLeft="true"
android:layout_alignParentRight="true"
android:layout_below="@+id/button1"
android:layout_marginTop="20dp" />
</RelativeLayout>
其次,我们将实现自定义AsyncTask:
package com.exemple.devhacksecuretest.asynctaskwithprogressbar;
import com.example.devhacksecuretest.R;
import android.app.Activity;
import android.os.AsyncTask;
import android.util.Log;
import android.view.View;
import android.widget.ProgressBar;
import android.widget.Toast;
public class CustomAsyncTask extends AsyncTask<String, Integer, Integer>{
private Activity mContext;
private ProgressBar pbAsyncBackgroundTraitement;
public CustomAsyncTask(Activity mContext) {
super();
this.mContext = mContext;
}
/* function which is called first */
@Override
protected void onPreExecute() {
this.pbAsyncBackgroundTraitement = (ProgressBar) mContext.findViewById(R.id.pbAsyncBackgroundTraitement);
this.pbAsyncBackgroundTraitement.setVisibility(View.VISIBLE);
super.onPreExecute();
}
/* function work on background */
@Override
protected Integer doInBackground(String... params) {
// Here you have to put what you want to do
for (int i = 0; i< params[0].length(); i++){
try {
Thread.sleep(100);
} catch (InterruptedException e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
int progress = (i * 100 / params[0].length());
Log.i("test", " progress : " + progress);
// call onProgressUpdate()
publishProgress(progress);
}
return null;
}
/* function to update the ProgressBar */
@Override
protected void onProgressUpdate(Integer... values) {
// update the progress bar
this.pbAsyncBackgroundTraitement.setProgress(values[0]);
super.onProgressUpdate(values);
}
/* function called after work on background function is over */
@Override
protected void onPostExecute(Integer result) {
// The work is done, you can do an action like create an activity or set invisible some UI components
this.pbAsyncBackgroundTraitement.setVisibility(View.GONE);
Toast.makeText(this.mContext, "Work is over... Do what you want now...bla bla bla", Toast.LENGTH_LONG).show();
super.onPostExecute(result);
}
}
3.最后,在包含Button和ProgressBar的主活动中,只需在OnClick
按钮中添加以下行:
public void onClick(View v) {
// TODO Auto-generated method stub
switch (v.getId()){
case R.id.btDoTask:
// Call CustomAsyncTask
CustomAsyncTask myCustomTask = new CustomAsyncTask(this);
// Execute task, we give it the parameter to work with
myCustomTask.execute("Params to execute in background");
break;
}
}
答案 1 :(得分:0)
你不应该只是人为地弥补已取得的进展。一个补充的进度要么太慢(这将导致任务看起来太早完成),要么太快(这将导致进度条长时间显示100%)。
如果您知道正在取得的实际进展,那么您应该使用它。如果处理需要N步(大约相同的长度),并且您已完成x步,则您的百分比为100 * x / N.使用AsyncTask来包含逻辑是一种很好的方法,可以让UI线程保持响应。
另一方面,如果您不知道取得了多少进展,那么您应该使用&#34;不确定模式&#34;进度条。引用ProgressBar JavaDoc:
在不确定模式下,进度条显示循环动画 没有进展的迹象。应用程序使用此模式 当任务的长度未知时。不确定的进度条 可以是纺车轮也可以是单杠。
答案 2 :(得分:0)
我已经为我想要的东西做了一个解决方法,一个非常&#39; interdeterminate&#39;这样做的方式
首先我有一个登录类
公共类登录扩展Activity实现OnClickListener
static String port_text;
static String ip_text;
static int portnum;
public void onClick(View v) {
if(v.getId() == btn1.getId())
{
port_text = port.getText().toString();
ip_text = ip.getText().toString();
portnum = Integer.parseInt(port_text);
/**.....exception handling operations......
**/
Intent myIntent = new Intent(Login.this, Loader.class);
startActivity(myIntent);
}
}
我打算转到一个专门用于等待加载所需类的加载屏幕
公共类加载器扩展登录
private ProgressDialog progressBar;
static LoadingScreen instance;
static LoadingScreen getInstance()
{
return instance;
}
public int getPort()
{
return portnum;
}
public String getIP()
{
return ip_text;
}
@Override
public void onCreate(Bundle savedInstanceState){
super.onCreate(savedInstanceState);
setContentView(R.layout.blank_activity);
instance = this;
progressBar = new ProgressDialog(this);
progressBar.setCancelable(true);
progressBar.setMessage("Loading...");
progressBar.setProgressStyle(ProgressDialog.STYLE_SPINNER);
progressBar.setIndeterminate(true);
progressBar.show();
final Intent mainIntent = new Intent(LoadingScreen.this, MainActivity.class);
new Handler().postDelayed(new Runnable(){
@Override
public void run() {
try
{
Thread.sleep(1000);
}
catch (InterruptedException e)
{
e.printStackTrace();
}
startActivity(mainIntent);
finish();
progressBar.cancel();
}
}, 2000);
}
我必须让Singleton从&#34; Login&#34;中获取静态变量数据。超类,原因是,如果我在Handler中启动了一个intent bundle,那么数据将无法在所需的类中被检索,所以在这种情况下,我使用一个postdelayed Handler来启动一个Intent并等待一个处理程序结束之前指定的时间量(此时间值可以通过反复试验获取)所以这样我可以避免在活动尝试加载时出现黑屏
公共类MainActivity扩展了FragmentActivity
Loader ls = Loader.getInstance();
int port_num = ls.getPort();
String ip_address = ls.getIP();
/* ....do operations with the port num and IP address...*/