Hoe u kunt bellen en sms gebruiken in Android-apps

In deze zelfstudie leert u meer over de Android-telefonie en SMS-API. U leert hoe u belt vanuit uw app en hoe u telefoonoproepgebeurtenissen controleert en hoe u sms-berichten kunt verzenden en ontvangen.

1. Hoe een oproep te doen 

Om te beginnen, laat ik u zien hoe u een oproep vanuit uw toepassing kunt starten door de telefoonkiezer-app of rechtstreeks vanuit uw app te gebruiken om het uw gebruikers gemakkelijker te maken.

Maak een nieuw Android Studio-project

Start Android Studio en maak een nieuw project met een lege activiteit genaamd Hoofdactiviteit.


Lay-out het scherm

Voor nu heeft onze lay-out gewoon een Tekst bewerken veld en een Wijzerplaat knop:

   

Wijzig de Hoofdactiviteit Klasse

In het onderstaande codeblok maken we een ACTION_DIAL bedoeling om de telefoonkiezer weer te geven. Het telefoonnummer wordt geparseerd vanuit onze tel URI-schema: tel: XXXXXXXX. Merk op dat u hiervoor geen toestemming nodig heeft om te werken:

importeer android.content.Intent; import android.net.Uri; import android.os.Bundle; import android.support.v7.app.AppCompatActivity; importeer android.text.TextUtils; import android.view.View; importeer android.widget.Button; importeer android.widget.EditText; import android.widget.Toast; public class MainActivity breidt AppCompatActivity uit @Override protected void onCreate (Bundle savedInstanceState) super.onCreate (savedInstanceState); setContentView (R.layout.activity_main); Knop mDialButton = (Knop) findViewById (R.id.btn_dial); final EditText mPhoneNoEt = (EditText) findViewById (R.id.et_phone_no); mDialButton.setOnClickListener (nieuwe View.OnClickListener () @Override public void onClick (View view) String phoneNo = mPhoneNoEt.getText (). toString (); if (! TextUtils.isEmpty (phoneNo)) String dial = "tel : "+ phoneNo; startActivity (new Intent (Intent.ACTION_DIAL, Uri.parse (dial)); else Toast.makeText (MainActivity.this," Voer een telefoonnummer in ", Toast.LENGTH_SHORT) .show (); ); 

Als u de app uitvoert en op de knop klikt, wordt u naar de dialer-app geleid en vanaf daar moet u het nummer daadwerkelijk bellen. U kunt deze stroom wijzigen om de oproep vanuit uw app daadwerkelijk te voeren door simpelweg de ACTION_DIAL bedoeling om ACTION_CALL in plaats daarvan. Dit vereist de android.permission.CALL_PHONE toestemming. 

2. Bewaken van telefoongebeurtenissen

In dit gedeelte gaan we leren hoe we telefoonoproepgebeurtenissen in het Android-systeem kunnen volgen. De telefoon kan in drie staten zijn: 

  1. inactief (wanneer het niet wordt gebruikt)
  2. rinkelen (wanneer er een inkomende oproep is)
  3. van de haak (wanneer de oproep wordt beantwoord)

Voeg de toestemming toe 

We hebben de toestemming nodig READ_PHONE_STATE om de telefoonstatus te kunnen controleren. Voeg het toe aan AndroidManifest.xml:

Maak het PhoneStateListener Voorwerp

We maken een object van de PhoneStateListener klasse en negeer de bijbehorende onCallStateChanged () methode (in IntelliJ is dit eenvoudig om mee te doen Ctrl-O, en selecteer dan of zoek naar de methode om te negeren). We behandelen wijzigingen in de statuswijzigingen door een a weer te geven Geroosterd brood. Houd er rekening mee dat we ook toegang kunnen krijgen tot de inkomende telefoonnummers wanneer deze methode wordt geactiveerd:

// ... PhoneStateListener mPhoneStateListener = new PhoneStateListener () @Override public void onCallStateChanged (int state, String incoming Number) super.onCallStateChanged (state, incomingNumber); switch (state) case TelephonyManager.CALL_STATE_IDLE: Toast.makeText (MainActivity.this, "CALL_STATE_IDLE", Toast.LENGTH_SHORT) .show (); breken; case TelephonyManager.CALL_STATE_RINGING: Toast.makeText (MainActivity.this, "CALL_STATE_RINGING", Toast.LENGTH_SHORT) .show (); breken; case TelephonyManager.CALL_STATE_OFFHOOK: Toast.makeText (MainActivity.this, "CALL_STATE_OFFHOOK", Toast.LENGTH_SHORT) .show (); breken; ; // ... 

Afhankelijk van uw toepassingsbehoeften, kunt u ook een van deze andere evenementmethoden overschrijven: onCellInfoChanged ()onCallForwardingIndicatorChanged ()onCellLocationChanged (), of onSignalStrengthChanged ().

Luisteren naar de telefoonoproepstatus

Om te beginnen met luisteren naar de status van het telefoongesprek, moeten we de TelephonyManager van de systeemservice en initialiseer het in onCreate ().

// ... private TelephonyManager mTelephonyManager; @Override protected void onCreate (Bundle savedInstanceState) // ... mTelephonyManager = (TelephonyManager) getSystemService (getApplicationContext (). TELEPHONY_SERVICE); 

In de onResume () methode, kunnen we beginnen te luisteren met behulp van de TelephonyManager luister() methode, het doorgeven van de PhoneStateListener instantie en de statische LISTEN_CALL_STATE. We stoppen met luisteren in de onStop () methode door de LISTEN_NONE als het tweede argument voor luister().

// ... @Override beschermde leegte onResume () super.onResume (); mTelephonyManager.listen (mPhoneStateListener, PhoneStateListener.LISTEN_CALL_STATE);  @Override beschermde ongeldig onStop () super.onStop (); mTelephonyManager.listen (mPhoneStateListener, PhoneStateListener.LISTEN_NONE);  // ... 

Andere telefoonbeluisteropties zijn mogelijk LISTEN_CELL_LOCATIONLISTEN_SIGNAL_STRENGTHLISTEN_CALL_FORWARDING_INDICATOR, en LISTEN_CELL_INFO.

Eindelijk, voer de app uit en zorg ervoor dat er een binnenkomend gesprek binnenkomt. 

Deze monitoring werkt alleen als de app op de voorgrond staat. Om dit op de achtergrond te laten werken (als onze applicatie niet actief is), moeten we een Uitzending ontvanger zodat zelfs als de app niet actief is, we nog steeds kunnen controleren op telefoongesprekken. Afhankelijk van uw app-vereisten, zou dat een veel betere manier kunnen zijn om te luisteren naar statuswijzigingen van telefoongesprekken. Ik zal je laten zien hoe je dit in het volgende gedeelte kunt doen.

Houd er rekening mee dat we alleen inkomende oproepen controleren. Voor ons om uitgaande oproepen te controleren, hebben we extra rechten nodig. Als u uitgaande oproepen wilt controleren, neemt u de volgende regel op in uw AndroidManifest.xml het dossier.

 

De emulator gebruiken om te bellen en sms-berichten te verzenden

U kunt uw emulator gebruiken om te simuleren om te bellen of een SMS-bericht te verzenden, maar u moet wel een beetje instellen. Open uw emulator, klik op de laatste knop op de navigatiebalk aan de rechterkant om het uitgebreide besturingsvenster te openen en selecteer vervolgens de regelknop voor de telefoon. 

3. Monitoring van telefoongebeurtenissen op de achtergrond

Maak een BroadcastReceiver

Net als in het vorige gedeelte moeten we een gebeurtenislistener maken om wijzigingen in de telefoonstatus te controleren. Het grote verschil is dat we deze keer de Uitzending ontvanger basisklasse, zodat we kunnen luisteren naar de status van het telefoongesprek, zelfs als de toepassing niet actief is. Zorg ervoor dat u de luisteraar niet meerdere keren registreert! Onze controle hierop is op regel 36.

import android.content.BroadcastReceiver; importeer android.content.Context; importeer android.content.Intent; import android.telephony.PhoneStateListener; import android.telephony.TelephonyManager; import android.widget.Toast; openbare klasse PhoneCallStateReceiver breidt BroadcastReceiver uit private TelephonyManager mTelephonyManager; public static boolean isListening = false; @Override public void onReceive (laatste context context, Intent opzet) mTelephonyManager = (TelephonyManager) context.getSystemService (context.TELEPHONY_SERVICE); PhoneStateListener mPhoneStateListener = new PhoneStateListener () @Override public void onCallStateChanged (int state, String incoming Number) super.onCallStateChanged (state, incomingNumber); switch (state) case TelephonyManager.CALL_STATE_IDLE: Toast.makeText (context, "CALL_STATE_IDLE", Toast.LENGTH_SHORT) .show (); breken; case TelephonyManager.CALL_STATE_RINGING: Toast.makeText (context, "CALL_STATE_RINGING", Toast.LENGTH_SHORT) .show (); breken; case TelephonyManager.CALL_STATE_OFFHOOK: Toast.makeText (context, "CALL_STATE_OFFHOOK", Toast.LENGTH_SHORT) .show (); breken; ; if (! isListening) mTelephonyManager.listen (mPhoneStateListener, PhoneStateListener.LISTEN_CALL_STATE); isListening = true; 

Wijzigen AndroidManifest.xml

Een uitzendontvanger werkt alleen als deze is geregistreerd. We moeten het Android-systeem vertellen over onze uitzendontvanger door het te registreren in de AndroidManifest.xml bestand door ons te verbinden PhoneCallStateReceiver klasse voor de die de systeemuitzending beschrijft die we willen ontvangen, in dit geval, PHONE_STATE.

    

Uitgaande gesprekken bewaken

Voor uitgaande oproepen moet u de NEW_OUTGOING_CALL actie opzet  in de van de ontvanger in AndroidManifest.xml

Om het telefoonnummer van de geplande uitgaande oproep te krijgen, in de onReceive (Context, Intent) methode, we krijgen het nummer van de intentie als een extra. Om te voorkomen dat de bedoelde oproep doorkomt, kunnen we bellen setResultData () en geef het een nul argument. De resultData wordt gebruikt als het daadwerkelijke nummer om te bellen. 

@Override public void onReceive (laatste context context, Intent opzet) // voor uitgaand gesprek String outgoingPhoneNo = intent.getStringExtra (Intent.EXTRA_PHONE_NUMBER) .toString (); // verhinder uitgaand gesprek setResultData (nul); 

U kunt meer leren over uitzendingen en uitzendontvangers in onze tutorial hier op Envato Tuts +:

4. SMS-berichten verzenden

U hebt slechts twee belangrijke keuzes voor het verzenden van sms-berichten: het gebruik van de sms-clienttoepassing van het apparaat of het overslaan van de client door de sms rechtstreeks vanuit uw app te verzenden. We zullen beide scenario's bekijken en u kunt beslissen welke het beste is voor uw gebruik. Laten we beginnen met het verzenden van een sms met de SMS-client van het apparaat.

Stel de lay-out in

Ten eerste moeten we onze hoofdlay-out wijzigen om een Tekst bewerken veld voor het bericht en een Bericht versturen knop.

  

Wijzig de MainActivity 

In onze onCreate () methode in onze Hoofdactiviteit klasse, maak een intentie aan met ACTION_SENDTO als het eerste argument en een smsto: URI als het tweede argument. Het SMS-bericht is de waarde van de SMS_BODY extra: 

// ... Button sendMessageBtn = (Button) findViewById (R.id.btn_send_message); final EditText messagetEt = (EditText) findViewById (R.id.et_message); sendMessageBtn.setOnClickListener (new View.OnClickListener () @Override public void onClick (View view) String message = messagetEt.getText (). toString (); String phoneNo = mPhoneNoEt.getText (). toString (); if (! TextUtils.isEmpty (bericht) &&! TextUtils.isEmpty (phoneNo)) Intent smsIntent = new Intent (Intent.ACTION_SENDTO, Uri.parse ("smsto:" + phoneNo)); smsIntent.putExtra ("sms_body", bericht); startActivity (smsIntent);); // ... 

Hier controleert de SMS-client de status van de bezorging van het bericht. 

Voer de app uit

Wanneer alle verplichte velden zijn ingevoerd, klikt u op Verstuur sms knop opent de SMS-client van de gebruiker of geeft de gebruiker opties om een ​​app te selecteren als er nog geen is gekozen.

5. SMS-berichten rechtstreeks verzenden

Laten we hierna eens kijken hoe we de sms direct vanuit onze applicatie kunnen verzenden in plaats van de sms-client van het apparaat te gebruiken. 

Voeg toestemming toe AndroidManifest.xml

Zoals gewoonlijk moeten we de toestemming registreren in AndroidManifest.xml.

 

Wijzig de klasse MainActivity 

Vervolgens moeten we voor Android 6.0 (API level 23) en hoger de VERSTUUR SMS toestemming tijdens runtime. 

Voor meer informatie over Android-runtimemachtigingen en hoe deze zijn gewijzigd in versie 6.0, raadpleegt u onze zelfstudie hier op Envato Tuts +:

Voor het verzenden van een sms krijgen we de standaard SmsManager voorbeeld en bel dan de sendTextMessage () methode, waarbij het telefoonnummer als het eerste argument wordt doorgegeven en het bericht als het tweede argument:

// ... final int SEND_SMS_PERMISSION_REQUEST_CODE = 111; private Button mSendMessageBtn; @Override protected void onCreate (Bundle savedInstanceState) // ... mSendMessageBtn = (Button) findViewById (R.id.btn_send_message); final EditText messagetEt = (EditText) findViewById (R.id.et_message); mSendMessageBtn.setEnabled (false); if (checkPermission (Manifest.permission.SEND_SMS)) mSendMessageBtn.setEnabled (true);  else ActivityCompat.requestPermissions (this, new String [] Manifest.permission.SEND_SMS, SEND_SMS_PERMISSION_REQUEST_CODE);  mSendMessageBtn.setOnClickListener (new View.OnClickListener () @Override public void onClick (View view) String message = messagetEt.getText (). toString (); String phoneNo = mPhoneNoEt.getText (). toString (); if ( ! TextUtils.isEmpty (bericht) &&! TextUtils.isEmpty (phoneNo)) if (checkPermission (Manifest.permission.SEND_SMS)) SmsManager smsManager = SmsManager.getDefault (); smsManager.sendTextMessage (phoneNo, null, message, null, null); else Toast.makeText (MainActivity.this, "Toestemming geweigerd", Toast.LENGTH_SHORT) .show (););  private boolean checkPermission (String permission) int checkPermission = ContextCompat.checkSelfPermission (this, permission); return (checkPermission == PackageManager.PERMISSION_GRANTED);  @Override public void onRequestPermissionsResult (int requestCode, @NonNull String [] permissies, @NonNull int [] grantResults) switch (requestCode) case SEND_SMS_PERMISSION_REQUEST_CODE: if (grantResults.length> 0 && (grantResults [0] == PackageManager .PERMISSION_GRANTED)) mSendMessageBtn.setEnabled (true);  terug;  // ... 

Om de status van levering te controleren, de SMSManager sendTextMessage () methode heeft twee optionele PendingIntent parameters: sentIntent en deliveryIntent.

void sendTextMessage (String destinationAddress, String scAddress, String text, PendingIntent sentIntent, PendingIntent deliveryIntent)

Als je wilt gebruiken sentIntent, let op de resultaatcode Activity.RESULT_OK op succes, of een van RESULT_ERROR_GENERIC_FAILURERESULT_ERROR_RADIO_OFF, en RESULT_ERROR_NULL_PDU om een ​​fout aan te geven.

6. Een sms-bericht ontvangen

Om ervoor te zorgen dat uw app begint met het ontvangen van sms-berichten van de telefoon van de gebruiker, is het het beste om een ​​uitzendontvanger geregistreerd te hebben zodat deze kan worden gewaarschuwd wanneer een nieuw sms-bericht binnenkomt, zelfs als uw app niet op de voorgrond wordt uitgevoerd. 

Voeg de toestemming toe 

Voeg de toe RECEIVE_SMS toestemming om AndroidManifest.xml:

Vervolgens moeten we controleren of de app toestemming heeft om tijdens runtime sms-berichten te ontvangen. Dus in de Hoofdactiviteit klas, kijk voor de RECEIVE_SMS toestemming. Als het niet wordt gevonden, vraag het dan aan.

// ... @Override protected void onCreate (Bundle savedInstanceState) // ... if (! CheckPermission (Manifest.permission.RECEIVE_SMS)) ActivityCompat.requestPermissions (this, new String [] Manifest.permission.RECEIVE_SMS, 222);  // ... 

Maak een broadcast-ontvanger

We halen elk object van de SmsMessage klasse door de methode te gebruiken createFromPdu (byte [] pdu), het doorgeven van een PDU (protocol data-eenheid). We voegen het dan toe aan onze berichtenreeks. 

Als u API 23 en hoger wilt ondersteunen, moet u de indeling String extra opnemen (ofwel "3gpp" voor GSM / UMTS / LTE-berichten in 3GPP-indeling of "3gpp2" voor CDMA / LTE-berichten in 3GPP2-indeling). 

import android.content.BroadcastReceiver; importeer android.content.Context; importeer android.content.Intent; import android.os.Build; import android.os.Bundle; import android.telephony.SmsMessage; import android.widget.Toast; openbare klasse SMSReceiver breidt BroadcastReceiver uit @Overleden openbare ongeldig voor Ongewenst (Contextcontext, Intent opzet) Bundel bundle = intent.getExtras (); if (bundle! = null) Object [] pdus = (Object []) bundle.get ("pdus"); Tekenreeksindeling = bundle.getString ("indeling"); laatste SmsMessage [] berichten = nieuwe SmsMessage [pdus.length]; voor (int i = 0; i < pdus.length; i++)  if(Build.VERSION.SDK_INT >= Build.VERSION_CODES.M) messages [i] = SmsMessage.createFromPdu ((byte []) pdus [i], format);  else messages [i] = SmsMessage.createFromPdu ((byte []) pdus [i]);  String senderPhoneNo = berichten [i] .getDisplayOriginatingAddress (); Toast.makeText (context, "Message" + messages [0] .getMessageBody () + ", from" + senderPhoneNo, Toast.LENGTH_SHORT) .show (); 

Start nu de app, sluit hem en verzend uw geëmuleerde telefoon een sms.

Conclusie

In deze tutorial leerde je over:

  • bellen vanuit uw app
  • het bewaken van telefoongesprekken
  • verzenden van sms-berichten met behulp van de apparaat-app voor berichten of rechtstreeks vanuit uw eigen app
  • ontvangen van sms-berichten op de achtergrond

Er is veel meer dat u kunt doen met telefoontjes en sms-berichten in Android. Ga naar de Android Telephony API en de API-documentatie van SMSManager voor meer informatie. 

Bekijk in de tussentijd enkele van onze andere berichten over Android-ontwikkeling!

  • Android-sensoren in de diepte: nabijheid en gyroscoop

    Gyroscopen en naderingssensoren zijn tegenwoordig beschikbaar op de meeste Android-telefoons. Door ze op een creatieve manier te gebruiken, kunt u een geheel nieuwe dimensie aan uw gebruiker toevoegen ...
    Ashraff Hathibelagal
    Android SDK
  • 6 Do's and Don'ts voor een geweldige Android-gebruikerservaring

    De populairste Android-apps hebben iets gemeen: ze bieden allemaal een geweldige gebruikerservaring. In dit bericht deel ik wat tips die je app helpen ...
    Jessica Thornsby
    Android SDK
  • Achtergrondaudio in Android met MediaSessionCompat

    Een van de populairste toepassingen voor mobiele apparaten is het afspelen van audio via services voor muziekstreaming, gedownloade podcasts of een ander aantal audio ...
    Paul Trebilcox-Ruiz
    Android SDK
  • Migreer een Android-app naar Material Design

    Jaren geleden, toen Android nog een ontluikend mobiel besturingssysteem was, was het nogal berucht om zijn lelijke gebruikersinterface. Omdat er geen ontwerp was ...
    Ashraff Hathibelagal
    Android