ImsCallSession.java revision 8887294f480ccedb16c1938c2214e08580d2d7cc
1/* 2 * Copyright (c) 2013 The Android Open Source Project 3 * 4 * Licensed under the Apache License, Version 2.0 (the "License"); 5 * you may not use this file except in compliance with the License. 6 * You may obtain a copy of the License at 7 * 8 * http://www.apache.org/licenses/LICENSE-2.0 9 * 10 * Unless required by applicable law or agreed to in writing, software 11 * distributed under the License is distributed on an "AS IS" BASIS, 12 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 13 * See the License for the specific language governing permissions and 14 * limitations under the License. 15 */ 16 17package com.android.ims.internal; 18 19import android.os.Message; 20import android.os.RemoteException; 21import android.telecom.Connection; 22 23import com.android.ims.ImsCallProfile; 24import com.android.ims.ImsConferenceState; 25import com.android.ims.ImsReasonInfo; 26import com.android.ims.ImsStreamMediaProfile; 27import com.android.ims.ImsSuppServiceNotification; 28 29/** 30 * Provides the call initiation/termination, and media exchange between two IMS endpoints. 31 * It directly communicates with IMS service which implements the IMS protocol behavior. 32 * 33 * @hide 34 */ 35public class ImsCallSession { 36 private static final String TAG = "ImsCallSession"; 37 38 /** 39 * Defines IMS call session state. 40 */ 41 public static class State { 42 public static final int IDLE = 0; 43 public static final int INITIATED = 1; 44 public static final int NEGOTIATING = 2; 45 public static final int ESTABLISHING = 3; 46 public static final int ESTABLISHED = 4; 47 48 public static final int RENEGOTIATING = 5; 49 public static final int REESTABLISHING = 6; 50 51 public static final int TERMINATING = 7; 52 public static final int TERMINATED = 8; 53 54 public static final int INVALID = (-1); 55 56 /** 57 * Converts the state to string. 58 */ 59 public static String toString(int state) { 60 switch (state) { 61 case IDLE: 62 return "IDLE"; 63 case INITIATED: 64 return "INITIATED"; 65 case NEGOTIATING: 66 return "NEGOTIATING"; 67 case ESTABLISHING: 68 return "ESTABLISHING"; 69 case ESTABLISHED: 70 return "ESTABLISHED"; 71 case RENEGOTIATING: 72 return "RENEGOTIATING"; 73 case REESTABLISHING: 74 return "REESTABLISHING"; 75 case TERMINATING: 76 return "TERMINATING"; 77 case TERMINATED: 78 return "TERMINATED"; 79 default: 80 return "UNKNOWN"; 81 } 82 } 83 84 private State() { 85 } 86 } 87 88 /** 89 * Listener for events relating to an IMS session, such as when a session is being 90 * recieved ("on ringing") or a call is outgoing ("on calling"). 91 * <p>Many of these events are also received by {@link ImsCall.Listener}.</p> 92 */ 93 public static class Listener { 94 /** 95 * Called when a request is sent out to initiate a new session 96 * and 1xx response is received from the network. 97 * 98 * @param session the session object that carries out the IMS session 99 */ 100 public void callSessionProgressing(ImsCallSession session, 101 ImsStreamMediaProfile profile) { 102 // no-op 103 } 104 105 /** 106 * Called when the session is established. 107 * 108 * @param session the session object that carries out the IMS session 109 */ 110 public void callSessionStarted(ImsCallSession session, 111 ImsCallProfile profile) { 112 // no-op 113 } 114 115 /** 116 * Called when the session establishment is failed. 117 * 118 * @param session the session object that carries out the IMS session 119 * @param reasonInfo detailed reason of the session establishment failure 120 */ 121 public void callSessionStartFailed(ImsCallSession session, 122 ImsReasonInfo reasonInfo) { 123 } 124 125 /** 126 * Called when the session is terminated. 127 * 128 * @param session the session object that carries out the IMS session 129 * @param reasonInfo detailed reason of the session termination 130 */ 131 public void callSessionTerminated(ImsCallSession session, 132 ImsReasonInfo reasonInfo) { 133 } 134 135 /** 136 * Called when the session is in hold. 137 * 138 * @param session the session object that carries out the IMS session 139 */ 140 public void callSessionHeld(ImsCallSession session, 141 ImsCallProfile profile) { 142 } 143 144 /** 145 * Called when the session hold is failed. 146 * 147 * @param session the session object that carries out the IMS session 148 * @param reasonInfo detailed reason of the session hold failure 149 */ 150 public void callSessionHoldFailed(ImsCallSession session, 151 ImsReasonInfo reasonInfo) { 152 } 153 154 /** 155 * Called when the session hold is received from the remote user. 156 * 157 * @param session the session object that carries out the IMS session 158 */ 159 public void callSessionHoldReceived(ImsCallSession session, 160 ImsCallProfile profile) { 161 } 162 163 /** 164 * Called when the session resume is done. 165 * 166 * @param session the session object that carries out the IMS session 167 */ 168 public void callSessionResumed(ImsCallSession session, 169 ImsCallProfile profile) { 170 } 171 172 /** 173 * Called when the session resume is failed. 174 * 175 * @param session the session object that carries out the IMS session 176 * @param reasonInfo detailed reason of the session resume failure 177 */ 178 public void callSessionResumeFailed(ImsCallSession session, 179 ImsReasonInfo reasonInfo) { 180 } 181 182 /** 183 * Called when the session resume is received from the remote user. 184 * 185 * @param session the session object that carries out the IMS session 186 */ 187 public void callSessionResumeReceived(ImsCallSession session, 188 ImsCallProfile profile) { 189 } 190 191 /** 192 * Called when the session merge has been started. At this point, the {@code newSession} 193 * represents the session which has been initiated to the IMS conference server for the 194 * new merged conference. 195 * 196 * @param session the session object that carries out the IMS session 197 * @param newSession the session object that is merged with an active & hold session 198 */ 199 public void callSessionMergeStarted(ImsCallSession session, 200 ImsCallSession newSession, ImsCallProfile profile) { 201 } 202 203 /** 204 * Called when the session merge is successful and the merged session is active. 205 * 206 * @param session the session object that carries out the IMS session 207 */ 208 public void callSessionMergeComplete(ImsCallSession session) { 209 } 210 211 /** 212 * Called when the session merge has failed. 213 * 214 * @param session the session object that carries out the IMS session 215 * @param reasonInfo detailed reason of the call merge failure 216 */ 217 public void callSessionMergeFailed(ImsCallSession session, 218 ImsReasonInfo reasonInfo) { 219 } 220 221 /** 222 * Called when the session is updated (except for hold/unhold). 223 * 224 * @param call the call object that carries out the IMS call 225 */ 226 public void callSessionUpdated(ImsCallSession session, 227 ImsCallProfile profile) { 228 } 229 230 /** 231 * Called when the session update is failed. 232 * 233 * @param session the session object that carries out the IMS session 234 * @param reasonInfo detailed reason of the session update failure 235 */ 236 public void callSessionUpdateFailed(ImsCallSession session, 237 ImsReasonInfo reasonInfo) { 238 } 239 240 /** 241 * Called when the session update is received from the remote user. 242 * 243 * @param session the session object that carries out the IMS session 244 */ 245 public void callSessionUpdateReceived(ImsCallSession session, 246 ImsCallProfile profile) { 247 // no-op 248 } 249 250 /** 251 * Called when the session is extended to the conference session. 252 * 253 * @param session the session object that carries out the IMS session 254 * @param newSession the session object that is extended to the conference 255 * from the active session 256 */ 257 public void callSessionConferenceExtended(ImsCallSession session, 258 ImsCallSession newSession, ImsCallProfile profile) { 259 } 260 261 /** 262 * Called when the conference extension is failed. 263 * 264 * @param session the session object that carries out the IMS session 265 * @param reasonInfo detailed reason of the conference extension failure 266 */ 267 public void callSessionConferenceExtendFailed(ImsCallSession session, 268 ImsReasonInfo reasonInfo) { 269 } 270 271 /** 272 * Called when the conference extension is received from the remote user. 273 * 274 * @param session the session object that carries out the IMS session 275 */ 276 public void callSessionConferenceExtendReceived(ImsCallSession session, 277 ImsCallSession newSession, ImsCallProfile profile) { 278 // no-op 279 } 280 281 /** 282 * Called when the invitation request of the participants is delivered to the conference 283 * server. 284 * 285 * @param session the session object that carries out the IMS session 286 */ 287 public void callSessionInviteParticipantsRequestDelivered(ImsCallSession session) { 288 // no-op 289 } 290 291 /** 292 * Called when the invitation request of the participants is failed. 293 * 294 * @param session the session object that carries out the IMS session 295 * @param reasonInfo detailed reason of the conference invitation failure 296 */ 297 public void callSessionInviteParticipantsRequestFailed(ImsCallSession session, 298 ImsReasonInfo reasonInfo) { 299 // no-op 300 } 301 302 /** 303 * Called when the removal request of the participants is delivered to the conference 304 * server. 305 * 306 * @param session the session object that carries out the IMS session 307 */ 308 public void callSessionRemoveParticipantsRequestDelivered(ImsCallSession session) { 309 // no-op 310 } 311 312 /** 313 * Called when the removal request of the participants is failed. 314 * 315 * @param session the session object that carries out the IMS session 316 * @param reasonInfo detailed reason of the conference removal failure 317 */ 318 public void callSessionRemoveParticipantsRequestFailed(ImsCallSession session, 319 ImsReasonInfo reasonInfo) { 320 // no-op 321 } 322 323 /** 324 * Called when the conference state is updated. 325 * 326 * @param session the session object that carries out the IMS session 327 */ 328 public void callSessionConferenceStateUpdated(ImsCallSession session, 329 ImsConferenceState state) { 330 // no-op 331 } 332 333 /** 334 * Called when the USSD message is received from the network. 335 * 336 * @param mode mode of the USSD message (REQUEST / NOTIFY) 337 * @param ussdMessage USSD message 338 */ 339 public void callSessionUssdMessageReceived(ImsCallSession session, 340 int mode, String ussdMessage) { 341 // no-op 342 } 343 344 /** 345 * Called when session access technology changes 346 * 347 * @param session IMS session object 348 * @param srcAccessTech original access technology 349 * @param targetAccessTech new access technology 350 * @param reasonInfo 351 */ 352 public void callSessionHandover(ImsCallSession session, 353 int srcAccessTech, int targetAccessTech, 354 ImsReasonInfo reasonInfo) { 355 // no-op 356 } 357 358 /** 359 * Called when session access technology change fails 360 * 361 * @param session IMS session object 362 * @param srcAccessTech original access technology 363 * @param targetAccessTech new access technology 364 * @param reasonInfo handover failure reason 365 */ 366 public void callSessionHandoverFailed(ImsCallSession session, 367 int srcAccessTech, int targetAccessTech, 368 ImsReasonInfo reasonInfo) { 369 // no-op 370 } 371 372 /** 373 * Called when TTY mode of remote party changed 374 * 375 * @param session IMS session object 376 * @param mode TTY mode of remote party 377 */ 378 public void callSessionTtyModeReceived(ImsCallSession session, 379 int mode) { 380 // no-op 381 } 382 383 /** 384 * Notifies of a change to the multiparty state for this {@code ImsCallSession}. 385 * 386 * @param session The call session. 387 * @param isMultiParty {@code true} if the session became multiparty, {@code false} 388 * otherwise. 389 */ 390 public void callSessionMultipartyStateChanged(ImsCallSession session, 391 boolean isMultiParty) { 392 // no-op 393 } 394 395 /** 396 * Called when the session supplementary service is received 397 * 398 * @param session the session object that carries out the IMS session 399 */ 400 public void callSessionSuppServiceReceived(ImsCallSession session, 401 ImsSuppServiceNotification suppServiceInfo) { 402 } 403 } 404 405 private final IImsCallSession miSession; 406 private boolean mClosed = false; 407 private Listener mListener; 408 409 public ImsCallSession(IImsCallSession iSession) { 410 miSession = iSession; 411 412 if (iSession != null) { 413 try { 414 iSession.setListener(new IImsCallSessionListenerProxy()); 415 } catch (RemoteException e) { 416 } 417 } else { 418 mClosed = true; 419 } 420 } 421 422 public ImsCallSession(IImsCallSession iSession, Listener listener) { 423 this(iSession); 424 setListener(listener); 425 } 426 427 /** 428 * Closes this object. This object is not usable after being closed. 429 */ 430 public synchronized void close() { 431 if (mClosed) { 432 return; 433 } 434 435 try { 436 miSession.close(); 437 mClosed = true; 438 } catch (RemoteException e) { 439 } 440 } 441 442 /** 443 * Gets the call ID of the session. 444 * 445 * @return the call ID 446 */ 447 public String getCallId() { 448 if (mClosed) { 449 return null; 450 } 451 452 try { 453 return miSession.getCallId(); 454 } catch (RemoteException e) { 455 return null; 456 } 457 } 458 459 /** 460 * Gets the call profile that this session is associated with 461 * 462 * @return the call profile that this session is associated with 463 */ 464 public ImsCallProfile getCallProfile() { 465 if (mClosed) { 466 return null; 467 } 468 469 try { 470 return miSession.getCallProfile(); 471 } catch (RemoteException e) { 472 return null; 473 } 474 } 475 476 /** 477 * Gets the local call profile that this session is associated with 478 * 479 * @return the local call profile that this session is associated with 480 */ 481 public ImsCallProfile getLocalCallProfile() { 482 if (mClosed) { 483 return null; 484 } 485 486 try { 487 return miSession.getLocalCallProfile(); 488 } catch (RemoteException e) { 489 return null; 490 } 491 } 492 493 /** 494 * Gets the remote call profile that this session is associated with 495 * 496 * @return the remote call profile that this session is associated with 497 */ 498 public ImsCallProfile getRemoteCallProfile() { 499 if (mClosed) { 500 return null; 501 } 502 503 try { 504 return miSession.getRemoteCallProfile(); 505 } catch (RemoteException e) { 506 return null; 507 } 508 } 509 510 /** 511 * Gets the video call provider for the session. 512 * 513 * @return The video call provider. 514 */ 515 public IImsVideoCallProvider getVideoCallProvider() { 516 if (mClosed) { 517 return null; 518 } 519 520 try { 521 return miSession.getVideoCallProvider(); 522 } catch (RemoteException e) { 523 return null; 524 } 525 } 526 527 /** 528 * Gets the value associated with the specified property of this session. 529 * 530 * @return the string value associated with the specified property 531 */ 532 public String getProperty(String name) { 533 if (mClosed) { 534 return null; 535 } 536 537 try { 538 return miSession.getProperty(name); 539 } catch (RemoteException e) { 540 return null; 541 } 542 } 543 544 /** 545 * Gets the session state. 546 * The value returned must be one of the states in {@link State}. 547 * 548 * @return the session state 549 */ 550 public int getState() { 551 if (mClosed) { 552 return State.INVALID; 553 } 554 555 try { 556 return miSession.getState(); 557 } catch (RemoteException e) { 558 return State.INVALID; 559 } 560 } 561 562 /** 563 * Determines if the {@link ImsCallSession} is currently alive (e.g. not in a terminated or 564 * closed state). 565 * 566 * @return {@code True} if the session is alive. 567 */ 568 public boolean isAlive() { 569 if (mClosed) { 570 return false; 571 } 572 573 int state = getState(); 574 switch (state) { 575 case State.IDLE: 576 case State.INITIATED: 577 case State.NEGOTIATING: 578 case State.ESTABLISHING: 579 case State.ESTABLISHED: 580 case State.RENEGOTIATING: 581 case State.REESTABLISHING: 582 return true; 583 default: 584 return false; 585 } 586 } 587 588 /** 589 * Gets the native IMS call session. 590 * @hide 591 */ 592 public IImsCallSession getSession() { 593 return miSession; 594 } 595 596 /** 597 * Checks if the session is in call. 598 * 599 * @return true if the session is in call 600 */ 601 public boolean isInCall() { 602 if (mClosed) { 603 return false; 604 } 605 606 try { 607 return miSession.isInCall(); 608 } catch (RemoteException e) { 609 return false; 610 } 611 } 612 613 /** 614 * Sets the listener to listen to the session events. A {@link ImsCallSession} 615 * can only hold one listener at a time. Subsequent calls to this method 616 * override the previous listener. 617 * 618 * @param listener to listen to the session events of this object 619 */ 620 public void setListener(Listener listener) { 621 mListener = listener; 622 } 623 624 /** 625 * Mutes or unmutes the mic for the active call. 626 * 627 * @param muted true if the call is muted, false otherwise 628 */ 629 public void setMute(boolean muted) { 630 if (mClosed) { 631 return; 632 } 633 634 try { 635 miSession.setMute(muted); 636 } catch (RemoteException e) { 637 } 638 } 639 640 /** 641 * Initiates an IMS call with the specified target and call profile. 642 * The session listener is called back upon defined session events. 643 * The method is only valid to call when the session state is in 644 * {@link ImsCallSession#State#IDLE}. 645 * 646 * @param callee dialed string to make the call to 647 * @param profile call profile to make the call with the specified service type, 648 * call type and media information 649 * @see Listener#callSessionStarted, Listener#callSessionStartFailed 650 */ 651 public void start(String callee, ImsCallProfile profile) { 652 if (mClosed) { 653 return; 654 } 655 656 try { 657 miSession.start(callee, profile); 658 } catch (RemoteException e) { 659 } 660 } 661 662 /** 663 * Initiates an IMS conference call with the specified target and call profile. 664 * The session listener is called back upon defined session events. 665 * The method is only valid to call when the session state is in 666 * {@link ImsCallSession#State#IDLE}. 667 * 668 * @param participants participant list to initiate an IMS conference call 669 * @param profile call profile to make the call with the specified service type, 670 * call type and media information 671 * @see Listener#callSessionStarted, Listener#callSessionStartFailed 672 */ 673 public void start(String[] participants, ImsCallProfile profile) { 674 if (mClosed) { 675 return; 676 } 677 678 try { 679 miSession.startConference(participants, profile); 680 } catch (RemoteException e) { 681 } 682 } 683 684 /** 685 * Accepts an incoming call or session update. 686 * 687 * @param callType call type specified in {@link ImsCallProfile} to be answered 688 * @param profile stream media profile {@link ImsStreamMediaProfile} to be answered 689 * @see Listener#callSessionStarted 690 */ 691 public void accept(int callType, ImsStreamMediaProfile profile) { 692 if (mClosed) { 693 return; 694 } 695 696 try { 697 miSession.accept(callType, profile); 698 } catch (RemoteException e) { 699 } 700 } 701 702 /** 703 * Rejects an incoming call or session update. 704 * 705 * @param reason reason code to reject an incoming call 706 * @see Listener#callSessionStartFailed 707 */ 708 public void reject(int reason) { 709 if (mClosed) { 710 return; 711 } 712 713 try { 714 miSession.reject(reason); 715 } catch (RemoteException e) { 716 } 717 } 718 719 /** 720 * Terminates a call. 721 * 722 * @see Listener#callSessionTerminated 723 */ 724 public void terminate(int reason) { 725 if (mClosed) { 726 return; 727 } 728 729 try { 730 miSession.terminate(reason); 731 } catch (RemoteException e) { 732 } 733 } 734 735 /** 736 * Puts a call on hold. When it succeeds, {@link Listener#callSessionHeld} is called. 737 * 738 * @param profile stream media profile {@link ImsStreamMediaProfile} to hold the call 739 * @see Listener#callSessionHeld, Listener#callSessionHoldFailed 740 */ 741 public void hold(ImsStreamMediaProfile profile) { 742 if (mClosed) { 743 return; 744 } 745 746 try { 747 miSession.hold(profile); 748 } catch (RemoteException e) { 749 } 750 } 751 752 /** 753 * Continues a call that's on hold. When it succeeds, 754 * {@link Listener#callSessionResumed} is called. 755 * 756 * @param profile stream media profile {@link ImsStreamMediaProfile} to resume the call 757 * @see Listener#callSessionResumed, Listener#callSessionResumeFailed 758 */ 759 public void resume(ImsStreamMediaProfile profile) { 760 if (mClosed) { 761 return; 762 } 763 764 try { 765 miSession.resume(profile); 766 } catch (RemoteException e) { 767 } 768 } 769 770 /** 771 * Merges the active & hold call. When it succeeds, 772 * {@link Listener#callSessionMergeStarted} is called. 773 * 774 * @see Listener#callSessionMergeStarted , Listener#callSessionMergeFailed 775 */ 776 public void merge() { 777 if (mClosed) { 778 return; 779 } 780 781 try { 782 miSession.merge(); 783 } catch (RemoteException e) { 784 } 785 } 786 787 /** 788 * Updates the current call's properties (ex. call mode change: video upgrade / downgrade). 789 * 790 * @param callType call type specified in {@link ImsCallProfile} to be updated 791 * @param profile stream media profile {@link ImsStreamMediaProfile} to be updated 792 * @see Listener#callSessionUpdated, Listener#callSessionUpdateFailed 793 */ 794 public void update(int callType, ImsStreamMediaProfile profile) { 795 if (mClosed) { 796 return; 797 } 798 799 try { 800 miSession.update(callType, profile); 801 } catch (RemoteException e) { 802 } 803 } 804 805 /** 806 * Extends this call to the conference call with the specified recipients. 807 * 808 * @participants participant list to be invited to the conference call after extending the call 809 * @see Listener#sessionConferenceExtened, Listener#sessionConferenceExtendFailed 810 */ 811 public void extendToConference(String[] participants) { 812 if (mClosed) { 813 return; 814 } 815 816 try { 817 miSession.extendToConference(participants); 818 } catch (RemoteException e) { 819 } 820 } 821 822 /** 823 * Requests the conference server to invite an additional participants to the conference. 824 * 825 * @participants participant list to be invited to the conference call 826 * @see Listener#sessionInviteParticipantsRequestDelivered, 827 * Listener#sessionInviteParticipantsRequestFailed 828 */ 829 public void inviteParticipants(String[] participants) { 830 if (mClosed) { 831 return; 832 } 833 834 try { 835 miSession.inviteParticipants(participants); 836 } catch (RemoteException e) { 837 } 838 } 839 840 /** 841 * Requests the conference server to remove the specified participants from the conference. 842 * 843 * @param participants participant list to be removed from the conference call 844 * @see Listener#sessionRemoveParticipantsRequestDelivered, 845 * Listener#sessionRemoveParticipantsRequestFailed 846 */ 847 public void removeParticipants(String[] participants) { 848 if (mClosed) { 849 return; 850 } 851 852 try { 853 miSession.removeParticipants(participants); 854 } catch (RemoteException e) { 855 } 856 } 857 858 859 /** 860 * Sends a DTMF code. According to <a href="http://tools.ietf.org/html/rfc2833">RFC 2833</a>, 861 * event 0 ~ 9 maps to decimal value 0 ~ 9, '*' to 10, '#' to 11, event 'A' ~ 'D' to 12 ~ 15, 862 * and event flash to 16. Currently, event flash is not supported. 863 * 864 * @param c the DTMF to send. '0' ~ '9', 'A' ~ 'D', '*', '#' are valid inputs. 865 */ 866 public void sendDtmf(char c, Message result) { 867 if (mClosed) { 868 return; 869 } 870 871 try { 872 miSession.sendDtmf(c, result); 873 } catch (RemoteException e) { 874 } 875 } 876 877 /** 878 * Starts a DTMF code. According to <a href="http://tools.ietf.org/html/rfc2833">RFC 2833</a>, 879 * event 0 ~ 9 maps to decimal value 0 ~ 9, '*' to 10, '#' to 11, event 'A' ~ 'D' to 12 ~ 15, 880 * and event flash to 16. Currently, event flash is not supported. 881 * 882 * @param c the DTMF to send. '0' ~ '9', 'A' ~ 'D', '*', '#' are valid inputs. 883 */ 884 public void startDtmf(char c) { 885 if (mClosed) { 886 return; 887 } 888 889 try { 890 miSession.startDtmf(c); 891 } catch (RemoteException e) { 892 } 893 } 894 895 /** 896 * Stops a DTMF code. 897 */ 898 public void stopDtmf() { 899 if (mClosed) { 900 return; 901 } 902 903 try { 904 miSession.stopDtmf(); 905 } catch (RemoteException e) { 906 } 907 } 908 909 /** 910 * Sends an USSD message. 911 * 912 * @param ussdMessage USSD message to send 913 */ 914 public void sendUssd(String ussdMessage) { 915 if (mClosed) { 916 return; 917 } 918 919 try { 920 miSession.sendUssd(ussdMessage); 921 } catch (RemoteException e) { 922 } 923 } 924 925 /** 926 * Determines if the session is multiparty. 927 * 928 * @return {@code True} if the session is multiparty. 929 */ 930 public boolean isMultiparty() { 931 if (mClosed) { 932 return false; 933 } 934 935 try { 936 return miSession.isMultiparty(); 937 } catch (RemoteException e) { 938 return false; 939 } 940 } 941 942 /** 943 * A listener type for receiving notification on IMS call session events. 944 * When an event is generated for an {@link IImsCallSession}, 945 * the application is notified by having one of the methods called on 946 * the {@link IImsCallSessionListener}. 947 */ 948 private class IImsCallSessionListenerProxy extends IImsCallSessionListener.Stub { 949 /** 950 * Notifies the result of the basic session operation (setup / terminate). 951 */ 952 @Override 953 public void callSessionProgressing(IImsCallSession session, 954 ImsStreamMediaProfile profile) { 955 if (mListener != null) { 956 mListener.callSessionProgressing(ImsCallSession.this, profile); 957 } 958 } 959 960 @Override 961 public void callSessionStarted(IImsCallSession session, 962 ImsCallProfile profile) { 963 if (mListener != null) { 964 mListener.callSessionStarted(ImsCallSession.this, profile); 965 } 966 } 967 968 @Override 969 public void callSessionStartFailed(IImsCallSession session, 970 ImsReasonInfo reasonInfo) { 971 if (mListener != null) { 972 mListener.callSessionStartFailed(ImsCallSession.this, reasonInfo); 973 } 974 } 975 976 @Override 977 public void callSessionTerminated(IImsCallSession session, 978 ImsReasonInfo reasonInfo) { 979 if (mListener != null) { 980 mListener.callSessionTerminated(ImsCallSession.this, reasonInfo); 981 } 982 } 983 984 /** 985 * Notifies the result of the call hold/resume operation. 986 */ 987 @Override 988 public void callSessionHeld(IImsCallSession session, 989 ImsCallProfile profile) { 990 if (mListener != null) { 991 mListener.callSessionHeld(ImsCallSession.this, profile); 992 } 993 } 994 995 @Override 996 public void callSessionHoldFailed(IImsCallSession session, 997 ImsReasonInfo reasonInfo) { 998 if (mListener != null) { 999 mListener.callSessionHoldFailed(ImsCallSession.this, reasonInfo); 1000 } 1001 } 1002 1003 @Override 1004 public void callSessionHoldReceived(IImsCallSession session, 1005 ImsCallProfile profile) { 1006 if (mListener != null) { 1007 mListener.callSessionHoldReceived(ImsCallSession.this, profile); 1008 } 1009 } 1010 1011 @Override 1012 public void callSessionResumed(IImsCallSession session, 1013 ImsCallProfile profile) { 1014 if (mListener != null) { 1015 mListener.callSessionResumed(ImsCallSession.this, profile); 1016 } 1017 } 1018 1019 @Override 1020 public void callSessionResumeFailed(IImsCallSession session, 1021 ImsReasonInfo reasonInfo) { 1022 if (mListener != null) { 1023 mListener.callSessionResumeFailed(ImsCallSession.this, reasonInfo); 1024 } 1025 } 1026 1027 @Override 1028 public void callSessionResumeReceived(IImsCallSession session, 1029 ImsCallProfile profile) { 1030 if (mListener != null) { 1031 mListener.callSessionResumeReceived(ImsCallSession.this, profile); 1032 } 1033 } 1034 1035 /** 1036 * Notifies the start of a call merge operation. 1037 * 1038 * @param session The call session. 1039 * @param newSession The merged call session. 1040 * @param profile The call profile. 1041 */ 1042 @Override 1043 public void callSessionMergeStarted(IImsCallSession session, 1044 IImsCallSession newSession, ImsCallProfile profile) { 1045 if (mListener != null) { 1046 mListener.callSessionMergeStarted(ImsCallSession.this, 1047 new ImsCallSession(newSession), profile); 1048 } 1049 } 1050 1051 /** 1052 * Notifies the successful completion of a call merge operation. 1053 * 1054 * @param session The call session. 1055 */ 1056 @Override 1057 public void callSessionMergeComplete(IImsCallSession session) { 1058 if (mListener != null) { 1059 mListener.callSessionMergeComplete(ImsCallSession.this); 1060 } 1061 } 1062 1063 /** 1064 * Notifies of a failure to perform a call merge operation. 1065 * 1066 * @param session The call session. 1067 * @param reasonInfo The merge failure reason. 1068 */ 1069 @Override 1070 public void callSessionMergeFailed(IImsCallSession session, 1071 ImsReasonInfo reasonInfo) { 1072 if (mListener != null) { 1073 mListener.callSessionMergeFailed(ImsCallSession.this, reasonInfo); 1074 } 1075 } 1076 1077 /** 1078 * Notifies the result of call upgrade / downgrade or any other call updates. 1079 */ 1080 @Override 1081 public void callSessionUpdated(IImsCallSession session, 1082 ImsCallProfile profile) { 1083 if (mListener != null) { 1084 mListener.callSessionUpdated(ImsCallSession.this, profile); 1085 } 1086 } 1087 1088 @Override 1089 public void callSessionUpdateFailed(IImsCallSession session, 1090 ImsReasonInfo reasonInfo) { 1091 if (mListener != null) { 1092 mListener.callSessionUpdateFailed(ImsCallSession.this, reasonInfo); 1093 } 1094 } 1095 1096 @Override 1097 public void callSessionUpdateReceived(IImsCallSession session, 1098 ImsCallProfile profile) { 1099 if (mListener != null) { 1100 mListener.callSessionUpdateReceived(ImsCallSession.this, profile); 1101 } 1102 } 1103 1104 /** 1105 * Notifies the result of conference extension. 1106 */ 1107 @Override 1108 public void callSessionConferenceExtended(IImsCallSession session, 1109 IImsCallSession newSession, ImsCallProfile profile) { 1110 if (mListener != null) { 1111 mListener.callSessionConferenceExtended(ImsCallSession.this, 1112 new ImsCallSession(newSession), profile); 1113 } 1114 } 1115 1116 @Override 1117 public void callSessionConferenceExtendFailed(IImsCallSession session, 1118 ImsReasonInfo reasonInfo) { 1119 if (mListener != null) { 1120 mListener.callSessionConferenceExtendFailed(ImsCallSession.this, reasonInfo); 1121 } 1122 } 1123 1124 @Override 1125 public void callSessionConferenceExtendReceived(IImsCallSession session, 1126 IImsCallSession newSession, ImsCallProfile profile) { 1127 if (mListener != null) { 1128 mListener.callSessionConferenceExtendReceived(ImsCallSession.this, 1129 new ImsCallSession(newSession), profile); 1130 } 1131 } 1132 1133 /** 1134 * Notifies the result of the participant invitation / removal to/from 1135 * the conference session. 1136 */ 1137 @Override 1138 public void callSessionInviteParticipantsRequestDelivered(IImsCallSession session) { 1139 if (mListener != null) { 1140 mListener.callSessionInviteParticipantsRequestDelivered(ImsCallSession.this); 1141 } 1142 } 1143 1144 @Override 1145 public void callSessionInviteParticipantsRequestFailed(IImsCallSession session, 1146 ImsReasonInfo reasonInfo) { 1147 if (mListener != null) { 1148 mListener.callSessionInviteParticipantsRequestFailed(ImsCallSession.this, 1149 reasonInfo); 1150 } 1151 } 1152 1153 @Override 1154 public void callSessionRemoveParticipantsRequestDelivered(IImsCallSession session) { 1155 if (mListener != null) { 1156 mListener.callSessionRemoveParticipantsRequestDelivered(ImsCallSession.this); 1157 } 1158 } 1159 1160 @Override 1161 public void callSessionRemoveParticipantsRequestFailed(IImsCallSession session, 1162 ImsReasonInfo reasonInfo) { 1163 if (mListener != null) { 1164 mListener.callSessionRemoveParticipantsRequestFailed(ImsCallSession.this, 1165 reasonInfo); 1166 } 1167 } 1168 1169 /** 1170 * Notifies the changes of the conference info. in the conference session. 1171 */ 1172 @Override 1173 public void callSessionConferenceStateUpdated(IImsCallSession session, 1174 ImsConferenceState state) { 1175 if (mListener != null) { 1176 mListener.callSessionConferenceStateUpdated(ImsCallSession.this, state); 1177 } 1178 } 1179 1180 /** 1181 * Notifies the incoming USSD message. 1182 */ 1183 @Override 1184 public void callSessionUssdMessageReceived(IImsCallSession session, 1185 int mode, String ussdMessage) { 1186 if (mListener != null) { 1187 mListener.callSessionUssdMessageReceived(ImsCallSession.this, mode, ussdMessage); 1188 } 1189 } 1190 1191 /** 1192 * Notifies of handover information for this call 1193 */ 1194 @Override 1195 public void callSessionHandover(IImsCallSession session, 1196 int srcAccessTech, int targetAccessTech, 1197 ImsReasonInfo reasonInfo) { 1198 if (mListener != null) { 1199 mListener.callSessionHandover(ImsCallSession.this, srcAccessTech, 1200 targetAccessTech, reasonInfo); 1201 } 1202 } 1203 1204 /** 1205 * Notifies of handover failure info for this call 1206 */ 1207 @Override 1208 public void callSessionHandoverFailed(IImsCallSession session, 1209 int srcAccessTech, int targetAccessTech, 1210 ImsReasonInfo reasonInfo) { 1211 if (mListener != null) { 1212 mListener.callSessionHandoverFailed(ImsCallSession.this, srcAccessTech, 1213 targetAccessTech, reasonInfo); 1214 } 1215 } 1216 1217 /** 1218 * Notifies the TTY mode received from remote party. 1219 */ 1220 @Override 1221 public void callSessionTtyModeReceived(IImsCallSession session, 1222 int mode) { 1223 if (mListener != null) { 1224 mListener.callSessionTtyModeReceived(ImsCallSession.this, mode); 1225 } 1226 } 1227 1228 /** 1229 * Notifies of a change to the multiparty state for this {@code ImsCallSession}. 1230 * 1231 * @param session The call session. 1232 * @param isMultiParty {@code true} if the session became multiparty, {@code false} 1233 * otherwise. 1234 */ 1235 public void callSessionMultipartyStateChanged(IImsCallSession session, 1236 boolean isMultiParty) { 1237 1238 if (mListener != null) { 1239 mListener.callSessionMultipartyStateChanged(ImsCallSession.this, isMultiParty); 1240 } 1241 } 1242 1243 @Override 1244 public void callSessionSuppServiceReceived(IImsCallSession session, 1245 ImsSuppServiceNotification suppServiceInfo ) { 1246 if (mListener != null) { 1247 mListener.callSessionSuppServiceReceived(ImsCallSession.this, suppServiceInfo); 1248 } 1249 } 1250 1251 } 1252 1253 /** 1254 * Provides a string representation of the {@link ImsCallSession}. Primarily intended for 1255 * use in log statements. 1256 * 1257 * @return String representation of session. 1258 */ 1259 @Override 1260 public String toString() { 1261 StringBuilder sb = new StringBuilder(); 1262 sb.append("[ImsCallSession objId:"); 1263 sb.append(System.identityHashCode(this)); 1264 sb.append(" state:"); 1265 sb.append(State.toString(getState())); 1266 sb.append(" callId:"); 1267 sb.append(getCallId()); 1268 sb.append("]"); 1269 return sb.toString(); 1270 } 1271} 1272