Java 如何在 Android 上调出可用通知声音列表

声明:本页面是StackOverFlow热门问题的中英对照翻译,遵循CC BY-SA 4.0协议,如果您需要使用它,必须同样遵循CC BY-SA许可,注明原文地址和作者信息,同时你必须将它归于原作者(不是我):StackOverFlow 原文地址: http://stackoverflow.com/questions/2724871/
Warning: these are provided under cc-by-sa 4.0 license. You are free to use/share it, But you must attribute it to the original authors (not me): StackOverFlow

提示:将鼠标放在中文语句上可以显示对应的英文。显示中英文
时间:2020-08-13 12:08:31  来源:igfitidea点击:

How to bring up list of available notification sounds on Android

javaandroidaudionotifications

提问by robintw

I'm creating notifications in my Android application, and would like to have an option in my preferences to set what sound is used for the notification. I know that in the Settings application you can choose a default notification sound from a list. Where does that list come from, and is there a way for me to display the same list in my application?

我正在我的 Android 应用程序中创建通知,并希望在我的首选项中有一个选项来设置用于通知的声音。我知道在“设置”应用程序中,您可以从列表中选择默认通知声音。该列表来自哪里,有没有办法在我的应用程序中显示相同的列表?

采纳答案by Mark B

Just copy/pasting some code from one of my apps that does what you are looking for.

只需从我的一个应用程序中复制/粘贴一些代码即可完成您正在寻找的内容。

This is in an onClick handler of a button labeled "set ringtone" or something similar:

这是在标记为“设置铃声”或类似内容的按钮的 onClick 处理程序中:

Intent intent = new Intent(RingtoneManager.ACTION_RINGTONE_PICKER);
intent.putExtra(RingtoneManager.EXTRA_RINGTONE_TYPE, RingtoneManager.TYPE_NOTIFICATION);
intent.putExtra(RingtoneManager.EXTRA_RINGTONE_TITLE, "Select Tone");
intent.putExtra(RingtoneManager.EXTRA_RINGTONE_EXISTING_URI, (Uri) null);
this.startActivityForResult(intent, 5);

And this code captures the choice made by the user:

此代码捕获用户所做的选择:

 @Override
 protected void onActivityResult(final int requestCode, final int resultCode, final Intent intent)
 {
     if (resultCode == Activity.RESULT_OK && requestCode == 5)
     {
          Uri uri = intent.getParcelableExtra(RingtoneManager.EXTRA_RINGTONE_PICKED_URI);

          if (uri != null)
          {
              this.chosenRingtone = uri.toString();
          }
          else
          {
              this.chosenRingtone = null;
          }
      }            
  }

Also, I advise my users to install the "Rings Extended" app from the Android Market. Then whenever this dialog is opened on their device, such as from my app or from the phone's settings menu, the user will have the additional choice of picking any of the mp3s stored on their device, not just the built in ringtones.

另外,我建议我的用户从 Android Market 安装“Rings Extended”应用程序。然后每当在他们的设备上打开此对话框时,例如从我的应用程序或从手机的设置菜单,用户将有额外的选择来选择存储在他们设备上的任何 mp3,而不仅仅是内置的铃声。

回答by JD.

Or just stick this in your preferences XML:

或者只是将其粘贴在您的偏好 XML 中:

  <RingtonePreference android:showDefault="true"
     android:key="Audio" android:title="Alarm Noise"
     android:ringtoneType="notification" />

Full content of my sample XML just for context:

我的示例 XML 的全部内容仅用于上下文:

<?xml version="1.0" encoding="UTF-8"?>
<PreferenceScreen xmlns:android="http://schemas.android.com/apk/res/android">
<EditTextPreference android:title="Some value"
                    android:key="someval"
                    android:summary="Please provide some value" />
<EditTextPreference android:title="Some other value"
                    android:key="someval2"
                    android:summary="Please provide some other value" />
 <RingtonePreference android:showDefault="true"
     android:key="Audio" android:title="Alarm Noise"
     android:ringtoneType="notification" />

</PreferenceScreen>

回答by Murphybro2

This is the method I use to get a list of notification sounds available in the phone :)

这是我用来获取手机中可用通知声音列表的方法:)

public Map<String, String> getNotifications() {
    RingtoneManager manager = new RingtoneManager(this);
    manager.setType(RingtoneManager.TYPE_NOTIFICATION);
    Cursor cursor = manager.getCursor();

    Map<String, String> list = new HashMap<>();
    while (cursor.moveToNext()) {
        String notificationTitle = cursor.getString(RingtoneManager.TITLE_COLUMN_INDEX);
        String notificationUri = cursor.getString(RingtoneManager.URI_COLUMN_INDEX);

        list.put(notificationTitle, notificationUri);
    }

    return list;
}

EDIT: This is for the comment regarding how to set the sound in the NotificationCompat.Builder. This method instead gets the ringtone's ID which is what the phone uses, instead of the human readable TITLE the other method got. Combine the uri and the id, and you have the ringtones location.

编辑:这是关于如何在 NotificationCompat.Builder 中设置声音的评论。这个方法取而代之的是获取手机使用的铃声 ID,而不是另一种方法获得的人类可读的 TITLE。结合 uri 和 id,你就有了铃声位置。

public ArrayList<String> getNotificationSounds() {
    RingtoneManager manager = new RingtoneManager(this);
    manager.setType(RingtoneManager.TYPE_NOTIFICATION);
    Cursor cursor = manager.getCursor();

    ArrayList<String> list = new ArrayList<>();
    while (cursor.moveToNext()) {
        String id = cursor.getString(RingtoneManager.ID_COLUMN_INDEX);
        String uri = cursor.getString(RingtoneManager.URI_COLUMN_INDEX);

        list.add(uri + "/" + id);
    }

    return list;
}

The above code will return a list of strings like "content://media/internal/audio/media/27".. you can then pass one of these strings as a Uri into the .setSound() like:

上面的代码将返回一个字符串列表,如"content://media/internal/audio/media/27".. 然后你可以将这些字符串之一作为 Uri 传递到 .setSound() 中,例如:

.setSound(Uri.parse("content://media/internal/audio/media/27"))

Hope that was clear enough :)

希望这足够清楚:)

回答by Nicolai Harbo

Here's another approach (in Kotlin), build from other answers in this question, that allows you to specify the name of the tone, and then play it:

这是另一种方法(在 Kotlin 中),根据这个问题中的其他答案构建,它允许您指定音调的名称,然后播放它:

fun playErrorTone(activity: Activity, context: Context, notificationName: String = "Betelgeuse") {

        val notifications = getNotificationSounds(activity)

        try {
            val tone = notifications.getValue(notificationName)
            val errorTone = RingtoneManager.getRingtone(context, Uri.parse(tone))
            errorTone.play()
        } catch (e: NoSuchElementException) {
            try {
                // If sound not found, default to first one in list
                val errorTone = RingtoneManager.getRingtone(context, Uri.parse(notifications.values.first()))
                errorTone.play()
            } catch (e: NoSuchElementException) {
                Timber.d("NO NOTIFICATION SOUNDS FOUND")
            }
        }
    }

    private fun getNotificationSounds(activity: Activity): HashMap<String, String> {
        val manager = RingtoneManager(activity)
        manager.setType(RingtoneManager.TYPE_NOTIFICATION)
        val cursor = manager.cursor

        val list = HashMap<String, String>()
        while (cursor.moveToNext()) {
            val id = cursor.getString(RingtoneManager.ID_COLUMN_INDEX)
            val uri = cursor.getString(RingtoneManager.URI_COLUMN_INDEX)
            val title = cursor.getString(RingtoneManager.TITLE_COLUMN_INDEX)

            list.set(title, "$uri/$id")
        }

        return list
    }

It can probably take some refactoring and optimization, but you should get the idea.

它可能需要一些重构和优化,但您应该明白这一点。

回答by Manthan Patel

  public void listRingtones() {
            RingtoneManager manager = new RingtoneManager(this);
            manager.setType(RingtoneManager.TYPE_NOTIFICATION);
           // manager.setType(RingtoneManager.TYPE_RINGTONE);//For Get System Ringtone
            Cursor cursor = manager.getCursor();

            while (cursor.moveToNext()) {
                String title = cursor.getString(RingtoneManager.TITLE_COLUMN_INDEX);
                String uri = manager.getRingtoneUri(cursor.getPosition());

                String ringtoneName= cursor.getString(cursor.getColumnIndex("title"));



                Log.e("All Data", "getNotifications: "+ title+"-=---"+uri+"------"+ringtoneName);
                // Do something with the title and the URI of ringtone
            }
        }