AsyncTask的启动画面

时间:2013-10-07 13:18:15

标签: java android android-asynctask splash-screen

我想在我的应用中实现启动画面。我已经这样做了。但此刻它只等待3秒钟,然后调用MainActivity类。问题是我要加载数据,并且当前设置用户必须等待两次。我想要一个加载所有数据的启动画面。我有一个MainActivity类,一切都发生了,我有我的SplashScreen类。

我想在后台运行的方法是在我的MainClass中。所以基本上我有像我那样的启动画面类

public class SplashScreenActivity extends AsyncTask<Void, Void, Void> {

@Override
protected Void doInBackground(Void... params) {
    // TODO Auto-generated method stub
    return null;
}

protected void onPostExecute(Void... params) {
    // TODO Auto-generated method stub

}

protected void onCancelled() {
    // TODO Auto-generated method stub
}

}

我也实现但没有复制导入和包,所以这应该不是问题。现在,如果我理解正确,我需要编写应该在doInBackground方法中完成的任务。所以我基本上必须从我的其他活动类调用该方法,对吧?

public MainActivity mA = new MainActivity();

然后在方法中我会写mA.parseXMLfromURL();

然后我会像这样开始将主类的意图引入onPostExecute方法?

protected void onPostExecute(Void... params) {
    Intent mainClass = new Intent(SplashScreenActivity.this, MainActivity.class);
    startActivity(mainClass);

}

如果需要更多信息,我将很乐意进一步阐述。

更新

好吧,在你的评论之后我尝试了一下。

这是我的oncreate方法

    public void onCreate(Bundle savedInstanceState) {
    StrictMode.setThreadPolicy(policy);
    super.onCreate(savedInstanceState);
    sv      = new ScrollView(this);
    layout = new LinearLayout(this);
    layout.setOrientation(LinearLayout.VERTICAL);
    sv.addView(layout);
    setContentView(sv);     

    new SplashScreenActivity().execute("URL TO FILE");
}

这就是SplashScreenActivity

public class SplashScreenActivity extends AsyncTask<String, Void, Void> {
public MainActivity mA = new MainActivity();

protected void onPostExecute(Void... params) {
}

protected void onCancelled() {
    // TODO Auto-generated method stub
}

@Override
protected Void doInBackground(String... params) {
    mA.parseXMLfromURL(params);
    return null;
}

}

但这只会返回一个空白屏幕。但是,如果我在主要活动中调用parseXMLfromURL,它就可以正常工作。

@Raghunandan在评论中说我错误地创建了该类的实例。如果你能详细说明你的答案,我将很高兴。

更新号码

当前的SplashScreen-Code如下:

package de.activevalue.T1000flies;

import android.app.Activity;
import android.content.Intent;
import android.os.AsyncTask;
import android.os.Bundle;

public class SplashScreenActivity extends Activity{

@Override
protected void onCreate(Bundle savedInstanceState) {
    super.onCreate(savedInstanceState);
    setContentView(R.layout.splash_screen);

    new mTask().execute();
}

private class mTask extends AsyncTask<Void, Void, Void>{

    MainActivity mA = new MainActivity();
    @Override
    protected Void doInBackground(Void... arg0) {
        mA.parseXML();
        return null;
    }

    protected void onPostExecute(Void... params){
        Intent i = new Intent(SplashScreenActivity.this, MainActivity.class);
        startActivity(i);
        finish();
    }


}

}

使用该代码,该应用程序只是停留在Splash-Screen。它看起来像我的XML-Parsing存在问题。这是XML-Parsing代码。请注意,当我刚启动启动画面时的主要活动

时,它没有任何问题

更新数量

我刚开始通过每行创建断点来调试。它跳出这一行

rankingDate [k]             = new TextView(this);

其余代码

for(int k = 0; k < metaList.getLength(); k++){

            Node metaNode = metaList.item(k);
            System.out.println(metaList.getLength());
            rankingDate [k]             = new TextView(this);
            rdate       [k]             = new TextView(this);
            numberOE    [k]             = new TextView(this);

            Element metaElement = (Element) metaNode;
            NodeList rankingDateList    = metaElement.getElementsByTagName("date");
            Element rankingDateElement  = (Element) rankingDateList.item(0);
            rankingDateList             = rankingDateElement.getChildNodes();
            rankingDate [k].setText("RankingDate: " + ((Node) rankingDateList.item(0)).getNodeValue());
            layout.addView(rankingDate[k]);

            xmlSerializer.startTag(null, "date");
            xmlSerializer.text(((Node) rankingDateList.item(0)).getNodeValue());
            xmlSerializer.endTag(null, "date");

        }

system.out.println给了我1.而k是0.那么为什么它是一个空指针异常?

5 个答案:

答案 0 :(得分:3)

您应该为SplashScreen创建新活动 - &gt; SplashScreenActivity扩展了Activity,在manifest中声明,而不是设置布局;

public SplashScreenActivity extends Activity{

 protected void onCreate(Bundle ...){
  super.onCreate(...);
  setContentView(...);
  new mTask().execute();
 }

 private class mTask extends AsyncTask<Void, Void, Void>{

@Override
protected Void doInBackground(Void... params) {
    // TODO Auto-generated method stub
    return null;
}

protected void onPostExecute(Void... params) {
   Intent mainClass = new Intent(SplashScreenActivity.this, MainActivity.class);
    startActivity(mainClass);
    finish();
}

 }

}

答案 1 :(得分:1)

小猪退出nurisezgin的答案解释了AsyncTasks如何在android中运行,你几乎就在那里,但需要让其他东西不受影响。

首先:在Android世界中,您从不通过调用其构造函数来初始化活动。活动由操作系统处理,您可以使用Intent s。

运行它们

这样,您就可以解决问题了。您需要获取parseXML MainActivity函数中的任何代码,并将其放入SplashScreenActivity并调用它,或者直接将其放在doInBackground方法中

您的doInBackground方法不应该调用任何外部活动。

答案 2 :(得分:0)

执行启动画面的一种更简单的方法是让它出现在主要活动的前面,需要使用Dialogs加载数据。最简单的方法是覆盖AsyncTask中的onPreExecute()方法。以下是启动画面的简单示例。

MainActivity.java

public class MainActivity extends Activity
{
    protected void onCreate(Bundle savedInstanceState)
    {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.activity_main);

        new SplashScreen(this).execute();
    }
}

SplashScreen.java

public class SplashScreen extends AsyncTask<Void, Void, Void>
{
    Context ctxt;
    Dialog splash;

    public SplashScreen(Context ctxt)
    {
        this.ctxt = ctxt;
    }

    protected void onPreExecute()
    {
        splash = new Dialog(ctxt, R.style.full_screen);
        splash.show();
    }

    protected Void doInBackground(Void... ignore)
    {
        //Fetch stuff
        return null;
    }

    protected void onPostExecute(Void ignore)
    {
        splash.dismiss();
    }
}

在res / values / styles.xml文件中,您希望将以下xml用于全屏。

<!-- Stuff that's already in here -->

<style name="full_screen" parent="android:Theme.Light">
    <item name="android:windowActionBar">false</item>
    <item name="android:windowNoTitle">true</item>
</style>

<!-- Stuff that's already in here -->

这将为您提供一个非常基本的启动画面(即一个什么都没说的空白屏幕)。如果您查看Dialogs API,您可以找到其他方法来自定义它,允许您使用图片而不是文本,以及完全自定义Dialog的布局。如果您想进一步定制,也请查看DialogFragments。以这种方式执行启动屏幕的好处是,您可以检索所有信息并将其设置在onPostExecute()中,而不必担心传输数据。

希望这有帮助!祝你好运。

答案 3 :(得分:0)

我在一个项目中尝试过完全相同,但我的方法不同。也许它可以解决你的问题...

首先,我的SplashScreenMainActivity

中的叠加层
 //main-activtiy xml
 <RelativeLayout ...
     <RelativeLayout id="overlay" visible="true"... //filled parent and had a centered image
     <RelativeLayout id="mainActivity" visible="false"... //the application
  • 已启动应用程序
  • AsyncTask
  • 中开始ServiceonCreateMethod
  • 如果加载了数据,请将Notification发送到MainActivity并“交换您的视图”,如

    public void functionCalledOnDataLoaded(){
       //do you init stuff
    
      ((RelativeLayout) findViewById(R.id.overlay)).setVisibility(View.INVISIBLE);
      ((RelativeLayout) findViewById(R.id.mainActivity)).setVisibility(View.VISIBLE);
    

    }

答案 4 :(得分:0)

为什么不只创建MainActivity。 Splash只是main.xml的框架布局,并且在一定时间后将是setVisibility(View.GONE)。

使用此方法,您只有1个活动。因此,更容易处理来自网络的负载数据而不会中断。