---
sidebar_position: 8
---

# The call screen

A ready call interface for any page, with no JavaScript to write: a call button, a group call button, the ring for incoming calls, and a call window with the usual controls.

```php
add_action( 'wp_enqueue_scripts', function () {
	if ( is_user_logged_in() ) {
		wordplus_realtime()->call_screen();
	}
} );
```

```html
<wordplus-call to="34" call="support-42" type="video" name="Ann" avatar="https://…/ann.jpg">Call Ann</wordplus-call>

<wordplus-room room="support-staff" type="video" title="Staff room">Join the staff room</wordplus-room>
```

Who may call whom is still your plugin's to decide, in its `calls()` callback ([calls](calls.md), [group calls](group-calls.md)). The screen shows the refusal it gets.

## Where to load it

`call_screen()` enqueues the screen and everything it runs on, and returns `false` on a site without credentials. Call it while scripts are enqueued (`wp_enqueue_scripts`):

- **On the pages with the buttons,** so they work.
- **On every page a person may be called on.** A call rings only on pages that load the screen (or your own calls code). A support agent's calls ring on any page of the site they have open, when every page loads it.

Its scripts load in the footer, about 110 KB in all; the media client for rooms only when a room is joined.

## `<wordplus-call>`

A button that places a call between two people.

| Attribute | |
|---|---|
| `to` | the user id to call |
| `call` | the call's name, which your `calls()` callback owns |
| `type` | `video` (default) or `audio` |
| `name`, `avatar` | how the window shows the person called |

Its content is the button's label, `Video call` or `Audio call` when empty.

## `<wordplus-room>`

A button that joins a group call.

| Attribute | |
|---|---|
| `room` | the room's name, which your `calls()` callback owns |
| `type` | `video` (default) or `audio` |
| `title` | the window's title |

Its content is the button's label, `Join` when empty.

## The ring

When the page's user is called, a box in the corner says who calls, with Accept and Decline, and a ring tone plays (where the browser allows sound before a click). It goes as soon as the call stops ringing anywhere: answered or declined on another tab or device, called off, or unanswered. A person already in a call is busy: the caller hears so, and nothing rings.

## The call window

One on the page, in a corner, expandable to the whole window:

- **The other side's picture,** their screen share first when they share one, and their sound. Without a picture, their name and picture from `info`.
- **The page's own camera,** small, mirrored.
- **The status:** calling, connecting, reconnecting, and why it ended.
- **A timer** once connected.
- **Mute, camera, screen share and hang up.** A room has Leave in place of Hang up, and everyone on a grid, the speakers marked.

It opens the camera and the microphone when the call starts, and stops them when it ends, so the camera's light goes off with the call. Without a camera or a microphone, the call goes on with what there is.

## Making it yours

It draws in shadow roots, so a theme's styles don't reach in. Set these custom properties on the page to change its look:

```css
:root {
	--wordplus-call-accent: #1a73e8;     /* buttons that start or accept */
	--wordplus-call-danger: #d93025;     /* hang up and decline */
	--wordplus-call-surface: #ffffff;    /* the ring's box */
	--wordplus-call-text: #1f1f1f;       /* text on it */
	--wordplus-call-stage: #111418;      /* behind the pictures */
	--wordplus-call-radius: 12px;
	--wordplus-call-font: inherit;
	--wordplus-call-z: 99999;            /* how far above the page it sits */
}
```

The buttons expose their inner button as a `part`: `wordplus-call::part(button) { … }`.

Right-to-left pages mirror it.

## Its words

The screen's words come from `wordplus_realtime()->screen_strings()`, translated in the text domain `wordplus-realtime`. The filter `wordplus_realtime_call_screen_strings` changes any of them:

```php
add_filter( 'wordplus_realtime_call_screen_strings', function ( $strings ) {
	$strings['accept']  = __( 'Answer', 'my-plugin' );
	$strings['waiting'] = __( 'Getting your call ready…', 'my-plugin' );
	return $strings;
} );
```

On one page, `wordplusRealtimeCallScreen.setStrings( { waiting: '…' } )` does the same from JavaScript. `:name` in a string is the other person's name, `:count` a number of people.

| Keys | Where they show |
|---|---|
| `call`, `videoCall`, `audioCall`, `join` | the buttons' own words, when a button has none |
| `calling` | the caller's window while it rings |
| `incomingVideo`, `incomingAudio`, `accept`, `decline` | the ring |
| `connecting`, `reconnecting`, `waiting` | the status while a call or a room connects, reconnects, or waits for its place |
| `ended`, `endedNoAnswer`, `endedDeclined`, `endedBusy`, `endedLost`, `endedFailed` | why a call ended |
| `refused`, `unavailable`, `noDevices` | why a call can't start |
| `mute`, `unmute`, `cameraOn`, `cameraOff`, `shareScreen`, `stopSharing`, `hangUp`, `leave`, `expand`, `shrink` | the controls |
| `you`, `muted`, `people` | the people's tiles, and how many are in a room |
| `playSound` | when the browser needs a click before it plays sound |

## From your own code

The screen is also `window.wordplusRealtimeCallScreen`:

```js
wordplusRealtimeCallScreen.place( 'support-42', 34, 'video', { name: 'Ann' } );   // what <wordplus-call> does
wordplusRealtimeCallScreen.join( 'support-staff', 'video', 'Staff room' );        // what <wordplus-room> does
```

It starts by itself once the page has loaded. The screen uses the page's calls (`wordplusRealtimeCalls.page()`), so your own code on the same page shares its line and its calls.

## Buttons without the ring

`call_screen( array( 'ring' => false ) )` loads the screen on a page that shouldn't ring: its buttons work, and the page holds no line, so the user's calls ring only on their other pages.
