# Interface CallBridge

public interface CallBridge

Internal service-provider interface implemented by each platform port to carry the `com.codename1.call` API onto the native call stacks: Apple's CallKit and PushKit, and Android's `ConnectionService`, `TelecomManager` and `CallScreeningService`.

Application code never touches this interface. It is obtained by the `com.codename1.call` packages from `com.codename1.ui.Display#getCallBridge()`, and the base implementation returns `null` -- which is why the public API degrades to a well-behaved `NOT_SUPPORTED` on ports that implement nothing, and why application code needs no platform `if` statements.

##### Everything here is primitives, strings and byte arrays

A port may be Objective-C reached through ParparVM, where constructing a Java object is expensive and easy to get wrong. So no method on this interface takes or returns a framework type: enums cross as their ordinals, capability sets cross as bit masks, and structured records cross as tab-delimited strings built by `com.codename1.impl.call.CallWire`.

##### Asynchrony is by request id, and every operation must answer

Operations that can fail take a `requestId` allocated by the caller and answer exactly once by calling the matching `deliver...` entry point on the public class. An operation that never answers is worse than one that fails: the caller holds an `AsyncResource` that will never settle and has no way to find out. A port that cannot start something must still report the failure. This bites harder here than elsewhere, because both platforms have a documented "the system refused your call" path -- Telecom's `onCreateIncomingConnectionFailed` and the `NSError` handed to CallKit's report completion -- that is easy to leave unwired, and an unwired refusal looks exactly like a call that is still ringing.

Unsolicited events -- the user answering, the system taking the audio -- carry the call id they belong to instead of a request id. Every entry point may be called from any thread; they marshal to the EDT themselves.

##### The up direction has a deadline too

A system-originated action must be answered with `completeAction(long, boolean)` within a few seconds or the platform times it out and the system UI and the app disagree about the call, silently. The facade guarantees an answer the same way this interface guarantees one downward.

- ## Field Summary

  Fields
  Modifier and Type
  Field
  Description
  `static final int`
  `CAPABILITY_DIRECTORY`
  `getCallCapabilities()` bit: caller identification can be installed.
  `static final int`
  `CAPABILITY_DTMF`
  `getCallCapabilities()` bit: the system offers a keypad and delivers DTMF digits.
  `static final int`
  `CAPABILITY_GROUPING`
  Reserved.
  `static final int`
  `CAPABILITY_HOLD`
  `getCallCapabilities()` bit: calls can be held and resumed.
  `static final int`
  `CAPABILITY_MUTE`
  `getCallCapabilities()` bit: the app can SET the system mute state.
  `static final int`
  `CAPABILITY_OUTGOING`
  `getCallCapabilities()` bit: outgoing calls can be reported.
  `static final int`
  `CAPABILITY_ROUTE_PICKER`
  Reserved.
  `static final int`
  `CAPABILITY_SCREENING`
  `getCallCapabilities()` bit: incoming calls can be screened or blocked.
  `static final int`
  `CAPABILITY_SYSTEM_UI`
  `getCallCapabilities()` bit: the platform draws a system call UI.
  `static final int`
  `CAPABILITY_VIDEO`
  `getCallCapabilities()` bit: video calls are supported.
  `static final int`
  `CAPABILITY_VOIP_PUSH`
  `getCallCapabilities()` bit: the app can be woken by a VoIP push.
  `static final int`
  `PERMISSION_CAMERA`
  `requestPermissions(int, int)` bit: camera access, for video calls.
  `static final int`
  `PERMISSION_MANAGE_CALLS`
  `requestPermissions(int, int)` bit: the grant needed to own calls -- `MANAGE_OWN_CALLS` on Android.
  `static final int`
  `PERMISSION_MICROPHONE`
  `requestPermissions(int, int)` bit: microphone access.
  `static final int`
  `PERMISSION_NOTIFICATIONS`
  `requestPermissions(int, int)` bit: permission to post notifications, which Android needs to show a call in the shade.
  `static final int`
  `PERMISSION_SCREENING_ROLE`
  `requestPermissions(int, int)` bit: the call-screening role.

- ## Method Summary

  Modifier and Type
  Method
  Description
  `boolean`
  `completeAction(long actionToken, boolean fulfilled)`
  Answers a system-originated action delivered with `actionToken`.
  `void`
  `configureProvider(int requestId, String configWire)`
  Installs the calling identity: the name the system shows, the ringtone, whether video is offered.
  `void`
  `drainPendingCalls(int requestId)`
  Delivers every call reported natively but not yet seen by Java, then answers once with the count.
  `void`
  `endCall(int requestId, String callId, int endReasonOrdinal)`
  This side is ending the call.
  `int`
  `getAudioRoute()`
  The ordinal of the current `com.codename1.call.session.CallAudioRoute`.
  `int`
  `getCallAvailability()`
  The ordinal of the current `com.codename1.call.CallAvailability` -- whether a call could be rung right now, which is a different question from whether the platform supports calling.
  `int`
  `getCallCapabilities()`
  The `CAPABILITY_*` bit mask this port supports.
  `void`
  `getDirectoryStatus(int requestId)`
  Answers with a `CallWire`-encoded status record.
  `int`
  `getGrantedPermissions()`
  The `PERMISSION_*` bit mask currently granted.
  `boolean`
  `isCallSupported()`
  Whether this port can report calls to a system call UI at all.
  `boolean`
  `isDirectorySupported()`
  Whether this port can install caller identification or blocking.
  `boolean`
  `isVoipPushSupported()`
  Whether this port can be woken by a VoIP push.
  `void`
  `registerVoipPush(int requestId)`
  Registers for VoIP pushes, answering with the token.
  `void`
  `reloadDirectory(int requestId)`
  Asks the system to re-read the directory source.
  `void`
  `reportCallEnded(String callId, int endReasonOrdinal, long timestampMs)`
  The far end ended the call.
  `void`
  `reportIncomingCall(int requestId, String callId, String handleWire, String displayName, int capabilityBits, boolean hasVideo)`
  Reports a new incoming call and starts it ringing.
  `void`
  `reportIncomingConnected(String callId, long timestampMs)`
  The incoming call is connected.
  `void`
  `reportOutgoingCall(int requestId, String callId, String handleWire, String displayName, int capabilityBits, boolean hasVideo)`
  Reports a new outgoing call the app is placing.
  `void`
  `reportOutgoingConnected(String callId, long timestampMs)`
  The outgoing call is connected.
  `void`
  `reportOutgoingStartedConnecting(String callId, long timestampMs)`
  The outgoing call has begun connecting.
  `void`
  `requestPermissions(int requestId, int permissionBits)`
  Requests the `PERMISSION_*` bits in `permissionBits`, answering with the granted mask.
  `void`
  `requestScreeningRole(int requestId)`
  Asks the user for the call-screening role.
  `void`
  `sendDtmf(int requestId, String callId, String digits)`
  Sends DTMF digits.
  `void`
  `setAudioRoute(int requestId, int routeOrdinal)`
  Asks for a route by ordinal.
  `void`
  `setCallGroup(int requestId, String callId, String otherCallId)`
  Groups `callId` with `otherCallId`, or ungroups it when that is null.
  `void`
  `setDirectorySource(int requestId, String filePath)`
  Installs the caller-identification and blocking data at `filePath`.
  `void`
  `setHeld(int requestId, String callId, boolean held)`
  Holds or resumes a call.
  `void`
  `setJavaReady(boolean ready)`
  Tells the port whether application code is listening yet.
  `void`
  `setMuted(int requestId, String callId, boolean muted)`
  Mutes or unmutes a call.
  `void`
  `showAudioRoutePicker(int requestId, String callId)`
  Shows the system's audio route picker.
  `void`
  `unregisterVoipPush(int requestId)`
  Stops VoIP push delivery.
  `void`
  `updateCall(String callId, String handleWire, String displayName, int capabilityBits, boolean hasVideo)`
  Updates the display of a call already reported.

- ## Field Details

  - ### CAPABILITY_SYSTEM_UI

    static final int CAPABILITY_SYSTEM_UI
    `getCallCapabilities()` bit: the platform draws a system call UI.
    See Also:
      - Constant Field Values

  - ### CAPABILITY_OUTGOING

    static final int CAPABILITY_OUTGOING
    `getCallCapabilities()` bit: outgoing calls can be reported.
    See Also:
      - Constant Field Values

  - ### CAPABILITY_HOLD

    static final int CAPABILITY_HOLD
    `getCallCapabilities()` bit: calls can be held and resumed.
    See Also:
      - Constant Field Values

  - ### CAPABILITY_MUTE

    static final int CAPABILITY_MUTE

    `getCallCapabilities()` bit: the app can SET the system mute state.

    About `setMuted(int, String, boolean)` only. Hearing what the user does with the system's own mute control is not gated by this and arrives everywhere, through `Calls.deliverMuteChanged`; Android reports that and offers no way to drive it, so it does not set this bit.

    See Also:
      - Constant Field Values

  - ### CAPABILITY_DTMF

    static final int CAPABILITY_DTMF
    `getCallCapabilities()` bit: the system offers a keypad and delivers DTMF digits.
    See Also:
      - Constant Field Values

  - ### CAPABILITY_GROUPING

    static final int CAPABILITY_GROUPING

    Reserved. No port sets this. Neither platform lets an app put two of its own calls into a conference: CallKit's `CXSetGroupCallAction` travels system to app and has no app-initiated counterpart, and Telecom conferences self-managed calls only through a `ConnectionService` conference this port does not build. So

    invalid reference

        CallSession#groupWith

    always answers NOT_SUPPORTED. The constant is

    kept so the bit values do not shift if that changes.

    See Also:
      - Constant Field Values

  - ### CAPABILITY_VIDEO

    static final int CAPABILITY_VIDEO
    `getCallCapabilities()` bit: video calls are supported.
    See Also:
      - Constant Field Values

  - ### CAPABILITY_VOIP_PUSH

    static final int CAPABILITY_VOIP_PUSH
    `getCallCapabilities()` bit: the app can be woken by a VoIP push.
    See Also:
      - Constant Field Values

  - ### CAPABILITY_DIRECTORY

    static final int CAPABILITY_DIRECTORY
    `getCallCapabilities()` bit: caller identification can be installed.
    See Also:
      - Constant Field Values

  - ### CAPABILITY_SCREENING

    static final int CAPABILITY_SCREENING
    `getCallCapabilities()` bit: incoming calls can be screened or blocked.
    See Also:
      - Constant Field Values

  - ### CAPABILITY_ROUTE_PICKER

    static final int CAPABILITY_ROUTE_PICKER
    Reserved. No port sets this. Neither platform has a system audio route picker an app can present for a call -- iOS offers `AVRoutePickerView`, a view the app places itself, and Android offers nothing -- so `showAudioRoutePicker(int, String)` always answers NOT_SUPPORTED. The constant is kept so the bit values do not shift if that changes.
    See Also:
      - Constant Field Values

  - ### PERMISSION_MANAGE_CALLS

    static final int PERMISSION_MANAGE_CALLS
    `requestPermissions(int, int)` bit: the grant needed to own calls -- `MANAGE_OWN_CALLS` on Android. Implicit on iOS.
    See Also:
      - Constant Field Values

  - ### PERMISSION_MICROPHONE

    static final int PERMISSION_MICROPHONE
    `requestPermissions(int, int)` bit: microphone access.
    See Also:
      - Constant Field Values

  - ### PERMISSION_CAMERA

    static final int PERMISSION_CAMERA
    `requestPermissions(int, int)` bit: camera access, for video calls.
    See Also:
      - Constant Field Values

  - ### PERMISSION_NOTIFICATIONS

    static final int PERMISSION_NOTIFICATIONS
    `requestPermissions(int, int)` bit: permission to post notifications, which Android needs to show a call in the shade.
    See Also:
      - Constant Field Values

  - ### PERMISSION_SCREENING_ROLE

    static final int PERMISSION_SCREENING_ROLE
    `requestPermissions(int, int)` bit: the call-screening role.
    See Also:
      - Constant Field Values

- ## Method Details

  - ### isCallSupported

    boolean isCallSupported()
    Whether this port can report calls to a system call UI at all.

  - ### isVoipPushSupported

    boolean isVoipPushSupported()
    Whether this port can be woken by a VoIP push.

  - ### isDirectorySupported

    boolean isDirectorySupported()
    Whether this port can install caller identification or blocking.

  - ### getCallCapabilities

    int getCallCapabilities()
    The `CAPABILITY_*` bit mask this port supports.

  - ### getCallAvailability

    int getCallAvailability()
    The ordinal of the current `com.codename1.call.CallAvailability` -- whether a call could be rung right now, which is a different question from whether the platform supports calling.

  - ### getGrantedPermissions

    int getGrantedPermissions()
    The `PERMISSION_*` bit mask currently granted.

  - ### requestPermissions

    void requestPermissions(int requestId, int permissionBits)
    Requests the `PERMISSION_*` bits in `permissionBits`, answering with the granted mask.

  - ### configureProvider

    void configureProvider(int requestId, String configWire)

    Installs the calling identity: the name the system shows, the ringtone, whether video is offered. `configWire` is a `CallWire`-encoded record.

    On Android this registers the `PhoneAccount`; until it has run, `TelecomManager.addNewIncomingCall` is a silent no-op, which is why this is a separate step rather than something inferred from the first report.

  - ### reportIncomingCall

    void reportIncomingCall(int requestId, String callId, String handleWire, String displayName, int capabilityBits, boolean hasVideo)
    Reports a new incoming call and starts it ringing.

  - ### reportOutgoingCall

    void reportOutgoingCall(int requestId, String callId, String handleWire, String displayName, int capabilityBits, boolean hasVideo)
    Reports a new outgoing call the app is placing.

  - ### reportOutgoingStartedConnecting

    void reportOutgoingStartedConnecting(String callId, long timestampMs)
    The outgoing call has begun connecting. `timestampMs` is wall clock.

  - ### reportOutgoingConnected

    void reportOutgoingConnected(String callId, long timestampMs)
    The outgoing call is connected.

  - ### reportIncomingConnected

    void reportIncomingConnected(String callId, long timestampMs)
    The incoming call is connected.

  - ### updateCall

    void updateCall(String callId, String handleWire, String displayName, int capabilityBits, boolean hasVideo)
    Updates the display of a call already reported. Any argument may be null or -1 to leave that field alone.

  - ### reportCallEnded

    void reportCallEnded(String callId, int endReasonOrdinal, long timestampMs)
    The far end ended the call. `endReasonOrdinal` is a `com.codename1.call.CallEndReason` ordinal and becomes what the system writes in the call log.

  - ### endCall

    void endCall(int requestId, String callId, int endReasonOrdinal)
    This side is ending the call.

  - ### setHeld

    void setHeld(int requestId, String callId, boolean held)
    Holds or resumes a call.

  - ### setMuted

    void setMuted(int requestId, String callId, boolean muted)
    Mutes or unmutes a call.

  - ### sendDtmf

    void sendDtmf(int requestId, String callId, String digits)
    Sends DTMF digits.

  - ### setCallGroup

    void setCallGroup(int requestId, String callId, String otherCallId)
    Groups `callId` with `otherCallId`, or ungroups it when that is null.

  - ### getAudioRoute

    int getAudioRoute()
    The ordinal of the current `com.codename1.call.session.CallAudioRoute`.

  - ### setAudioRoute

    void setAudioRoute(int requestId, int routeOrdinal)
    Asks for a route by ordinal.

  - ### showAudioRoutePicker

    void showAudioRoutePicker(int requestId, String callId)
    Shows the system's audio route picker.

  - ### completeAction

    boolean completeAction(long actionToken, boolean fulfilled)

    Answers a system-originated action delivered with `actionToken`.

    The token is opaque and allocated by the port. Exactly one call per token; a second is ignored rather than treated as an error, because the facade's safety net and the application may both answer and the race between them is not worth making the application think about.

    ###### Returns

    whether the platform still held this action. A `false` says the platform gave up on it -- a CallKit timeout, a Telecom connection torn down underneath it -- and the caller must not apply the local effect, because the system is no longer going to carry the action out.

  - ### registerVoipPush

    void registerVoipPush(int requestId)
    Registers for VoIP pushes, answering with the token.

  - ### unregisterVoipPush

    void unregisterVoipPush(int requestId)
    Stops VoIP push delivery.

  - ### setJavaReady

    void setJavaReady(boolean ready)

    Tells the port whether application code is listening yet.

    Until this is true the port must hold pushed calls rather than delivering them, because on iOS the system call is reported by native code before any application code has run.

  - ### drainPendingCalls

    void drainPendingCalls(int requestId)
    Delivers every call reported natively but not yet seen by Java, then answers once with the count.

  - ### setDirectorySource

    void setDirectorySource(int requestId, String filePath)

    Installs the caller-identification and blocking data at `filePath`.

    A path rather than an array: the list routinely runs to hundreds of thousands of numbers, and on iOS the process that reads it is a separate extension, so the data has to be on disk in a shared container whatever this API looked like.

  - ### reloadDirectory

    void reloadDirectory(int requestId)
    Asks the system to re-read the directory source.

  - ### getDirectoryStatus

    void getDirectoryStatus(int requestId)
    Answers with a `CallWire`-encoded status record.

  - ### requestScreeningRole

    void requestScreeningRole(int requestId)
    Asks the user for the call-screening role.