Skip to main content

EmulatorControllerClient

Struct EmulatorControllerClient 

Source
pub struct EmulatorControllerClient<T> { /* private fields */ }
Expand description

An EmulatorController service lets you control the emulator. Note that this is currently an experimental feature, and that the service definition might change without notice. Use at your own risk!

We use the following rough conventions:

streamXXX –> streams values XXX (usually for emulator lifetime). Values are updated as soon as they become available. getXXX –> gets a single value XXX setXXX –> sets a single value XXX, does not returning state, these usually have an observable lasting side effect. sendXXX –> send a single event XXX, possibly returning state information. android usually responds to these events.

Implementations§

Source§

impl EmulatorControllerClient<Channel>

Source

pub async fn connect<D>(dst: D) -> Result<Self, Error>
where D: TryInto<Endpoint>, D::Error: Into<StdError>,

Attempt to create a new client by connecting to a given endpoint.

Source§

impl<T> EmulatorControllerClient<T>
where T: GrpcService<Body>, T::Error: Into<StdError>, T::ResponseBody: Body<Data = Bytes> + Send + 'static, <T::ResponseBody as Body>::Error: Into<StdError> + Send,

Source

pub fn new(inner: T) -> Self

Source

pub fn with_origin(inner: T, origin: Uri) -> Self

Source

pub fn with_interceptor<F>( inner: T, interceptor: F, ) -> EmulatorControllerClient<InterceptedService<T, F>>
where F: Interceptor, T::ResponseBody: Default, T: Service<Request<Body>, Response = Response<<T as GrpcService<Body>>::ResponseBody>>, <T as Service<Request<Body>>>::Error: Into<StdError> + Send + Sync,

Source

pub fn send_compressed(self, encoding: CompressionEncoding) -> Self

Compress requests with the given encoding.

This requires the server to support it otherwise it might respond with an error.

Source

pub fn accept_compressed(self, encoding: CompressionEncoding) -> Self

Enable decompressing responses.

Source

pub fn max_decoding_message_size(self, limit: usize) -> Self

Limits the maximum size of a decoded message.

Default: 4MB

Source

pub fn max_encoding_message_size(self, limit: usize) -> Self

Limits the maximum size of an encoded message.

Default: usize::MAX

Source

pub async fn stream_sensor( &mut self, request: impl IntoRequest<SensorValue>, ) -> Result<Response<Streaming<SensorValue>>, Status>

set/get/stream the sensor data This RPC is not implemented in EmulatorController and will return an unimplemented error.

Source

pub async fn get_sensor( &mut self, request: impl IntoRequest<SensorValue>, ) -> Result<Response<SensorValue>, Status>

Gets the current value of a specified sensor.

The following gRPC error codes can be returned:

  • INTERNAL (code 13) if getSensorSize fails to retrieve sensor dimensions.

The status field in the SensorValue reply indicates the operational state:

  • OK (0): Sensor data retrieved successfully.
  • UNKNOWN (2): Unknown sensor type (should not happen if using valid SensorType).
  • DISABLED (3): The sensor is disabled.
  • NO_SERVICE (4): The qemud service responsible for sensors is not available or initiated.
Source

pub async fn set_sensor( &mut self, request: impl IntoRequest<SensorValue>, ) -> Result<Response<()>, Status>

Sets the override value for a specified sensor. This operation is asynchronous and executed on the emulator’s main looper. An immediate subsequent getSensor call might not reflect the newly set value.

This method returns OK (code 0) upon successful asynchronous scheduling of the operation. No specific gRPC error codes are returned by this method itself, but underlying operations might log warnings if the sensor agent is unavailable.

Source

pub async fn set_physical_model( &mut self, request: impl IntoRequest<PhysicalModelValue>, ) -> Result<Response<()>, Status>

set/get/stream the physical model, this is likely the one you are looking for when you wish to modify the device state.

This operation is asynchronous and executed on the emulator’s main looper. An immediate subsequent getPhysicalModel call might not reflect the newly set value. The interpolation field from the request is used to determine the physical interpolation method, mapped using abs((static_cast<int>(physicalValue.interpolation())) - 1).

This method returns OK (code 0) upon successful asynchronous scheduling of the operation.

Source

pub async fn get_physical_model( &mut self, request: impl IntoRequest<PhysicalModelValue>, ) -> Result<Response<PhysicalModelValue>, Status>

Gets the current value of a specified physical model parameter.

The status field in the PhysicalModelValue reply indicates the operational state:

  • OK (0): Physical model data retrieved successfully.
  • UNKNOWN (2): Unknown physical type (should not happen if using valid PhysicalType).
  • NO_SERVICE (3): The qemud service responsible for physical parameters is not available or initiated.
Source

pub async fn stream_physical_model( &mut self, request: impl IntoRequest<PhysicalModelValue>, ) -> Result<Response<Streaming<PhysicalModelValue>>, Status>

This RPC is not implemented in EmulatorController and will return an unimplemented error.

Source

pub async fn set_clipboard( &mut self, request: impl IntoRequest<ClipData>, ) -> Result<Response<()>, Status>

Atomically sets the current primary clipboard data. This operation is asynchronous and executed on the emulator’s main looper. It triggers a ClipboardEvent to all listeners (except the originating channel) indicating the new content.

This method returns OK (code 0) upon successful asynchronous scheduling of the operation.

Source

pub async fn get_clipboard( &mut self, request: impl IntoRequest<()>, ) -> Result<Response<ClipData>, Status>

Retrieves the current primary clipboard data. This is a synchronous operation.

This method returns OK (code 0) and the current ClipData upon success.

Source

pub async fn stream_clipboard( &mut self, request: impl IntoRequest<()>, ) -> Result<Response<Streaming<ClipData>>, Status>

Streams real-time updates of the clipboard content. Upon subscription, it immediately sends the current clipboard state. Subsequent updates are streamed as new content becomes available from the guest or is set via setClipboard from a different client. Events originating from the same client that initiated the stream are filtered out to prevent echoing.

It is possible to miss very rapid clipboard updates. The stream will block awaiting new events after the initial state is sent.

This method returns a server-side streaming reactor.

Source

pub async fn set_battery( &mut self, request: impl IntoRequest<BatteryState>, ) -> Result<Response<()>, Status>

Sets the emulator’s battery state to the provided values. This operation is executed asynchronously on the main looper.

This method returns OK (code 0) upon successful asynchronous scheduling of the operation. No explicit gRPC error codes are returned by this method.

Source

pub async fn get_battery( &mut self, request: impl IntoRequest<()>, ) -> Result<Response<BatteryState>, Status>

Retrieves the current battery state from the emulator. This is a synchronous operation that waits for completion.

This method returns OK (code 0) and populates the BatteryState reply with the current information upon success. No explicit gRPC error codes are returned by this method.

Source

pub async fn set_gps( &mut self, request: impl IntoRequest<GpsState>, ) -> Result<Response<()>, Status>

Sets the state of the GPS in the emulator. This operation is asynchronous and executed on the main looper. It updates the emulator’s GPS location (latitude, longitude, altitude, speed, bearing, and satellites) and sets the timestamp.

Note: Setting the GPS position will not be immediately reflected in the user interface. Android typically samples GPS at 1 Hz. This method returns OK (code 0) upon successful asynchronous scheduling of the operation.

Source

pub async fn get_gps( &mut self, request: impl IntoRequest<()>, ) -> Result<Response<GpsState>, Status>

Gets the latest GPS state as reported by the emulator. This includes data delivered by previous setGps calls or from the location UI if active. This is a synchronous operation that waits for completion.

Note: The returned GPS state is not necessarily the exact coordinate visible at the time due to Android’s typical 1 Hz GPS sample frequency.

This method returns OK (code 0) and populates the GpsState reply with the retrieved information upon success. No explicit gRPC error codes are returned by this method.

Source

pub async fn send_fingerprint( &mut self, request: impl IntoRequest<Fingerprint>, ) -> Result<Response<()>, Status>

Simulates a touch event on the fingerprint sensor. This operation is executed asynchronously on the main looper.

The isTouching field indicates whether the fingerprint sensor is being touched, and touchId specifies the identifier of the registered fingerprint. The setTouch agent function is used to apply these values.

This method returns OK (code 0) upon successful asynchronous scheduling of the operation. No explicit gRPC error codes are returned by this method.

Source

pub async fn send_key( &mut self, request: impl IntoRequest<KeyboardEvent>, ) -> Result<Response<()>, Status>

Sends a keyboard event to the emulator. This operation is asynchronous and executed on the main looper.

The KeyboardEvent message allows specifying input using keyCode, key (W3C standard string), or text (UTF-8 string). The KeyEventSender prioritizes key, then keyCode, then text.

  • If key is a non-printable W3C key string (e.g., “Backspace”, “ArrowUp”), it’s translated to an evdev keycode and sent.
  • If key is a printable Unicode character, it’s converted to a sequence of evdev keydown/keyup events, handling modifiers.
  • If keyCode is provided, it’s translated from its codeType (Usb, Evdev, XKB, Win, Mac) to an evdev keycode and sent as keydown/keyup pairs.
  • If text is provided, each UTF-8 character is converted to evdev keypress (keydown then keyup) events.

This method returns OK (code 0) upon successful asynchronous scheduling of the operation.

Source

pub async fn send_touch( &mut self, request: impl IntoRequest<TouchEvent>, ) -> Result<Response<()>, Status>

Sends touch events to the emulator. This operation is asynchronous and executed on the main looper.

The TouchEvent contains a list of Touch objects, each with x, y coordinates, identifier, pressure, touch_major, touch_minor, expiration, and orientation. Coordinates are scaled to the emulator’s display resolution. Each Touch identifier is mapped to an internal Linux multitouch slot. Expiration handling ensures that inactive touch events are properly “lifted” after 120 seconds.

This method returns OK (code 0) upon successful asynchronous scheduling of the operation. Warnings are logged if no touch slots are available.

Source

pub async fn send_mouse( &mut self, request: impl IntoRequest<MouseEvent>, ) -> Result<Response<()>, Status>

Sends mouse events to the emulator. This operation is asynchronous and executed on the main looper.

The MouseEvent specifies x, y coordinates, buttons state (bitmask: 1 for left, 2 for right), and display ID. In certain virtual input configurations (VirtioInput enabled, but VirtioMouse and VirtioTablet disabled), buttons may be masked to only consider the primary button. The event is sent to the emulator’s user_event_agent.

This method returns OK (code 0) upon successful asynchronous scheduling of the operation.

Source

pub async fn inject_wheel( &mut self, request: impl IntoStreamingRequest<Message = WheelEvent>, ) -> Result<Response<()>, Status>

Injects a stream of wheel events into the emulator. This is a server-side streaming RPC.

Each WheelEvent contains dx, dy (delta values, dy is pre-multiplied by 120 for scroll clicks), and display ID. If the emulator’s input device has rotary capabilities (e.g., AVD_WEAR flavor), dy is scaled and sent as a rotary event. Otherwise, it’s sent as a standard mouse wheel event.

This method returns a server-side streaming reactor.

Source

pub async fn stream_input_event( &mut self, request: impl IntoStreamingRequest<Message = InputEvent>, ) -> Result<Response<()>, Status>

Streams a series of generic input events to the emulator. The events are processed in the order they arrive. This is a server-side streaming RPC that supports various input types encapsulated within InputEvent’s oneof type field.

Supported input types:

  • key_event (KeyboardEvent): Processed by KeyEventSender as described in sendKey.
  • touch_event (TouchEvent): Processed by TouchEventSender as described in sendTouch.
  • mouse_event (MouseEvent): Processed by MouseEventSender as described in sendMouse.
  • android_event (AndroidEvent): Raw Linux input events (type, code, value) sent directly to the kernel.
  • pen_event (PenEvent): Processed by PenEventSender for pen input, including pressure, orientation, and button state.
  • wheel_event (WheelEvent): Processed by WheelEventSender as described in injectWheel.
  • xr_command (XrCommand): Executes XR-specific commands (e.g., RECENTER to recenter the viewport). Unknown actions are logged as warnings.
  • xr_head_rotation_event (RotationRadian): Sends head rotation data in radians. Logs an error if the agent call fails.
  • xr_head_movement_event (Translation): Sends head movement data in meters. Logs an error if the agent call fails.
  • xr_head_angular_velocity_event (AngularVelocity): Sends head angular velocity data in radians per second. Logs an error if the agent call fails.
  • xr_head_velocity_event (Velocity): Sends head velocity data in meters per second. Logs an error if the agent call fails.
  • touchpad_event (TouchpadEvent): Processed by TouchpadEventSender for touchpad input, similar to touch events but for a touchpad device.

All underlying input sending operations for XR events are executed asynchronously on the main looper.

Returns INVALID_ARGUMENT (code 3) if an unrecognized input event type is received, indicating a potential out-of-date emulator. The stream reactor automatically deletes itself upon completion.

Source

pub async fn send_phone( &mut self, request: impl IntoRequest<PhoneCall>, ) -> Result<Response<PhoneResponse>, Status>

Initiates or manipulates a phone call in the emulator. This is a synchronous operation executed on the main looper.

The PhoneCall message specifies the operation (e.g., InitCall, AcceptCall) and the target phone number. The telephonyCmd agent function handles the actual call action.

Returns a PhoneResponse indicating the outcome:

  • OK (0): The operation was successful.
  • BadOperation (1): The provided operation enum is out of range.
  • BadNumber (2): The provided number is malformed.
  • InvalidAction (3): The requested operation is invalid given the current call state (e.g., disconnecting when no call is active).
  • ActionFailed (4): An internal error occurred, typically if the modem agent is unavailable.
  • RadioOff (5): The emulator’s radio is turned off.
Source

pub async fn send_sms( &mut self, request: impl IntoRequest<SmsMessage>, ) -> Result<Response<PhoneResponse>, Status>

Sends an SMS message to the emulator. This is a synchronous operation.

The SmsMessage contains the srcAddress (source phone number) and the text of the message. The srcAddress is validated for GSM formatting. The message text is converted into SMS PDUs (Protocol Data Units) and delivered via the modem agent.

Returns a PhoneResponse indicating the outcome:

  • OK (0): The SMS message was successfully delivered.
  • BadNumber (2): The srcAddress is malformed.
  • ActionFailed (4): An internal error occurred, e.g., if the modem agent is unavailable or PDU creation fails.

Other error cases from PDU creation (e.g., invalid characters in text) also result in ActionFailed.

Source

pub async fn set_phone_number( &mut self, request: impl IntoRequest<PhoneNumber>, ) -> Result<Response<PhoneResponse>, Status>

Sets the emulator’s phone number. This is a synchronous operation.

The PhoneNumber message contains the new number to be set. The modem agent’s amodem_update_phone_number function is used for this update.

Returns a PhoneResponse indicating the outcome:

  • OK (0): The phone number was successfully updated.
  • BadNumber (2): The provided number is invalid for the modem.
  • ActionFailed (4): An internal error occurred, typically if the modem agent is unavailable.
Source

pub async fn get_status( &mut self, request: impl IntoRequest<()>, ) -> Result<Response<EmulatorStatus>, Status>

Retrieves the current status of the emulator. This includes comprehensive information about the virtual machine’s configuration and the guest operating system’s state.

The EmulatorStatus reply contains:

  • version: The emulator version string.
  • uptime: The time the emulator has been active in milliseconds.
  • booted: A boolean indicating if the device has completed booting.
  • vmConfig: Detailed VmConfiguration (hypervisor type, CPU cores, RAM size).
  • hardwareConfig: Key-value pairs describing the emulator’s hardware configuration.
  • heartbeat: A monotonically increasing number indicating guest activity (incremented approximately once per second).
  • guestConfig: A map of key-value pairs with guest-specific configurations, including:
  • “multidisplay”: “available” or “unavailable” based on display pipe readiness.
  • “androidVersion”: The Android version of the guest OS.
  • “hypervisorVersion”: The hypervisor version used by the guest.

This method returns OK (code 0) upon successful retrieval of the emulator status.

Source

pub async fn get_screenshot( &mut self, request: impl IntoRequest<ImageFormat>, ) -> Result<Response<Image>, Status>

Retrieves a single screenshot in the desired format.

The image will be scaled to the desiredWidth and desiredHeight specified in ImageFormat, while maintaining the aspect ratio. If width or height are 0, the device’s current display dimensions are used. The returned image will never exceed the device’s actual display resolution, but can be smaller.

The display field in ImageFormat specifies the target display; 0 (or omitted) indicates the main display. For folded Pixel Fold devices, the display ID might be internally remapped, and foldedDisplay information will be populated. The resulting image is properly oriented based on the device’s coarse-grained orientation, derived from sensor state.

The transport field in ImageFormat can specify MMAP for shared memory delivery, but if the shared memory region is too small, a FAILED_PRECONDITION error will be returned.

This method returns:

  • OK (code 0) and an Image object upon success.
  • INVALID_ARGUMENT (code 3) if the specified display ID is invalid or disabled.
  • CANCELLED (code 1) if the gRPC context is cancelled during the operation (an expensive operation).
  • FAILED_PRECONDITION (code 9) if the guest has not posted a new frame yet (for non-PNG formats when fast path is used).

This method will return an image with width 0 and height 0 if the display is not visible.

Source

pub async fn stream_screenshot( &mut self, request: impl IntoRequest<ImageFormat>, ) -> Result<Response<Streaming<Image>>, Status>

Streams a series of screenshots in the desired format. This is a server-side streaming RPC.

A new frame is delivered whenever the device produces a new frame or when sensor changes occur. Initial state: The first frame delivered might be an empty image (width 0, height 0) if the display is inactive. Subsequent frames are delivered when new content is available or a sensor event triggers an update. If the display becomes inactive, an empty image will be delivered again. Images resume when the display becomes active.

ImageFormat parameters (format, width, height, display) behave as described in getScreenshot. The transport field in ImageFormat can specify MMAP for shared memory delivery. If MMAP is used and the provided shared memory handle is valid and mapped, pixel data will be written directly to it. The image field in the Image reply will be empty if MMAP transport is used.

Performance considerations:

  • Streaming can produce a significant amount of data.
  • PNG format is CPU-intensive due to encoding overhead.
  • Using MMAP transport can significantly reduce gRPC overhead for pixel data.

This method returns:

  • A server-side streaming reactor.
  • INVALID_ARGUMENT (code 3) if the specified display ID is invalid or disabled.
  • CANCELLED (code 1) if the gRPC context is cancelled during the operation.
Source

pub async fn stream_audio( &mut self, request: impl IntoRequest<AudioFormat>, ) -> Result<Response<Streaming<AudioPacket>>, Status>

Streams a series of audio packets in the desired format. This is a server-side streaming RPC. A new frame is delivered approximately every 20-30ms when the emulated device produces audio. If samplingRate is 0, it defaults to 44100 Hz. The stream may block indefinitely if the emulator ceases to produce audio. Packets are allocated with a buffer size calculated based on the audio format and a 30ms frame time.

This method returns OK (code 0) upon successful streaming initiation.

Source

pub async fn inject_audio( &mut self, request: impl IntoStreamingRequest<Message = AudioPacket>, ) -> Result<Response<()>, Status>

Injects a series of audio packets into the Android microphone. This is a client-side streaming RPC. Audio packets are processed at a rate determined by the emulator’s request for frames. An internal buffer can hold approximately 300ms of audio.

Notes:

  • Only the AudioFormat from the first received packet is honored. Subsequent AudioFormat changes are ignored.
  • MODE_REAL_TIME is experimental: incoming data may overwrite existing data if the client does not control timing properly.
  • The circular buffer attempts to deliver all queued samples upon stream closure by writing silence for up to 300ms.

Returns the following gRPC error codes:

  • FAILED_PRECONDITION (code 9): If another microphone is already active, or if unable to register the microphone.
  • INVALID_ARGUMENT (code 3): If the desired samplingRate exceeds 48kHz, or if an AudioPacket is too large for the internal buffer.

This method returns OK (code 0) upon successful completion of the stream.

Source

pub async fn get_microphone_state( &mut self, request: impl IntoRequest<()>, ) -> Result<Response<MicrophoneState>, Status>

Retrieves the current settings for the microphone

Source

pub async fn set_microphone_state( &mut self, request: impl IntoRequest<MicrophoneState>, ) -> Result<Response<()>, Status>

Sets the state for the microphone

Source

pub async fn get_logcat( &mut self, request: impl IntoRequest<LogMessage>, ) -> Result<Response<LogMessage>, Status>

👎Deprecated

Deprecated, please use the streamLogcat method instead.

Source

pub async fn stream_logcat( &mut self, request: impl IntoRequest<LogMessage>, ) -> Result<Response<Streaming<LogMessage>>, Status>

Streams the logcat output from the emulator in real-time. This is a server-side streaming RPC. The stream sources its data from the logcat command executed via AdbShellStream in the Android guest. Log lines are processed individually as they arrive.

The LogMessage.sort field determines the output format:

  • If LogMessage.sort is Parsed, each incoming log line is parsed into a structured LogcatEntry object, and these entries are returned in the LogMessage.entries field. Structured parsing is typically available for Android API Level 23 (Marshmallow) and later.
  • If LogMessage.sort is Text (or unspecified), the raw log line is returned in the LogMessage.contents field.

The stream continues as long as the underlying logcat process is running and the client is connected. The stream will naturally terminate if the logcat process stops or the connection is lost. No explicit gRPC error codes are returned by this method during active streaming.

Source

pub async fn set_vm_state( &mut self, request: impl IntoRequest<VmRunState>, ) -> Result<Response<()>, Status>

Transitions the virtual machine to the desired state. This operation is scheduled asynchronously.

Transition commands:

  • RUNNING or START: Starts or resumes execution of the virtual machine.
  • PAUSED or STOP: Pauses execution of the virtual machine, halting CPU cycles.
  • RESET or RESTART: Performs a warm reset of the virtual machine.
  • SHUTDOWN: Initiates a graceful shutdown of the emulator.
  • TERMINATE: Forcefully terminates the emulator process immediately without cleanup. This can cause data corruption and must be used with caution.

Note that write-only actions (START, STOP, RESET, RESTART) perform the transition but are not observed as states in getVmState. Purely observable states (UNKNOWN, RESTORE_VM, SAVE_VM, INTERNAL_ERROR) cannot be set directly.

Returns once the operation has been scheduled. Note: The call may not return when the state is set to TERMINATE or SHUTDOWN.

Source

pub async fn get_vm_state( &mut self, request: impl IntoRequest<()>, ) -> Result<Response<VmRunState>, Status>

Retrieves the current execution state of the virtual machine.

The returned VmRunState represents the current condition of the VM:

  • RUNNING: The virtual machine is actively executing.
  • PAUSED: Execution is suspended (CPUs are halted).
  • SHUTDOWN: The guest operating system has initiated a shutdown.
  • RESTORE_VM: The virtual machine is paused while restoring its state (e.g., loading a snapshot).
  • SAVE_VM: The virtual machine is paused while saving its state (e.g., taking a snapshot).
  • INTERNAL_ERROR: Execution has stopped due to a guest panic, I/O error, or hypervisor failure.
  • UNKNOWN: The virtual machine is in an unmapped or transient state.

This is a synchronous query operation.

Source

pub async fn set_display_configurations( &mut self, request: impl IntoRequest<DisplayConfigurations>, ) -> Result<Response<DisplayConfigurations>, Status>

Atomically changes the current multi-display configuration. This operation applies the provided DisplayConfigurations, with special handling for secondary displays. Display ID 0 (the primary display) cannot be modified via this RPC.

Preconditions:

  • The android::featurecontrol::MultiDisplay feature must be enabled.

Input Validation:

  • INVALID_ARGUMENT (code 3): If duplicate display IDs are found in the request.
  • INVALID_ARGUMENT (code 3): If any DisplayConfiguration (width, height, dpi, flags) is outside valid ranges as determined by multiDisplayParamValidate.
  • INVALID_ARGUMENT (code 3): If any display ID is outside the configurable range [1, userConfigurable].

Atomic Update and Rollback: The system attempts to apply each display configuration. If any update fails (e.g., after multiple retries for transient pipe errors), a rollback mechanism is initiated: successfully updated displays are reverted to their previous state, and newly added displays are deleted. In such cases, an INTERNAL error is returned.

Deletion of Unrequested Displays: Any displays that were active before this call but are not present in the new request.displays (and are not display ID 0) will be deleted.

Notifications: Upon successful completion, notifyDisplayChanges() is called to inform third-party subscribers.

Returns the following gRPC error codes:

  • OK (code 0): Upon successful application of all configurations, returning the final active DisplayConfigurations.
  • FAILED_PRECONDITION (code 9): If the multi-display feature is not available.
  • INTERNAL (code 13): If an internal emulator failure occurs during display modification or rollback.
Source

pub async fn get_display_configurations( &mut self, request: impl IntoRequest<()>, ) -> Result<Response<DisplayConfigurations>, Status>

Returns all currently valid logical displays configured in the emulator. This is a synchronous operation.

Preconditions:

  • The android::featurecontrol::MultiDisplay feature must be enabled.

The DisplayConfigurations reply contains:

  • displays: A repeated field of DisplayConfiguration objects, each detailing the width, height, DPI, flags, and ID of an active display. For Pixel Fold devices, only the main display configuration might be relevant.
  • userConfigurable: The maximum number of user-configurable displays (IDs from 1 up to this value).
  • maxDisplays: The total maximum number of displays the emulator supports.

This method returns:

  • OK (code 0) and the current DisplayConfigurations upon success.
  • FAILED_PRECONDITION (code 9): If the AVD does not support the multi-display feature.
Source

pub async fn stream_notification( &mut self, request: impl IntoRequest<()>, ) -> Result<Response<Streaming<Notification>>, Status>

Notifies the client of various emulator state changes in real-time. This is a server-side streaming RPC. Upon subscription, the current states of virtual scene camera, foldable posture, boot completion, and XR options are immediately sent. The stream then continuously delivers new notifications when relevant events occur. UniqueEventStreamWriter ensures that only distinct state changes are streamed.

Notifications include:

  • CameraNotification: Reports virtual scene camera activation/deactivation and associated display.
  • DisplayConfigurationsChangedNotification: Triggered when display configurations are modified via the extended UI. Does not fire for changes made through console or gRPC.
  • Posture: Reports changes in the device’s foldable posture.
  • BootCompletedNotification: Indicates when the emulator has finished booting.
  • BrightnessValue: Reports changes in backlight brightness (LCD, keyboard, or button).
  • TextViewFocus: Sent when a text view gains or loses focus, or immediately on subscription.
  • XrOptions: Reports changes in XR-related settings (environment, passthrough coefficient), or immediately on subscription.
  • MicrophoneState : Reports changes in the microphone state (currently whether host microphone access is allowed)
  • LedIndicator: Reports changes in AI Glasses XR LED light state on subscription.

This method returns a server-side streaming reactor.

Source

pub async fn rotate_virtual_scene_camera( &mut self, request: impl IntoRequest<RotationRadian>, ) -> Result<Response<()>, Status>

Rotates the virtual scene camera relative to its current orientation. This operation is asynchronous and executed on the main looper.

The RotationRadian message specifies angles in radians around the x, y, and z axes. The z component of rotation is currently unused. The coordinate system is right-handed: x-axis points right, y-axis points up, and z-axis points towards the viewer. This operation only succeeds if the virtual scene camera is actively connected.

This method returns OK (code 0) upon successful asynchronous scheduling of the operation.

Source

pub async fn set_virtual_scene_camera_velocity( &mut self, request: impl IntoRequest<Velocity>, ) -> Result<Response<()>, Status>

Sets the absolute velocity of the virtual scene camera. This operation is asynchronous and executed on the main looper.

The Velocity message specifies components in meters per second along the x, y, and z axes. The coordinate system is right-handed: x-axis points right, y-axis points up, and z-axis points towards the viewer. The transition to these target velocity values may be smoothed over time by the implementation. This operation only succeeds if the virtual scene camera is actively connected.

This method returns OK (code 0) upon successful asynchronous scheduling of the operation.

Source

pub async fn set_posture( &mut self, request: impl IntoRequest<Posture>, ) -> Result<Response<()>, Status>

Sets the foldable posture of the device. This operation is asynchronous and executed on the main looper.

The Posture message contains a PostureValue enum, defining the desired physical configuration of the foldable device.

Returns the following gRPC error codes:

  • OK (code 0): Upon successful asynchronous scheduling of the operation.
  • FAILED_PRECONDITION (code 9): If the emulator is unable to set the specified posture.
Source

pub async fn get_brightness( &mut self, request: impl IntoRequest<BrightnessValue>, ) -> Result<Response<BrightnessValue>, Status>

Retrieves the current backlight brightness for a specified light type. This is a synchronous operation.

The BrightnessValue.target field (e.g., LCD, KEYBOARD, BUTTON) determines which light’s brightness is queried. Internal mapping converts these to string names like “lcd_backlight”.

Returns the following gRPC error codes:

  • OK (code 0): Upon successful retrieval, populating the BrightnessValue reply with the target and current value.
  • FAILED_PRECONDITION (code 9): If the AVD does not support the hw-control agent or its getBrightness function is unavailable.
Source

pub async fn set_brightness( &mut self, request: impl IntoRequest<BrightnessValue>, ) -> Result<Response<()>, Status>

Sets the backlight brightness for a specified light type. This operation is asynchronous and executed on the main looper.

The BrightnessValue.target field (e.g., LCD, KEYBOARD, BUTTON) determines which light’s brightness is set. The BrightnessValue.value specifies the desired intensity, ranging from 0 to 255. Internal mapping converts LightType to string names like “lcd_backlight”.

Returns the following gRPC error codes:

  • OK (code 0): Upon successful asynchronous scheduling of the operation.
  • FAILED_PRECONDITION (code 9): If the AVD does not support the hw-control agent or its setBrightness function is unavailable.
  • INVALID_ARGUMENT (code 3): If the brightness value exceeds the valid range (0-255).
Source

pub async fn get_display_mode( &mut self, request: impl IntoRequest<()>, ) -> Result<Response<DisplayMode>, Status>

Returns the current mode of the primary display of a resizable AVD. This is a synchronous operation.

Preconditions:

  • The AVD must be configured to support resizable displays (resizableEnabled() must be true).

The DisplayMode.value field will be populated with the current DisplayModeValue, derived from the getResizableActiveConfigId().

Returns the following gRPC error codes:

  • OK (code 0): Upon successful retrieval of the display mode.
  • FAILED_PRECONDITION (code 9): If the AVD is not resizable.
Source

pub async fn set_display_mode( &mut self, request: impl IntoRequest<DisplayMode>, ) -> Result<Response<()>, Status>

Sets the size of the primary display of a resizable AVD to the specified DisplayModeValue. This operation is asynchronous and executed on the main looper.

Preconditions:

  • The AVD must be configured to support resizable displays (resizableEnabled() must be true).
  • The emulator’s changeResizableDisplay agent function must be available.

The DisplayMode.value field specifies the desired display configuration (e.g., PHONE, FOLDABLE, TABLET, DESKTOP).

Returns the following gRPC error codes:

  • OK (code 0): Upon successful asynchronous scheduling of the operation.
  • FAILED_PRECONDITION (code 9): If the AVD is not resizable.
  • INTERNAL (code 13): If the internal window agent function changeResizableDisplay is not available.
Source

pub async fn set_xr_options( &mut self, request: impl IntoRequest<XrOptions>, ) -> Result<Response<()>, Status>

Changes the XR-related settings of the emulator. This operation is asynchronous and executed on the main looper.

The XrOptions message specifies the environment (e.g., LIVING_ROOM_DAY, LIVING_ROOM_NIGHT) and passthrough_coefficient (a float between 0.0 and 1.0 for real/artificial environment visibility). Values for passthrough_coefficient outside [0.0, 1.0] are ignored.

Returns the following gRPC error codes:

  • OK (code 0): Upon successful asynchronous scheduling of the operation.
  • FAILED_PRECONDITION (code 9): If the setXrOptions agent function fails (e.g., if XR is not supported).
Source

pub async fn get_xr_options( &mut self, request: impl IntoRequest<()>, ) -> Result<Response<XrOptions>, Status>

Retrieves the current state of XR-related settings from the emulator. This is a synchronous operation.

Preconditions:

  • XR mode must be supported in the current AVD (isXrGuestOs() must be true). (Note: Current implementation of isXrGuestOs() always returns true).

The XrOptions reply contains the current environment and passthrough_coefficient.

Returns the following gRPC error codes:

  • OK (code 0): Upon successful retrieval of the XR options.
  • FAILED_PRECONDITION (code 9): If XR mode is not supported in the current AVD or if the getXrOptions agent function fails.
Source

pub async fn set_environment( &mut self, request: impl IntoRequest<Environment>, ) -> Result<Response<()>, Status>

Sets the environment background for AI glasses.

Source

pub async fn get_environment( &mut self, request: impl IntoRequest<()>, ) -> Result<Response<Environment>, Status>

Gets the current environment configuration for AI glasses. Values that are not set in environment.ini will be set to default values.

Source

pub async fn get_host_cameras( &mut self, request: impl IntoRequest<()>, ) -> Result<Response<CameraList>, Status>

Returns the list of video cameras connected to the host machine.

Trait Implementations§

Source§

impl<T: Clone> Clone for EmulatorControllerClient<T>

Source§

fn clone(&self) -> Self

Returns a duplicate of the value. Read more
1.0.0 (const: unstable) · Source§

fn clone_from(&mut self, source: &Self)

Performs copy-assignment from source. Read more
Source§

impl<T: Debug> Debug for EmulatorControllerClient<T>

Source§

fn fmt(&self, f: &mut Formatter<'_>) -> Result

Formats the value using the given formatter. Read more

Auto Trait Implementations§

Blanket Implementations§

Source§

impl<T> Any for T
where T: 'static + ?Sized,

Source§

fn type_id(&self) -> TypeId

Gets the TypeId of self. Read more
Source§

impl<T> Borrow<T> for T
where T: ?Sized,

Source§

fn borrow(&self) -> &T

Immutably borrows from an owned value. Read more
Source§

impl<T> BorrowMut<T> for T
where T: ?Sized,

Source§

fn borrow_mut(&mut self) -> &mut T

Mutably borrows from an owned value. Read more
Source§

impl<T> CloneToUninit for T
where T: Clone,

Source§

unsafe fn clone_to_uninit(&self, dest: *mut u8)

🔬This is a nightly-only experimental API. (clone_to_uninit)
Performs copy-assignment from self to dest. Read more
Source§

impl<T> From<T> for T

Source§

fn from(t: T) -> T

Returns the argument unchanged.

Source§

impl<T> Instrument for T

Source§

fn instrument(self, span: Span) -> Instrumented<Self> ⓘ

Instruments this type with the provided Span, returning an Instrumented wrapper. Read more
Source§

fn in_current_span(self) -> Instrumented<Self> ⓘ

Instruments this type with the current Span, returning an Instrumented wrapper. Read more
Source§

impl<T, U> Into<U> for T
where U: From<T>,

Source§

fn into(self) -> U

Calls U::from(self).

That is, this conversion is whatever the implementation of From<T> for U chooses to do.

Source§

impl<T> IntoRequest<T> for T

Source§

fn into_request(self) -> Request<T>

Wrap the input message T in a tonic::Request
Source§

impl<L> LayerExt<L> for L

Source§

fn named_layer<S>(&self, service: S) -> Layered<<L as Layer<S>>::Service, S>
where L: Layer<S>,

Applies the layer to a service and wraps it in Layered.
Source§

impl<T> ToOwned for T
where T: Clone,

Source§

type Owned = T

The resulting type after obtaining ownership.
Source§

fn to_owned(&self) -> T

Creates owned data from borrowed data, usually by cloning. Read more
Source§

fn clone_into(&self, target: &mut T)

Uses borrowed data to replace owned data, usually by cloning. Read more
Source§

impl<T, U> TryFrom<U> for T
where U: Into<T>,

Source§

type Error = !

The type returned in the event of a conversion error.
Source§

fn try_from(value: U) -> Result<T, !>

Performs the conversion.
Source§

impl<T, U> TryInto<U> for T
where U: TryFrom<T>,

Source§

type Error = <U as TryFrom<T>>::Error

The type returned in the event of a conversion error.
Source§

fn try_into(self) -> Result<U, <U as TryFrom<T>>::Error>

Performs the conversion.
Source§

impl<T> WithSubscriber for T

Source§

fn with_subscriber<S>(self, subscriber: S) -> WithDispatch<Self> ⓘ
where S: Into<Dispatch>,

Attaches the provided Subscriber to this type, returning a WithDispatch wrapper. Read more
Source§

fn with_current_subscriber(self) -> WithDispatch<Self> ⓘ

Attaches the current default Subscriber to this type, returning a WithDispatch wrapper. Read more