@seamlink/cordova-plugin-jitsi 2.1.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
@@ -0,0 +1,47 @@
1
+ name: Release
2
+
3
+ on:
4
+ push:
5
+ branches:
6
+ - main
7
+
8
+ permissions:
9
+ contents: read
10
+
11
+ jobs:
12
+ release:
13
+ # prevent this action from running on forks
14
+ if: github.repository == 'your/repo'
15
+ permissions:
16
+ contents: write
17
+ pull-requests: read
18
+ runs-on: ubuntu-latest
19
+ steps:
20
+ - uses: actions/checkout@v4
21
+ - uses: actions/setup-node@v4
22
+ with:
23
+ node-version: '20.x'
24
+ registry-url: 'https://registry.npmjs.org'
25
+ - name: Install dependencies
26
+ run: npm ci
27
+ - name: Extract version from package.json
28
+ uses: sergeysova/jq-action@v2
29
+ id: version
30
+ with:
31
+ cmd: 'jq .version package.json -r'
32
+ - name: Get latest tag
33
+ uses: actions-ecosystem/action-get-latest-tag@v1
34
+ id: get-latest-tag
35
+ - name: Publish GitHub Release
36
+ uses: release-drafter/release-drafter@v6
37
+ if: ${{ contains(steps.get-latest-tag.outputs.tag, steps.version.outputs.value) == false }}
38
+ with:
39
+ version: ${{ steps.version.outputs.value }}
40
+ publish: true
41
+ env:
42
+ GITHUB_TOKEN: ${{ secrets.GH_TOKEN }}
43
+ - name: Publish to NPM
44
+ if: ${{ contains(steps.get-latest-tag.outputs.tag, steps.version.outputs.value) == false }}
45
+ run: npm publish
46
+ env:
47
+ NODE_AUTH_TOKEN: ${{ secrets.NPM_TOKEN }}
package/README.md ADDED
@@ -0,0 +1,31 @@
1
+ # cordova-plugin-jitsimeet
2
+ Cordova plugin for Jitsi Meet React Native SDK. Works with both iOS and Android, and fixes the 64-bit binary dependency issue with Android found in previous versions of this plugin.
3
+
4
+ # Summary
5
+ This is based on the repo by findmate, but I updated the JitsiMeet SDK and WebRTC framework to the latest version, to get all features working in a Cordova app.
6
+ The original repo is here: https://github.com/findmate/cordova-plugin-jitsi
7
+
8
+ # Installation
9
+ `cordova plugin add https://github.com/seamlink-dev/cordova-plugin-jitsi`
10
+
11
+ # Usage
12
+ ```
13
+ const roomId = 'your-custom-room-id';
14
+
15
+ jitsiplugin.join('https://meet.jit.si/', roomId, false, (data) => {
16
+ //CONFERENCE_WILL_JOIN
17
+ //CONFERENCE_JOINED
18
+ //CONFERENCE_TERMINATED
19
+ //CONFERENCE_FINISHED
20
+ //CONFERENCE_DESTROYED
21
+ if (data === "CONFERENCE_TERMINATED") {
22
+ jitsiplugin.destroy((data) => {
23
+ // call finished
24
+ }, f(err) => {
25
+ console.log(err);
26
+ });
27
+ }
28
+ }, (err) => {
29
+ console.log(err);
30
+ });
31
+ ```
@@ -0,0 +1,14 @@
1
+ android {
2
+ compileSdkVersion 26
3
+ buildToolsVersion "26.0.1"
4
+
5
+ defaultConfig {
6
+ minSdkVersion 23
7
+ targetSdkVersion 26
8
+ multiDexEnabled true
9
+ }
10
+ packagingOptions {
11
+ exclude 'META-INF/NOTICE'
12
+ exclude 'META-INF/LICENSE’
13
+ }
14
+ }
@@ -0,0 +1,22 @@
1
+ # Project-wide Gradle settings.
2
+
3
+ # IDE (e.g. Android Studio) users:
4
+ # Gradle settings configured through the IDE *will override*
5
+ # any settings specified in this file.
6
+
7
+ # For more details on how to configure your build environment visit
8
+ # http://www.gradle.org/docs/current/userguide/build_environment.html
9
+
10
+ # Specifies the JVM arguments used for the daemon process.
11
+ # The setting is particularly useful for tweaking memory settings.
12
+ # Default value: -Xmx10248m -XX:MaxPermSize=256m
13
+ # org.gradle.jvmargs=-Xmx2048m -XX:MaxPermSize=512m -XX:+HeapDumpOnOutOfMemoryError -Dfile.encoding=UTF-8
14
+
15
+ # When configured, Gradle will run in incubating parallel mode.
16
+ # This option should only be used with decoupled projects. More details, visit
17
+ # http://www.gradle.org/docs/current/userguide/multi_project_builds.html#sec:decoupled_projects
18
+ # org.gradle.parallel=true
19
+
20
+ android.useDeprecatedNdk=true
21
+ android.useAndroidX=true
22
+ android.enableJetifier=true
package/package.json ADDED
@@ -0,0 +1,27 @@
1
+ {
2
+ "name": "@seamlink/cordova-plugin-jitsi",
3
+ "version": "2.1.0",
4
+ "description": "\n This is plugin for Jitsi Meet calling service!\n ",
5
+ "cordova": {
6
+ "id": "@seamlink/cordova-plugin-jitsi",
7
+ "platforms": [
8
+ "android",
9
+ "ios"
10
+ ]
11
+ },
12
+ "repository": {
13
+ "type": "git",
14
+ "url": "git+https://github.com/seamlink-dev/cordova-plugin-jitsi.git"
15
+ },
16
+ "keywords": [
17
+ "ecosystem:cordova",
18
+ "cordova-android",
19
+ "cordova-ios"
20
+ ],
21
+ "author": "Seamlink",
22
+ "license": "Auris",
23
+ "bugs": {
24
+ "url": "https://github.com/seamlink-dev/cordova-plugin-jitsi/issues"
25
+ },
26
+ "homepage": "https://github.com/seamlink-dev/cordova-plugin-jitsi#readme"
27
+ }
package/plugin.xml ADDED
@@ -0,0 +1,80 @@
1
+ <?xml version='1.0' encoding='utf-8'?>
2
+ <plugin id='@seamlink/cordova-plugin-jitsi' version='2.1.0'
3
+ xmlns='http://apache.org/cordova/ns/plugins/1.0'
4
+ xmlns:tools="http://schemas.android.com/tools"
5
+ xmlns:android='http://schemas.android.com/apk/res/android'>
6
+ <name>JitsiPlugin</name>
7
+ <js-module name='JitsiPlugin' src='www/JitsiPlugin.js'>
8
+ <clobbers target='jitsiplugin' />
9
+ </js-module>
10
+
11
+
12
+ <platform name='android'>
13
+ <config-file parent='/*' target='res/xml/config.xml'>
14
+ <feature name='JitsiPlugin'>
15
+ <param name='android-package' value='com.cordova.plugin.jitsi.JitsiPlugin' />
16
+ </feature>
17
+ </config-file>
18
+ <config-file parent='/*' target='AndroidManifest.xml'>
19
+ <uses-permission android:name="android.permission.ACCESS_NETWORK_STATE" />
20
+ <uses-permission android:name="android.permission.BLUETOOTH" />
21
+ <uses-permission android:name="android.permission.CAMERA" />
22
+ <uses-permission android:name="android.permission.INTERNET" />
23
+ <uses-permission android:name="android.permission.MODIFY_AUDIO_SETTINGS" />
24
+ <uses-permission android:name="android.permission.RECORD_AUDIO" />
25
+ <uses-permission android:name="android.permission.SYSTEM_ALERT_WINDOW" />
26
+ <uses-permission android:name="android.permission.WAKE_LOCK" />
27
+ <uses-permission android:name="android.permission.ACCESS_WIFI_STATE" />
28
+ <uses-permission android:name="android.permission.FOREGROUND_SERVICE" />
29
+ <uses-permission android:name="android.permission.FOREGROUND_SERVICE_MEDIA_PLAYBACK" />
30
+ <uses-permission android:name="android.permission.FOREGROUND_SERVICE_MEDIA_PROJECTION" />
31
+ </config-file>
32
+ <config-file target="AndroidManifest.xml" parent="/manifest/application">
33
+ <activity
34
+ android:name="com.cordova.plugin.jitsi.JitsiMeetPluginActivity"
35
+ android:configChanges="keyboard|keyboardHidden|orientation|screenLayout|screenSize|smallestScreenSize"
36
+ android:launchMode="singleTask"
37
+ android:resizeableActivity="true"
38
+ android:supportsPictureInPicture="true"
39
+ android:theme="@style/Theme.AppCompat"
40
+ android:parentActivityName=".MainActivity"
41
+ android:fitsSystemWindows="true"
42
+ android:background="@android:color/black"
43
+ android:allowTaskReparenting="true"
44
+ android:windowSoftInputMode="adjustResize">
45
+ </activity>
46
+ <service android:name="com.cordova.plugin.jitsi.JitsiService"
47
+ android:stopWithTask="false" />
48
+ </config-file>
49
+ <source-file src='src/android/JitsiPlugin.java' target-dir='src/com/cordova/plugin/jitsi/' />
50
+ <framework src='src/android/jitsiplugin.gradle' custom='true' type='gradleReference' />
51
+ </platform>
52
+
53
+ <!-- ios -->
54
+ <platform name="ios">
55
+ <config-file target="config.xml" parent="/*">
56
+ <feature name="JitsiPlugin">
57
+ <param name="ios-package" value="JitsiPlugin" />
58
+ </feature>
59
+ </config-file>
60
+ <config-file target="*-Info.plist" parent="UIBackgroundModes">
61
+ <array>
62
+ <string>audio</string>
63
+ <string>voip</string>
64
+ </array>
65
+ </config-file>
66
+ <header-file src="src/ios/JitsiMeetView.h" />
67
+ <header-file src="src/ios/JitsiMeetViewDelegate.h" />
68
+ <header-file src="src/ios/JitsiPlugin.h" />
69
+ <source-file src="src/ios/JitsiPlugin.mm" />
70
+ <podspec>
71
+ <config>
72
+ <source url="https://cdn.cocoapods.org" />
73
+ <source url="https://github.com/CocoaPods/Specs.git" />
74
+ </config>
75
+ <pods use-frameworks="true">
76
+ <pod name="JitsiMeetSDK" spec="10.3.0" />
77
+ </pods>
78
+ </podspec>
79
+ </platform>
80
+ </plugin>
@@ -0,0 +1,251 @@
1
+ package com.cordova.plugin.jitsi;
2
+
3
+ import org.apache.cordova.CordovaInterface;
4
+ import org.apache.cordova.CordovaPlugin;
5
+ import org.apache.cordova.CallbackContext;
6
+ import org.apache.cordova.PluginResult;
7
+ import org.apache.cordova.PermissionHelper;
8
+ import org.apache.cordova.CordovaWebView;
9
+
10
+ import org.jitsi.meet.sdk.JitsiMeetActivity;
11
+ import org.json.JSONArray;
12
+ import org.json.JSONException;
13
+
14
+ import android.content.BroadcastReceiver;
15
+ import android.content.Context;
16
+ import android.content.Intent;
17
+ import android.content.IntentFilter;
18
+ import android.Manifest;
19
+ import android.content.pm.PackageManager;
20
+ import android.content.pm.PackageManager.NameNotFoundException;
21
+ import android.view.View;
22
+
23
+ import androidx.localbroadcastmanager.content.LocalBroadcastManager;
24
+
25
+ import java.net.MalformedURLException;
26
+ import java.net.URL;
27
+
28
+ import org.jitsi.meet.sdk.JitsiMeetConferenceOptions;
29
+ import org.jitsi.meet.sdk.JitsiMeetActivityDelegate;
30
+ import org.jitsi.meet.sdk.JitsiMeetActivityInterface;
31
+ import org.jitsi.meet.sdk.BroadcastEvent; // Import BroadcastEvent
32
+
33
+ import com.facebook.react.modules.core.PermissionListener;
34
+
35
+ import timber.log.Timber;
36
+
37
+ public class JitsiPlugin extends CordovaPlugin
38
+ implements JitsiMeetActivityInterface {
39
+
40
+ private CallbackContext _callback;
41
+ private BroadcastReceiver jitsiBroadcastReceiver;
42
+
43
+ public static final int TAKE_PIC_SEC = 0;
44
+
45
+ private static final String JOIN_ACTION = "join";
46
+ private static final String DESTROY_ACTION = "destroy";
47
+
48
+ @Override
49
+ public void pluginInitialize() {
50
+ super.pluginInitialize();
51
+
52
+ // Create the receiver to listen for Jitsi events
53
+ jitsiBroadcastReceiver = new BroadcastReceiver() {
54
+ @Override
55
+ public void onReceive(Context context, Intent intent) {
56
+ if (intent == null) {
57
+ return;
58
+ }
59
+
60
+ BroadcastEvent event = new BroadcastEvent(intent);
61
+ String eventName = "";
62
+
63
+ Timber.d("Jitsi event received: %s", event.getType());
64
+
65
+ switch (event.getType()) {
66
+ case CONFERENCE_JOINED:
67
+ eventName = "CONFERENCE_JOINED";
68
+ break;
69
+ case CONFERENCE_WILL_JOIN:
70
+ eventName = "CONFERENCE_WILL_JOIN";
71
+ break;
72
+ case CONFERENCE_TERMINATED:
73
+ eventName = "CONFERENCE_TERMINATED";
74
+ break;
75
+ case PARTICIPANT_JOINED:
76
+ eventName = "PARTICIPANT_JOINED";
77
+ break;
78
+ case PARTICIPANT_LEFT:
79
+ eventName = "PARTICIPANT_LEFT";
80
+ break;
81
+ case READY_TO_CLOSE:
82
+ eventName = "READY_TO_CLOSE";
83
+ break;
84
+ }
85
+
86
+ if (!eventName.isEmpty() && _callback != null) {
87
+ PluginResult pluginResult = new PluginResult(PluginResult.Status.OK, eventName);
88
+ pluginResult.setKeepCallback(true);
89
+ _callback.sendPluginResult(pluginResult);
90
+ }
91
+ }
92
+ };
93
+ LocalBroadcastManager.getInstance(cordova.getActivity())
94
+ .registerReceiver(jitsiBroadcastReceiver, createJitsiIntentFilter());
95
+ }
96
+
97
+ @Override
98
+ public void onResume(boolean multitasking) {
99
+ super.onResume(multitasking);
100
+ }
101
+
102
+ @Override
103
+ public void onPause(boolean multitasking) {
104
+ super.onPause(multitasking);
105
+ }
106
+
107
+ private IntentFilter createJitsiIntentFilter() {
108
+ IntentFilter filter = new IntentFilter();
109
+ // Add all actions that the receiver should listen for
110
+ filter.addAction(BroadcastEvent.Type.CONFERENCE_JOINED.getAction());
111
+ filter.addAction(BroadcastEvent.Type.CONFERENCE_WILL_JOIN.getAction());
112
+ filter.addAction(BroadcastEvent.Type.CONFERENCE_TERMINATED.getAction());
113
+ filter.addAction(BroadcastEvent.Type.PARTICIPANT_JOINED.getAction());
114
+ filter.addAction(BroadcastEvent.Type.PARTICIPANT_LEFT.getAction());
115
+ filter.addAction(BroadcastEvent.Type.READY_TO_CLOSE.getAction());
116
+ return filter;
117
+ }
118
+
119
+ @Override
120
+ public boolean execute(String action, JSONArray args, CallbackContext callbackContext) throws JSONException {
121
+ _callback = callbackContext;
122
+
123
+ if (action.equals(JOIN_ACTION)) {
124
+ String serverUrl = args.getString(0);
125
+ String roomId = args.getString(1);
126
+ boolean audioOnly = args.getBoolean(2);
127
+ String token = args.getString(3);
128
+ try {
129
+ this.callJoin(serverUrl, roomId, audioOnly, token);
130
+ } catch (NameNotFoundException e) {
131
+ e.printStackTrace();
132
+ }
133
+ return true;
134
+ } else if (action.equals(DESTROY_ACTION)) {
135
+ this.destroy(callbackContext);
136
+ return true;
137
+ }
138
+ return false;
139
+ }
140
+
141
+ // ... all your other methods (callJoin, join, destroy, etc.) remain the same
142
+ // ...
143
+ // You can now completely remove the stateChanged() method as it is no longer
144
+ // needed.
145
+ private void callJoin(String serverUrl, String roomId, Boolean audioOnly, String token)
146
+ throws NameNotFoundException {
147
+
148
+ this.join(serverUrl, roomId, audioOnly, token);
149
+
150
+ }
151
+
152
+ private void join(final String serverUrl, final String roomId, final Boolean audioOnly, final String token) {
153
+ Timber.e("join called! Server: " + serverUrl + ", room : " + roomId);
154
+
155
+ cordova.getActivity().runOnUiThread(() -> {
156
+ URL serverUrlObject;
157
+ try {
158
+ serverUrlObject = new URL(serverUrl);
159
+ } catch (MalformedURLException e) {
160
+ Timber.e(e, "Invalid server URL");
161
+ return;
162
+ }
163
+
164
+ JitsiMeetConferenceOptions options = new JitsiMeetConferenceOptions.Builder()
165
+ .setServerURL(serverUrlObject)
166
+ .setRoom(roomId)
167
+ .setSubject(" ")
168
+ .setToken(token)
169
+ .setAudioOnly(audioOnly)
170
+ .setFeatureFlag("chat.enabled", true)
171
+ .setFeatureFlag("add-people.enabled", false)
172
+ .setFeatureFlag("invite.enabled", false)
173
+ .setFeatureFlag("calendar.enabled", false)
174
+ .setFeatureFlag("call-integration.enabled", false)
175
+ .setFeatureFlag("close-captions.enabled", false)
176
+ .setFeatureFlag("ios.recording.enabled", false)
177
+ .setFeatureFlag("kick-out.enabled", false)
178
+ .setFeatureFlag("live-streaming.enabled", false)
179
+ .setFeatureFlag("meeting-name.enabled", false)
180
+ .setFeatureFlag("meeting-password.enabled", false)
181
+ .setFeatureFlag("raise-hand.enabled", false)
182
+ .setFeatureFlag("recording.enabled", false)
183
+ .setFeatureFlag("server-url-change.enabled", false)
184
+ .setFeatureFlag("video-share.enabled", false)
185
+ .setFeatureFlag("welcomepage.enabled", false)
186
+ .setFeatureFlag("help.enabled", false)
187
+ .setFeatureFlag("lobby-mode.enabled", false)
188
+ .setFeatureFlag("server-url-change.enabled", false)
189
+ .setConfigOverride("requireDisplayName", false)
190
+ .setConfigOverride("disableModeratorIndicator", true)
191
+ .build();
192
+
193
+ JitsiMeetActivity.launch(cordova.getActivity(), options);
194
+ });
195
+ }
196
+
197
+ private void destroy(final CallbackContext callbackContext) {
198
+ cordova.getActivity().runOnUiThread(() -> {
199
+ JitsiMeetActivityDelegate.onHostDestroy(cordova.getActivity());
200
+ cordova.getActivity().setContentView(getView());
201
+ PluginResult pluginResult = new PluginResult(PluginResult.Status.OK, "DESTROYED");
202
+ pluginResult.setKeepCallback(true);
203
+ callbackContext.sendPluginResult(pluginResult);
204
+ });
205
+ }
206
+
207
+ private View getView() {
208
+ try {
209
+ return (View) webView.getClass().getMethod("getView").invoke(webView);
210
+ } catch (Exception e) {
211
+ return (View) webView;
212
+ }
213
+ }
214
+
215
+ @Override
216
+ public void onRequestPermissionsResult(final int requestCode, final String[] permissions,
217
+ final int[] grantResults) {
218
+ JitsiMeetActivityDelegate.onRequestPermissionsResult(requestCode, permissions, grantResults);
219
+ }
220
+
221
+ @Override
222
+ public void requestPermissions(String[] permissions, int requestCode, PermissionListener listener) {
223
+ JitsiMeetActivityDelegate.requestPermissions(cordova.getActivity(), permissions, requestCode, listener);
224
+ }
225
+
226
+ @Override
227
+ public boolean shouldShowRequestPermissionRationale(String permissions) {
228
+ return true;
229
+ }
230
+
231
+ @Override
232
+ public int checkSelfPermission(String permission) {
233
+ return 0;
234
+ }
235
+
236
+ @Override
237
+ public int checkPermission(String permission, int pid, int uid) {
238
+ return 0;
239
+ }
240
+
241
+ @Override
242
+ public void onDestroy() {
243
+ super.onDestroy();
244
+ // Unregister the receiver when the plugin is destroyed to prevent memory leaks
245
+ if (jitsiBroadcastReceiver != null) {
246
+ LocalBroadcastManager.getInstance(cordova.getActivity())
247
+ .unregisterReceiver(jitsiBroadcastReceiver);
248
+ jitsiBroadcastReceiver = null;
249
+ }
250
+ }
251
+ }
@@ -0,0 +1,64 @@
1
+ repositories{
2
+ jcenter()
3
+ maven {
4
+ url "https://github.com/jitsi/jitsi-maven-repository/raw/master/releases"
5
+ }
6
+ google()
7
+ mavenCentral()
8
+ maven { url 'https://www.jitpack.io' }
9
+ configurations.all {
10
+ resolutionStrategy {
11
+ force "com.google.android.gms:play-services-basement:15.0.1"
12
+ force "com.google.android.gms:play-services-tasks:15.0.1"
13
+ }
14
+ }
15
+ }
16
+ android {
17
+ compileSdkVersion 35
18
+ buildToolsVersion "26.0.1"
19
+
20
+ defaultConfig {
21
+ minSdkVersion 23
22
+ targetSdkVersion 35
23
+ multiDexEnabled true
24
+ ndk {
25
+ abiFilters 'armeabi-v7a', 'arm64-v8a', 'x86', 'x86_64'
26
+ }
27
+
28
+ packagingOptions {
29
+ // The project react-native does not provide 64-bit binaries at the
30
+ // time of this writing. Unfortunately, packaging any 64-bit
31
+ // binaries into the .apk will crash the app at runtime on 64-bit
32
+ // platforms.
33
+ // exclude '/lib/mips64/**'
34
+ // exclude '/lib/arm64-v8a/**'
35
+ // exclude '/lib/x86_64/**'
36
+ }
37
+ }
38
+
39
+ buildTypes {
40
+ debug {
41
+ signingConfig signingConfigs.debug
42
+ }
43
+ release {
44
+ // Caution! In production, you need to generate your own keystore file.
45
+ // see https://facebook.github.io/react-native/docs/signed-apk-android.
46
+ signingConfig signingConfigs.debug
47
+ // minifyEnabled true
48
+ // proguardFiles getDefaultProguardFile('proguard-android-optimize.txt'), 'proguard-rules.pro'
49
+ }
50
+ }
51
+
52
+ compileOptions {
53
+ sourceCompatibility JavaVersion.VERSION_1_8
54
+ targetCompatibility JavaVersion.VERSION_1_8
55
+ }
56
+ }
57
+ dependencies {
58
+ implementation fileTree(dir: 'libs', include: ['*.jar'])
59
+ implementation ('org.jitsi.react:jitsi-meet-sdk:+') {
60
+ transitive = true;
61
+ }
62
+ implementation 'androidx.appcompat:appcompat:1.4.1'
63
+ implementation 'androidx.constraintlayout:constraintlayout:2.1.3'
64
+ }
@@ -0,0 +1,45 @@
1
+ /*
2
+ * Copyright @ 2017-present Atlassian Pty Ltd
3
+ *
4
+ * Licensed under the Apache License, Version 2.0 (the "License");
5
+ * you may not use this file except in compliance with the License.
6
+ * You may obtain a copy of the License at
7
+ *
8
+ * http://www.apache.org/licenses/LICENSE-2.0
9
+ *
10
+ * Unless required by applicable law or agreed to in writing, software
11
+ * distributed under the License is distributed on an "AS IS" BASIS,
12
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13
+ * See the License for the specific language governing permissions and
14
+ * limitations under the License.
15
+ */
16
+
17
+ #import <Foundation/Foundation.h>
18
+ #import <UIKit/UIKit.h>
19
+ #import <JitsiMeetSDK/JitsiMeetConferenceOptions.h>
20
+
21
+ #import "JitsiMeetViewDelegate.h"
22
+
23
+ @interface JitsiMeetView : UIView
24
+
25
+ @property (nonatomic, nullable, weak) id<JitsiMeetViewDelegate> delegate;
26
+
27
+ @property (copy, nonatomic, nullable) NSURL *defaultURL;
28
+
29
+ @property (nonatomic) BOOL welcomePageEnabled;
30
+
31
+ + (BOOL)application:(UIApplication *_Nonnull)application
32
+ didFinishLaunchingWithOptions:(NSDictionary *_Nonnull)launchOptions;
33
+
34
+ + (BOOL)application:(UIApplication * _Nonnull)application
35
+ continueUserActivity:(NSUserActivity * _Nonnull)userActivity
36
+ restorationHandler:(void (^ _Nullable)(NSArray * _Nullable))restorationHandler;
37
+
38
+ + (BOOL)application:(UIApplication * _Nonnull)application
39
+ openURL:(NSURL * _Nonnull)URL
40
+ sourceApplication:(NSString * _Nullable)sourceApplication
41
+ annotation:(id _Nullable)annotation;
42
+
43
+ - (void)join:(JitsiMeetConferenceOptions * _Nullable)options;
44
+
45
+ @end
@@ -0,0 +1,68 @@
1
+ /*
2
+ * Copyright @ 2017-present Atlassian Pty Ltd
3
+ *
4
+ * Licensed under the Apache License, Version 2.0 (the "License");
5
+ * you may not use this file except in compliance with the License.
6
+ * You may obtain a copy of the License at
7
+ *
8
+ * http://www.apache.org/licenses/LICENSE-2.0
9
+ *
10
+ * Unless required by applicable law or agreed to in writing, software
11
+ * distributed under the License is distributed on an "AS IS" BASIS,
12
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13
+ * See the License for the specific language governing permissions and
14
+ * limitations under the License.
15
+ */
16
+
17
+ @protocol JitsiMeetViewDelegate <NSObject>
18
+
19
+ @optional
20
+
21
+ /**
22
+ * Called when a joining a conference was unsuccessful or when there was an
23
+ * error while in a conference.
24
+ *
25
+ * The `data` dictionary contains an `error` key describing the error and a
26
+ * `url` key with the conference URL.
27
+ */
28
+ - (void)conferenceFailed:(NSDictionary *)data;
29
+
30
+ /**
31
+ * Called when a conference was joined.
32
+ *
33
+ * The `data` dictionary contains a `url` key with the conference URL.
34
+ */
35
+ - (void)conferenceJoined:(NSDictionary *)data;
36
+
37
+ /**
38
+ * Called when a conference was left.
39
+ *
40
+ * The `data` dictionary contains a `url` key with the conference URL.
41
+ */
42
+ - (void)conferenceLeft:(NSDictionary *)data;
43
+
44
+ /**
45
+ * Called before a conference is joined.
46
+ *
47
+ * The `data` dictionary contains a `url` key with the conference URL.
48
+ */
49
+ - (void)conferenceWillJoin:(NSDictionary *)data;
50
+
51
+ /**
52
+ * Called before a conference is left.
53
+ *
54
+ * The `data` dictionary contains a `url` key with the conference URL.
55
+ */
56
+ - (void)conferenceTerminated:(NSDictionary *)data;
57
+
58
+ /**
59
+ * Called when loading the main configuration file from the Jitsi Meet
60
+ * deployment file.
61
+ *
62
+ * The `data` dictionary contains an `error` key with the error and a `url` key
63
+ * with the conference URL which necessitated the loading of the configuration
64
+ * file.
65
+ */
66
+ - (void)loadConfigError:(NSDictionary *)data;
67
+
68
+ @end
@@ -0,0 +1,20 @@
1
+ #import <Cordova/CDVPlugin.h>
2
+ #import "JitsiMeetViewDelegate.h"
3
+ #import "JitsiMeetView.h"
4
+
5
+ @interface JitsiPlugin : CDVPlugin<JitsiMeetViewDelegate> {
6
+ JitsiMeetView* jitsiMeetView;
7
+ CDVInvokedUrlCommand* commandBack;
8
+ }
9
+
10
+ - (void)join:(CDVInvokedUrlCommand *)command;
11
+ - (void)destroy:(CDVInvokedUrlCommand *)command;
12
+ - (void)backButtonPressed:(CDVInvokedUrlCommand *)command;
13
+ - (void)conferenceFailed:(NSDictionary *)data;
14
+ - (void)conferenceJoined:(NSDictionary *)data;
15
+ - (void)conferenceLeft:(NSDictionary *)data;
16
+ - (void)conferenceWillJoin:(NSDictionary *)data;
17
+ - (void)conferenceTerminated:(NSDictionary *)data;
18
+ - (void)loadConfigError:(NSDictionary *)data;
19
+
20
+ @end
@@ -0,0 +1,117 @@
1
+ #import "JitsiPlugin.h"
2
+ #import <JitsiMeetSDK/JitsiMeetConferenceOptions.h>
3
+
4
+ @implementation JitsiPlugin
5
+ {
6
+ CDVPluginResult *plgResult;
7
+ }
8
+
9
+ - (void)join:(CDVInvokedUrlCommand *)command {
10
+ NSString* serverUrl = [command.arguments objectAtIndex:0];
11
+ NSString* room = [command.arguments objectAtIndex:1];
12
+ Boolean isAudioOnly = [[command.arguments objectAtIndex:2] boolValue];
13
+ NSString* token = [command.arguments objectAtIndex:3];
14
+ commandBack = command;
15
+ jitsiMeetView = [[JitsiMeetView alloc] initWithFrame:self.viewController.view.frame];
16
+ jitsiMeetView.autoresizingMask = UIViewAutoresizingFlexibleWidth | UIViewAutoresizingFlexibleHeight;
17
+ jitsiMeetView.delegate = self;
18
+
19
+ JitsiMeetConferenceOptions *options = [JitsiMeetConferenceOptions fromBuilder:^(JitsiMeetConferenceOptionsBuilder *builder) {
20
+ builder.serverURL = [NSURL URLWithString: serverUrl];
21
+ builder.room = room;
22
+ builder.subject = @" ";
23
+ builder.token = token;
24
+ builder.audioOnly = isAudioOnly;
25
+ [builder setFeatureFlag:@"welcomepage.enabled" withBoolean:false];
26
+ [builder setFeatureFlag:@"chat.enabled" withBoolean:true];
27
+ [builder setFeatureFlag:@"invite.enabled" withBoolean:false];
28
+ [builder setFeatureFlag:@"add-people.enabled" withBoolean:false];
29
+ [builder setFeatureFlag:@"calendar.enabled" withBoolean:false];
30
+ [builder setFeatureFlag:@"pip.enabled" withBoolean:true];
31
+ [builder setFeatureFlag:@"call-integration.enabled" withBoolean:false];
32
+ [builder setFeatureFlag:@"close-captions.enabled" withBoolean:false];
33
+ [builder setFeatureFlag:@"ios.recording.enabled" withBoolean:false];
34
+ [builder setFeatureFlag:@"kick-out.enabled" withBoolean:false];
35
+ [builder setFeatureFlag:@"live-streaming.enabled" withBoolean:false];
36
+ [builder setFeatureFlag:@"meeting-name.enabled" withBoolean:false];
37
+ [builder setFeatureFlag:@"meeting-password.enabled" withBoolean:false];
38
+ [builder setFeatureFlag:@"raise-hand.enabled" withBoolean:false];
39
+ [builder setFeatureFlag:@"recording.enabled" withBoolean:false];
40
+ [builder setFeatureFlag:@"server-url-change.enabled" withBoolean:false];
41
+ [builder setFeatureFlag:@"video-share.enabled" withBoolean:false];
42
+ [builder setFeatureFlag:@"help.enabled" withBoolean:false];
43
+ [builder setFeatureFlag:@"lobby-mode.enabled" withBoolean:false];
44
+ [builder setFeatureFlag:@"server-url-change.enabled" withBoolean:false];
45
+ [builder setConfigOverride:@"requireDisplayName" withBoolean:false];
46
+ [builder setConfigOverride:@"disableModeratorIndicator" withBoolean:true];
47
+ }];
48
+
49
+ [jitsiMeetView join: options];
50
+ [self.viewController.view addSubview:jitsiMeetView];
51
+ }
52
+
53
+
54
+ - (void)destroy:(CDVInvokedUrlCommand *)command {
55
+ if(jitsiMeetView){
56
+ [jitsiMeetView removeFromSuperview];
57
+ jitsiMeetView = nil;
58
+ }
59
+ plgResult = [CDVPluginResult resultWithStatus:CDVCommandStatus_OK messageAsString:@"DESTROYED"];
60
+ [self.commandDelegate sendPluginResult:plgResult callbackId:command.callbackId];
61
+ }
62
+
63
+ void _onJitsiMeetViewDelegateEvent(NSString *name, NSDictionary *data) {
64
+ NSLog(
65
+ @"[%s:%d] JitsiMeetViewDelegate %@ %@",
66
+ __FILE__, __LINE__, name, data);
67
+
68
+ }
69
+
70
+ - (void)conferenceFailed:(NSDictionary *)data {
71
+ _onJitsiMeetViewDelegateEvent(@"CONFERENCE_FAILED", data);
72
+ plgResult = [CDVPluginResult resultWithStatus:CDVCommandStatus_OK messageAsString:@"CONFERENCE_FAILED"];
73
+ [plgResult setKeepCallbackAsBool:YES];
74
+ [self.commandDelegate sendPluginResult:plgResult callbackId:commandBack.callbackId];
75
+ }
76
+
77
+ - (void)conferenceJoined:(NSDictionary *)data {
78
+ _onJitsiMeetViewDelegateEvent(@"CONFERENCE_JOINED", data);
79
+ plgResult = [CDVPluginResult resultWithStatus:CDVCommandStatus_OK messageAsString:@"CONFERENCE_JOINED"];
80
+ [plgResult setKeepCallbackAsBool:YES];
81
+ [self.commandDelegate sendPluginResult:plgResult callbackId:commandBack.callbackId];
82
+ }
83
+
84
+ - (void)conferenceLeft:(NSDictionary *)data {
85
+ _onJitsiMeetViewDelegateEvent(@"CONFERENCE_LEFT", data);
86
+ plgResult = [CDVPluginResult resultWithStatus:CDVCommandStatus_OK messageAsString:@"CONFERENCE_LEFT"];
87
+ [plgResult setKeepCallbackAsBool:YES];
88
+ [self.commandDelegate sendPluginResult:plgResult callbackId:commandBack.callbackId];
89
+
90
+ }
91
+
92
+ - (void)conferenceWillJoin:(NSDictionary *)data {
93
+ _onJitsiMeetViewDelegateEvent(@"CONFERENCE_WILL_JOIN", data);
94
+ plgResult = [CDVPluginResult resultWithStatus:CDVCommandStatus_OK messageAsString:@"CONFERENCE_WILL_JOIN"];
95
+ [plgResult setKeepCallbackAsBool:YES];
96
+ [self.commandDelegate sendPluginResult:plgResult callbackId:commandBack.callbackId];
97
+ }
98
+
99
+ - (void)conferenceTerminated:(NSDictionary *)data {
100
+ _onJitsiMeetViewDelegateEvent(@"CONFERENCE_TERMINATED", data);
101
+ plgResult = [CDVPluginResult resultWithStatus:CDVCommandStatus_OK messageAsString:@"CONFERENCE_TERMINATED"];
102
+ [plgResult setKeepCallbackAsBool:YES];
103
+ [self.commandDelegate sendPluginResult:plgResult callbackId:commandBack.callbackId];
104
+ }
105
+
106
+ - (void)loadConfigError:(NSDictionary *)data {
107
+ _onJitsiMeetViewDelegateEvent(@"LOAD_CONFIG_ERROR", data);
108
+ plgResult = [CDVPluginResult resultWithStatus:CDVCommandStatus_OK messageAsString:@"LOAD_CONFIG_ERROR"];
109
+ [plgResult setKeepCallbackAsBool:YES];
110
+ [self.commandDelegate sendPluginResult:plgResult callbackId:commandBack.callbackId];
111
+ }
112
+
113
+ //- (void)enterPictureInPicture:(NSDictionary *)data {
114
+ //}
115
+
116
+
117
+ @end
@@ -0,0 +1,9 @@
1
+ var exec = require('cordova/exec');
2
+
3
+ exports.join = function(serverUrl, room, audioOnly, token, success, error) {
4
+ exec(success, error, "JitsiPlugin", "join", [serverUrl, room, !!audioOnly, token]);
5
+ };
6
+
7
+ exports.destroy = function(success, error) {
8
+ exec(success, error, "JitsiPlugin", "destroy", []);
9
+ };