我剛剛得到了這個,但我遇到了一些小問題。 具體來說,在我的線程()中,我設置了一個由Spinner使用的數組。問題是在我的thread()完成之前,Spinner基本上都被設置和完成了,因此它使用一個空數組來設置它自己。Android ProgressDialog進度條以正確的順序處理事情
如何關聯的紡紗ArrayAdapter與正在被另一個線程加載一個數組?
我剪的代碼下降到什麼,我認爲是有必要了解的問題,只是讓我知道,如果需要更多。無論是否調用refreshData()都會出現問題。
按照同樣的思路,有時我想從菜單中調用loadData()。直接跟在loadData()之後,如果我嘗試在下一行觸發一個toast,這會導致forceclose,這也是因爲我如何實現ProgressDialog。
謝謝你看
public class CMSHome extends Activity {
private static List<String> pmList = new ArrayList<String>();
// Instantiate helpers
PMListHelper plh = new PMListHelper();
ProjectObjectHelper poc = new ProjectObjectHelper();
// These objects hold lists and methods for dealing with them
private Employees employees;
private Projects projects;
@Override
public void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.main);
// Loads data from filesystem, or webservice if necessary
loadData();
// Capture spinner and associate pmList with it through ArrayAdapter
spinner = (Spinner) findViewById(R.id.spinner);
ArrayAdapter<String> adapter = new ArrayAdapter<String>(
this, android.R.layout.simple_spinner_item,
pmList);
adapter.setDropDownViewResource(android.R.layout.simple_spinner_dropdown_item);
spinner.setAdapter(adapter);
//---the button is wired to an event handler---
Button btn1 = (Button)findViewById(R.id.btnGetProjects);
btn1.setOnClickListener(btnListAllProjectsListener);
spinner.setOnItemSelectedListener(new MyOnItemSelectedListener());
}
private void loadData()
{
final ProgressDialog pd = ProgressDialog.show(this,
"Please wait", "Loading Data...", true, false);
new Thread(new Runnable(){
public void run(){
employees = plh.deserializeEmployeeData();
projects = poc.deserializeProjectData();
// Check to see if data actually loaded, if not then refresh
if ((employees == null) || (projects == null)) {
refreshData();
}
// Load up pmList for spinner control
pmList = employees.getPMList();
pd.dismiss();
}
}).start();
}
private void refreshData()
{
// Refresh data for Projects
projects = poc.refreshData();
poc.saveProjectData(mCtx, projects);
// Refresh data for PMList
employees = plh.refreshData();
plh.savePMData(mCtx, employees);
}
}
< ---- EDIT -----> 我試圖改變的onCreate()來吉姆的建議之後以下。不知道是否我沒這個權利,仍然不能正常工作:
@Override
public void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.main);
mCtx = this;
// Loads data from filesystem, or webservice if necessary
// Would like to extend this to update if files are over x days old
final ProgressDialog pd = ProgressDialog.show(this,
"Please wait", "Loading Data...", true, false);
new Thread(new Runnable(){
public void run(){
employees = plh.deserializeEmployeeData();
projects = poc.deserializeProjectData();
// Check to see if data actually loaded, if not then refresh
if ((employees == null) || (projects == null)) {
refreshData();
}
pd.dismiss();
runOnUiThread(new Runnable() {
public void run(){
// Load up pmList for spinner control
pmList = employees.getPMList();
}
});
}
}).start();
spinner = (Spinner) findViewById(R.id.spinner);
ArrayAdapter<String> adapter = new ArrayAdapter<String>(
this, android.R.layout.simple_spinner_item, pmList);
adapter.setDropDownViewResource(android.R.layout.simple_spinner_dropdown_item);
spinner.setAdapter(adapter);
//---the button is wired to an event handler---
Button btn1 = (Button)findViewById(R.id.btnGetProjects);
btn1.setOnClickListener(btnListAllProjectsListener);
spinner.setOnItemSelectedListener(new MyOnItemSelectedListener());
}
哇,這花了永遠爲我找到一個解決方案,但是我喜出望外地終於得到了這個工作。
更新微調用後臺線程可通過利用一個處理程序來完成。處理程序在線程的主要工作完成後調用。
mProgressDlg = ProgressDialog.show(this, "App_Name", "Loading data...",
true, false);
new Thread(new Runnable(){
public void run() {
/*Load Data, set pmList in my case*/
mProgressDlg.dismiss();
hRefresh.sendEmptyMessage(REFRESH);
}
}).start();
Handler hRefresh = new Handler(){
@Override
public void handleMessage(Message msg) {
switch(msg.what){
case REFRESH:
spinner = (Spinner) findViewById(R.id.spinner);
final ArrayAdapter<String> adapter = new ArrayAdapter<String>(
mCtx, android.R.layout.simple_spinner_item, pmList);
adapter.setDropDownViewResource(android.R.layout.simple_spinner_dropdown_item);
spinner.setAdapter(adapter);
spinner.setOnItemSelectedListener(new MyOnItemSelectedListener());
break;
}
}
};
感謝bhatt4982和他的this thread
感謝吉姆, 林沒有專家,程序員,所以我怕我不正是你的意思,尤其是部分關於「內聯」知道 我也嘗試修改loadData()(包括在編輯的問題),但無濟於事。同樣的問題。我可能沒有實現你的建議。 任何進一步的幫助非常感謝。謝謝 – FauxReal 2010-04-08 17:58:12
我對這個術語表示歉意,'內聯'意味着將一個方法的代碼複製到它被調用的地方並刪除該方法。您可以自己完成,也可以使用重構菜單在Eclipse中自動完成。無論如何,我最初的建議的要點是,設置控件涉及一些冗長操作的正確方法是1.初始設置,它爲2創建一個新線程,獲取數據,當數據完成時,runOnUiThread() 3.用數據填充控件。 – 2010-04-08 19:04:53
再次感謝Jim, 我改變了像你所建議的(我認爲)onCreate方法。你可以在第二個代碼窗口中看到它。 runOnUiThread是否應該進入Thread()?這仍然不起作用。 當我調試時,它甚至在它開始運行線程之前就設置了整個UI。 – FauxReal 2010-04-08 19:40:31