Como reproduzir um som de notificação do Android

169

Eu queria saber como eu poderia reproduzir um som de notificação sem reproduzi-lo no fluxo de mídia. No momento, posso fazer isso através do media player, mas não quero que ele seja reproduzido como um arquivo de mídia, quero que seja reproduzido como uma notificação, alerta ou toque. Aqui está um exemplo de como meu código se parece agora:

MediaPlayer mp = new MediaPlayer();
mp.reset();
mp.setDataSource(notificationsPath+ (String) apptSounds.getSelectedItem());
mp.prepare();
mp.start();
ninjasense
fonte

Respostas:

421

Se alguém ainda estiver procurando uma solução para isso, encontrei uma resposta em Como reproduzir som de toque / alarme no Android

try {
    Uri notification = RingtoneManager.getDefaultUri(RingtoneManager.TYPE_NOTIFICATION);
    Ringtone r = RingtoneManager.getRingtone(getApplicationContext(), notification);
    r.play();
} catch (Exception e) {
    e.printStackTrace();
}

Você pode alterar TYPE_NOTIFICATION para TYPE_ALARM, mas desejará acompanhar o toque r para parar de reproduzi-lo ... digamos, quando o usuário clicar em um botão ou algo assim.

Phidius
fonte
2
Os telefones da Motorola, por exemplo, estenderam a atividade de preferências e permitem ao usuário definir um som de notificação para sms e outras categorias. O método acima não funcionará com este tipo de telefone. Você tem alguma idéia de como resolver esse problema?
David
2
Eu tenho um erro com este: MediaPlayer - Should have subtitle controller already set. O que isso significa?
Deqing
Usando esta solução, após 28/29 vezes, o som para de tocar. Alguém sabe o porquê?
Tom Brinkkemper
1
Por que você pega todas as exceções? Qual deles pode ser jogado?
21317 Mih_x64
2
@ Sam, sim. stackoverflow.com/q/39876885/2614353 . Basicamente , não crie um objeto RingTone toda vez que o reproduzir. Crie-o uma vez e, em seguida, reproduza o mesmo objeto várias vezes.
Tom Brinkkemper
205

Agora você pode fazer isso incluindo o som ao criar uma notificação em vez de chamá-lo separadamente.

//Define Notification Manager
NotificationManager notificationManager = (NotificationManager) context.getSystemService(Context.NOTIFICATION_SERVICE);

//Define sound URI
Uri soundUri = RingtoneManager.getDefaultUri(RingtoneManager.TYPE_NOTIFICATION);

NotificationCompat.Builder mBuilder = new NotificationCompat.Builder(getApplicationContext())
        .setSmallIcon(icon)
        .setContentTitle(title)
        .setContentText(message)
        .setSound(soundUri); //This sets the sound to play

//Display notification
notificationManager.notify(0, mBuilder.build());
Rob Riddle
fonte
12
Isso resolve um problema diferente - não "como reproduzir um som de notificação", mas "como reproduzir uma notificação e exibir um som". A resposta aceita é justificada em sua solução.
Fabian Tamp #
7
Talvez você também deve definir isso para jogar através STREAM_NOTIFICATION por isso é jogado com o sistema operacional atual preferência volume de notificação: .setSound (soundUri, AudioManager.STREAM_NOTIFICATION)
mwk
@Rob Riddle Está funcionando bem. mas no caso de várias notificações, por exemplo, 100 notificações paralelas, o som se mistura com o próximo som de notificação. logicamente, se o som já estiver sendo reproduzido, aguarde a conclusão da reprodução anterior. Você pode ajudar neste cenário?
Waqas Ali Razzaq
não reproduz o som quando o aplicativo está em segundo plano. alguma sugestão?
Sagar Nayak
47

Se você deseja que um som de notificação padrão seja reproduzido, use o método setDefaults (int) da NotificationCompat.Builderclasse:

NotificationCompat.Builder mBuilder =
        new NotificationCompat.Builder(this)
                .setSmallIcon(R.drawable.ic_notification)
                .setContentTitle(getString(R.string.app_name))
                .setContentText(someText)
                .setDefaults(Notification.DEFAULT_SOUND)
                .setAutoCancel(true);

Acredito que seja a maneira mais fácil de realizar sua tarefa.

aga
fonte
não reproduz o som quando o aplicativo está em segundo plano. alguma sugestão?
Sagar Nayak 28/03
13

Tente o seguinte:

public void ringtone(){
    try {
        Uri notification = RingtoneManager.getDefaultUri(RingtoneManager.TYPE_NOTIFICATION);
        Ringtone r = RingtoneManager.getRingtone(getApplicationContext(), notification);
        r.play();
     } catch (Exception e) {
         e.printStackTrace();
     }
}
Ragu
fonte
9

Já faz um tempo desde a sua pergunta, mas ... Você já tentou definir o tipo de fluxo de áudio?

mp.setAudioStreamType(AudioManager.STREAM_NOTIFICATION);

Isso deve ser feito antes da preparação.

copolii
fonte
2

Eu tinha praticamente a mesma pergunta. Após algumas pesquisas, acho que, se você deseja reproduzir o "som de notificação" padrão do sistema, é necessário exibir uma notificação e dizer para usar o som padrão. E há algo a ser dito para o argumento em algumas das outras respostas: se você estiver tocando um som de notificação, também deverá apresentar uma mensagem de notificação.

No entanto, um pouco de ajustes na API de notificação e você pode se aproximar do que deseja. Você pode exibir uma notificação em branco e removê-la automaticamente após alguns segundos. Eu acho que isso vai funcionar para mim; Talvez funcione para você.

Criei um conjunto de métodos de conveniência nos com.globalmentor.android.app.Notifications.javaquais você pode criar um som de notificação como este:

Notifications.notify(this);

O LED também pisca e, se você tiver permissão para vibrar, ocorrerá uma vibração. Sim, um ícone de notificação aparecerá na barra de notificações, mas desaparecerá após alguns segundos.

Nesse ponto, você pode perceber que, como a notificação desaparecerá de qualquer maneira, você também pode ter uma mensagem de rolagem na barra de notificação; você pode fazer isso assim:

Notifications.notify(this, 5000, "This text will go away after five seconds.");

Existem muitos outros métodos de conveniência nesta classe. Você pode baixar a biblioteca inteira do repositório Subversion e construí-la com o Maven. Depende da biblioteca globalmentor-core, que também pode ser criada e instalada com o Maven.

Garret Wilson
fonte
É muito complicado simplesmente tocar um som. Você poderia apenas fazer isso: stackoverflow.com/a/9622040/1417267
slinden77
1

Você pode usar o Notification and NotificationManager para exibir a notificação desejada. Você pode personalizar o som que deseja reproduzir com sua notificação.

Valentin Rocher
fonte
5
Não desejo exibir uma notificação, apenas quero reproduzir o som.
Ninjasense
1

Eu acho que o conceito de "som de notificação" está de alguma forma errado para a interface do usuário do Android.

O comportamento esperado do Android é usar a notificação padrão para alertar o usuário. Se você tocar um som de notificação sem o ícone da barra de status, confundirá o usuário ("que som era esse? Não há ícone aqui, talvez eu esteja com problemas de audição?").

Como definir som em uma notificação, por exemplo, aqui: Configuração do som para notificação

think01
fonte
1
Na verdade, isso pode ser uma notificação no aplicativo. Por exemplo, se você estiver em um aplicativo de bate-papo e tiver pequenos efeitos sonoros para mensagens recebidas e enviadas. Essas são as notificações em essência e você deseja que elas sejam desligadas quando o telefone estiver no modo silencioso.
copolii 14/09/11
Bem, você está certo, mas isso é outra coisa. Eu estava falando (assumindo que esse era o tópico da pergunta) de "sons de notificação do sistema", que está na GUI do sistema Android. Claro, quando você está no seu próprio aplicativo, tudo depende de você.
think01
1
Intent intent = new Intent(this, MembersLocation.class);
    intent.addFlags(Intent.FLAG_ACTIVITY_CLEAR_TOP);
    intent.putExtra("type",type);
    intent.putExtra("sender",sender);
    PendingIntent pendingIntent = PendingIntent.getActivity(this, 0 /* Request code */, intent,
            PendingIntent.FLAG_ONE_SHOT);

    String channelId = getString(R.string.default_notification_channel_id);

    Uri Emergency_sound_uri=Uri.parse("android.resource://"+getPackageName()+"/raw/emergency_sound");
   // Uri Default_Sound_uri= RingtoneManager.getDefaultUri(RingtoneManager.TYPE_NOTIFICATION);
    if(type.equals("emergency"))
    {
        playSound=Emergency_sound_uri;
    }
    else
    {
        playSound= Settings.System.DEFAULT_NOTIFICATION_URI;
    }

    NotificationCompat.Builder notificationBuilder =
            new NotificationCompat.Builder(this, channelId)
                    .setSmallIcon(R.drawable.ic_notification)
                    .setContentTitle(title)
                    .setContentText(body)
                    .setSound(playSound, AudioManager.STREAM_NOTIFICATION)
                    .setAutoCancel(true)
                    .setColor(getColor(R.color.dark_red))
                    .setPriority(NotificationCompat.PRIORITY_HIGH)
                    .setContentIntent(pendingIntent);

   // notificationBuilder.setOngoing(true);//for Android notification swipe delete disabling...

    NotificationManager notificationManager =
            (NotificationManager) getSystemService(Context.NOTIFICATION_SERVICE);

    // Since android Oreo notification channel is needed.
    if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.O) {
        NotificationChannel channel = new NotificationChannel(channelId,
                "Channel human readable title",
                NotificationManager.IMPORTANCE_HIGH);
        AudioAttributes att = new AudioAttributes.Builder()
                .setUsage(AudioAttributes.USAGE_NOTIFICATION)
                .setContentType(AudioAttributes.CONTENT_TYPE_SPEECH)
                .build();
        channel.setSound(Emergency_sound_uri, att);
        if (notificationManager != null) {
            notificationManager.createNotificationChannel(channel);
        }
    }

    if (notificationManager != null) {
        notificationManager.notify(0 /* ID of notification */, notificationBuilder.build());
    }
}
dsc clg
fonte
1
Obrigado por este trecho de código, que pode fornecer ajuda imediata e limitada. Uma explicação adequada melhoraria muito seu valor a longo prazo, mostrando por que essa é uma boa solução para o problema e a tornaria mais útil para futuros leitores com outras perguntas semelhantes. Por favor edite sua resposta para adicionar alguma explicação, incluindo as suposições que você fez.
NOHS
0

Definir som para o canal de notificação

        Uri alarmUri = Uri.fromFile(new File(<path>));

        AudioAttributes attributes = new AudioAttributes.Builder()
                .setUsage(AudioAttributes.USAGE_ALARM)
                .build();

        channel.setSound(alarmUri, attributes);
Milind Chaudhary
fonte