简体   繁体   中英

How to control the volume of multiple sounds at once using multiple SeekBars (Android)?

How can I control the volume of multiple sounds playing at the same time using multiple SeekBars? There are three mp3 files are played at the same time. There are three SeekBars, each Seekbar progress should relate to the volume of it's relative sound file. The issue I'm having is that when I move one SeekBar, that controls the volume of all three sounds.

Here's the Android code followed by the XML:

/*
Created by: Justin Clark
Company: VaughnX
Date: June 15 2017
Purpose: To block out external sound using white, brown, and pink noise.
To do:  -Increase duration of brown and pink noise files.
        -use seek slider as an in-app volume controller
 */

package com.vaughnx.vaugi.soundwall;

import android.app.Activity;
import android.content.Context;
import android.support.v7.app.AppCompatActivity;
import android.os.Bundle;
import android.widget.Button;
import android.widget.CompoundButton;
import android.widget.SeekBar;
import android.widget.TextView;
import android.widget.ToggleButton;
import android.media.MediaPlayer;
import android.media.AudioManager;

public class MainActivity extends Activity {

    private SeekBar whiteVolumeSeekBar;
    private SeekBar pinkVolumeSeekBar;
    private SeekBar brownVolumeSeekBar;
    private AudioManager whiteAudioManager;
    private AudioManager pinkAudioManager;
    private AudioManager brownAudioManager;
    private int maxVolume;
    private int curVOlume;
    final MediaPlayer whiteNoiseMP = MediaPlayer.create(this, R.raw.whitenoise);
    final MediaPlayer brownNoiseMP = MediaPlayer.create(this, R.raw.brownnoise);
    final MediaPlayer pinkNoiseMP = MediaPlayer.create(this, R.raw.pinknoise);

    @Override
    protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.activity_main);
        setVolumeControlStream(AudioManager.STREAM_MUSIC);
        initializeSoundController();
        initializeVolumeController();
    }
    //Sets up white, brown, and pink noise players. Uses toggle buttons to turn sound on
    //and off.
    public void initializeSoundController() {


        ToggleButton whiteNoiseToggle = (ToggleButton) findViewById(R.id.whitenoisebutton);
        whiteNoiseToggle.setOnCheckedChangeListener(new CompoundButton.OnCheckedChangeListener() {
            public void onCheckedChanged(CompoundButton buttonView, boolean isChecked) {
                if (isChecked) {
                    // The toggle is enabled
                    whiteNoiseMP.start();
                } else {
                    // The toggle is disabled
                    whiteNoiseMP.pause();
                }
            }
        });
        ToggleButton brownNoiseToggle = (ToggleButton) findViewById(R.id.brownnoisebutton);
        brownNoiseToggle.setOnCheckedChangeListener(new CompoundButton.OnCheckedChangeListener() {
            public void onCheckedChanged(CompoundButton buttonView, boolean isChecked) {
                if (isChecked) {
                    // The toggle is enabled
                    brownNoiseMP.start();
                } else {
                    // The toggle is disabled
                    brownNoiseMP.pause();
                }
            }
        });
        ToggleButton pinkNoiseToggle = (ToggleButton) findViewById(R.id.pinknoisebutton);
        pinkNoiseToggle.setOnCheckedChangeListener(new CompoundButton.OnCheckedChangeListener() {
            public void onCheckedChanged(CompoundButton buttonView, boolean isChecked) {
                if (isChecked) {
                    // The toggle is enabled
                    pinkNoiseMP.start();
                } else {
                    // The toggle is disabled
                    pinkNoiseMP.pause();
                }
            }
        });

    }
    //End of sound controller initializations

    //Start of control volume with sliders//
    private void initializeVolumeController()
    {
        try{
            whiteVolumeSeekBar = (SeekBar) findViewById(R.id.whiteVolumeSeekBar);
            whiteVolumeSeekBar.setMax(50);
            whiteVolumeSeekBar.setOnSeekBarChangeListener(new SeekBar.OnSeekBarChangeListener() {
                @Override
                public void onProgressChanged(SeekBar seekBar, int progress, boolean b) {
                    float log1 = (float) (Math.log(50-progress)/Math.log(50));
                    whiteNoiseMP.setVolume(1-log1, 1-log1);
                }

                @Override
                public void onStartTrackingTouch(SeekBar seekBar) {

                }

                @Override
                public void onStopTrackingTouch(SeekBar seekBar) {

                }
            });
            pinkVolumeSeekBar.setProgress(25);
        } catch (Exception e){

        }
        try{
            pinkVolumeSeekBar = (SeekBar) findViewById(R.id.pinkVolumeSeekBar);
            pinkVolumeSeekBar.setMax(50);
            pinkVolumeSeekBar.setOnSeekBarChangeListener(new SeekBar.OnSeekBarChangeListener() {
                @Override
                public void onProgressChanged(SeekBar seekBar, int progress, boolean b) {
                    float log1 = (float) (Math.log(50-progress)/Math.log(50));
                    pinkNoiseMP.setVolume(1-log1, 1-log1);
                }

                @Override
                public void onStartTrackingTouch(SeekBar seekBar) {

                }

                @Override
                public void onStopTrackingTouch(SeekBar seekBar) {

                }
            });
            pinkVolumeSeekBar.setProgress(25);
        } catch (Exception e){

        }
        try{
            brownVolumeSeekBar = (SeekBar) findViewById(R.id.brownVolumeSeekBar);
            brownVolumeSeekBar.setMax(50);
            brownVolumeSeekBar.setOnSeekBarChangeListener(new SeekBar.OnSeekBarChangeListener() {
                @Override
                public void onProgressChanged(SeekBar seekBar, int progress, boolean b) {
                    float log1 = (float) (Math.log(50-progress)/Math.log(50));
                    brownNoiseMP.setVolume(1-log1, 1-log1);
                }

                @Override
                public void onStartTrackingTouch(SeekBar seekBar) {

                }

                @Override
                public void onStopTrackingTouch(SeekBar seekBar) {

                }
            });
            brownVolumeSeekBar.setProgress(25);

        } catch (Exception e){

        }

        //end of volume controller

}}

<?xml version="1.0" encoding="utf-8"?>
<RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android"
    xmlns:app="http://schemas.android.com/apk/res-auto"
    xmlns:tools="http://schemas.android.com/tools"
    android:layout_width="match_parent"
    android:layout_height="match_parent"
    android:background="@drawable/numbsound"
    tools:context="com.vaughnx.vaugi.soundwall.MainActivity">

    <ToggleButton
        android:id="@+id/whitenoisebutton"
        android:layout_width="wrap_content"
        android:layout_height="wrap_content"
        android:textOff="@string/whiteToggleButton"
        android:textOn="@string/whiteToggleButton"
        tools:layout_editor_absoluteX="0dp"
        tools:layout_editor_absoluteY="247dp"
        android:layout_alignParentTop="true"
        android:layout_alignParentLeft="true"
        android:layout_alignParentStart="true"
        android:layout_marginTop="16dp"
        android:layout_alignParentRight="true"
        android:layout_alignParentEnd="true" />

    <ToggleButton
        android:id="@+id/pinknoisebutton"
        android:layout_width="match_parent"
        android:layout_height="wrap_content"
        android:text="Button"
        android:textOff="@string/pinkToggleButton"
        android:textOn="@string/pinkToggleButton"
        tools:layout_editor_absoluteX="260dp"
        tools:layout_editor_absoluteY="247dp"
        android:layout_marginTop="48dp"
        android:layout_below="@+id/brownnoisebutton"
        android:layout_alignParentLeft="true"
        android:layout_alignParentStart="true" />

    <ToggleButton
        android:id="@+id/brownnoisebutton"
        android:layout_width="match_parent"
        android:layout_height="wrap_content"
        android:layout_alignParentLeft="true"
        android:layout_alignParentStart="true"
        android:layout_below="@+id/whitenoisebutton"
        android:layout_marginTop="44dp"
        android:text="Button"
        android:textOff="@string/brownToggleButton"
        android:textOn="@string/brownToggleButton"
        tools:layout_editor_absoluteX="137dp"
        tools:layout_editor_absoluteY="247dp" />

    <SeekBar
        android:id="@+id/whiteVolumeSeekBar"
        android:layout_width="fill_parent"
        android:layout_height="wrap_content"
        android:layout_below="@+id/pinknoisebutton"
        android:layout_marginTop="62dp" />
    <SeekBar
        android:id="@+id/brownVolumeSeekBar"
        android:layout_width="fill_parent"
        android:layout_height="wrap_content"
        android:layout_below="@+id/whiteVolumeSeekBar"
        android:layout_marginTop="62dp" />
    <SeekBar
        android:id="@+id/pinkVolumeSeekBar"
        android:layout_width="fill_parent"
        android:layout_height="wrap_content"
        android:layout_below="@+id/brownVolumeSeekBar"
        android:layout_marginTop="62dp" />

</RelativeLayout>


**************************************************************************
        LogCat Results:
07-09 17:05:52.621: E/AndroidRuntime(3147): FATAL EXCEPTION: main
07-09 17:05:52.621: E/AndroidRuntime(3147): Process: com.vaughnx.vaugi.soundwall, PID: 3147
07-09 17:05:52.621: E/AndroidRuntime(3147): java.lang.RuntimeException: Unable to instantiate activity ComponentInfo{com.vaughnx.vaugi.soundwall/com.vaughnx.vaugi.soundwall.MainActivity}: java.lang.NullPointerException: Attempt to invoke virtual method 'android.content.res.Resources android.content.Context.getResources()' on a null object reference
07-09 17:05:52.621: E/AndroidRuntime(3147):     at android.app.ActivityThread.performLaunchActivity(ActivityThread.java:3135)
07-09 17:05:52.621: E/AndroidRuntime(3147):     at android.app.ActivityThread.handleLaunchActivity(ActivityThread.java:3418)
07-09 17:05:52.621: E/AndroidRuntime(3147):     at android.app.ActivityThread.access$1100(ActivityThread.java:231)
07-09 17:05:52.621: E/AndroidRuntime(3147):     at android.app.ActivityThread$H.handleMessage(ActivityThread.java:1823)
07-09 17:05:52.621: E/AndroidRuntime(3147):     at android.os.Handler.dispatchMessage(Handler.java:102)
07-09 17:05:52.621: E/AndroidRuntime(3147):     at android.os.Looper.loop(Looper.java:148)
07-09 17:05:52.621: E/AndroidRuntime(3147):     at android.app.ActivityThread.main(ActivityThread.java:7422)
07-09 17:05:52.621: E/AndroidRuntime(3147):     at java.lang.reflect.Method.invoke(Native Method)
07-09 17:05:52.621: E/AndroidRuntime(3147):     at com.android.internal.os.ZygoteInit$MethodAndArgsCaller.run(ZygoteInit.java:1230)
07-09 17:05:52.621: E/AndroidRuntime(3147):     at com.android.internal.os.ZygoteInit.main(ZygoteInit.java:1120)
07-09 17:05:52.621: E/AndroidRuntime(3147): Caused by: java.lang.NullPointerException: Attempt to invoke virtual method 'android.content.res.Resources android.content.Context.getResources()' on a null object reference
07-09 17:05:52.621: E/AndroidRuntime(3147):     at android.content.ContextWrapper.getResources(ContextWrapper.java:92)
07-09 17:05:52.621: E/AndroidRuntime(3147):     at android.view.ContextThemeWrapper.getResources(ContextThemeWrapper.java:81)
07-09 17:05:52.621: E/AndroidRuntime(3147):     at android.support.v7.app.AppCompatActivity.getResources(AppCompatActivity.java:549)

You should use MediaPlayer.setVolume instead of Audio Manager to control volume.

package com.vaughnx.vaugi.soundwall;

import android.content.Context;
import android.support.v7.app.AppCompatActivity;
import android.os.Bundle;
import android.widget.Button;
import android.widget.CompoundButton;
import android.widget.SeekBar;
import android.widget.TextView;
import android.widget.ToggleButton;
import android.media.MediaPlayer;

public class MainActivity extends AppCompatActivity {

    private SeekBar whiteVolumeSeekBar;
    private SeekBar pinkVolumeSeekBar;
    private SeekBar brownVolumeSeekBar;
    private int maxVolume;
    private int curVOlume;
    private MediaPlayer whiteNoiseMP;
    private MediaPlayer brownNoiseMP;
    private MediaPlayer pinkNoiseMP;
    private ToggleButton whiteNoiseToggle;
    private ToggleButton brownNoiseToggle;
    private ToggleButton pinkNoiseToggle;

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

        //Sets up white, brown, and pink noise players. Uses toggle buttons to turn sound on
        //and off.
        whiteNoiseMP = MediaPlayer.create(MainActivity.this, R.raw.whitenoise);
        brownNoiseMP = MediaPlayer.create(MainActivity.this, R.raw.brownnoise);
        pinkNoiseMP = MediaPlayer.create(MainActivity.this, R.raw.pinknoise);
        whiteNoiseToggle = (ToggleButton) findViewById(R.id.whitenoisebutton);
        whiteNoiseToggle.setOnCheckedChangeListener(new CompoundButton.OnCheckedChangeListener() {
            public void onCheckedChanged(CompoundButton buttonView, boolean isChecked) {
                if (isChecked) {
                    // The toggle is enabled
                    whiteNoiseMP.start();
                } else {
                    // The toggle is disabled
                    whiteNoiseMP.pause();
                }
            }
        });
        brownNoiseToggle = (ToggleButton) findViewById(R.id.brownnoisebutton);
        brownNoiseToggle.setOnCheckedChangeListener(new CompoundButton.OnCheckedChangeListener() {
            public void onCheckedChanged(CompoundButton buttonView, boolean isChecked) {
                if (isChecked) {
                    // The toggle is enabled
                    brownNoiseMP.start();
                } else {
                    // The toggle is disabled
                    brownNoiseMP.pause();
                }
            }
        });
        pinkNoiseToggle = (ToggleButton) findViewById(R.id.pinknoisebutton);
        pinkNoiseToggle.setOnCheckedChangeListener(new CompoundButton.OnCheckedChangeListener() {
            public void onCheckedChanged(CompoundButton buttonView, boolean isChecked) {
                if (isChecked) {
                    // The toggle is enabled
                    pinkNoiseMP.start();
                } else {
                    // The toggle is disabled
                    pinkNoiseMP.pause();
                }
            }
        });
       //End of sound controller initializations

       //Start of control volume with sliders//
       try{
           whiteVolumeSeekBar = (SeekBar) findViewById(R.id.whiteVolumeSeekBar);
           whiteVolumeSeekBar.setMax(50);
           whiteVolumeSeekBar.setOnSeekBarChangeListener(new SeekBar.OnSeekBarChangeListener() {
               @Override
               public void onProgressChanged(SeekBar seekBar, int progress, boolean b) {
                   float log1 = (float) (Math.log(50-progress)/Math.log(50));
                   whiteNoiseMP.setVolume(1-log1);
               }

               @Override
               public void onStartTrackingTouch(SeekBar seekBar) {

               }

               @Override
               public void onStopTrackingTouch(SeekBar seekBar) {

               }
           });
           pinkVolumeSeekBar.setProgress(25);
        } catch (Exception e){
            Log.e("Exception", e.getMessage());
        }
        try{
            pinkVolumeSeekBar = (SeekBar) findViewById(R.id.pinkVolumeSeekBar);
            pinkVolumeSeekBar.setMax(50);
            pinkVolumeSeekBar.setOnSeekBarChangeListener(new SeekBar.OnSeekBarChangeListener() {
                @Override
                public void onProgressChanged(SeekBar seekBar, int progress, boolean b) {
                    float log1 = (float) (Math.log(50-progress)/Math.log(50));
                    pinkNoiseMP.setVolume(1-log1);
                }

                @Override
                public void onStartTrackingTouch(SeekBar seekBar) {

                }

                @Override
                public void onStopTrackingTouch(SeekBar seekBar) {

                }
            });
            pinkVolumeSeekBar.setProgress(25);
        } catch (Exception e){
            Log.e("Exception", e.getMessage());
        }
        try{
            brownVolumeSeekBar = (SeekBar) findViewById(R.id.brownVolumeSeekBar);
            brownVolumeSeekBar.setMax(50);
            brownVolumeSeekBar.setOnSeekBarChangeListener(new SeekBar.OnSeekBarChangeListener() {
                @Override
                public void onProgressChanged(SeekBar seekBar, int progress, boolean b) {
                    float log1 = (float) (Math.log(50-progress)/Math.log(50));
                    brownNoiseMP.setVolume(1-log1);
                }

                @Override
                public void onStartTrackingTouch(SeekBar seekBar) {

                }

                @Override
                public void onStopTrackingTouch(SeekBar seekBar) {

                }
            });
           brownVolumeSeekBar.setProgress(25);

        } catch (Exception e){
            Log.e("Exception", e.getMessage());
        }
        //end of volume controller
    }
}

I have set 50 as the maximum volume and starting volume to be 50% ie 25.

Use setVolume with Mediaplayer instead of AudioManager.For the latest android users, kindly add two arguments on the SetVolume. both for left and right volume.

whiteVolumeSeekBar.setOnSeekBarChangeListener(new SeekBar.OnSeekBarChangeListener() {
           @Override
           public void onProgressChanged(SeekBar seekBar, int progress, boolean b) {
               float log1 = (float) (Math.log(50-progress)/Math.log(50));
               whiteNoiseMP.setVolume(1-log1,1-log1);
           }

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM