nimeet Docs
中文

Flutter SDK Guide

Flutter SDK install, join a channel, events and platform support.

Interface sections generated from the public SDK definitions

Version v1.1.0 · Updated 2026-10-26 · revision 1

The Flutter platform is Dart with the RtcEngine shape (isomorphic with Android/iOS): RtcEngine + RtcEngineEventHandler, with return values wrapped in Future.

Prerequisites

  • Flutter 3.22+, Dart 3.4+.
  • Native permissions per platform: CAMERA/RECORD_AUDIO on Android, NSCameraUsageDescription/NSMicrophoneUsageDescription on iOS.
  • You already have an appId and a token service (see Enable services and get credentials).

Install

yaml
# pubspec.yaml — local path dependency (not yet published to pub.dev)
dependencies:
  nimeet_rtc:
    path: ../ni-meet/sdk/flutter

Get a token

A Flutter client must not hold customerSecret; tokens are issued by your backend and injected on the Flutter side through a TokenProvider:

dart
final provider = FallbackTokenProvider([
  CallbackTokenProvider((channel, uid, role) => authApi.fetchRtcToken(channel, uid, role)),
  StaticTokenProvider(Platform.environment['NIMEET_TEST_TOKEN'] ?? ''),
]);

Join a channel

dart
import 'package:nimeet_rtc/nimeet_rtc.dart';

class MeetingController extends RtcEngineEventHandler {
  late final RtcEngine engine;

  Future<void> start(String appId, String token) async {
    engine = await RtcEngine.create(RtcEngineConfig(appId: appId));
    engine.registerEventHandler(this);

    await engine.setChannelProfile(ChannelProfileType.channelProfileLiveBroadcasting);
    await engine.enableVideo();
    await engine.setupLocalVideo(const VideoCanvas(uid: 0));
    await engine.startPreview();

    await engine.joinChannel(
      token: token,
      channelId: 'weekly-sync',
      uid: 10001,
      options: const ChannelMediaOptions(clientRoleType: ClientRoleType.clientRoleBroadcaster),
    );
  }

  @override
  void onJoinChannelSuccess(RtcConnection connection, int elapsed) {
    // Join succeeded
  }

  @override
  void onUserJoined(RtcConnection connection, int remoteUid, int elapsed) {
    // A remote user joined
  }

  @override
  void onUserOffline(RtcConnection connection, int remoteUid, UserOfflineReasonType reason) {
    // A remote user left
  }

  @override
  void onTokenPrivilegeWillExpire(String token) {
    // After refreshing the token, call engine.renewToken(newToken)
  }
}

Publish and subscribe

dart
await engine.muteLocalAudioStream(true);   // mute the microphone
await engine.muteLocalVideoStream(true);   // turn off the local video
await engine.enableLocalVideo(false);      // stop capture
await engine.updateChannelMediaOptions(options);

Screen sharing: getScreenCaptureSources() enumerates sources → startScreenCapture(...); stop with stopScreenCapture().

Events

RtcEngineEventHandler is the callback class; it covers onJoinChannelSuccess, onUserJoined, onUserOffline, onFirstRemoteVideoDecoded, onTokenPrivilegeWillExpire, onError, onConnectionStateChanged and others. Flutter callbacks return to the main isolate by default, so you can call setState directly.

Error handling

  • A failed Future throws RtcException (carrying code/sdkCode/message/retryable);
  • Asynchronous errors go through the onError callback;
  • Unimplemented capabilities throw -4 (ERR_NOT_SUPPORTED).

Troubleshooting

SymptomCauseHandling
The iOS build failsPods are not installed, or the platform minimum is not metRun cd ios && pod install, and raise platform :ios
Black screen on AndroidRuntime permission was not requestedThe host app must request CAMERA/RECORD_AUDIO itself
Callbacks are lost after a hot reloadThe handler was recreatedRegister in initState and unregister in dispose
MissingPluginException at compile timeThe native side did not register the pluginDo a full restart (flutter run rather than a hot reload)
Cannot recover after the token expiresonTokenPrivilegeWillExpire is not handledRenew the token and call renewToken

Next steps

Platform information

Itemvalue
PlatformFlutter
LanguageDart
SDK packagenimeet_rtc
Interface version6.6.4
Compatible Agora APIAgora flutter API

The public interfaces are aligned with the Agora flutter API; installation and runtime requirements are listed under Prerequisites above.

Availability

This platform's SDK: Generally available. The examples use the public API; runtime capability follows the published SDK package.

join-channel flow

The method names, parameter types and return values match the API reference for the same platform. Where a method has several overloads, the most common one is shown here; see the API reference for all overloads.

StepInterfaceMethodOverload count
subscribe to remote mediaBaseSpatialAudioEnginemuteRemoteAudioStream1
Create instance / initializeLocalSpatialAudioEngineinitialize1
Renew the TokenMusicContentCenterrenewToken1
enable video and local previewRtcEngineenableVideo1
Join a channelRtcEnginejoinChannel1
Leave a channelRtcEngineleaveChannel1
Channel scenariosRtcEnginesetChannelProfile1
switch rolesRtcEnginesetClientRole1
bind the local videoRtcEnginesetupLocalVideo1
typescript
muteRemoteAudioStream(mute: int uid,required bool): Future
initialize(): Future
renewToken(token: String): Future
enableVideo(): Future
joinChannel(options: String token,required String channelId,required int uid,required ChannelMediaOptions): Future
leaveChannel(options?: LeaveChannelOptions?): Future
setChannelProfile(profile: ChannelProfileType): Future
setClientRole(options?: ClientRoleType role,ClientRoleOptions?): Future
setupLocalVideo(canvas: VideoCanvas): Future

Events and callbacks

Callbacks are registered on RtcEngineEventHandler; naming differs by platform, and the full list is in the API reference for the same platform.

CallbacksSignaturePurpose
onConnectionStateChangedonConnectionStateChanged(connection: RtcConnection, state: ConnectionStateType, reason: ConnectionChangedReasonType): voidjoin result / connection-state changes:update the UI accordingly and decide whether to reconnect.
onUserJoinedonUserJoined(connection: RtcConnection, remoteUid: int, elapsed: int): voidRemote user joined:allocate the frame container.
onFirstRemoteVideoDecodedonFirstRemoteVideoDecoded(connection: RtcConnection, remoteUid: int, width: int, height: int, elapsed: int): voidRemote video status:it can render once the first frame is decoded.
onUserOfflineonUserOffline(connection: RtcConnection, remoteUid: int, reason: UserOfflineReasonType): voidRemote user left:release the container and subscription.
onRequestTokenonRequestToken(connection: RtcConnection): voidToken expiring soon:call the server to renew, then `renewToken`.
onErroronError(err: ErrorCodeType, msg: String): voidRuntime errors:`err` is an Agora error number, route by the error-code table.
onNetworkQualityonNetworkQuality(connection: RtcConnection, remoteUid: int, txQuality: QualityType, rxQuality: QualityType): voidNetwork quality:report to Analytics or prompt the user.

Error codes

Constantvalue
RtcEnginenull
errAborted20
errAdmGeneralError1005
errAdmInitPlayout1008
errAdmInitRecording1011
errAdmStartPlayout1009
errAdmStartRecording1012
errAdmStopPlayout1010
errAdmStopRecording1013
errAlreadyInUse19
errBitrateLimit115
errBufferTooSmall6
errClientIsBannedByServer123
errConnectionInterrupted111
errConnectionLost112
errDatastreamDecryptionFailed122
errDecryptionFailed120
errEncryptedStreamNotAllowedPublish130
errFailed1
errInitNetEngine21
errInvalidAppId101
errInvalidArgument2
errInvalidChannelName102
errInvalidState8
errInvalidTokennull
errInvalidUserAccount134
errInvalidUserId121
errJoinChannelRejected17
errLeaveChannelRejected18
errLoadMediaEngine1001
errNoPermission9
errNoServerResources103
errNotInChannel113
errNotInitialized7
errNotReady3
errNotSupported4
errOk0
errPcmsendBufferoverflow201
errPcmsendFormat200
errRefused5
errResourceLimited22
errSetClientRoleNotAuthorized119
errSizeTooLarge114
errStreamMessageTimeout117
errTimedout10
errTokenExpired109
errTooManyDataStreams116
errVdmCameraNotAuthorized1501

the platform REST layer uses REST error codes;the SDK layer maps connection/authentication failures to Agora error numbers, for the mapping table see SDK error identifiers per platform。

Generated by the documentation build pipeline · 2026-10-31 01:24:02 UTC · Documentation center v1.1.0.

Content follows the public API definitions.

ni-meet is a self-hosted RTC PaaS with a LiveKit-based media plane (Apache-2.0) and an Agora-compatible API.