Android 如何每秒运行一个 AsyncTask?

标签 android android-asynctask continuous

我是 Android 新手,并不知道如何处理这个问题:我有一个 AsyncTask,它从 XML 文件中读取位置 (X,Y,Z)。由于这个位置每秒都在变化,我希望在我按下一个按钮(用“StartListener”调用)后连续读取和绘制每个新位置并在我再次按下按钮时停止读取它......
有人可以帮助我吗? - 这是我的 MainActivity 的一部分

(目前我的应用程序仅在我按下按钮时读取和绘制位置...)

      private OnClickListener StartListener = new OnClickListener() {

          @Override
          public void onClick(View v) {

                TextView ButText = (TextView)findViewById(R.id.buttonStart);

                 String value=ButText.getText().toString();
                 if(value.equals("Start positioning")){
                     ButText.setText("Stop positioning");

                     new PositionAsync().execute(); //read data from XML file

                 }
                 else if(value.equals("Stop positioning")){
                     ButText.setText("Start positioning");
                     //new PositionAsync().cancel(true);
                 }              
            }                   
      }; // END LISTENER START BUTTON


// READ XML FILE
class PositionAsync extends AsyncTask<Void, Void, Void> {

    XMLHelper helper;
    @Override
    protected Void doInBackground(Void... arg0) {
        helper = new XMLHelper();
        helper.get();
        return null;
    }   

    @Override
    protected void onPostExecute(Void result) {         

        Paint paintBlack = new Paint(); paintBlack.setAntiAlias(true); paintBlack.setColor(Color.BLACK);

        BitmapFactory.Options myOptions = new BitmapFactory.Options();
        myOptions.inDither = true;
        myOptions.inScaled = false;
        myOptions.inPreferredConfig = Bitmap.Config.ARGB_8888;// important
        myOptions.inPurgeable = true;
        File ImageSource = new File("/sdcard/app_background3.jpg");
        Bitmap bitmap2 = BitmapFactory.decodeFile(ImageSource.getAbsolutePath(),myOptions);         
        Bitmap workingBitmap = Bitmap.createBitmap(bitmap2);
        Bitmap mutableBitmap2 = workingBitmap.copy(Bitmap.Config.ARGB_8888, true);

        Canvas canvas2 = new Canvas(mutableBitmap2);

        float RoomWidthPx = canvas2.getWidth();
        float RoomHeightPx = canvas2.getHeight();
        float RoomXmeter = (float) 9.3;
        float RoomZmeter = (float) 14.7;

        for (PositionValue position : helper.positions) {

            String PosX = position.getPositionX(); String PosY = position.getPositionY(); String PosZ = position.getPositionZ();

            float x = Float.valueOf(PosX); float y = Float.valueOf(PosY); float z = Float.valueOf(PosZ);

            float xm = x*RoomWidthPx/RoomXmeter; 
            float zm = z*RoomHeightPx/RoomZmeter;

            canvas2.drawCircle(xm, zm, 25, paintBlack);

            ImageView imageView = (ImageView)findViewById(R.id.imageView1);
            imageView.setAdjustViewBounds(true);
            imageView.setImageBitmap(mutableBitmap2);

            // SAVE DRAWINGS INTO FILE
            FileOutputStream fos = null;
            try {
            fos = new FileOutputStream ("/sdcard/app_background3.jpg");
            mutableBitmap2.compress (Bitmap.CompressFormat.JPEG, 95, fos); 
            } catch (Throwable ex) {ex.printStackTrace (); }    
        };

    }
} //END READ XML FILE

最佳答案

我认为你在一秒钟内完成了太多任务。相反,您可以在 AsyncTask 的 onPreExecute() 中准备所有繁重的工作人员,在 doInBackground() 中读取 XML 并进行绘制,在onProgressUpdate() 最后,当任务完成时,将图像保存到 sdcard

我已经修改了您的 Asynctask 来完成上述场景,我没有测试它,但它给了您想法。

在 Activity 的 onCreate() 方法中,您只需启动 AsyncTask 一次。它会一直执行或休眠,直到您将 Quit_Task 变量设置为 true。当按下按钮时,您切换变量 Do_Drawing: Do_Drawing=!Do_Drawing; 就这样。

private boolean Do_Drawing = false;
private boolean Quit_Task = false;

// READ XML FILE
class PositionAsync extends AsyncTask<Void, Void, Void>
{
    Paint paintBlack;
    BitmapFactory.Options myOptions;
    Bitmap mutableBitmap2;
    Canvas canvas2;
    XMLHelper helper;

    void Sleep(int ms)
    {
        try
        {
            Thread.sleep(ms);
        }
        catch (Exception e)
        {
        }
    }

    @Override
    protected void onPreExecute()
    {
        // Prepare everything for doInBackground thread
        paintBlack = new Paint();
        paintBlack.setAntiAlias(true);
        paintBlack.setColor(Color.BLACK);
        myOptions = new BitmapFactory.Options();
        myOptions.inDither = true;
        myOptions.inScaled = false;
        myOptions.inPreferredConfig = Bitmap.Config.ARGB_8888;// important
        myOptions.inPurgeable = true;
        File ImageSource = new File("/sdcard/app_background3.jpg");
        Bitmap bitmap2 = BitmapFactory.decodeFile(ImageSource.getAbsolutePath(), myOptions);
        Bitmap workingBitmap = Bitmap.createBitmap(bitmap2);
        mutableBitmap2 = workingBitmap.copy(Bitmap.Config.ARGB_8888, true);
        canvas2 = new Canvas(mutableBitmap2);
        helper = new XMLHelper();
    }

    @Override
    protected Void doInBackground(Void... arg0)
    {
        while (!Quit_Task)
        {
            // Sleep until button is pressed or quit
            while (!Do_Drawing)
            {
                Sleep(1000);
                if (Quit_Task)
                    return null;
            }

            float RoomWidthPx = canvas2.getWidth();
            float RoomHeightPx = canvas2.getHeight();
            float RoomXmeter = (float) 9.3;
            float RoomZmeter = (float) 14.7;
            // keep drawing until button is pressed again or quit
            while (Do_Drawing)
            {
                if (Quit_Task)
                    return null;
                helper.get();
                for (PositionValue position : helper.positions)
                {
                    String PosX = position.getPositionX();
                    String PosY = position.getPositionY();
                    String PosZ = position.getPositionZ();

                    float x = Float.valueOf(PosX);
                    float y = Float.valueOf(PosY);
                    float z = Float.valueOf(PosZ);

                    float xm = x * RoomWidthPx / RoomXmeter;
                    float zm = z * RoomHeightPx / RoomZmeter;

                    canvas2.drawCircle(xm, zm, 25, paintBlack);
                }
                this.publishProgress((Void) null);
                Sleep(1000);
            }
        }
        return null;
    }

    @Override
    protected void onProgressUpdate(Void... progress)
    {
        // once all points are read & drawn refresh the imageview
        try
        {
            ImageView imageView = (ImageView) findViewById(R.id.imageView1);
            imageView.setAdjustViewBounds(true);
            imageView.setImageBitmap(mutableBitmap2);
        }
        catch (Exception e)
        {
            e.printStackTrace();
        }
    }

    @Override
    protected void onPostExecute(Void result)
    {
        // SAVE DRAWINGS INTO FILE once the task is done.
        FileOutputStream fos = null;
        try
        {
            fos = new FileOutputStream(Environment.getExternalStorageDirectory().getPath() + "app_background3.jpg");
            mutableBitmap2.compress(Bitmap.CompressFormat.JPEG, 95, fos);
        }
        catch (Throwable ex)
        {
            ex.printStackTrace();
        }
    }
} // END READ XML FILE

关于Android 如何每秒运行一个 AsyncTask?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/18702298/

相关文章:

按下主页按钮时Android清除 Activity 列表

android - 如果从主线程执行方法,如何抛出异常

Android Asynctask 在 Fragment Tabs 中运行两次

python - 如何在没有任何输出数据的情况下预测连续变量?我所拥有的只是输入数据

r - 在R中创建连续的热图

android - ajax jquery 代码不适用于 android -Phonegap-

java - 无法查看 ScrollView 内的任何内容( TextView )

android - 钛 : Label over lapping issue

android - 由于 AsyncTask 是一个单独的类,如何将 OnPostExecute() 的结果获取到主要 Activity ?

simulation - *像box2d/bullet3d这样的*连续物理模拟*的基本思想是什么?