【问题标题】:Android/Java: How to reference from a class to the MainActivity.javaAndroid/Java:如何从类引用 MainActivity.java
【发布时间】:2012-03-29 06:59:33
【问题描述】:

很抱歉这个问题,可能会在几分钟内得到回答。 我是 Android 应用开发的新手,一直在寻找大约 2 小时的答案,但我没有找到解决方案。

所以,这是我的问题: 我创建了一个布局非常简单的 MainActivity,只有一个 ToggleButton 来启动/停止一些声音。我从 MainActivity-Class 中调用 MediaPlayer。 现在我想把 MediaPlayer-Handling 放到一个单独的类中,这样它也可以从小部件中调用。 当举起 Toast 或调用 MediaPlayer-Method 时,我需要参考 MainActivity,它(在 MainActivity 本身中)是“this”。 但是我不知道如何引用 MainActivity 的实例。

代码如下:

package com.heavyloadreverse;

//import java.io.IOException;

import android.app.Activity;
//import android.media.MediaPlayer;
import android.os.Bundle;
import android.view.View;
//import android.widget.Toast;
import android.widget.ToggleButton;

public class MainActivity extends Activity {

    //private MediaPlayer mp;
    private Sound snd;
    private ToggleButton btn;   

    /** Called when the activity is first created. */
    @Override
    public void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.main);
        btn = (ToggleButton) findViewById(R.id.btn_OnOff);
        snd = new Sound();
        snd.mp_create(MainActivity.this);
    }

    public void onToggleClicked(View v) {       
        // Perform action on clicks
        if (((ToggleButton) v).isChecked()) {            
            snd.mp_start();
        } else {            
            snd.mp_stop();
        }
    }

    /*********************************************************************************
    public void mp_create() {
        mp = MediaPlayer.create(this, R.raw.truckreverse);
    }

    public void mp_start () {
        Toast.makeText(this, R.string.start, Toast.LENGTH_SHORT).show();
        // start the sound  
        mp.setLooping(true);
        mp.start();
    }

    public void mp_stop () {
        Toast.makeText(this, R.string.stop, Toast.LENGTH_SHORT).show();
        // stop the sound
        mp.stop();
        try {
            mp.prepare();
        } catch (IllegalStateException e) {
            // TODO Auto-generated catch block
            e.printStackTrace();
        } catch (IOException e) {
            // TODO Auto-generated catch block
            e.printStackTrace();
        }
    }

    public void mp_init() {
        btn.setChecked(false); 
    }
    **********************************************************************************/

    public void btn_init() {
        btn.setChecked(false); 
    }   

    @Override
    public void onStart() {
        super.onStart();
    }

    @Override
    public void onRestart() {
        super.onRestart();      
        btn_init();     
    }

    @Override
    public void onResume() {
        super.onResume();
        btn_init();
    }

    @Override
    public void onPause() {
        super.onPause();
        snd.mp_stop();
    }

    @Override
    public void onStop() {
        super.onStop();
        snd.mp_stop();
    }

    @Override
    public void onDestroy() {
        super.onDestroy(); 
        snd.mp_stop();
    }

    @Override
    public void onSaveInstanceState(Bundle savedInstanceState) {
        super.onSaveInstanceState(savedInstanceState);      
    }

}

MediaPlayer-Handling 的类:

package com.heavyloadreverse;

import java.io.IOException;

import android.app.Application;
import android.media.MediaPlayer;
import android.widget.Toast;
import com.heavyloadreverse.R;

public class Sound extends Application {

    private MediaPlayer mp; 

    public void mp_create (MainActivity main) {
        Toast.makeText(main.this, "test", Toast.LENGTH_SHORT).show();
        mp = new MediaPlayer();
        try {
            mp = MediaPlayer.create(this, R.raw.truckreverse); 
        } catch (IllegalStateException e) {
            // TODO Auto-generated catch block
            e.printStackTrace();
        } catch (RuntimeException e) {
            e.printStackTrace();
        }       
    }

    public void mp_start () {
        Toast.makeText(MainActivity.this, R.string.start, Toast.LENGTH_SHORT).show();
        // start the sound  
        try {
            mp.setLooping(true);
            mp.start();
        } catch (IllegalStateException e) {
            // TODO Auto-generated catch block
            e.printStackTrace();
        } catch (RuntimeException e) {
            e.printStackTrace();
        }       
    }

    public void mp_stop () {
        //Toast.makeText(this, R.string.stop, Toast.LENGTH_SHORT).show();       
        try {
            // stop the sound
            mp.stop();
            mp.prepare();
        } catch (IllegalStateException e) {
            // TODO Auto-generated catch block
            e.printStackTrace();
        } catch (IOException e) {
            // TODO Auto-generated catch block
            e.printStackTrace();
        } catch (RuntimeException e) {
            e.printStackTrace();
        }
    }

}

Toast.makeText(this, "test", Toast.LENGTH_SHORT).show();

--> 执行时引发运行时错误:

--> 03-12 20:23:18.412: E/AndroidRuntime(862): java.lang.RuntimeException: 无法启动活动 ComponentInfo{com.heavyloadreverse/com.heavyloadreverse.MainActivity}: java。 lang.NullPointerException

Toast.makeText(main.this, "test", Toast.LENGTH_SHORT).show();

--> 代码错误:

--> *此行有多个标记 - main 无法解析为类型 - 行断点:声音 [line: 15] - mp_create(MainActivity)*

Toast.makeText(MainActivity.this, "test", Toast.LENGTH_SHORT).show();

--> 代码错误:

--> 在范围内没有可以访问 MainActivity 类型的封闭实例

为了使“Sound.java”中的 Toast- 和 MediaPlayer-Calls 正常工作,我需要做什么?

非常感谢。

斯文

【问题讨论】:

    标签: java android class


    【解决方案1】:

    对于 Toast,这是您需要做的:

    Toast toast=Toast.makeText(this, "Hello toast", 2000);
    
         toast.show();
    

    如果有帮助,请查看此tutorial tutorial。

    【讨论】:

    • 这行得通,如果我从 MainActivity 中调用 Toast。如果我从 Sound 类中调用它,我会收到上面提到的运行时错误。对“this”的引用是问题所在。
    • 我明白了,你可以试试 getApplicationContext() 代替这个。我不在电脑前验证这一点,但你可以试一试。
    • 今晚回家后我会试一试。谢谢。
    【解决方案2】:

    不确定这是否可行,只是一个想法。

    首先从 MainActivity 扩展 Sound 类

    public class Sound extends MainActivity {
    

    其次,这是我用于 Toast 工作的代码:

    Toast.makeText(MainActivity.this,"Your Text Here",Toast.LENGTH_LONG).show();
    

    【讨论】:

    • 我想,我昨天试过了。也遇到了一些错误,但我今晚回家时会试一试。谢谢..
    • 这是一个非常糟糕的主意,这样做会在系统中引入一个新的活动(包含所有需要的对象),需要比所需更多的资源。
    【解决方案3】:

    选项 1 在“声音”上添加“上下文”作为参数

    public class Sound{
        private Context mContext;
        Sound(Context context){
            mContext = context;
        }
    
        ...
        Toast.makeText(mContext, text, length).show();
        ...
    }
    

    当您从活动创建 Sound 时,您将像 new Sound(this); 一样进行操作

    选项 2

    在 Sound 中定义一个接口以提供回调

    public class Sound {
        interface OnSoundListener{
            public void onSoundStarted();
            public void onSoundStopped();
        }
    }
    

    你的主要活动看起来像

    public class MainActivity implements Sound.OnSoundListener{
        @Override
        public void onSoundStarted(){
            //your toast here
        }
    }
    

    我个人更喜欢第二种,这样你就可以将逻辑与 UI 分开。

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 1970-01-01
      • 2013-12-03
      • 1970-01-01
      • 1970-01-01
      • 2021-11-08
      • 1970-01-01
      • 2018-06-16
      • 1970-01-01
      相关资源
      最近更新 更多