flutter_pitel_voip
Integrate VoIP call to your project
flutter_pitel_voip is package support for voip call. Please contact pitel to use the service.
Demo
 

Pitel Connect Flow
When user make call from Pitel Connect app, Pitel Server pushes a notification for all user login (who receives the call). When user "Accept" call, extension will re-register to receive call.

Features
- Register Extension
- Call
- Hangup
- Turn on/off micro
- Turn on/of speaker
Installation
- Install Packages
- Run this command:
flutter pub add flutter_pitel_voip
- Or add pubspec.yaml:
flutter_pitel_voip: any
- Get package
flutter pub get
- Import
import 'package:flutter_pitel_voip/flutter_pitel_voip.dart';
- Configure Project
- In file app.dart config easyloading
import 'package:flutter_easyloading/flutter_easyloading.dart';
  // ....
  return MaterialApp.router(
    // ...
    builder: EasyLoading.init(),
  )
Android:
- In file android/app/src/main/AndroidManifest.xml
 <manifest...>
    ...
    // Request permission
    <uses-permission android:name="android.permission.INTERNET" />
    <uses-permission android:name="android.permission.ACCESS_NETWORK_STATE" />
    <uses-permission android:name="android.permission.RECORD_AUDIO" />
    <uses-permission android:name="android.permission.MODIFY_AUDIO_SETTINGS"/>
    <uses-permission android:name="android.permission.SYSTEM_ALERT_WINDOW" />
    <uses-permission android:name="android.permission.FOREGROUND_SERVICE"/>
 </manifest>
IOS
- Request permission in file Info.plist
<key>NSMicrophoneUsageDescription</key>
<string>Use microphone</string>
<key>UIBackgroundModes</key>
<array>
	<string>fetch</string>
	<string>processing</string>
	<string>remote-notification</string>
	<string>voip</string>
</array>
- Make sure platform ios 13.0inPodfile
platform :ios, '13.0'
- Pushkit/ Push notification - Received VoIP and Wake app from Terminated State.
Note Please check PUSH_NOTIF.md. setup Pushkit (for IOS), push notification (for Android). 
Troubleshooting
Android only: If you give a error flutter_webrtc when run app in android. Please update code in file
$HOME/.pub-cache/hosted/pub.flutter-io.cn/flutter_webrtc-{version}/android/build.gradle
dependencies {
  // Remove
  // implementation 'com.github.webrtc-sdk:android:104.5112.03'
  // Replace
  implementation 'io.github.webrtc-sdk:android:104.5112.09'
}
Example
Please checkout repo github to get example
Usage
- In file app.dart, Wrap MaterialApp with PitelVoip widget Please follow example
Note: handleRegisterCall, handleRegister, registerFunc in here
Widget build(BuildContext context) {
    return PitelVoip(                           // Wrap with PitelVoip
      handleRegister: handleRegister,           // Handle register
      handleRegisterCall: handleRegisterCall,   // Handle register call
      child: MaterialApp.router(
        ...
      ),
    );
  }
- In file home_screen.dart. Please follow example. Add WidgetsBindingObserver to handle AppLifecycleState change
...
Widget build(BuildContext context) {
    return PitelVoipCall(
        // Wrap with PitelVoipCall
        bundleId: '${bundle_id}',
        appMode: 'dev', // dev or production
        sipInfoData: sipInfoData,
        goBack: () {
            // go back function
        },
        goToCall: () {
            // go to call screen
        },
        onCallState: (callState) {
            // IMPORTANT: Set callState to your global state management. Example: bloc, getX, riverpod,..
            // Example riverpod
            // ref.read(callStateController.notifier).state = callState;
        },
        onRegisterState: (String registerState) {
            // get Register Status in here
        },
      child: ...,
    );
  }
Properties
| Prop | Description | Type | Default | 
|---|---|---|---|
| bundleId | bundleId IOS, packageId android | String | Required | 
| appMode | debug mode or release mode | String | Required | 
| sipInfoData | SIP information data | () {} | Required | 
| goBack | goback navigation | () {} | Required | 
| goToCall | navigation, go to call screen | () {} | Required | 
| onCallState | set call status | (callState) {} | Required | 
| onRegisterState | get extension register status | (String registerState) {} | Required | 
| child | child widget | Widget | Required | 
Register extension from data of Tel4vn provide. Example: 101, 102,… Create 1 button to fill data to register extension.
ElevatedButton(
        onPressed: () asyns {
          final PushNotifParams pushNotifParams = PushNotifParams(
            teamId: '${apple_team_id}',
            bundleId: '${bundle_id}',
          );
          final sipInfoData = SipInfoData.fromJson({
            "authPass": "${Password}",
            "registerServer": "${Domain}",
            "outboundServer": "${Outbound Proxy}",
            "port": PORT,
            "accountName": "${UUser}",      // Example 101
            "displayName": "${Display Name}",
            "wssUrl": "${URL WSS}"
          });
          final pitelClient = PitelServiceImpl();
          final pitelSetting = await pitelClient.setExtensionInfo(sipInfoData, pushNotifParams);
          // IMPORTANT: Set pitelSetting to your global state management. Example: bloc, getX, riverpod,..
          // Example riverpod
          // ref.read(pitelSettingProvider.notifier).state = pitelSettingRes;
        },
        child: const Text("Register"),),
- Logout extension
pitelClient.logoutExtension(sipInfoData);
- In file call_screen.dartExample
import 'package:flutter/material.dart';
import 'package:flutter_pitel_voip/flutter_pitel_voip.dart';
class CallPage extends StatelessWidget {
  const CallPage({super.key});
  @override
  Widget build(BuildContext context) {
    // IMPORTANT: Get callState from your global state management. Example: bloc, getX, riverpod,..
    // Example riverpod
    // final callState = ref.watch(callStateController);
    return CallScreen(
      callState: callState, // callState from state management you set before
      goBack: () {
        // Call your go back function in here
      },
      bgColor: Colors.cyan,
    );
  }
}
Properties
| Prop | Description | Type | Default | 
|---|---|---|---|
| goBack | go back navigation | () {} | Required | 
| bgColor | background color | Color | Required | 
| txtMute | Text display of micro mute | String | Optional | 
| txtUnMute | Text display of micro unmute | String | Optional | 
| txtSpeaker | Text display speaker | String | Optional | 
| txtOutgoing | Text display direction outgoing call | String | Optional | 
| txtIncoming | Text display direction incoming call | String | Optional | 
| textStyle | Style for mic/speaker text | TextStyle | Optional | 
| titleTextStyle | Style for display phone number text | TextStyle | Optional | 
| timerTextStyle | Style for timer text | TextStyle | Optional | 
| directionTextStyle | Style for direction text | TextStyle | Optional | 
| showHoldCall | Show action button hold call | bool | Optional | 
- Outgoing call
pitelCall.outGoingCall(
  phoneNumber: "",
  handleRegisterCall: (){},
);
Properties
| Prop | Description | Type | Default | 
|---|---|---|---|
| phoneNumber | phone number for call out | String | Required | 
| handleRegisterCall | re-register when call out | () {} | Required | 
| nameCaller | set name caller | String | Optional | 
How to test
Using tryit to test voip call connection & conversation Link: https://tryit.jssip.net/ Setting:
- Access to link https://tryit.jssip.net/
- Enter extension: example 102
- Click Setting icon
- Enter information to input field
 
- Save
- Click icon -> to connect
Libraries
- component/app_life_cycle/app_life_cycle
- component/pitel_call_state
- component/pitel_rtc_video_renderer
- component/pitel_rtc_video_view
- component/pitel_ua_helper
- component/sip_pitel_helper_listener
- config/pitel_config
- flutter_pitel_voip
- model/http/base_header
- model/http/delete_aor_ext
- model/http/get_extension_info
- model/http/get_profile
- model/http/get_sip_info
- model/http/login
- model/http/push_notif_model
- model/pitel_error
- model/sip_account
- model/sip_server
- pitel_plugin/pitel_plugin
- pitel_sdk/pitel_api
- pitel_sdk/pitel_call
- pitel_sdk/pitel_client
- pitel_sdk/pitel_log
- pitel_sdk/pitel_profile
- screens/call_screen/call_page
- screens/call_screen/call_screen
- screens/call_screen/widgets/call_timer
- screens/call_screen/widgets/select_audio_modal
- screens/call_screen/widgets/voice_header
- screens/pitel_voip/pitel_voip
- screens/pitel_voip_call/pitel_voip_call
- services/models/pn_push_params
- services/models/push_notif_params
- services/pitel_service
- services/pitel_service_interface
- services/sip_info_data
- sip/sip_ua
- only expose the bare minimum of internals required
- sip/src/config
- sip/src/constants
- sip/src/data
- sip/src/dialog
- sip/src/dialog/request_sender
- sip/src/digest_authentication
- sip/src/enum_helper
- sip/src/event_manager/call_events
- sip/src/event_manager/event_manager
- sip/src/event_manager/events
- sip/src/event_manager/internal_events
- sip/src/event_manager/message_events
- sip/src/event_manager/refer_events
- sip/src/event_manager/register_events
- sip/src/event_manager/transport_events
- sip/src/exceptions
- sip/src/grammar
- sip/src/grammar_parser
- sip/src/logger
- sip/src/message
- sip/src/name_addr_header
- sip/src/parser
- sip/src/registrator
- sip/src/request_sender
- sip/src/rtc_session
- sip/src/rtc_session/dtmf
- sip/src/rtc_session/info
- sip/src/rtc_session/refer_notifier
- sip/src/rtc_session/refer_subscriber
- sip/src/sanity_check
- sip/src/sip_message
- sip/src/sip_ua_helper
- sip/src/socket
- sip/src/stack_trace_nj
- sip/src/timers
- sip/src/transactions/ack_client
- sip/src/transactions/invite_client
- sip/src/transactions/invite_server
- sip/src/transactions/non_invite_client
- sip/src/transactions/non_invite_server
- sip/src/transactions/transaction_base
- sip/src/transactions/transactions
- sip/src/transport
- sip/src/transports/websocket_dart_impl
- sip/src/transports/websocket_interface
- sip/src/transports/websocket_web_impl
- sip/src/ua
- sip/src/uri
- sip/src/utils
- utils/audio_helper
- voip_push/android_connection_service
- voip_push/device_information
- voip_push/push_notif
- voip_push/voip_notif
- web_service/api_web_service
- web_service/http_service
- web_service/portal_service
- web_service/push_notif_service
- web_service/sdk_service
