mirror of
https://gitcode.com/GitHub_Trending/ji/jitsi-meet.git
synced 2026-01-09 00:00:19 +00:00
Compare commits
414 Commits
android-22
...
android-sd
| Author | SHA1 | Date | |
|---|---|---|---|
|
|
2d7968b683 | ||
|
|
c77e2c8301 | ||
|
|
3403d7bec2 | ||
|
|
c4557c66aa | ||
|
|
cfda02ee10 | ||
|
|
575ab1f1cb | ||
|
|
b4f98e7386 | ||
|
|
e8de9b4d66 | ||
|
|
6fe353cfa4 | ||
|
|
882d343e8b | ||
|
|
cc3a8b7b8d | ||
|
|
104bfe7339 | ||
|
|
fb9d35a991 | ||
|
|
8fabba1679 | ||
|
|
5fbf741278 | ||
|
|
bebcc8234f | ||
|
|
1e9f599a35 | ||
|
|
cc5a3e499f | ||
|
|
dbcbafe088 | ||
|
|
b034cf27cb | ||
|
|
126dba8070 | ||
|
|
a7c1aa4900 | ||
|
|
206215c7c1 | ||
|
|
f38c5f39d2 | ||
|
|
09efaecc41 | ||
|
|
3bb581c8d9 | ||
|
|
96099a06a8 | ||
|
|
4ef5da6c82 | ||
|
|
289ece42df | ||
|
|
7dba5f8a7e | ||
|
|
1010955393 | ||
|
|
3bd3be4df0 | ||
|
|
fc60ab8383 | ||
|
|
85d2123fac | ||
|
|
5790742d53 | ||
|
|
be1752c162 | ||
|
|
b9aeb19379 | ||
|
|
7951dc3ce7 | ||
|
|
dfb2a07cfa | ||
|
|
94dc6309de | ||
|
|
3f2018a1de | ||
|
|
cd4ab8a5f1 | ||
|
|
594f9dfcdd | ||
|
|
8dd71a921b | ||
|
|
6d39d13af7 | ||
|
|
372c2cb0f9 | ||
|
|
5b41d68d39 | ||
|
|
1b9870dade | ||
|
|
38eff2ba24 | ||
|
|
11f6b442fe | ||
|
|
e458eed931 | ||
|
|
f07bd4a0d6 | ||
|
|
40637aa3dc | ||
|
|
2f10d80184 | ||
|
|
739c060018 | ||
|
|
41a6cbd3fc | ||
|
|
61df6f6794 | ||
|
|
d44cbb6d1e | ||
|
|
06ed0e43ad | ||
|
|
eb911ec9b5 | ||
|
|
e8cdf38fda | ||
|
|
e578f6c30f | ||
|
|
77d687952d | ||
|
|
bf222c5094 | ||
|
|
08f9dc5e83 | ||
|
|
9c83831b2c | ||
|
|
97bc41f644 | ||
|
|
f70ed9cb8a | ||
|
|
123ab32e75 | ||
|
|
3c370eb6ca | ||
|
|
3e6c988c30 | ||
|
|
649ace1f44 | ||
|
|
57f27b4234 | ||
|
|
2ae4ba3875 | ||
|
|
0bfa1027a9 | ||
|
|
f412ff7f11 | ||
|
|
3975db7a68 | ||
|
|
02e4d2b902 | ||
|
|
ca095240b9 | ||
|
|
3d60773963 | ||
|
|
895ce56e8d | ||
|
|
d12860082c | ||
|
|
4e03f20a51 | ||
|
|
0435c3cc64 | ||
|
|
ea4be6cb30 | ||
|
|
fa39c10766 | ||
|
|
82c047707f | ||
|
|
00221b7482 | ||
|
|
8266d55cb9 | ||
|
|
b2396ff809 | ||
|
|
fb20786b65 | ||
|
|
f5649efa49 | ||
|
|
7b361b3e23 | ||
|
|
05fdd5f31f | ||
|
|
5c52ee97ed | ||
|
|
3626e51c24 | ||
|
|
ef748c576d | ||
|
|
dd044ad252 | ||
|
|
5f04c5ba64 | ||
|
|
8f5eabe1f2 | ||
|
|
43578474a0 | ||
|
|
6dbf283f3d | ||
|
|
a1e0a46bad | ||
|
|
627027b167 | ||
|
|
4d41d36020 | ||
|
|
0f57c37d6a | ||
|
|
5b34068435 | ||
|
|
52ce9a86ed | ||
|
|
bdff92397b | ||
|
|
1abc6b1e4a | ||
|
|
ca259287be | ||
|
|
5601a62b60 | ||
|
|
d3c7b074d4 | ||
|
|
0fa0e99ffa | ||
|
|
002d0fed42 | ||
|
|
873cdbb404 | ||
|
|
91cbeb0b3f | ||
|
|
3a87282e26 | ||
|
|
fa5ee32720 | ||
|
|
03c91de5c1 | ||
|
|
2ec82c371c | ||
|
|
abc9d36c4c | ||
|
|
efa0a132c4 | ||
|
|
083b009eba | ||
|
|
f0ba37e605 | ||
|
|
a2c3bdf05f | ||
|
|
22a52dafca | ||
|
|
3960b59765 | ||
|
|
db54c45b13 | ||
|
|
3e66e0009d | ||
|
|
d091881851 | ||
|
|
de44c53482 | ||
|
|
64fef80f31 | ||
|
|
87f6d27fb2 | ||
|
|
3f0e50a9cd | ||
|
|
d63e0c5ab6 | ||
|
|
9b9fbc0bc9 | ||
|
|
5505f01cd9 | ||
|
|
7e7d3c0cc7 | ||
|
|
1f99ce3457 | ||
|
|
94074836ec | ||
|
|
ccba7e8f75 | ||
|
|
727b6dab9e | ||
|
|
0f1bf09c69 | ||
|
|
a6f93db8e3 | ||
|
|
8e0cb583af | ||
|
|
30a0a624a2 | ||
|
|
2cea6c7b98 | ||
|
|
69365d7e1f | ||
|
|
5783e8992a | ||
|
|
dbc29a08ee | ||
|
|
6f4b858e35 | ||
|
|
ffef8f78ea | ||
|
|
82b2e77747 | ||
|
|
abc752635d | ||
|
|
5ec6581d2e | ||
|
|
e139c6d32d | ||
|
|
4e1af131fb | ||
|
|
867d998d15 | ||
|
|
b1a9d68cf5 | ||
|
|
8b4c7ebc03 | ||
|
|
63ea273b20 | ||
|
|
ca3bd9138c | ||
|
|
c5115f99f0 | ||
|
|
0a385c561d | ||
|
|
44e5fa35af | ||
|
|
432d07c2ad | ||
|
|
2f42af0b70 | ||
|
|
e9055df9e3 | ||
|
|
cc7d3247ab | ||
|
|
fa8608eea0 | ||
|
|
0d9c4318ba | ||
|
|
2a5e169c2f | ||
|
|
2def75db50 | ||
|
|
53e05fdea9 | ||
|
|
c727b603af | ||
|
|
5dbb17bc81 | ||
|
|
cb712eb4ab | ||
|
|
c1e9724bba | ||
|
|
24b9f5d113 | ||
|
|
4ef88aa90e | ||
|
|
06491e2406 | ||
|
|
9ce52b237e | ||
|
|
ac2af79807 | ||
|
|
4a8c8899a9 | ||
|
|
b08ed3ade4 | ||
|
|
718d32990d | ||
|
|
009588a3d8 | ||
|
|
449d52f26b | ||
|
|
5a4ffea9aa | ||
|
|
d8b435ad16 | ||
|
|
b259757c79 | ||
|
|
7995c7ed00 | ||
|
|
08173ac1df | ||
|
|
e33b65da36 | ||
|
|
defd0d2aaf | ||
|
|
c7f96de787 | ||
|
|
29669d88dc | ||
|
|
131eed0f62 | ||
|
|
77da65b8ea | ||
|
|
989b8d9c2b | ||
|
|
eb20e85166 | ||
|
|
d981acb94a | ||
|
|
155a14b351 | ||
|
|
139fa9b3f2 | ||
|
|
f31a7f31e6 | ||
|
|
df887d24a2 | ||
|
|
6286c76904 | ||
|
|
780019a711 | ||
|
|
4d51aedde0 | ||
|
|
058c82a704 | ||
|
|
7e2f3f7d68 | ||
|
|
30b0bb7bd6 | ||
|
|
f02a75bc9d | ||
|
|
6b5a821696 | ||
|
|
ad46df0a1a | ||
|
|
b0deb9ec0c | ||
|
|
61a6ce2a2e | ||
|
|
bacdbeff21 | ||
|
|
7fc9f6f515 | ||
|
|
d34aae4a4b | ||
|
|
ab86d336fb | ||
|
|
ffc412c18d | ||
|
|
077901cd2b | ||
|
|
ba3cd53017 | ||
|
|
0d50f1867d | ||
|
|
e9cfa78aaf | ||
|
|
76f7f3943f | ||
|
|
b9b8090996 | ||
|
|
d42e18c7bb | ||
|
|
a685f096a0 | ||
|
|
49357e3cd2 | ||
|
|
049a3eb7fb | ||
|
|
a31cc62c25 | ||
|
|
75ddf3e75f | ||
|
|
40128277bc | ||
|
|
7770d59c93 | ||
|
|
2dd3c72473 | ||
|
|
4a4856f3de | ||
|
|
47bdf800e7 | ||
|
|
f6d088149c | ||
|
|
cbe3d6d505 | ||
|
|
b41c71e80b | ||
|
|
a4b997362a | ||
|
|
a5da90ddaf | ||
|
|
dffa71666c | ||
|
|
892751154c | ||
|
|
935e4d3261 | ||
|
|
f115028961 | ||
|
|
d910b9db57 | ||
|
|
b2b576f6fb | ||
|
|
a39d9f283d | ||
|
|
0913cf2c4f | ||
|
|
51f7b46628 | ||
|
|
d029045fda | ||
|
|
ddab27e292 | ||
|
|
6df2e4009c | ||
|
|
21cf7f23c2 | ||
|
|
bac1347961 | ||
|
|
c4f39e9c34 | ||
|
|
ee266160f9 | ||
|
|
730d42cba1 | ||
|
|
3f795cd1ff | ||
|
|
252441da29 | ||
|
|
b89c470366 | ||
|
|
6e32a146e3 | ||
|
|
6f02382472 | ||
|
|
de37c3e809 | ||
|
|
ec47f530bc | ||
|
|
7b538fc3e9 | ||
|
|
d5146aaf2e | ||
|
|
efb46df3d9 | ||
|
|
88e6aa3323 | ||
|
|
a7c96e302f | ||
|
|
b85da1e1bb | ||
|
|
e7c5421e33 | ||
|
|
4b4caf5b1c | ||
|
|
8f1fae79e4 | ||
|
|
9a99c517ab | ||
|
|
40a6240444 | ||
|
|
4d6ca4383f | ||
|
|
ddce2e6bec | ||
|
|
7dca91a50a | ||
|
|
31348179d4 | ||
|
|
e77679d025 | ||
|
|
44a9363f5b | ||
|
|
bb76090bce | ||
|
|
d0790736db | ||
|
|
0308ba71b1 | ||
|
|
f7d1a5ec80 | ||
|
|
d61fe58fcf | ||
|
|
b428ce2dcd | ||
|
|
d1c9720033 | ||
|
|
c29e8bbdd1 | ||
|
|
3fb3be9727 | ||
|
|
517ec29d85 | ||
|
|
6ad279f029 | ||
|
|
0e98f90205 | ||
|
|
2c5b132483 | ||
|
|
4d8f29d4fe | ||
|
|
22be96d838 | ||
|
|
ccc1157df5 | ||
|
|
f613126776 | ||
|
|
38b21e986d | ||
|
|
38abca8a65 | ||
|
|
f3c6b54ffa | ||
|
|
7dd85bb6ad | ||
|
|
624f88e069 | ||
|
|
fbf693b2dc | ||
|
|
dbf7bf4750 | ||
|
|
d31eb3b248 | ||
|
|
9b75fc98c1 | ||
|
|
1ee9f6a7e5 | ||
|
|
06d0cbd418 | ||
|
|
066dd71afb | ||
|
|
d573bd41b4 | ||
|
|
d06d190229 | ||
|
|
d3b650c741 | ||
|
|
4a04b8b5ee | ||
|
|
6718ba7423 | ||
|
|
e662433c2a | ||
|
|
08bb957672 | ||
|
|
78d8176cc8 | ||
|
|
59ee984e09 | ||
|
|
f6fab051ce | ||
|
|
f0ff6a9f1c | ||
|
|
dfa761b963 | ||
|
|
ad8cdcd81b | ||
|
|
98ef0e74d6 | ||
|
|
746fde7c10 | ||
|
|
bedddd4760 | ||
|
|
7ea78e9845 | ||
|
|
9383942cb9 | ||
|
|
2f1fe637ca | ||
|
|
15d453de1d | ||
|
|
a272995b8c | ||
|
|
10b800e57f | ||
|
|
ca77563bf1 | ||
|
|
44ff1aac11 | ||
|
|
79e648867d | ||
|
|
fc725c07e9 | ||
|
|
d49c86bd5f | ||
|
|
aee94ad6fb | ||
|
|
38011e537a | ||
|
|
13194ddfba | ||
|
|
7895abb9ea | ||
|
|
9060bebca9 | ||
|
|
38724458e3 | ||
|
|
1bce1524db | ||
|
|
def3c76e10 | ||
|
|
5be770cad1 | ||
|
|
dd867b2a92 | ||
|
|
958ffb3076 | ||
|
|
bab3c4abc4 | ||
|
|
1f342b79a8 | ||
|
|
3af782f894 | ||
|
|
e27069447b | ||
|
|
7ac573d628 | ||
|
|
b3db9ce6cf | ||
|
|
1397b9ac80 | ||
|
|
de294cae92 | ||
|
|
5cef3dc1ba | ||
|
|
1dce802031 | ||
|
|
11d61d6d7d | ||
|
|
b5f3cd14c2 | ||
|
|
f87ce0defe | ||
|
|
201ff8f1da | ||
|
|
0c44b9a478 | ||
|
|
9dba1d30b0 | ||
|
|
ad70f12cb4 | ||
|
|
6ea7ab2b46 | ||
|
|
0ef71f4368 | ||
|
|
ae565aaac6 | ||
|
|
7e942173aa | ||
|
|
e1b87c48bc | ||
|
|
8cd259c43f | ||
|
|
d2d2507e86 | ||
|
|
f3f9cd3d05 | ||
|
|
543f273792 | ||
|
|
d9eedb0dad | ||
|
|
7f2fec756d | ||
|
|
607021a890 | ||
|
|
b4febf728d | ||
|
|
769f0a8452 | ||
|
|
f5004a2a0c | ||
|
|
a707022d0b | ||
|
|
43b0118ff8 | ||
|
|
97ca3fb622 | ||
|
|
ffa55cca1e | ||
|
|
0098091a37 | ||
|
|
6c1cb5d4be | ||
|
|
8240c3703e | ||
|
|
35572700bf | ||
|
|
5df774c569 | ||
|
|
8a503e7b40 | ||
|
|
4f49cde73e | ||
|
|
ea5ce3f72f | ||
|
|
5152638529 | ||
|
|
e4b50ba419 | ||
|
|
05127467c2 | ||
|
|
420c7c87e3 | ||
|
|
c23d38807a | ||
|
|
fb6f38800b | ||
|
|
4fb698ea04 | ||
|
|
ebe81e2835 | ||
|
|
c4106b8d89 | ||
|
|
4a350df695 | ||
|
|
0638d9d303 | ||
|
|
0fe7383154 | ||
|
|
9d7b6cafc5 | ||
|
|
39d30ea0b4 | ||
|
|
1400b6ff0a | ||
|
|
3fc3a217eb | ||
|
|
6068a30488 |
4
.github/workflows/ci.yml
vendored
4
.github/workflows/ci.yml
vendored
@@ -20,4 +20,6 @@ jobs:
|
||||
run: $(exit $(git status --porcelain --untracked-files=no | head -255 | wc -l)) || (echo "Dirty git tree"; git diff; exit 1)
|
||||
- run: npm run lint
|
||||
- run: for file in lang/*.json; do npx --yes jsonlint -q $file || exit 1; done
|
||||
- run: make
|
||||
- env:
|
||||
NODE_OPTIONS: '--max-old-space-size=4096'
|
||||
run: make
|
||||
|
||||
4
Makefile
4
Makefile
@@ -4,7 +4,7 @@ DEPLOY_DIR = libs
|
||||
LIBJITSIMEET_DIR = node_modules/lib-jitsi-meet
|
||||
OLM_DIR = node_modules/@matrix-org/olm
|
||||
TF_WASM_DIR = node_modules/@tensorflow/tfjs-backend-wasm/dist/
|
||||
RNNOISE_WASM_DIR = node_modules/rnnoise-wasm/dist
|
||||
RNNOISE_WASM_DIR = node_modules/@jitsi/rnnoise-wasm/dist
|
||||
TFLITE_WASM = react/features/stream-effects/virtual-background/vendor/tflite
|
||||
MEET_MODELS_DIR = react/features/stream-effects/virtual-background/vendor/models
|
||||
FACE_MODELS_DIR = node_modules/@vladmandic/human-models/models
|
||||
@@ -49,6 +49,8 @@ deploy-appbundle:
|
||||
$(BUILD_DIR)/analytics-ga.min.js.map \
|
||||
$(BUILD_DIR)/face-landmarks-worker.min.js \
|
||||
$(BUILD_DIR)/face-landmarks-worker.min.js.map \
|
||||
$(BUILD_DIR)/noise-suppressor-worklet.min.js \
|
||||
$(BUILD_DIR)/noise-suppressor-worklet.min.js.map \
|
||||
$(DEPLOY_DIR)
|
||||
cp \
|
||||
$(BUILD_DIR)/close3.min.js \
|
||||
|
||||
@@ -1,8 +1,7 @@
|
||||
<resources>
|
||||
<!-- Base application theme. -->
|
||||
<style name="AppTheme" parent="Theme.AppCompat.Light.NoActionBar">
|
||||
<!-- Customize your theme here. -->
|
||||
<item name="android:editTextBackground">@drawable/rn_edit_text_material</item>
|
||||
<item name="android:forceDarkAllowed">false</item>
|
||||
<item name="android:navigationBarColor">@color/colorPrimaryDark</item>
|
||||
<item name="android:windowDisablePreview">true</item>
|
||||
</style>
|
||||
|
||||
@@ -26,5 +26,5 @@ android.useAndroidX=true
|
||||
android.enableJetifier=true
|
||||
android.bundle.enableUncompressedNativeLibs=false
|
||||
|
||||
appVersion=22.2.0
|
||||
sdkVersion=5.1.0
|
||||
appVersion=22.5.1
|
||||
sdkVersion=6.1.0
|
||||
|
||||
@@ -51,15 +51,10 @@ dependencies {
|
||||
implementation 'com.google.code.gson:gson:2.8.6'
|
||||
implementation "androidx.startup:startup-runtime:1.1.0"
|
||||
|
||||
if (rootProject.ext.libreBuild) {
|
||||
implementation(project(':react-native-device-info')) {
|
||||
exclude group: 'com.google.firebase'
|
||||
exclude group: 'com.google.android.gms'
|
||||
exclude group: 'com.android.installreferrer'
|
||||
}
|
||||
} else {
|
||||
// Only add these packages if we are NOT doing a LIBRE_BUILD
|
||||
if (!rootProject.ext.libreBuild) {
|
||||
implementation project(':react-native-amplitude')
|
||||
implementation project(':react-native-device-info')
|
||||
implementation project(':react-native-giphy')
|
||||
implementation(project(":react-native-google-signin")) {
|
||||
exclude group: 'com.google.android.gms'
|
||||
exclude group: 'androidx'
|
||||
@@ -72,15 +67,18 @@ dependencies {
|
||||
implementation project(':react-native-community_clipboard')
|
||||
implementation project(':react-native-community_netinfo')
|
||||
implementation project(':react-native-default-preference')
|
||||
implementation(project(':react-native-device-info')) {
|
||||
exclude group: 'com.google.firebase'
|
||||
exclude group: 'com.google.android.gms'
|
||||
exclude group: 'com.android.installreferrer'
|
||||
}
|
||||
implementation project(':react-native-gesture-handler')
|
||||
implementation project(':react-native-get-random-values')
|
||||
implementation project(':react-native-giphy')
|
||||
implementation project(':react-native-immersive')
|
||||
implementation project(':react-native-keep-awake')
|
||||
implementation project(':react-native-masked-view_masked-view')
|
||||
implementation project(':react-native-pager-view')
|
||||
implementation project(':react-native-performance')
|
||||
implementation project(':react-native-reanimated')
|
||||
implementation project(':react-native-safe-area-context')
|
||||
implementation project(':react-native-screens')
|
||||
implementation project(':react-native-slider')
|
||||
|
||||
@@ -32,6 +32,7 @@
|
||||
android:name=".JitsiMeetActivity"
|
||||
android:configChanges="keyboard|keyboardHidden|orientation|screenLayout|screenSize|smallestScreenSize|uiMode"
|
||||
android:launchMode="singleTask"
|
||||
android:theme="@style/JitsiMeetActivityStyle"
|
||||
android:resizeableActivity="true"
|
||||
android:supportsPictureInPicture="true"
|
||||
android:windowSoftInputMode="adjustResize"/>
|
||||
|
||||
@@ -1,240 +0,0 @@
|
||||
/*
|
||||
* Copyright @ 2018-present 8x8, Inc.
|
||||
* Copyright @ 2018 Atlassian Pty Ltd
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
* You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*/
|
||||
|
||||
package org.jitsi.meet.sdk;
|
||||
|
||||
import android.app.Activity;
|
||||
import android.content.Context;
|
||||
import android.os.Bundle;
|
||||
import android.util.AttributeSet;
|
||||
import android.widget.FrameLayout;
|
||||
import androidx.annotation.NonNull;
|
||||
import androidx.annotation.Nullable;
|
||||
|
||||
import com.facebook.react.ReactRootView;
|
||||
import com.facebook.react.bridge.ReadableMap;
|
||||
import com.rnimmersive.RNImmersiveModule;
|
||||
|
||||
import java.lang.reflect.Method;
|
||||
import java.util.ArrayList;
|
||||
import java.util.Collections;
|
||||
import java.util.Map;
|
||||
import java.util.Set;
|
||||
import java.util.UUID;
|
||||
import java.util.WeakHashMap;
|
||||
|
||||
/**
|
||||
* Base class for all views which are backed by a React Native view.
|
||||
*/
|
||||
public abstract class BaseReactView<ListenerT>
|
||||
extends FrameLayout {
|
||||
|
||||
/**
|
||||
* Background color used by {@code BaseReactView} and the React Native root
|
||||
* view.
|
||||
*/
|
||||
protected static int BACKGROUND_COLOR = 0xFF111111;
|
||||
|
||||
/**
|
||||
* The collection of all existing {@code BaseReactView}s. Used to find the
|
||||
* {@code BaseReactView} when delivering events coming from
|
||||
* {@link ExternalAPIModule}.
|
||||
*/
|
||||
static final Set<BaseReactView> views
|
||||
= Collections.newSetFromMap(new WeakHashMap<BaseReactView, Boolean>());
|
||||
|
||||
/**
|
||||
* Finds a {@code BaseReactView} which matches a specific external API
|
||||
* scope.
|
||||
*
|
||||
* @param externalAPIScope - The external API scope associated with the
|
||||
* {@code BaseReactView} to find.
|
||||
* @return The {@code BaseReactView}, if any, associated with the specified
|
||||
* {@code externalAPIScope}; otherwise, {@code null}.
|
||||
*/
|
||||
public static BaseReactView findViewByExternalAPIScope(
|
||||
String externalAPIScope) {
|
||||
synchronized (views) {
|
||||
for (BaseReactView view : views) {
|
||||
if (view.externalAPIScope.equals(externalAPIScope)) {
|
||||
return view;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
return null;
|
||||
}
|
||||
|
||||
/**
|
||||
* Gets all registered React views.
|
||||
*
|
||||
* @return An {@link ArrayList} containing all views currently held by React.
|
||||
*/
|
||||
static ArrayList<BaseReactView> getViews() {
|
||||
return new ArrayList<>(views);
|
||||
}
|
||||
|
||||
/**
|
||||
* The unique identifier of this {@code BaseReactView} within the process
|
||||
* for the purposes of {@link ExternalAPIModule}. The name scope was
|
||||
* inspired by postis which we use on Web for the similar purposes of the
|
||||
* iframe-based external API.
|
||||
*/
|
||||
protected String externalAPIScope;
|
||||
|
||||
/**
|
||||
* The listener (e.g. {@link JitsiMeetViewListener}) instance for reporting
|
||||
* events occurring in Jitsi Meet.
|
||||
*/
|
||||
@Deprecated
|
||||
private ListenerT listener;
|
||||
|
||||
/**
|
||||
* React Native root view.
|
||||
*/
|
||||
private ReactRootView reactRootView;
|
||||
|
||||
public BaseReactView(@NonNull Context context) {
|
||||
super(context);
|
||||
initialize((Activity)context);
|
||||
}
|
||||
|
||||
public BaseReactView(Context context, AttributeSet attrs) {
|
||||
super(context, attrs);
|
||||
initialize((Activity)context);
|
||||
}
|
||||
|
||||
public BaseReactView(Context context, AttributeSet attrs, int defStyle) {
|
||||
super(context, attrs, defStyle);
|
||||
initialize((Activity)context);
|
||||
}
|
||||
|
||||
/**
|
||||
* Creates the {@code ReactRootView} for the given app name with the given
|
||||
* props. Once created it's set as the view of this {@code FrameLayout}.
|
||||
*
|
||||
* @param appName - The name of the "app" (in React Native terms) to load.
|
||||
* @param props - The React Component props to pass to the app.
|
||||
*/
|
||||
public void createReactRootView(String appName, @Nullable Bundle props) {
|
||||
if (props == null) {
|
||||
props = new Bundle();
|
||||
}
|
||||
|
||||
props.putString("externalAPIScope", externalAPIScope);
|
||||
|
||||
if (reactRootView == null) {
|
||||
reactRootView = new ReactRootView(getContext());
|
||||
reactRootView.startReactApplication(
|
||||
ReactInstanceManagerHolder.getReactInstanceManager(),
|
||||
appName,
|
||||
props);
|
||||
reactRootView.setBackgroundColor(BACKGROUND_COLOR);
|
||||
addView(reactRootView);
|
||||
} else {
|
||||
reactRootView.setAppProperties(props);
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Releases the React resources (specifically the {@link ReactRootView})
|
||||
* associated with this view.
|
||||
*
|
||||
* MUST be called when the {@link Activity} holding this view is destroyed,
|
||||
* typically in the {@code onDestroy} method.
|
||||
*/
|
||||
public void dispose() {
|
||||
if (reactRootView != null) {
|
||||
removeView(reactRootView);
|
||||
reactRootView.unmountReactApplication();
|
||||
reactRootView = null;
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Gets the listener set on this {@code BaseReactView}.
|
||||
*
|
||||
* @return The listener set on this {@code BaseReactView}.
|
||||
*/
|
||||
@Deprecated
|
||||
public ListenerT getListener() {
|
||||
return listener;
|
||||
}
|
||||
|
||||
/**
|
||||
* Abstract method called by {@link ExternalAPIModule} when an event is
|
||||
* received for this view.
|
||||
*
|
||||
* @param name - The name of the event.
|
||||
* @param data - The details of the event associated with/specific to the
|
||||
* specified {@code name}.
|
||||
*/
|
||||
@Deprecated
|
||||
protected abstract void onExternalAPIEvent(String name, ReadableMap data);
|
||||
|
||||
@Deprecated
|
||||
protected void onExternalAPIEvent(
|
||||
Map<String, Method> listenerMethods,
|
||||
String name, ReadableMap data) {
|
||||
ListenerT listener = getListener();
|
||||
|
||||
if (listener != null) {
|
||||
ListenerUtils.runListenerMethod(
|
||||
listener, listenerMethods, name, data);
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Called when the window containing this view gains or loses focus.
|
||||
*
|
||||
* @param hasFocus If the window of this view now has focus, {@code true};
|
||||
* otherwise, {@code false}.
|
||||
*/
|
||||
@Override
|
||||
public void onWindowFocusChanged(boolean hasFocus) {
|
||||
super.onWindowFocusChanged(hasFocus);
|
||||
|
||||
// https://github.com/mockingbot/react-native-immersive#restore-immersive-state
|
||||
RNImmersiveModule immersive = RNImmersiveModule.getInstance();
|
||||
|
||||
if (hasFocus && immersive != null) {
|
||||
immersive.emitImmersiveStateChangeEvent();
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Sets a specific listener on this {@code BaseReactView}.
|
||||
*
|
||||
* @param listener The listener to set on this {@code BaseReactView}.
|
||||
*/
|
||||
@Deprecated
|
||||
public void setListener(ListenerT listener) {
|
||||
this.listener = listener;
|
||||
}
|
||||
|
||||
private void initialize(Activity activity) {
|
||||
setBackgroundColor(BACKGROUND_COLOR);
|
||||
|
||||
ReactInstanceManagerHolder.initReactInstanceManager(activity);
|
||||
|
||||
// Hook this BaseReactView into ExternalAPI.
|
||||
externalAPIScope = UUID.randomUUID().toString();
|
||||
synchronized (views) {
|
||||
views.add(this);
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -76,7 +76,8 @@ public class BroadcastAction {
|
||||
OPEN_CHAT("org.jitsi.meet.OPEN_CHAT"),
|
||||
CLOSE_CHAT("org.jitsi.meet.CLOSE_CHAT"),
|
||||
SEND_CHAT_MESSAGE("org.jitsi.meet.SEND_CHAT_MESSAGE"),
|
||||
SET_VIDEO_MUTED("org.jitsi.meet.SET_VIDEO_MUTED");
|
||||
SET_VIDEO_MUTED("org.jitsi.meet.SET_VIDEO_MUTED"),
|
||||
SET_CLOSED_CAPTIONS_ENABLED("org.jitsi.meet.SET_CLOSED_CAPTIONS_ENABLED");
|
||||
|
||||
private final String action;
|
||||
|
||||
|
||||
@@ -48,4 +48,10 @@ public class BroadcastIntentHelper {
|
||||
intent.putExtra("muted", muted);
|
||||
return intent;
|
||||
}
|
||||
|
||||
public static Intent buildSetClosedCaptionsEnabledIntent(boolean enabled) {
|
||||
Intent intent = new Intent(BroadcastAction.Type.SET_CLOSED_CAPTIONS_ENABLED.getAction());
|
||||
intent.putExtra("enabled", enabled);
|
||||
return intent;
|
||||
}
|
||||
}
|
||||
|
||||
@@ -95,37 +95,25 @@ class ExternalAPIModule extends ReactContextBaseJavaModule {
|
||||
constants.put("CLOSE_CHAT", BroadcastAction.Type.CLOSE_CHAT.getAction());
|
||||
constants.put("SEND_CHAT_MESSAGE", BroadcastAction.Type.SEND_CHAT_MESSAGE.getAction());
|
||||
constants.put("SET_VIDEO_MUTED", BroadcastAction.Type.SET_VIDEO_MUTED.getAction());
|
||||
constants.put("SET_CLOSED_CAPTIONS_ENABLED", BroadcastAction.Type.SET_CLOSED_CAPTIONS_ENABLED.getAction());
|
||||
|
||||
return constants;
|
||||
}
|
||||
|
||||
/**
|
||||
* Dispatches an event that occurred on the JavaScript side of the SDK to
|
||||
* the specified {@link BaseReactView}'s listener.
|
||||
* the native side.
|
||||
*
|
||||
* @param name The name of the event.
|
||||
* @param data The details/specifics of the event to send determined
|
||||
* by/associated with the specified {@code name}.
|
||||
* @param scope
|
||||
*/
|
||||
@ReactMethod
|
||||
public void sendEvent(String name, ReadableMap data, String scope) {
|
||||
public void sendEvent(String name, ReadableMap data) {
|
||||
// Keep track of the current ongoing conference.
|
||||
OngoingConferenceTracker.getInstance().onExternalAPIEvent(name, data);
|
||||
|
||||
// The JavaScript App needs to provide uniquely identifying information
|
||||
// to the native ExternalAPI module so that the latter may match the
|
||||
// former to the native BaseReactView which hosts it.
|
||||
BaseReactView view = BaseReactView.findViewByExternalAPIScope(scope);
|
||||
|
||||
if (view != null) {
|
||||
JitsiMeetLogger.d(TAG + " Sending event: " + name + " with data: " + data);
|
||||
try {
|
||||
view.onExternalAPIEvent(name, data);
|
||||
broadcastEmitter.sendBroadcast(name, data);
|
||||
} catch (Exception e) {
|
||||
JitsiMeetLogger.e(e, TAG + " onExternalAPIEvent: error sending event");
|
||||
}
|
||||
}
|
||||
JitsiMeetLogger.d(TAG + " Sending event: " + name + " with data: " + data);
|
||||
broadcastEmitter.sendBroadcast(name, data);
|
||||
}
|
||||
}
|
||||
|
||||
@@ -167,12 +167,9 @@ public class JitsiMeetActivity extends AppCompatActivity
|
||||
}
|
||||
}
|
||||
|
||||
public void leave() {
|
||||
if (this.jitsiView != null) {
|
||||
this.jitsiView .leave();
|
||||
} else {
|
||||
JitsiMeetLogger.w("Cannot leave, view is null");
|
||||
}
|
||||
protected void leave() {
|
||||
Intent hangupBroadcastIntent = BroadcastIntentHelper.buildHangUpIntent();
|
||||
LocalBroadcastManager.getInstance(getApplicationContext()).sendBroadcast(hangupBroadcastIntent);
|
||||
}
|
||||
|
||||
private @Nullable
|
||||
@@ -213,7 +210,7 @@ public class JitsiMeetActivity extends AppCompatActivity
|
||||
protected void onConferenceJoined(HashMap<String, Object> extraData) {
|
||||
JitsiMeetLogger.i("Conference joined: " + extraData);
|
||||
// Launch the service for the ongoing notification.
|
||||
JitsiMeetOngoingConferenceService.launch(this);
|
||||
JitsiMeetOngoingConferenceService.launch(this, extraData);
|
||||
}
|
||||
|
||||
protected void onConferenceTerminated(HashMap<String, Object> extraData) {
|
||||
|
||||
@@ -1,82 +0,0 @@
|
||||
/*
|
||||
* Copyright @ 2019-present 8x8, Inc.
|
||||
* Copyright @ 2017-2018 Atlassian Pty Ltd
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
* You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*/
|
||||
|
||||
package org.jitsi.meet.sdk;
|
||||
|
||||
import android.os.Bundle;
|
||||
import androidx.annotation.NonNull;
|
||||
import androidx.annotation.Nullable;
|
||||
import androidx.fragment.app.Fragment;
|
||||
|
||||
import android.view.LayoutInflater;
|
||||
import android.view.View;
|
||||
import android.view.ViewGroup;
|
||||
|
||||
/**
|
||||
* Base {@link Fragment} for applications integrating Jitsi Meet at a higher level. It
|
||||
* contains all the required wiring between the {@code JitsiMeetView} and
|
||||
* the Fragment lifecycle methods already implemented.
|
||||
*
|
||||
* In this fragment we use a single {@code JitsiMeetView} instance. This
|
||||
* instance gives us access to a view which displays the welcome page and the
|
||||
* conference itself. All lifecycle methods associated with this Fragment are
|
||||
* hooked to the React Native subsystem via proxy calls through the
|
||||
* {@code JitsiMeetActivityDelegate} static methods.
|
||||
*
|
||||
* @deprecated use {@link JitsiMeetActivity} or directly {@link JitsiMeetView}
|
||||
*/
|
||||
@Deprecated
|
||||
public class JitsiMeetFragment extends Fragment {
|
||||
|
||||
/**
|
||||
* Instance of the {@link JitsiMeetView} which this activity will display.
|
||||
*/
|
||||
private JitsiMeetView view;
|
||||
|
||||
@Nullable
|
||||
@Override
|
||||
public View onCreateView(@NonNull LayoutInflater inflater,
|
||||
@Nullable ViewGroup container,
|
||||
@Nullable Bundle savedInstanceState) {
|
||||
return this.view = new JitsiMeetView(getActivity());
|
||||
}
|
||||
|
||||
public JitsiMeetView getJitsiView() {
|
||||
return view;
|
||||
}
|
||||
|
||||
@Override
|
||||
public void onDestroy() {
|
||||
super.onDestroy();
|
||||
|
||||
JitsiMeetActivityDelegate.onHostDestroy(getActivity());
|
||||
}
|
||||
|
||||
@Override
|
||||
public void onResume() {
|
||||
super.onResume();
|
||||
|
||||
JitsiMeetActivityDelegate.onHostResume(getActivity());
|
||||
}
|
||||
|
||||
@Override
|
||||
public void onStop() {
|
||||
super.onStop();
|
||||
|
||||
JitsiMeetActivityDelegate.onHostPause(getActivity());
|
||||
}
|
||||
}
|
||||
@@ -17,18 +17,22 @@
|
||||
package org.jitsi.meet.sdk;
|
||||
|
||||
import android.app.Notification;
|
||||
import android.app.NotificationManager;
|
||||
import android.app.Service;
|
||||
import android.content.ComponentName;
|
||||
import android.content.Context;
|
||||
import android.content.Intent;
|
||||
import android.content.IntentFilter;
|
||||
import android.os.Build;
|
||||
import android.os.Bundle;
|
||||
import android.os.IBinder;
|
||||
|
||||
import androidx.localbroadcastmanager.content.LocalBroadcastManager;
|
||||
|
||||
import org.jitsi.meet.sdk.log.JitsiMeetLogger;
|
||||
|
||||
import java.util.HashMap;
|
||||
|
||||
/**
|
||||
* This class implements an Android {@link Service}, a foreground one specifically, and it's
|
||||
* responsible for presenting an ongoing notification when a conference is in progress.
|
||||
@@ -39,16 +43,22 @@ import org.jitsi.meet.sdk.log.JitsiMeetLogger;
|
||||
public class JitsiMeetOngoingConferenceService extends Service
|
||||
implements OngoingConferenceTracker.OngoingConferenceListener {
|
||||
private static final String TAG = JitsiMeetOngoingConferenceService.class.getSimpleName();
|
||||
private static final String EXTRA_DATA_KEY = "extraDataKey";
|
||||
private static final String EXTRA_DATA_BUNDLE_KEY = "extraDataBundleKey";
|
||||
private static final String IS_AUDIO_MUTED_KEY = "isAudioMuted";
|
||||
|
||||
private final BroadcastReceiver broadcastReceiver = new BroadcastReceiver();
|
||||
|
||||
private boolean isAudioMuted;
|
||||
|
||||
static void launch(Context context) {
|
||||
public static void launch(Context context, HashMap<String, Object> extraData) {
|
||||
OngoingNotification.createOngoingConferenceNotificationChannel();
|
||||
|
||||
Intent intent = new Intent(context, JitsiMeetOngoingConferenceService.class);
|
||||
intent.setAction(Action.START.getName());
|
||||
|
||||
Bundle extraDataBundle = new Bundle();
|
||||
extraDataBundle.putSerializable(EXTRA_DATA_KEY, extraData);
|
||||
intent.putExtra(EXTRA_DATA_BUNDLE_KEY, extraDataBundle);
|
||||
|
||||
ComponentName componentName;
|
||||
|
||||
@@ -70,7 +80,7 @@ public class JitsiMeetOngoingConferenceService extends Service
|
||||
}
|
||||
}
|
||||
|
||||
static void abort(Context context) {
|
||||
public static void abort(Context context) {
|
||||
Intent intent = new Intent(context, JitsiMeetOngoingConferenceService.class);
|
||||
context.stopService(intent);
|
||||
}
|
||||
@@ -79,6 +89,15 @@ public class JitsiMeetOngoingConferenceService extends Service
|
||||
public void onCreate() {
|
||||
super.onCreate();
|
||||
|
||||
Notification notification = OngoingNotification.buildOngoingConferenceNotification(isAudioMuted);
|
||||
if (notification == null) {
|
||||
stopSelf();
|
||||
JitsiMeetLogger.w(TAG + " Couldn't start service, notification is null");
|
||||
} else {
|
||||
startForeground(OngoingNotification.NOTIFICATION_ID, notification);
|
||||
JitsiMeetLogger.i(TAG + " Service started");
|
||||
}
|
||||
|
||||
OngoingConferenceTracker.getInstance().addListener(this);
|
||||
|
||||
IntentFilter intentFilter = new IntentFilter();
|
||||
@@ -101,37 +120,45 @@ public class JitsiMeetOngoingConferenceService extends Service
|
||||
|
||||
@Override
|
||||
public int onStartCommand(Intent intent, int flags, int startId) {
|
||||
|
||||
Boolean isAudioMuted = tryParseIsAudioMuted(intent);
|
||||
|
||||
if (isAudioMuted != null) {
|
||||
this.isAudioMuted = Boolean.parseBoolean(intent.getStringExtra("muted"));
|
||||
|
||||
Notification notification = OngoingNotification.buildOngoingConferenceNotification(isAudioMuted);
|
||||
if (notification == null) {
|
||||
stopSelf();
|
||||
JitsiMeetLogger.w(TAG + " Couldn't start service, notification is null");
|
||||
} else {
|
||||
NotificationManager notificationManager = (NotificationManager) getSystemService(Context.NOTIFICATION_SERVICE);
|
||||
notificationManager.notify(OngoingNotification.NOTIFICATION_ID, notification);
|
||||
}
|
||||
}
|
||||
|
||||
final String actionName = intent.getAction();
|
||||
final Action action = Action.fromName(actionName);
|
||||
|
||||
switch (action) {
|
||||
case UNMUTE:
|
||||
case MUTE:
|
||||
Intent muteBroadcastIntent = BroadcastIntentHelper.buildSetAudioMutedIntent(action == Action.MUTE);
|
||||
LocalBroadcastManager.getInstance(getApplicationContext()).sendBroadcast(muteBroadcastIntent);
|
||||
break;
|
||||
case START:
|
||||
Notification notification = OngoingNotification.buildOngoingConferenceNotification(isAudioMuted);
|
||||
if (notification == null) {
|
||||
// When starting the service, there is no action passed in the intent
|
||||
if (action != null) {
|
||||
switch (action) {
|
||||
case UNMUTE:
|
||||
case MUTE:
|
||||
Intent muteBroadcastIntent = BroadcastIntentHelper.buildSetAudioMutedIntent(action == Action.MUTE);
|
||||
LocalBroadcastManager.getInstance(getApplicationContext()).sendBroadcast(muteBroadcastIntent);
|
||||
break;
|
||||
case HANGUP:
|
||||
JitsiMeetLogger.i(TAG + " Hangup requested");
|
||||
|
||||
Intent hangupBroadcastIntent = BroadcastIntentHelper.buildHangUpIntent();
|
||||
LocalBroadcastManager.getInstance(getApplicationContext()).sendBroadcast(hangupBroadcastIntent);
|
||||
|
||||
stopSelf();
|
||||
JitsiMeetLogger.w(TAG + " Couldn't start service, notification is null");
|
||||
} else {
|
||||
startForeground(OngoingNotification.NOTIFICATION_ID, notification);
|
||||
JitsiMeetLogger.i(TAG + " Service started");
|
||||
}
|
||||
break;
|
||||
case HANGUP:
|
||||
JitsiMeetLogger.i(TAG + " Hangup requested");
|
||||
|
||||
Intent hangupBroadcastIntent = BroadcastIntentHelper.buildHangUpIntent();
|
||||
LocalBroadcastManager.getInstance(getApplicationContext()).sendBroadcast(hangupBroadcastIntent);
|
||||
|
||||
stopSelf();
|
||||
break;
|
||||
default:
|
||||
JitsiMeetLogger.w(TAG + " Unknown action received: " + action);
|
||||
stopSelf();
|
||||
break;
|
||||
break;
|
||||
default:
|
||||
JitsiMeetLogger.w(TAG + " Unknown action received: " + action);
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
return START_NOT_STICKY;
|
||||
@@ -147,7 +174,6 @@ public class JitsiMeetOngoingConferenceService extends Service
|
||||
}
|
||||
|
||||
public enum Action {
|
||||
START(TAG + ":START"),
|
||||
HANGUP(TAG + ":HANGUP"),
|
||||
MUTE(TAG + ":MUTE"),
|
||||
UNMUTE(TAG + ":UNMUTE");
|
||||
@@ -172,6 +198,15 @@ public class JitsiMeetOngoingConferenceService extends Service
|
||||
}
|
||||
}
|
||||
|
||||
private Boolean tryParseIsAudioMuted(Intent intent) {
|
||||
try {
|
||||
HashMap<String, Object> extraData = (HashMap<String, Object>) intent.getBundleExtra(EXTRA_DATA_BUNDLE_KEY).getSerializable(EXTRA_DATA_KEY);
|
||||
return Boolean.parseBoolean((String) extraData.get(IS_AUDIO_MUTED_KEY));
|
||||
} catch (Exception ignored) {
|
||||
}
|
||||
return null;
|
||||
}
|
||||
|
||||
private class BroadcastReceiver extends android.content.BroadcastReceiver {
|
||||
|
||||
@Override
|
||||
@@ -180,10 +215,12 @@ public class JitsiMeetOngoingConferenceService extends Service
|
||||
Notification notification = OngoingNotification.buildOngoingConferenceNotification(isAudioMuted);
|
||||
if (notification == null) {
|
||||
stopSelf();
|
||||
JitsiMeetLogger.w(TAG + " Couldn't start service, notification is null");
|
||||
JitsiMeetLogger.w(TAG + " Couldn't update service, notification is null");
|
||||
} else {
|
||||
startForeground(OngoingNotification.NOTIFICATION_ID, notification);
|
||||
JitsiMeetLogger.i(TAG + " Service started");
|
||||
NotificationManager notificationManager = (NotificationManager) getSystemService(Context.NOTIFICATION_SERVICE);
|
||||
notificationManager.notify(OngoingNotification.NOTIFICATION_ID, notification);
|
||||
|
||||
JitsiMeetLogger.i(TAG + " audio muted changed");
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@@ -16,36 +16,33 @@
|
||||
|
||||
package org.jitsi.meet.sdk;
|
||||
|
||||
import android.app.Activity;
|
||||
import android.content.Context;
|
||||
import android.os.Bundle;
|
||||
import android.util.AttributeSet;
|
||||
import android.widget.FrameLayout;
|
||||
|
||||
import androidx.annotation.NonNull;
|
||||
import androidx.annotation.Nullable;
|
||||
|
||||
import com.facebook.react.bridge.ReadableMap;
|
||||
import com.facebook.react.ReactRootView;
|
||||
import com.rnimmersive.RNImmersiveModule;
|
||||
|
||||
import org.jitsi.meet.sdk.log.JitsiMeetLogger;
|
||||
|
||||
import java.lang.reflect.Method;
|
||||
import java.util.Map;
|
||||
|
||||
public class JitsiMeetView extends BaseReactView<JitsiMeetViewListener>
|
||||
implements OngoingConferenceTracker.OngoingConferenceListener {
|
||||
public class JitsiMeetView extends FrameLayout {
|
||||
|
||||
/**
|
||||
* The {@code Method}s of {@code JitsiMeetViewListener} by event name i.e.
|
||||
* redux action types.
|
||||
* Background color used by {@code BaseReactView} and the React Native root
|
||||
* view.
|
||||
*/
|
||||
private static final Map<String, Method> LISTENER_METHODS
|
||||
= ListenerUtils.mapListenerMethods(JitsiMeetViewListener.class);
|
||||
private static final int BACKGROUND_COLOR = 0xFF111111;
|
||||
|
||||
/**
|
||||
* The URL of the current conference.
|
||||
* React Native root view.
|
||||
*/
|
||||
// XXX Currently, one thread writes and one thread reads, so it should be
|
||||
// fine to have this field volatile without additional synchronization.
|
||||
private volatile String url;
|
||||
private ReactRootView reactRootView;
|
||||
|
||||
/**
|
||||
* Helper method to recursively merge 2 {@link Bundle} objects representing React Native props.
|
||||
@@ -109,10 +106,19 @@ public class JitsiMeetView extends BaseReactView<JitsiMeetViewListener>
|
||||
initialize(context);
|
||||
}
|
||||
|
||||
@Override
|
||||
/**
|
||||
* Releases the React resources (specifically the {@link ReactRootView})
|
||||
* associated with this view.
|
||||
*
|
||||
* MUST be called when the {@link Activity} holding this view is destroyed,
|
||||
* typically in the {@code onDestroy} method.
|
||||
*/
|
||||
public void dispose() {
|
||||
OngoingConferenceTracker.getInstance().removeListener(this);
|
||||
super.dispose();
|
||||
if (reactRootView != null) {
|
||||
removeView(reactRootView);
|
||||
reactRootView.unmountReactApplication();
|
||||
reactRootView = null;
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
@@ -130,8 +136,7 @@ public class JitsiMeetView extends BaseReactView<JitsiMeetViewListener>
|
||||
PictureInPictureModule.class);
|
||||
if (pipModule != null
|
||||
&& pipModule.isPictureInPictureSupported()
|
||||
&& !JitsiMeetActivityDelegate.arePermissionsBeingRequested()
|
||||
&& this.url != null) {
|
||||
&& !JitsiMeetActivityDelegate.arePermissionsBeingRequested()) {
|
||||
try {
|
||||
pipModule.enterPictureInPicture();
|
||||
} catch (RuntimeException re) {
|
||||
@@ -151,10 +156,40 @@ public class JitsiMeetView extends BaseReactView<JitsiMeetViewListener>
|
||||
}
|
||||
|
||||
/**
|
||||
* Leaves the currently active conference.
|
||||
* Creates the {@code ReactRootView} for the given app name with the given
|
||||
* props. Once created it's set as the view of this {@code FrameLayout}.
|
||||
*
|
||||
* @param appName - The name of the "app" (in React Native terms) to load.
|
||||
* @param props - The React Component props to pass to the app.
|
||||
*/
|
||||
public void leave() {
|
||||
setProps(new Bundle());
|
||||
private void createReactRootView(String appName, @Nullable Bundle props) {
|
||||
if (props == null) {
|
||||
props = new Bundle();
|
||||
}
|
||||
|
||||
if (reactRootView == null) {
|
||||
reactRootView = new ReactRootView(getContext());
|
||||
reactRootView.startReactApplication(
|
||||
ReactInstanceManagerHolder.getReactInstanceManager(),
|
||||
appName,
|
||||
props);
|
||||
reactRootView.setBackgroundColor(BACKGROUND_COLOR);
|
||||
addView(reactRootView);
|
||||
} else {
|
||||
reactRootView.setAppProperties(props);
|
||||
}
|
||||
}
|
||||
|
||||
private void initialize(@NonNull Context context) {
|
||||
// Check if the parent Activity implements JitsiMeetActivityInterface,
|
||||
// otherwise things may go wrong.
|
||||
if (!(context instanceof JitsiMeetActivityInterface)) {
|
||||
throw new RuntimeException("Enclosing Activity must implement JitsiMeetActivityInterface");
|
||||
}
|
||||
|
||||
setBackgroundColor(BACKGROUND_COLOR);
|
||||
|
||||
ReactInstanceManagerHolder.initReactInstanceManager((Activity) context);
|
||||
}
|
||||
|
||||
/**
|
||||
@@ -171,7 +206,7 @@ public class JitsiMeetView extends BaseReactView<JitsiMeetViewListener>
|
||||
// by leaving the conference. However, React and, respectively,
|
||||
// appProperties/initialProperties are declarative expressions i.e. one
|
||||
// and the same URL will not trigger an automatic re-render in the
|
||||
// JavaScript source code. The workaround implemented bellow introduces
|
||||
// JavaScript source code. The workaround implemented below introduces
|
||||
// "imperativeness" in React Component props by defining a unique value
|
||||
// per setProps() invocation.
|
||||
props.putLong("timestamp", System.currentTimeMillis());
|
||||
@@ -179,46 +214,27 @@ public class JitsiMeetView extends BaseReactView<JitsiMeetViewListener>
|
||||
createReactRootView("App", props);
|
||||
}
|
||||
|
||||
/**
|
||||
* Handler for {@link OngoingConferenceTracker} events.
|
||||
* @param conferenceUrl
|
||||
*/
|
||||
@Override
|
||||
public void onCurrentConferenceChanged(String conferenceUrl) {
|
||||
// This property was introduced in order to address
|
||||
// an exception in the Picture-in-Picture functionality which arose
|
||||
// because of delays related to bridging between JavaScript and Java. To
|
||||
// reduce these delays do not wait for the call to be transferred to the
|
||||
// UI thread.
|
||||
this.url = conferenceUrl;
|
||||
}
|
||||
|
||||
/**
|
||||
* Handler for {@link ExternalAPIModule} events.
|
||||
*
|
||||
* @param name The name of the event.
|
||||
* @param data The details/specifics of the event to send determined
|
||||
* by/associated with the specified {@code name}.
|
||||
*/
|
||||
@Override
|
||||
@Deprecated
|
||||
protected void onExternalAPIEvent(String name, ReadableMap data) {
|
||||
onExternalAPIEvent(LISTENER_METHODS, name, data);
|
||||
}
|
||||
|
||||
@Override
|
||||
protected void onDetachedFromWindow() {
|
||||
dispose();
|
||||
super.onDetachedFromWindow();
|
||||
}
|
||||
|
||||
private void initialize(@NonNull Context context) {
|
||||
// Check if the parent Activity implements JitsiMeetActivityInterface,
|
||||
// otherwise things may go wrong.
|
||||
if (!(context instanceof JitsiMeetActivityInterface)) {
|
||||
throw new RuntimeException("Enclosing Activity must implement JitsiMeetActivityInterface");
|
||||
}
|
||||
/**
|
||||
* Called when the window containing this view gains or loses focus.
|
||||
*
|
||||
* @param hasFocus If the window of this view now has focus, {@code true};
|
||||
* otherwise, {@code false}.
|
||||
*/
|
||||
@Override
|
||||
public void onWindowFocusChanged(boolean hasFocus) {
|
||||
super.onWindowFocusChanged(hasFocus);
|
||||
|
||||
OngoingConferenceTracker.getInstance().addListener(this);
|
||||
// https://github.com/mockingbot/react-native-immersive#restore-immersive-state
|
||||
RNImmersiveModule immersive = RNImmersiveModule.getInstance();
|
||||
|
||||
if (hasFocus && immersive != null) {
|
||||
immersive.emitImmersiveStateChangeEvent();
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@@ -1,51 +0,0 @@
|
||||
/*
|
||||
* Copyright @ 2017-present Atlassian Pty Ltd
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
* You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*/
|
||||
|
||||
package org.jitsi.meet.sdk;
|
||||
|
||||
import java.util.Map;
|
||||
|
||||
/**
|
||||
* Interface for listening to events coming from Jitsi Meet.
|
||||
*/
|
||||
@Deprecated
|
||||
public interface JitsiMeetViewListener {
|
||||
/**
|
||||
* Called when a conference was joined.
|
||||
*
|
||||
* @param data Map with a "url" key with the conference URL.
|
||||
*/
|
||||
void onConferenceJoined(Map<String, Object> data);
|
||||
|
||||
/**
|
||||
* Called when the active conference ends, be it because of user choice or
|
||||
* because of a failure.
|
||||
*
|
||||
* @param data Map with an "error" key with the error and a "url" key with
|
||||
* the conference URL. If the conference finished gracefully no `error`
|
||||
* key will be present. The possible values for "error" are described here:
|
||||
* https://github.com/jitsi/lib-jitsi-meet/blob/master/JitsiConnectionErrors.js
|
||||
* https://github.com/jitsi/lib-jitsi-meet/blob/master/JitsiConferenceErrors.js
|
||||
*/
|
||||
void onConferenceTerminated(Map<String, Object> data);
|
||||
|
||||
/**
|
||||
* Called before the conference is joined.
|
||||
*
|
||||
* @param data Map with a "url" key with the conference URL.
|
||||
*/
|
||||
void onConferenceWillJoin(Map<String, Object> data);
|
||||
}
|
||||
@@ -1,167 +0,0 @@
|
||||
/*
|
||||
* Copyright @ 2018-present Atlassian Pty Ltd
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
* You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*/
|
||||
|
||||
package org.jitsi.meet.sdk;
|
||||
|
||||
import com.facebook.react.bridge.ReadableMap;
|
||||
import com.facebook.react.bridge.ReadableMapKeySetIterator;
|
||||
import com.facebook.react.bridge.UiThreadUtil;
|
||||
|
||||
import java.lang.reflect.InvocationTargetException;
|
||||
import java.lang.reflect.Method;
|
||||
import java.lang.reflect.Modifier;
|
||||
import java.util.HashMap;
|
||||
import java.util.Locale;
|
||||
import java.util.Map;
|
||||
import java.util.regex.Pattern;
|
||||
|
||||
/**
|
||||
* Utility methods for helping with transforming {@link ExternalAPIModule}
|
||||
* events into listener methods. Used with descendants of {@link BaseReactView}.
|
||||
*/
|
||||
@Deprecated
|
||||
public final class ListenerUtils {
|
||||
/**
|
||||
* Extracts the methods defined in a listener and creates a mapping of this
|
||||
* form: event name -> method.
|
||||
*
|
||||
* @param listener - The listener whose methods we want to slurp.
|
||||
* @return A mapping with event names - methods.
|
||||
*/
|
||||
public static Map<String, Method> mapListenerMethods(Class listener) {
|
||||
Map<String, Method> methods = new HashMap<>();
|
||||
|
||||
// Figure out the mapping between the listener methods
|
||||
// and the events i.e. redux action types.
|
||||
Pattern onPattern = Pattern.compile("^on[A-Z]+");
|
||||
Pattern camelcasePattern = Pattern.compile("([a-z0-9]+)([A-Z0-9]+)");
|
||||
|
||||
for (Method method : listener.getDeclaredMethods()) {
|
||||
// * The method must be public (because it is declared by an
|
||||
// interface).
|
||||
// * The method must be/return void.
|
||||
if (!Modifier.isPublic(method.getModifiers())
|
||||
|| !Void.TYPE.equals(method.getReturnType())) {
|
||||
continue;
|
||||
}
|
||||
|
||||
// * The method name must start with "on" followed by a
|
||||
// capital/uppercase letter (in agreement with the camelcase
|
||||
// coding style customary to Java in general and the projects of
|
||||
// the Jitsi community in particular).
|
||||
String name = method.getName();
|
||||
|
||||
if (!onPattern.matcher(name).find()) {
|
||||
continue;
|
||||
}
|
||||
|
||||
// * The method must accept/have exactly 1 parameter of a type
|
||||
// assignable from HashMap.
|
||||
Class<?>[] parameterTypes = method.getParameterTypes();
|
||||
|
||||
if (parameterTypes.length != 1
|
||||
|| !parameterTypes[0].isAssignableFrom(HashMap.class)) {
|
||||
continue;
|
||||
}
|
||||
|
||||
// Convert the method name to an event name.
|
||||
name
|
||||
= camelcasePattern.matcher(name.substring(2))
|
||||
.replaceAll("$1_$2")
|
||||
.toUpperCase(Locale.ROOT);
|
||||
methods.put(name, method);
|
||||
}
|
||||
|
||||
return methods;
|
||||
}
|
||||
|
||||
/**
|
||||
* Executes the right listener method for the given event.
|
||||
* NOTE: This function will run asynchronously on the UI thread.
|
||||
*
|
||||
* @param listener - The listener on which the method will be called.
|
||||
* @param listenerMethods - Mapping with event names and the matching
|
||||
* methods.
|
||||
* @param eventName - Name of the event.
|
||||
* @param eventData - Data associated with the event.
|
||||
*/
|
||||
public static void runListenerMethod(
|
||||
final Object listener,
|
||||
final Map<String, Method> listenerMethods,
|
||||
final String eventName,
|
||||
final ReadableMap eventData) {
|
||||
// Make sure listener methods are invoked on the UI thread. It
|
||||
// was requested by SDK consumers.
|
||||
if (UiThreadUtil.isOnUiThread()) {
|
||||
runListenerMethodOnUiThread(
|
||||
listener, listenerMethods, eventName, eventData);
|
||||
} else {
|
||||
UiThreadUtil.runOnUiThread(new Runnable() {
|
||||
@Override
|
||||
public void run() {
|
||||
runListenerMethodOnUiThread(
|
||||
listener, listenerMethods, eventName, eventData);
|
||||
}
|
||||
});
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Helper companion for {@link ListenerUtils#runListenerMethod} which runs
|
||||
* in the UI thread.
|
||||
*/
|
||||
private static void runListenerMethodOnUiThread(
|
||||
Object listener,
|
||||
Map<String, Method> listenerMethods,
|
||||
String eventName,
|
||||
ReadableMap eventData) {
|
||||
UiThreadUtil.assertOnUiThread();
|
||||
|
||||
Method method = listenerMethods.get(eventName);
|
||||
if (method != null) {
|
||||
try {
|
||||
method.invoke(listener, toHashMap(eventData));
|
||||
} catch (IllegalAccessException e) {
|
||||
throw new RuntimeException(e);
|
||||
} catch (InvocationTargetException e) {
|
||||
throw new RuntimeException(e);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Initializes a new {@code HashMap} instance with the key-value
|
||||
* associations of a specific {@code ReadableMap}.
|
||||
*
|
||||
* @param readableMap the {@code ReadableMap} specifying the key-value
|
||||
* associations with which the new {@code HashMap} instance is to be
|
||||
* initialized.
|
||||
* @return a new {@code HashMap} instance initialized with the key-value
|
||||
* associations of the specified {@code readableMap}.
|
||||
*/
|
||||
private static HashMap<String, Object> toHashMap(ReadableMap readableMap) {
|
||||
HashMap<String, Object> hashMap = new HashMap<>();
|
||||
|
||||
for (ReadableMapKeySetIterator i = readableMap.keySetIterator();
|
||||
i.hasNextKey();) {
|
||||
String key = i.nextKey();
|
||||
|
||||
hashMap.put(key, readableMap.getString(key));
|
||||
}
|
||||
|
||||
return hashMap;
|
||||
}
|
||||
}
|
||||
@@ -43,7 +43,7 @@ class PictureInPictureModule extends ReactContextBaseJavaModule {
|
||||
private static final String TAG = NAME;
|
||||
|
||||
private static boolean isSupported;
|
||||
private boolean isDisabled;
|
||||
private boolean isEnabled;
|
||||
|
||||
public PictureInPictureModule(ReactApplicationContext reactContext) {
|
||||
super(reactContext);
|
||||
@@ -84,7 +84,7 @@ class PictureInPictureModule extends ReactContextBaseJavaModule {
|
||||
*/
|
||||
@TargetApi(Build.VERSION_CODES.O)
|
||||
public void enterPictureInPicture() {
|
||||
if (isDisabled) {
|
||||
if (!isEnabled) {
|
||||
return;
|
||||
}
|
||||
|
||||
@@ -132,8 +132,8 @@ class PictureInPictureModule extends ReactContextBaseJavaModule {
|
||||
}
|
||||
|
||||
@ReactMethod
|
||||
public void setPictureInPictureDisabled(Boolean disabled) {
|
||||
this.isDisabled = disabled;
|
||||
public void setPictureInPictureEnabled(Boolean enabled) {
|
||||
this.isEnabled = enabled;
|
||||
}
|
||||
|
||||
public boolean isPictureInPictureSupported() {
|
||||
|
||||
@@ -193,7 +193,7 @@ class RNConnectionService extends ReactContextBaseJavaModule {
|
||||
* Called by the JS side to update the call's state.
|
||||
*
|
||||
* @param callUUID - the call's UUID.
|
||||
* @param callState - the map which carries infor about the current call's
|
||||
* @param callState - the map which carries info about the current call's
|
||||
* state. See static fields in {@link ConnectionService.ConnectionImpl}
|
||||
* prefixed with "KEY_" for the values supported by the Android
|
||||
* implementation.
|
||||
|
||||
@@ -46,6 +46,8 @@ import java.util.Arrays;
|
||||
import java.util.List;
|
||||
|
||||
class ReactInstanceManagerHolder {
|
||||
private static final String TAG = ReactInstanceManagerHolder.class.getSimpleName();
|
||||
|
||||
/**
|
||||
* FIXME (from linter): Do not place Android context classes in static
|
||||
* fields (static reference to ReactInstanceManager which has field
|
||||
@@ -110,13 +112,11 @@ class ReactInstanceManagerHolder {
|
||||
new com.corbt.keepawake.KCKeepAwakePackage(),
|
||||
new com.facebook.react.shell.MainReactPackage(),
|
||||
new com.reactnativecommunity.clipboard.ClipboardPackage(),
|
||||
new com.giphyreactnativesdk.GiphyReactNativeSdkPackage(),
|
||||
new com.reactnativecommunity.netinfo.NetInfoPackage(),
|
||||
new com.reactnativepagerview.PagerViewPackage(),
|
||||
new com.oblador.performance.PerformancePackage(),
|
||||
new com.reactnativecommunity.slider.ReactSliderPackage(),
|
||||
new com.brentvatne.react.ReactVideoPackage(),
|
||||
new com.swmansion.reanimated.ReanimatedPackage(),
|
||||
new org.reactnative.maskedview.RNCMaskedViewPackage(),
|
||||
new com.reactnativecommunity.webview.RNCWebViewPackage(),
|
||||
new com.kevinresol.react_native_default_preference.RNDefaultPreferencePackage(),
|
||||
@@ -146,6 +146,17 @@ class ReactInstanceManagerHolder {
|
||||
packages.add((ReactPackage)constructor.newInstance());
|
||||
} catch (Exception e) {
|
||||
// Ignore any error, the module is not compiled when LIBRE_BUILD is enabled.
|
||||
Log.d(TAG, "Not loading AmplitudeReactNativePackage");
|
||||
}
|
||||
|
||||
// GiphyReactNativeSdkPackage
|
||||
try {
|
||||
Class<?> giphyPackageClass = Class.forName("com.giphyreactnativesdk.GiphyReactNativeSdkPackage");
|
||||
Constructor constructor = giphyPackageClass.getConstructor();
|
||||
packages.add((ReactPackage)constructor.newInstance());
|
||||
} catch (Exception e) {
|
||||
// Ignore any error, the module is not compiled when LIBRE_BUILD is enabled.
|
||||
Log.d(TAG, "Not loading GiphyReactNativeSdkPackage");
|
||||
}
|
||||
|
||||
// RNGoogleSignInPackage
|
||||
@@ -155,6 +166,7 @@ class ReactInstanceManagerHolder {
|
||||
packages.add((ReactPackage)constructor.newInstance());
|
||||
} catch (Exception e) {
|
||||
// Ignore any error, the module is not compiled when LIBRE_BUILD is enabled.
|
||||
Log.d(TAG, "Not loading RNGoogleSignInPackage");
|
||||
}
|
||||
|
||||
return packages;
|
||||
@@ -240,7 +252,7 @@ class ReactInstanceManagerHolder {
|
||||
return;
|
||||
}
|
||||
|
||||
Log.d(ReactInstanceManagerHolder.class.getCanonicalName(), "initializing RN with Application");
|
||||
Log.d(TAG, "initializing RN with Application");
|
||||
|
||||
reactInstanceManager
|
||||
= ReactInstanceManager.builder()
|
||||
|
||||
3
android/sdk/src/main/res/values/styles.xml
Normal file
3
android/sdk/src/main/res/values/styles.xml
Normal file
@@ -0,0 +1,3 @@
|
||||
<resources>
|
||||
<style name="JitsiMeetActivityStyle" parent="Theme.AppCompat.Light.NoActionBar"/>
|
||||
</resources>
|
||||
@@ -37,8 +37,6 @@ include ':react-native-pager-view'
|
||||
project(':react-native-pager-view').projectDir = new File(rootProject.projectDir, '../node_modules/react-native-pager-view/android')
|
||||
include ':react-native-performance'
|
||||
project(':react-native-performance').projectDir = new File(rootProject.projectDir, '../node_modules/react-native-performance/android')
|
||||
include ':react-native-reanimated'
|
||||
project(':react-native-reanimated').projectDir = new File(rootProject.projectDir, '../node_modules/react-native-reanimated/android')
|
||||
include ':react-native-safe-area-context'
|
||||
project(':react-native-safe-area-context').projectDir = new File(rootProject.projectDir, '../node_modules/react-native-safe-area-context/android')
|
||||
include ':react-native-screens'
|
||||
|
||||
230
conference.js
230
conference.js
@@ -52,7 +52,8 @@ import {
|
||||
onStartMutedPolicyChanged,
|
||||
p2pStatusChanged,
|
||||
sendLocalParticipant,
|
||||
nonParticipantMessageReceived
|
||||
nonParticipantMessageReceived,
|
||||
CONFERENCE_LEAVE_REASONS
|
||||
} from './react/features/base/conference';
|
||||
import {
|
||||
getReplaceParticipant,
|
||||
@@ -137,6 +138,7 @@ import {
|
||||
submitFeedback
|
||||
} from './react/features/feedback';
|
||||
import { maybeSetLobbyChatMessageListener } from './react/features/lobby/actions.any';
|
||||
import { setNoiseSuppressionEnabled } from './react/features/noise-suppression/actions';
|
||||
import {
|
||||
isModerationNotificationDisplayed,
|
||||
showNotification,
|
||||
@@ -158,6 +160,7 @@ import { AudioMixerEffect } from './react/features/stream-effects/audio-mixer/Au
|
||||
import { createPresenterEffect } from './react/features/stream-effects/presenter';
|
||||
import { createRnnoiseProcessor } from './react/features/stream-effects/rnnoise';
|
||||
import { endpointMessageReceived } from './react/features/subtitles';
|
||||
import { handleToggleVideoMuted } from './react/features/toolbox/actions.any';
|
||||
import { muteLocal } from './react/features/video-menu/actions.any';
|
||||
import UIEvents from './service/UI/UIEvents';
|
||||
|
||||
@@ -380,7 +383,7 @@ class ConferenceConnector {
|
||||
// FIXME the conference should be stopped by the library and not by
|
||||
// the app. Both the errors above are unrecoverable from the library
|
||||
// perspective.
|
||||
room.leave().then(() => connection.disconnect());
|
||||
room.leave(CONFERENCE_LEAVE_REASONS.UNRECOVERABLE_ERROR).then(() => connection.disconnect());
|
||||
break;
|
||||
|
||||
case JitsiConferenceErrors.CONFERENCE_MAX_USERS:
|
||||
@@ -463,7 +466,7 @@ function _connectionFailedHandler(error) {
|
||||
_connectionFailedHandler);
|
||||
if (room) {
|
||||
APP.store.dispatch(conferenceWillLeave(room));
|
||||
room.leave();
|
||||
room.leave(CONFERENCE_LEAVE_REASONS.UNRECOVERABLE_ERROR);
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -923,6 +926,35 @@ export default {
|
||||
: isVideoMutedByUser(APP.store);
|
||||
},
|
||||
|
||||
/**
|
||||
* Verify if there is an ongoing system audio sharing session and apply to the provided track
|
||||
* as a AudioMixer effect.
|
||||
*
|
||||
* @param {*} localAudioTrack - track to which system audio track will be applied as an effect, most likely
|
||||
* microphone local audio track.
|
||||
*/
|
||||
async _maybeApplyAudioMixerEffect(localAudioTrack) {
|
||||
|
||||
// At the time of writing this comment there were two separate flows for toggling screen-sharing
|
||||
// and system audio sharing, the first is the legacy method using the functionality from conference.js
|
||||
// the second is used when both sendMultipleVideoStreams and sourceNameSignaling flags are set to true.
|
||||
// The second flow uses functionality from base/conference/middleware.web.js.
|
||||
// We check if system audio sharing was done using the first flow by verifying this._desktopAudioStream and
|
||||
// for the second by checking 'features/screen-share' state.
|
||||
const { desktopAudioTrack } = APP.store.getState()['features/screen-share'];
|
||||
const currentDesktopAudioTrack = this._desktopAudioStream || desktopAudioTrack;
|
||||
|
||||
// If system audio is already being sent, mix it with the provided audio track.
|
||||
if (currentDesktopAudioTrack) {
|
||||
// In case system audio sharing was done in the absence of an initial mic audio track, there is no
|
||||
// AudioMixerEffect so we have to remove system audio track from the room before setting it as an effect.
|
||||
await room.replaceTrack(currentDesktopAudioTrack, null);
|
||||
this._mixerEffect = new AudioMixerEffect(currentDesktopAudioTrack);
|
||||
logger.debug('Mixing new audio track with existing screen audio track.');
|
||||
await localAudioTrack.setEffect(this._mixerEffect);
|
||||
}
|
||||
},
|
||||
|
||||
/**
|
||||
* Simulates toolbar button click for audio mute. Used by shortcuts and API.
|
||||
* @param {boolean} mute true for mute and false for unmute.
|
||||
@@ -976,7 +1008,11 @@ export default {
|
||||
// Rollback the audio muted status by using null track
|
||||
return null;
|
||||
})
|
||||
.then(audioTrack => this.useAudioStream(audioTrack));
|
||||
.then(async audioTrack => {
|
||||
await this._maybeApplyAudioMixerEffect(audioTrack);
|
||||
|
||||
this.useAudioStream(audioTrack);
|
||||
});
|
||||
} else {
|
||||
muteLocalAudio(mute);
|
||||
}
|
||||
@@ -1117,9 +1153,13 @@ export default {
|
||||
* Simulates toolbar button click for video mute. Used by shortcuts and API.
|
||||
* @param {boolean} [showUI] when set to false will not display any error
|
||||
* dialogs in case of media permissions error.
|
||||
* @param {boolean} ensureTrack - True if we want to ensure that a new track is
|
||||
* created if missing.
|
||||
*/
|
||||
toggleVideoMuted(showUI = true) {
|
||||
this.muteVideo(!this.isLocalVideoMuted(), showUI);
|
||||
toggleVideoMuted(showUI = true, ensureTrack = false) {
|
||||
const mute = !this.isLocalVideoMuted();
|
||||
|
||||
APP.store.dispatch(handleToggleVideoMuted(mute, showUI, ensureTrack));
|
||||
},
|
||||
|
||||
/**
|
||||
@@ -1617,12 +1657,26 @@ export default {
|
||||
let promise = _prevMutePresenterVideo = _prevMutePresenterVideo.then(() => {
|
||||
// mute the presenter track if it exists.
|
||||
if (this.localPresenterVideo) {
|
||||
APP.store.dispatch(setVideoMuted(true, MEDIA_TYPE.PRESENTER));
|
||||
return (
|
||||
this.localPresenterVideo.dispose().then(() => {
|
||||
APP.store.dispatch(trackRemoved(this.localPresenterVideo));
|
||||
this.localPresenterVideo = null;
|
||||
})
|
||||
.then(() => {
|
||||
|
||||
return this.localPresenterVideo.dispose().then(() => {
|
||||
APP.store.dispatch(trackRemoved(this.localPresenterVideo));
|
||||
this.localPresenterVideo = null;
|
||||
});
|
||||
// This is needed only for setting the correct muted state in features/base/media.
|
||||
// NOTE: It is important to be executed after we have disposed and removed the presenter track.
|
||||
// This way all the side effects won't be executed and we won't start additional O/A cycle for
|
||||
// replacing the track with video with the one without video. This O/A cycle is not needed since
|
||||
// we are trying to destroy all tracks. Also due to the current async nature of muting the
|
||||
// presenter, the final removal of the screen sharing track (see the code at the end of the
|
||||
// function) can be executed between the removal of the stream with video and adding the
|
||||
// original screen sharing stream to the peer connection. This will lead to a failure to remove
|
||||
// the screen sharing track, compromising the screen sharing state in jitsi-meet and the user
|
||||
// won't be able to turn off the screen sharing.
|
||||
APP.store.dispatch(setVideoMuted(true, MEDIA_TYPE.PRESENTER));
|
||||
})
|
||||
);
|
||||
}
|
||||
});
|
||||
|
||||
@@ -1712,12 +1766,12 @@ export default {
|
||||
return Promise.reject('Cannot toggle screen sharing: not supported.');
|
||||
}
|
||||
|
||||
if (this.isAudioOnly()) {
|
||||
APP.store.dispatch(setAudioOnly(false));
|
||||
}
|
||||
if (toggle) {
|
||||
try {
|
||||
await this._switchToScreenSharing(options);
|
||||
if (this.isAudioOnly()) {
|
||||
APP.store.dispatch(setAudioOnly(false));
|
||||
}
|
||||
|
||||
return;
|
||||
} catch (err) {
|
||||
@@ -1970,6 +2024,11 @@ export default {
|
||||
}
|
||||
|
||||
if (this._desktopAudioStream) {
|
||||
// Noise suppression doesn't work with desktop audio because we can't chain
|
||||
// track effects yet, disable it first.
|
||||
// We need to to wait for the effect to clear first or it might interfere with the audio mixer.
|
||||
await APP.store.dispatch(setNoiseSuppressionEnabled(false));
|
||||
|
||||
const localAudio = getLocalJitsiAudioTrack(APP.store.getState());
|
||||
|
||||
// If there is a localAudio stream, mix in the desktop audio stream captured by the screen sharing
|
||||
@@ -2367,8 +2426,8 @@ export default {
|
||||
APP.UI.addListener(UIEvents.AUDIO_MUTED, muted => {
|
||||
this.muteAudio(muted);
|
||||
});
|
||||
APP.UI.addListener(UIEvents.VIDEO_MUTED, muted => {
|
||||
this.muteVideo(muted);
|
||||
APP.UI.addListener(UIEvents.VIDEO_MUTED, (muted, showUI = false) => {
|
||||
this.muteVideo(muted, showUI);
|
||||
});
|
||||
|
||||
room.addCommandListener(this.commands.defaults.ETHERPAD,
|
||||
@@ -2524,16 +2583,16 @@ export default {
|
||||
return stream;
|
||||
})
|
||||
.then(stream => {
|
||||
logger.log('Switching the local video device.');
|
||||
logger.info(`Switching the local video device to ${cameraDeviceId}.`);
|
||||
|
||||
return this.useVideoStream(stream);
|
||||
})
|
||||
.then(() => {
|
||||
logger.log('Switched local video device.');
|
||||
logger.info(`Switched local video device to ${cameraDeviceId}.`);
|
||||
this._updateVideoDeviceId();
|
||||
})
|
||||
.catch(error => {
|
||||
logger.error(`Switching the local video device failed: ${error}`);
|
||||
logger.error(`Failed to switch to selected camera:${cameraDeviceId}, error:${error}`);
|
||||
|
||||
return APP.store.dispatch(notifyCameraError(error));
|
||||
});
|
||||
@@ -2543,23 +2602,26 @@ export default {
|
||||
|
||||
APP.UI.addListener(
|
||||
UIEvents.AUDIO_DEVICE_CHANGED,
|
||||
micDeviceId => {
|
||||
async micDeviceId => {
|
||||
const audioWasMuted = this.isLocalAudioMuted();
|
||||
|
||||
// When the 'default' mic needs to be selected, we need to
|
||||
// pass the real device id to gUM instead of 'default' in order
|
||||
// to get the correct MediaStreamTrack from chrome because of the
|
||||
// following bug.
|
||||
// https://bugs.chromium.org/p/chromium/issues/detail?id=997689
|
||||
const hasDefaultMicChanged = micDeviceId === 'default';
|
||||
// Disable noise suppression if it was enabled on the previous track.
|
||||
await APP.store.dispatch(setNoiseSuppressionEnabled(false));
|
||||
|
||||
// When the 'default' mic needs to be selected, we need to pass the real device id to gUM instead of
|
||||
// 'default' in order to get the correct MediaStreamTrack from chrome because of the following bug.
|
||||
// https://bugs.chromium.org/p/chromium/issues/detail?id=997689.
|
||||
const isDefaultMicSelected = micDeviceId === 'default';
|
||||
const selectedDeviceId = isDefaultMicSelected
|
||||
? getDefaultDeviceId(APP.store.getState(), 'audioInput')
|
||||
: micDeviceId;
|
||||
|
||||
logger.info(`Switching audio input device to ${selectedDeviceId}`);
|
||||
sendAnalytics(createDeviceChangedEvent('audio', 'input'));
|
||||
createLocalTracksF({
|
||||
devices: [ 'audio' ],
|
||||
cameraDeviceId: null,
|
||||
micDeviceId: hasDefaultMicChanged
|
||||
? getDefaultDeviceId(APP.store.getState(), 'audioInput')
|
||||
: micDeviceId
|
||||
micDeviceId: selectedDeviceId
|
||||
})
|
||||
.then(([ stream ]) => {
|
||||
// if audio was muted before changing the device, mute
|
||||
@@ -2572,62 +2634,31 @@ export default {
|
||||
return stream;
|
||||
})
|
||||
.then(async stream => {
|
||||
// In case screen sharing audio is also shared we mix it with new input stream. The old _mixerEffect
|
||||
// will be cleaned up when the existing track is replaced.
|
||||
if (this._mixerEffect) {
|
||||
this._mixerEffect = new AudioMixerEffect(this._desktopAudioStream);
|
||||
|
||||
await stream.setEffect(this._mixerEffect);
|
||||
}
|
||||
await this._maybeApplyAudioMixerEffect(stream);
|
||||
|
||||
return this.useAudioStream(stream);
|
||||
})
|
||||
.then(() => {
|
||||
const localAudio = getLocalJitsiAudioTrack(APP.store.getState());
|
||||
|
||||
if (localAudio && hasDefaultMicChanged) {
|
||||
if (localAudio && isDefaultMicSelected) {
|
||||
// workaround for the default device to be shown as selected in the
|
||||
// settings even when the real device id was passed to gUM because of the
|
||||
// above mentioned chrome bug.
|
||||
localAudio._realDeviceId = localAudio.deviceId = 'default';
|
||||
}
|
||||
logger.log(`switched local audio device: ${localAudio?.getDeviceId()}`);
|
||||
|
||||
logger.info(`switched local audio input device to: ${selectedDeviceId}`);
|
||||
this._updateAudioDeviceId();
|
||||
})
|
||||
.catch(err => {
|
||||
logger.error(`Failed to switch to selected audio input device ${selectedDeviceId}, error=${err}`);
|
||||
APP.store.dispatch(notifyMicError(err));
|
||||
});
|
||||
}
|
||||
);
|
||||
|
||||
APP.UI.addListener(UIEvents.TOGGLE_AUDIO_ONLY, audioOnly => {
|
||||
|
||||
// FIXME On web video track is stored both in redux and in
|
||||
// 'localVideo' field, video is attempted to be unmuted twice when
|
||||
// turning off the audio only mode. This will crash the app with
|
||||
// 'unmute operation is already in progress'.
|
||||
// Because there's no logic in redux about creating new track in
|
||||
// case unmute when not track exists the things have to go through
|
||||
// muteVideo logic in such case.
|
||||
const tracks = APP.store.getState()['features/base/tracks'];
|
||||
const isTrackInRedux
|
||||
= Boolean(
|
||||
tracks.find(
|
||||
track => track.jitsiTrack
|
||||
&& track.jitsiTrack.getType() === 'video'));
|
||||
|
||||
|
||||
if (isTrackInRedux) {
|
||||
this.muteVideo(audioOnly);
|
||||
}
|
||||
|
||||
// Immediately update the UI by having remote videos and the large
|
||||
// video update themselves instead of waiting for some other event
|
||||
// to cause the update, usually PARTICIPANT_CONN_STATUS_CHANGED.
|
||||
// There is no guarantee another event will trigger the update
|
||||
// immediately and in all situations, for example because a remote
|
||||
// participant is having connection trouble so no status changes.
|
||||
APP.UI.addListener(UIEvents.TOGGLE_AUDIO_ONLY, () => {
|
||||
// Immediately update the UI by having remote videos and the large video update themselves.
|
||||
const displayedUserId = APP.UI.getLargeVideoID();
|
||||
|
||||
if (displayedUserId) {
|
||||
@@ -3033,14 +3064,15 @@ export default {
|
||||
/**
|
||||
* Leaves the room.
|
||||
*
|
||||
* @param {boolean} doDisconnect - Wether leaving the room should also terminate the connection.
|
||||
* @param {boolean} doDisconnect - Whether leaving the room should also terminate the connection.
|
||||
* @param {string} reason - reason for leaving the room.
|
||||
* @returns {Promise}
|
||||
*/
|
||||
async leaveRoom(doDisconnect = true) {
|
||||
async leaveRoom(doDisconnect = true, reason = '') {
|
||||
APP.store.dispatch(conferenceWillLeave(room));
|
||||
|
||||
if (room && room.isJoined()) {
|
||||
return room.leave().finally(() => {
|
||||
return room.leave(reason).finally(() => {
|
||||
if (doDisconnect) {
|
||||
return disconnect();
|
||||
}
|
||||
@@ -3057,34 +3089,12 @@ export default {
|
||||
* @param email {string} the new email
|
||||
*/
|
||||
changeLocalEmail(email = '') {
|
||||
const localParticipant = getLocalParticipant(APP.store.getState());
|
||||
|
||||
const formattedEmail = String(email).trim();
|
||||
|
||||
if (formattedEmail === localParticipant.email) {
|
||||
return;
|
||||
}
|
||||
|
||||
const localId = localParticipant.id;
|
||||
|
||||
APP.store.dispatch(participantUpdated({
|
||||
// XXX Only the local participant is allowed to update without
|
||||
// stating the JitsiConference instance (i.e. participant property
|
||||
// `conference` for a remote participant) because the local
|
||||
// participant is uniquely identified by the very fact that there is
|
||||
// only one local participant.
|
||||
|
||||
id: localId,
|
||||
local: true,
|
||||
email: formattedEmail
|
||||
}));
|
||||
|
||||
APP.store.dispatch(updateSettings({
|
||||
email: formattedEmail
|
||||
}));
|
||||
APP.API.notifyEmailChanged(localId, {
|
||||
email: formattedEmail
|
||||
});
|
||||
|
||||
sendData(commands.EMAIL, formattedEmail);
|
||||
},
|
||||
|
||||
@@ -3093,29 +3103,12 @@ export default {
|
||||
* @param url {string} the new url
|
||||
*/
|
||||
changeLocalAvatarUrl(url = '') {
|
||||
const { avatarURL, id } = getLocalParticipant(APP.store.getState());
|
||||
|
||||
const formattedUrl = String(url).trim();
|
||||
|
||||
if (formattedUrl === avatarURL) {
|
||||
return;
|
||||
}
|
||||
|
||||
APP.store.dispatch(participantUpdated({
|
||||
// XXX Only the local participant is allowed to update without
|
||||
// stating the JitsiConference instance (i.e. participant property
|
||||
// `conference` for a remote participant) because the local
|
||||
// participant is uniquely identified by the very fact that there is
|
||||
// only one local participant.
|
||||
|
||||
id,
|
||||
local: true,
|
||||
avatarURL: formattedUrl
|
||||
}));
|
||||
|
||||
APP.store.dispatch(updateSettings({
|
||||
avatarURL: formattedUrl
|
||||
}));
|
||||
|
||||
sendData(commands.AVATAR_URL, url);
|
||||
},
|
||||
|
||||
@@ -3156,23 +3149,6 @@ export default {
|
||||
*/
|
||||
changeLocalDisplayName(nickname = '') {
|
||||
const formattedNickname = getNormalizedDisplayName(nickname);
|
||||
const { id, name } = getLocalParticipant(APP.store.getState());
|
||||
|
||||
if (formattedNickname === name) {
|
||||
return;
|
||||
}
|
||||
|
||||
APP.store.dispatch(participantUpdated({
|
||||
// XXX Only the local participant is allowed to update without
|
||||
// stating the JitsiConference instance (i.e. participant property
|
||||
// `conference` for a remote participant) because the local
|
||||
// participant is uniquely identified by the very fact that there is
|
||||
// only one local participant.
|
||||
|
||||
id,
|
||||
local: true,
|
||||
name: formattedNickname
|
||||
}));
|
||||
|
||||
APP.store.dispatch(updateSettings({
|
||||
displayName: formattedNickname
|
||||
|
||||
382
config.js
382
config.js
@@ -1,11 +1,27 @@
|
||||
|
||||
/* eslint-disable no-unused-vars, no-var */
|
||||
/* eslint-disable comma-dangle, no-unused-vars, no-var, prefer-template, vars-on-top */
|
||||
|
||||
/*
|
||||
* NOTE: If you add a new option please remember to document it here:
|
||||
* https://jitsi.github.io/handbook/docs/dev-guide/dev-guide-configuration
|
||||
*/
|
||||
|
||||
var subdir = '<!--# echo var="subdir" default="" -->';
|
||||
var subdomain = '<!--# echo var="subdomain" default="" -->';
|
||||
|
||||
if (subdomain) {
|
||||
subdomain = subdomain.substr(0, subdomain.length - 1).split('.')
|
||||
.join('_')
|
||||
.toLowerCase() + '.';
|
||||
}
|
||||
|
||||
// In case of no ssi provided by the webserver, use empty strings
|
||||
if (subdir.startsWith('<!--')) {
|
||||
subdir = '';
|
||||
}
|
||||
if (subdomain.startsWith('<!--')) {
|
||||
subdomain = '';
|
||||
}
|
||||
|
||||
var config = {
|
||||
// Connection
|
||||
//
|
||||
@@ -24,14 +40,14 @@ var config = {
|
||||
// focus: 'focus.jitsi-meet.example.com',
|
||||
|
||||
// XMPP MUC domain. FIXME: use XEP-0030 to discover it.
|
||||
muc: 'conference.jitsi-meet.example.com'
|
||||
muc: 'conference.' + subdomain + 'jitsi-meet.example.com',
|
||||
},
|
||||
|
||||
// BOSH URL. FIXME: use XEP-0156 to discover it.
|
||||
bosh: '//jitsi-meet.example.com/http-bind',
|
||||
bosh: '//jitsi-meet.example.com/' + subdir + 'http-bind',
|
||||
|
||||
// Websocket URL
|
||||
// websocket: 'wss://jitsi-meet.example.com/xmpp-websocket',
|
||||
// websocket: 'wss://jitsi-meet.example.com/' + subdir + 'xmpp-websocket',
|
||||
|
||||
// The real JID of focus participant - can be overridden here
|
||||
// Do not change username - FIXME: Make focus username configurable
|
||||
@@ -52,18 +68,18 @@ var config = {
|
||||
// enableThumbnailReordering: true,
|
||||
|
||||
// Enables XMPP WebSocket (as opposed to BOSH) for the given amount of users.
|
||||
// mobileXmppWsThreshold: 10 // enable XMPP WebSockets on mobile for 10% of the users
|
||||
// mobileXmppWsThreshold: 10, // enable XMPP WebSockets on mobile for 10% of the users
|
||||
|
||||
// P2P test mode disables automatic switching to P2P when there are 2
|
||||
// participants in the conference.
|
||||
// p2pTestMode: false,
|
||||
|
||||
// Enables the test specific features consumed by jitsi-meet-torture
|
||||
// testMode: false
|
||||
// testMode: false,
|
||||
|
||||
// Disables the auto-play behavior of *all* newly created video element.
|
||||
// This is useful when the client runs on a host with limited resources.
|
||||
// noAutoPlayVideo: false
|
||||
// noAutoPlayVideo: false,
|
||||
|
||||
// Enable / disable 500 Kbps bitrate cap on desktop tracks. When enabled,
|
||||
// simulcast is turned off for the desktop share. If presenter is turned
|
||||
@@ -72,17 +88,17 @@ var config = {
|
||||
// the probability for this to be enabled. This setting has been deprecated.
|
||||
// desktopSharingFrameRate.max now determines whether simulcast will be enabled
|
||||
// or disabled for the screenshare.
|
||||
// capScreenshareBitrate: 1 // 0 to disable - deprecated.
|
||||
// capScreenshareBitrate: 1, // 0 to disable - deprecated.
|
||||
|
||||
// Whether to use fake constraints (height: 99999, width: 99999) when calling getDisplayMedia on
|
||||
// Chromium based browsers. This is intended as a workaround for
|
||||
// https://bugs.chromium.org/p/chromium/issues/detail?id=1056311
|
||||
// setScreenSharingResolutionConstraints: true
|
||||
// setScreenSharingResolutionConstraints: true,
|
||||
|
||||
// Enable callstats only for a percentage of users.
|
||||
// This takes a value between 0 and 100 which determines the probability for
|
||||
// the callstats to be enabled.
|
||||
// callStatsThreshold: 5 // enable callstats for 5% of the users.
|
||||
// callStatsThreshold: 5, // enable callstats for 5% of the users.
|
||||
},
|
||||
|
||||
// Feature Flags.
|
||||
@@ -92,7 +108,11 @@ var config = {
|
||||
|
||||
// Enables sending multiple video streams, i.e., camera and desktop tracks can be shared in the conference
|
||||
// separately as two different streams instead of one composite stream.
|
||||
// sendMultipleVideoStreams: false
|
||||
// sendMultipleVideoStreams: false,
|
||||
|
||||
// Signal that this client supports receiving multiple video streams. Without this flag jicofo will enable
|
||||
// multi-stream backward compatibility.
|
||||
receiveMultipleVideoStreams: true,
|
||||
},
|
||||
|
||||
// Disables moderator indicators.
|
||||
@@ -121,7 +141,7 @@ var config = {
|
||||
// Can be either 'recording' - screensharing screenshots are taken
|
||||
// only when the recording is also on,
|
||||
// or 'always' - screensharing screenshots are always taken.
|
||||
// mode: 'recording'
|
||||
// mode: 'recording',
|
||||
// }
|
||||
|
||||
// Disables ICE/UDP by filtering out local and remote UDP candidates in
|
||||
@@ -143,6 +163,7 @@ var config = {
|
||||
|
||||
// Disable measuring of audio levels.
|
||||
// disableAudioLevels: false,
|
||||
|
||||
// audioLevelsInterval: 200,
|
||||
|
||||
// Enabling this will run the lib-jitsi-meet no audio detection module which
|
||||
@@ -178,7 +199,7 @@ var config = {
|
||||
|
||||
// Enabling it (with #params) will disable local audio output of remote
|
||||
// participants and to enable it back a reload is needed.
|
||||
// startSilent: false
|
||||
// startSilent: false,
|
||||
|
||||
// Enables support for opus-red (redundancy for Opus).
|
||||
// enableOpusRed: false,
|
||||
@@ -187,7 +208,7 @@ var config = {
|
||||
// Beware, by doing so, you are disabling echo cancellation, noise suppression and AGC.
|
||||
// audioQuality: {
|
||||
// stereo: false,
|
||||
// opusMaxAverageBitrate: null // Value to fit the 6000 to 510000 range.
|
||||
// opusMaxAverageBitrate: null, // Value to fit the 6000 to 510000 range.
|
||||
// },
|
||||
|
||||
// Video
|
||||
@@ -206,7 +227,7 @@ var config = {
|
||||
// 'role', <- Moderators on top
|
||||
// 'name', <- Alphabetically by name
|
||||
// 'hasLeft', <- The ones that have left in the bottom
|
||||
// ] <- the order of the array elements determines priority
|
||||
// ], <- the order of the array elements determines priority
|
||||
|
||||
// How many participants while in the tile view mode, before the receiving video quality is reduced from HD to SD.
|
||||
// Use -1 to disable.
|
||||
@@ -222,9 +243,9 @@ var config = {
|
||||
// height: {
|
||||
// ideal: 720,
|
||||
// max: 720,
|
||||
// min: 240
|
||||
// }
|
||||
// }
|
||||
// min: 240,
|
||||
// },
|
||||
// },
|
||||
// },
|
||||
|
||||
// Enable / disable simulcast support.
|
||||
@@ -259,7 +280,7 @@ var config = {
|
||||
// Optional desktop sharing frame rate options. Default value: min:5, max:5.
|
||||
// desktopSharingFrameRate: {
|
||||
// min: 5,
|
||||
// max: 5
|
||||
// max: 5,
|
||||
// },
|
||||
|
||||
// This option has been deprecated since it is no longer supported as per the w3c spec.
|
||||
@@ -271,49 +292,107 @@ var config = {
|
||||
|
||||
// Recording
|
||||
|
||||
// Whether to enable file recording or not.
|
||||
// DEPRECATED. Use recordingService.enabled instead.
|
||||
// fileRecordingsEnabled: false,
|
||||
|
||||
// Enable the dropbox integration.
|
||||
// dropbox: {
|
||||
// appKey: '<APP_KEY>' // Specify your app key here.
|
||||
// appKey: '<APP_KEY>', // Specify your app key here.
|
||||
// // A URL to redirect the user to, after authenticating
|
||||
// // by default uses:
|
||||
// // 'https://jitsi-meet.example.com/static/oauth.html'
|
||||
// redirectURI:
|
||||
// 'https://jitsi-meet.example.com/subfolder/static/oauth.html'
|
||||
// 'https://jitsi-meet.example.com/subfolder/static/oauth.html',
|
||||
// },
|
||||
// When integrations like dropbox are enabled only that will be shown,
|
||||
// by enabling fileRecordingsServiceEnabled, we show both the integrations
|
||||
// and the generic recording service (its configuration and storage type
|
||||
// depends on jibri configuration)
|
||||
|
||||
// recordingService: {
|
||||
// // When integrations like dropbox are enabled only that will be shown,
|
||||
// // by enabling fileRecordingsServiceEnabled, we show both the integrations
|
||||
// // and the generic recording service (its configuration and storage type
|
||||
// // depends on jibri configuration)
|
||||
// enabled: false,
|
||||
|
||||
// // Whether to show the possibility to share file recording with other people
|
||||
// // (e.g. meeting participants), based on the actual implementation
|
||||
// // on the backend.
|
||||
// sharingEnabled: false,
|
||||
|
||||
// // Hide the warning that says we only store the recording for 24 hours.
|
||||
// hideStorageWarning: false,
|
||||
// },
|
||||
|
||||
// DEPRECATED. Use recordingService.enabled instead.
|
||||
// fileRecordingsServiceEnabled: false,
|
||||
// Whether to show the possibility to share file recording with other people
|
||||
// (e.g. meeting participants), based on the actual implementation
|
||||
// on the backend.
|
||||
|
||||
// DEPRECATED. Use recordingService.sharingEnabled instead.
|
||||
// fileRecordingsServiceSharingEnabled: false,
|
||||
|
||||
// Whether to enable live streaming or not.
|
||||
// Local recording configuration.
|
||||
// localRecording: {
|
||||
// // Whether to disable local recording or not.
|
||||
// disable: false,
|
||||
|
||||
// // Whether to notify all participants when a participant is recording locally.
|
||||
// notifyAllParticipants: false,
|
||||
|
||||
// // Whether to disable the self recording feature (only local participant streams).
|
||||
// disableSelfRecording: false,
|
||||
// },
|
||||
|
||||
// Customize the Live Streaming dialog. Can be modified for a non-YouTube provider.
|
||||
// liveStreaming: {
|
||||
// // Whether to enable live streaming or not.
|
||||
// enabled: false,
|
||||
// // Terms link
|
||||
// termsLink: 'https://www.youtube.com/t/terms',
|
||||
// // Data privacy link
|
||||
// dataPrivacyLink: 'https://policies.google.com/privacy',
|
||||
// // RegExp string that validates the stream key input field
|
||||
// validatorRegExpString: '^(?:[a-zA-Z0-9]{4}(?:-(?!$)|$)){4}',
|
||||
// // Documentation reference for the live streaming feature.
|
||||
// helpLink: 'https://jitsi.org/live'
|
||||
// },
|
||||
|
||||
// DEPRECATED. Use liveStreaming.enabled instead.
|
||||
// liveStreamingEnabled: false,
|
||||
|
||||
// Transcription (in interface_config,
|
||||
// subtitles and buttons can be configured)
|
||||
// DEPRECATED. Use transcription.enabled instead.
|
||||
// transcribingEnabled: false,
|
||||
|
||||
// If true transcriber will use the application language.
|
||||
// The application language is either explicitly set by participants in their settings or automatically
|
||||
// detected based on the environment, e.g. if the app is opened in a chrome instance which is using french as its
|
||||
// default language then transcriptions for that participant will be in french.
|
||||
// Defaults to true.
|
||||
// DEPRECATED. Use transcription.useAppLanguage instead.
|
||||
// transcribeWithAppLanguage: true,
|
||||
|
||||
// Transcriber language. This settings will only work if "transcribeWithAppLanguage" is explicitly set to false.
|
||||
// Available languages can be found in
|
||||
// ./src/react/features/transcribing/transcriber-langs.json.
|
||||
// DEPRECATED. Use transcription.preferredLanguage instead.
|
||||
// preferredTranscribeLanguage: 'en-US',
|
||||
|
||||
// Enables automatic turning on captions when recording is started
|
||||
// DEPRECATED. Use transcription.autoCaptionOnRecord instead.
|
||||
// autoCaptionOnRecord: false,
|
||||
|
||||
// Transcription options.
|
||||
// transcription: {
|
||||
// // Whether the feature should be enabled or not.
|
||||
// enabled: false,
|
||||
|
||||
// // If true transcriber will use the application language.
|
||||
// // The application language is either explicitly set by participants in their settings or automatically
|
||||
// // detected based on the environment, e.g. if the app is opened in a chrome instance which
|
||||
// // is using french as its default language then transcriptions for that participant will be in french.
|
||||
// // Defaults to true.
|
||||
// useAppLanguage: true,
|
||||
|
||||
// // Transcriber language. This settings will only work if "useAppLanguage"
|
||||
// // is explicitly set to false.
|
||||
// // Available languages can be found in
|
||||
// // ./src/react/features/transcribing/transcriber-langs.json.
|
||||
// preferredLanguage: 'en-US',
|
||||
|
||||
// // Disable start transcription for all participants.
|
||||
// disableStartForAll: false,
|
||||
|
||||
// // Enables automatic turning on captions when recording is started
|
||||
// autoCaptionOnRecord: false,
|
||||
// },
|
||||
|
||||
// Misc
|
||||
|
||||
// Default value for the channel "last N" attribute. -1 for unlimited.
|
||||
@@ -346,7 +425,7 @@ var config = {
|
||||
// 30: 15,
|
||||
// 50: 10,
|
||||
// 70: 5,
|
||||
// 90: 2
|
||||
// 90: 2,
|
||||
// },
|
||||
|
||||
// Provides a way to translate the legacy bridge signaling messages, 'LastNChangedEvent',
|
||||
@@ -375,7 +454,7 @@ var config = {
|
||||
// // This will result in Safari not being able to decode video from endpoints sending VP9 video.
|
||||
// // When set to false, the conference falls back to VP8 whenever there is an endpoint that doesn't support the
|
||||
// // preferred codec and goes back to the preferred codec when that endpoint leaves.
|
||||
// // enforcePreferredCodec: false,
|
||||
// enforcePreferredCodec: false,
|
||||
//
|
||||
// // Provides a way to configure the maximum bitrates that will be enforced on the simulcast streams for
|
||||
// // video tracks. The keys in the object represent the type of the stream (LD, SD or HD) and the values
|
||||
@@ -386,18 +465,18 @@ var config = {
|
||||
// H264: {
|
||||
// low: 200000,
|
||||
// standard: 500000,
|
||||
// high: 1500000
|
||||
// high: 1500000,
|
||||
// },
|
||||
// VP8 : {
|
||||
// low: 200000,
|
||||
// standard: 500000,
|
||||
// high: 1500000
|
||||
// high: 1500000,
|
||||
// },
|
||||
// VP9: {
|
||||
// low: 100000,
|
||||
// standard: 300000,
|
||||
// high: 1200000
|
||||
// }
|
||||
// high: 1200000,
|
||||
// },
|
||||
// },
|
||||
//
|
||||
// // The options can be used to override default thresholds of video thumbnail heights corresponding to
|
||||
@@ -412,19 +491,19 @@ var config = {
|
||||
// // the high quality.
|
||||
// minHeightForQualityLvl: {
|
||||
// 360: 'standard',
|
||||
// 720: 'high'
|
||||
// 720: 'high',
|
||||
// },
|
||||
//
|
||||
// // Provides a way to resize the desktop track to 720p (if it is greater than 720p) before creating a canvas
|
||||
// // for the presenter mode (camera picture-in-picture mode with screenshare).
|
||||
// resizeDesktopForPresenter: false
|
||||
// resizeDesktopForPresenter: false,
|
||||
// },
|
||||
|
||||
// Notification timeouts
|
||||
// notificationTimeouts: {
|
||||
// short: 2500,
|
||||
// medium: 5000,
|
||||
// long: 10000
|
||||
// long: 10000,
|
||||
// },
|
||||
|
||||
// // Options for the recording limit notification.
|
||||
@@ -439,7 +518,7 @@ var config = {
|
||||
// appName: 'Unlimited recordings APP',
|
||||
//
|
||||
// // The URL of the app with unlimited recordings.
|
||||
// appURL: 'https://unlimited.recordings.app.com/'
|
||||
// appURL: 'https://unlimited.recordings.app.com/',
|
||||
// },
|
||||
|
||||
// Disables or enables RTX (RFC 4588) (defaults to false).
|
||||
@@ -539,12 +618,9 @@ var config = {
|
||||
// Hides the email section under profile settings.
|
||||
// hideEmailInSettings: false,
|
||||
|
||||
// Whether or not some features are checked based on token.
|
||||
// enableFeaturesBasedOnToken: false,
|
||||
|
||||
// When enabled the password used for locking a room is restricted to up to the number of digits specified
|
||||
// roomPasswordNumberOfDigits: 10,
|
||||
// default: roomPasswordNumberOfDigits: false,
|
||||
// roomPasswordNumberOfDigits: 10,
|
||||
|
||||
// Message to show the users. Example: 'The service will be down for
|
||||
// maintenance at 01:00 AM GMT,
|
||||
@@ -559,12 +635,16 @@ var config = {
|
||||
// // When 'true', it shows an intermediate page before joining, where the user can configure their devices.
|
||||
// // This replaces `prejoinPageEnabled`.
|
||||
// enabled: true,
|
||||
// // Hides the participant name editing field in the prejoin screen.
|
||||
// // If requireDisplayName is also set as true, a name should still be provided through
|
||||
// // either the jwt or the userInfo from the iframe api init object in order for this to have an effect.
|
||||
// hideDisplayName: false,
|
||||
// // List of buttons to hide from the extra join options dropdown.
|
||||
// hideExtraJoinButtons: ['no-audio', 'by-phone']
|
||||
// hideExtraJoinButtons: ['no-audio', 'by-phone'],
|
||||
// },
|
||||
|
||||
// When 'true', the user cannot edit the display name.
|
||||
// (Mainly useful when used in conjuction with the JWT so the JWT name becomes read only.)
|
||||
// (Mainly useful when used in conjunction with the JWT so the JWT name becomes read only.)
|
||||
// readOnlyName: false,
|
||||
|
||||
// If etherpad integration is enabled, setting this to true will
|
||||
@@ -595,7 +675,7 @@ var config = {
|
||||
// // Defaults to Gravatar.
|
||||
// baseUrl: 'https://www.gravatar.com/avatar/',
|
||||
// // True if Gravatar should be disabled.
|
||||
// disabled: false
|
||||
// disabled: false,
|
||||
// },
|
||||
|
||||
// App name to be displayed in the invitation email subject, as an alternative to
|
||||
@@ -618,6 +698,7 @@ var config = {
|
||||
// 'chat',
|
||||
// 'closedcaptions',
|
||||
// 'desktop',
|
||||
// 'dock-iframe',
|
||||
// 'download',
|
||||
// 'embedmeeting',
|
||||
// 'etherpad',
|
||||
@@ -631,8 +712,7 @@ var config = {
|
||||
// 'linktosalesforce',
|
||||
// 'livestreaming',
|
||||
// 'microphone',
|
||||
// 'mute-everyone',
|
||||
// 'mute-video-everyone',
|
||||
// 'noisesuppression',
|
||||
// 'participants-pane',
|
||||
// 'profile',
|
||||
// 'raisehand',
|
||||
@@ -646,23 +726,23 @@ var config = {
|
||||
// 'stats',
|
||||
// 'tileview',
|
||||
// 'toggle-camera',
|
||||
// 'undock-iframe',
|
||||
// 'videoquality',
|
||||
// '__end'
|
||||
// ],
|
||||
|
||||
// Holds values related to toolbar visibility control.
|
||||
// toolbarConfig: {
|
||||
// // Moved from interfaceConfig.INITIAL_TOOLBAR_TIMEOUT
|
||||
// // The initial numer of miliseconds for the toolbar buttons to be visible on screen.
|
||||
// // The initial number of milliseconds for the toolbar buttons to be visible on screen.
|
||||
// initialTimeout: 20000,
|
||||
// // Moved from interfaceConfig.TOOLBAR_TIMEOUT
|
||||
// // Number of miliseconds for the toolbar buttons to be visible on screen.
|
||||
// // Number of milliseconds for the toolbar buttons to be visible on screen.
|
||||
// timeout: 4000,
|
||||
// // Moved from interfaceConfig.TOOLBAR_ALWAYS_VISIBLE
|
||||
// // Whether toolbar should be always visible or should hide after x miliseconds.
|
||||
// // Whether toolbar should be always visible or should hide after x milliseconds.
|
||||
// alwaysVisible: false,
|
||||
// // Indicates whether the toolbar should still autohide when chat is open
|
||||
// autoHideWhileChatIsOpen: false
|
||||
// autoHideWhileChatIsOpen: false,
|
||||
// },
|
||||
|
||||
// Toolbar buttons which have their click/tap event exposed through the API on
|
||||
@@ -697,6 +777,7 @@ var config = {
|
||||
// 'microphone',
|
||||
// 'mute-everyone',
|
||||
// 'mute-video-everyone',
|
||||
// 'noisesuppression',
|
||||
// 'participants-pane',
|
||||
// 'profile',
|
||||
// {
|
||||
@@ -718,8 +799,7 @@ var config = {
|
||||
// {
|
||||
// key: 'add-passcode',
|
||||
// preventExecution: false
|
||||
// }
|
||||
// '__end'
|
||||
// },
|
||||
// ],
|
||||
|
||||
// List of pre meeting screens buttons to hide. The values must be one or more of the 5 allowed buttons:
|
||||
@@ -742,6 +822,7 @@ var config = {
|
||||
// Application ID and Secret.
|
||||
// callStatsID: '',
|
||||
// callStatsSecret: '',
|
||||
// callstatsStoreLogs: true,
|
||||
|
||||
// The callstats initialize config params as described in the API:
|
||||
// https://docs.callstats.io/docs/javascript#callstatsinitialize-with-app-secret
|
||||
@@ -759,10 +840,10 @@ var config = {
|
||||
// pbxID: "PBX Identifier. Example, walmart.",
|
||||
// pbxExtensionID: "PBX Extension Identifier. Example, 5625.",
|
||||
// fqExtensionID: "Fully qualified Extension Identifier. Example, +71 (US) +5625.",
|
||||
// sessionID: "Session Identifier. Example, session-12-34"
|
||||
// sessionID: "Session Identifier. Example, session-12-34",
|
||||
// },
|
||||
// collectLegacyStats: true, //enables the collection of legacy stats in chrome browser
|
||||
// collectIP: true //enables the collection localIP address
|
||||
// collectIP: true, //enables the collection localIP address
|
||||
// },
|
||||
|
||||
// Enables sending participants' display names to callstats
|
||||
@@ -772,7 +853,7 @@ var config = {
|
||||
// enableEmailInStats: false,
|
||||
|
||||
// faceLandmarks: {
|
||||
// // Enables sharing your face cordinates. Used for centering faces within a video.
|
||||
// // Enables sharing your face coordinates. Used for centering faces within a video.
|
||||
// enableFaceCentering: false,
|
||||
|
||||
// // Enables detecting face expressions and sharing data with other participants
|
||||
@@ -781,11 +862,14 @@ var config = {
|
||||
// // Enables displaying face expressions in speaker stats
|
||||
// enableDisplayFaceExpressions: false,
|
||||
|
||||
// // Enable rtc stats for face landmarks
|
||||
// enableRTCStats: false,
|
||||
|
||||
// // Minimum required face movement percentage threshold for sending new face centering coordinates data.
|
||||
// faceCenteringThreshold: 10,
|
||||
|
||||
// // Miliseconds for processing a new image capture in order to detect face coordinates if they exist.
|
||||
// captureInterval: 100
|
||||
// // Milliseconds for processing a new image capture in order to detect face coordinates if they exist.
|
||||
// captureInterval: 1000,
|
||||
// },
|
||||
|
||||
// Controls the percentage of automatic feedback shown to participants when callstats is enabled.
|
||||
@@ -847,8 +931,8 @@ var config = {
|
||||
stunServers: [
|
||||
|
||||
// { urls: 'stun:jitsi-meet.example.com:3478' },
|
||||
{ urls: 'stun:meet-jit-si-turnrelay.jitsi.net:443' }
|
||||
]
|
||||
{ urls: 'stun:meet-jit-si-turnrelay.jitsi.net:443' },
|
||||
],
|
||||
},
|
||||
|
||||
analytics: {
|
||||
@@ -856,14 +940,18 @@ var config = {
|
||||
// disabled: false,
|
||||
|
||||
// The Google Analytics Tracking ID:
|
||||
// googleAnalyticsTrackingId: 'your-tracking-id-UA-123456-1'
|
||||
// googleAnalyticsTrackingId: 'your-tracking-id-UA-123456-1',
|
||||
|
||||
// Matomo configuration:
|
||||
// matomoEndpoint: 'https://your-matomo-endpoint/',
|
||||
// matomoSiteID: '42',
|
||||
|
||||
// The Amplitude APP Key:
|
||||
// amplitudeAPPKey: '<APP_KEY>'
|
||||
// amplitudeAPPKey: '<APP_KEY>',
|
||||
|
||||
// Obfuscates room name sent to analytics (amplitude, rtcstats)
|
||||
// Default value is false.
|
||||
// obfuscateRoomName: false,
|
||||
|
||||
// Configuration for the rtcstats server:
|
||||
// By enabling rtcstats server every time a conference is joined the rtcstats
|
||||
@@ -871,19 +959,24 @@ var config = {
|
||||
// PeerConnection states along with getStats metrics polled at the specified
|
||||
// interval.
|
||||
// rtcstatsEnabled: false,
|
||||
// rtcstatsStoreLogs: false,
|
||||
|
||||
// In order to enable rtcstats one needs to provide a endpoint url.
|
||||
// rtcstatsEndpoint: wss://rtcstats-server-pilot.jitsi.net/,
|
||||
|
||||
// The interval at which rtcstats will poll getStats, defaults to 1000ms.
|
||||
// The interval at which rtcstats will poll getStats, defaults to 10000ms.
|
||||
// If the value is set to 0 getStats won't be polled and the rtcstats client
|
||||
// will only send data related to RTCPeerConnection events.
|
||||
// rtcstatsPolIInterval: 1000,
|
||||
// rtcstatsPollInterval: 10000,
|
||||
|
||||
// This determines if rtcstats sends the SDP to the rtcstats server or replaces
|
||||
// all SDPs with an empty string instead.
|
||||
// rtcstatsSendSdp: false,
|
||||
|
||||
// Array of script URLs to load as lib-jitsi-meet "analytics handlers".
|
||||
// scriptURLs: [
|
||||
// "libs/analytics-ga.min.js", // google-analytics
|
||||
// "https://example.com/my-custom-analytics.js"
|
||||
// "https://example.com/my-custom-analytics.js",
|
||||
// ],
|
||||
},
|
||||
|
||||
@@ -892,11 +985,11 @@ var config = {
|
||||
|
||||
// Information about the jitsi-meet instance we are connecting to, including
|
||||
// the user region as seen by the server.
|
||||
deploymentInfo: {
|
||||
// shard: "shard1",
|
||||
// region: "europe",
|
||||
// userRegion: "asia"
|
||||
},
|
||||
// deploymentInfo: {
|
||||
// shard: "shard1",
|
||||
// region: "europe",
|
||||
// userRegion: "asia",
|
||||
// },
|
||||
|
||||
// Array<string> of disabled sounds.
|
||||
// Possible values:
|
||||
@@ -939,36 +1032,25 @@ var config = {
|
||||
// chromeExtensionBanner: {
|
||||
// // The chrome extension to be installed address
|
||||
// url: 'https://chrome.google.com/webstore/detail/jitsi-meetings/kglhbbefdnlheedjiejgomgmfplipfeb',
|
||||
// edgeUrl: 'https://microsoftedge.microsoft.com/addons/detail/jitsi-meetings/eeecajlpbgjppibfledfihobcabccihn',
|
||||
|
||||
// // Extensions info which allows checking if they are installed or not
|
||||
// chromeExtensionsInfo: [
|
||||
// {
|
||||
// id: 'kglhbbefdnlheedjiejgomgmfplipfeb',
|
||||
// path: 'jitsi-logo-48x48.png'
|
||||
// }
|
||||
// path: 'jitsi-logo-48x48.png',
|
||||
// },
|
||||
// // Edge extension info
|
||||
// {
|
||||
// id: 'eeecajlpbgjppibfledfihobcabccihn',
|
||||
// path: 'jitsi-logo-48x48.png',
|
||||
// },
|
||||
// ]
|
||||
// },
|
||||
|
||||
// Local Recording
|
||||
//
|
||||
|
||||
// localRecording: {
|
||||
// Enables local recording.
|
||||
// Additionally, 'localrecording' (all lowercase) needs to be added to
|
||||
// the `toolbarButtons`-array for the Local Recording button to show up
|
||||
// on the toolbar.
|
||||
//
|
||||
// enabled: true,
|
||||
//
|
||||
|
||||
// The recording format, can be one of 'ogg', 'flac' or 'wav'.
|
||||
// format: 'flac'
|
||||
//
|
||||
|
||||
// },
|
||||
// e2ee: {
|
||||
// labels,
|
||||
// externallyManagedKey: false
|
||||
// externallyManagedKey: false,
|
||||
// },
|
||||
|
||||
// Options related to end-to-end (participant to participant) ping.
|
||||
@@ -983,9 +1065,9 @@ var config = {
|
||||
// maxConferenceSize: 200,
|
||||
//
|
||||
// // The maximum number of e2e ping messages per second for the whole conference to aim for.
|
||||
// // This is used to contol the pacing of messages in order to reduce the load on the backend.
|
||||
// maxMessagesPerSecond: 250
|
||||
// },
|
||||
// // This is used to control the pacing of messages in order to reduce the load on the backend.
|
||||
// maxMessagesPerSecond: 250,
|
||||
// },
|
||||
|
||||
// If set, will attempt to use the provided video input device label when
|
||||
// triggering a screenshare, instead of proceeding through the normal flow
|
||||
@@ -1011,7 +1093,8 @@ var config = {
|
||||
// Disables all invite functions from the app (share, invite, dial out...etc)
|
||||
// disableInviteFunctions: true,
|
||||
|
||||
// Disables storing the room name to the recents list
|
||||
// Disables storing the room name to the recents list. When in an iframe this is ignored and
|
||||
// the room is never stored in the recents list.
|
||||
// doNotStoreRoom: true,
|
||||
|
||||
// Deployment specific URLs.
|
||||
@@ -1021,7 +1104,7 @@ var config = {
|
||||
// userDocumentationURL: 'https://docs.example.com/video-meetings.html',
|
||||
// // If specified a 'Download our apps' button will be displayed in the overflow menu with a link
|
||||
// // to the specified URL for an app download page.
|
||||
// downloadAppsUrl: 'https://docs.example.com/our-apps.html'
|
||||
// downloadAppsUrl: 'https://docs.example.com/our-apps.html',
|
||||
// },
|
||||
|
||||
// Options related to the remote participant menu.
|
||||
@@ -1033,7 +1116,7 @@ var config = {
|
||||
// // If set to true the 'Grant moderator' button will be disabled.
|
||||
// disableGrantModerator: true,
|
||||
// // If set to true the 'Send private message' button will be disabled.
|
||||
// disablePrivateChat: true
|
||||
// disablePrivateChat: true,
|
||||
// },
|
||||
|
||||
// Endpoint that enables support for salesforce integration with in-meeting resource linking
|
||||
@@ -1049,7 +1132,7 @@ var config = {
|
||||
// disableRemoteMute: true,
|
||||
|
||||
// Enables support for lip-sync for this client (if the browser supports it).
|
||||
// enableLipSync: false
|
||||
// enableLipSync: false,
|
||||
|
||||
/**
|
||||
External API url used to receive branding specific information.
|
||||
@@ -1092,15 +1175,15 @@ var config = {
|
||||
field02Hover: 'red',
|
||||
action01: 'green',
|
||||
action01Hover: 'lightgreen',
|
||||
action02Disabled: 'beige',
|
||||
disabled01: 'beige',
|
||||
success02: 'cadetblue',
|
||||
action02Hover: 'aliceblue'
|
||||
action02Hover: 'aliceblue',
|
||||
},
|
||||
typography: {
|
||||
labelRegular: {
|
||||
fontSize: 25,
|
||||
lineHeight: 30,
|
||||
fontWeight: 500
|
||||
fontWeight: 500,
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -1108,22 +1191,24 @@ var config = {
|
||||
*/
|
||||
// dynamicBrandingUrl: '',
|
||||
|
||||
// Options related to the participants pane.
|
||||
// participantsPane: {
|
||||
// // Hides the moderator settings tab.
|
||||
// hideModeratorSettingsTab: false,
|
||||
// // Hides the more actions button.
|
||||
// hideMoreActionsButton: false,
|
||||
// // Hides the mute all button.
|
||||
// hideMuteAllButton: false,
|
||||
// },
|
||||
|
||||
// Options related to the breakout rooms feature.
|
||||
// breakoutRooms: {
|
||||
// // Hides the add breakout room button. This replaces `hideAddRoomButton`.
|
||||
// hideAddRoomButton: false,
|
||||
// // Hides the auto assign participants button.
|
||||
// hideAutoAssignButton: false,
|
||||
// // Hides the participants pane footer menu.
|
||||
// hideFooterMenu: false,
|
||||
// // Hides the join breakout room button.
|
||||
// hideJoinRoomButton: false,
|
||||
// // Hides the moderator settings tab.
|
||||
// hideModeratorSettingsTab: false,
|
||||
// // Hides the more actions button.
|
||||
// hideMoreActionsButton: false,
|
||||
// // Hides the mute all button.
|
||||
// hideMuteAllButton: false
|
||||
// },
|
||||
|
||||
// When true the user cannot add more images to be used as virtual background.
|
||||
@@ -1162,7 +1247,8 @@ var config = {
|
||||
// 'transcribing',
|
||||
// 'video-quality',
|
||||
// 'insecure-room',
|
||||
// 'highlight-moment'
|
||||
// 'highlight-moment',
|
||||
// 'top-panel-toggle',
|
||||
// ]
|
||||
// },
|
||||
|
||||
@@ -1189,9 +1275,8 @@ var config = {
|
||||
// is not persisting the local storage inside the iframe.
|
||||
// useHostPageLocalStorage: true,
|
||||
|
||||
// etherpad ("shared document") integration.
|
||||
// Etherpad ("shared document") integration.
|
||||
//
|
||||
|
||||
// If set, add a "Open shared document" link to the bottom right menu that
|
||||
// will open an etherpad document.
|
||||
// etherpad_base: 'https://your-etherpad-installati.on/p/',
|
||||
@@ -1298,7 +1383,6 @@ var config = {
|
||||
// 'liveStreaming.unavailableTitle', // shown when livestreaming service is not reachable
|
||||
// 'lobby.joinRejectedMessage', // shown when while in a lobby, user's request to join is rejected
|
||||
// 'lobby.notificationTitle', // shown when lobby is toggled and when join requests are allowed / denied
|
||||
// 'localRecording.localRecording', // shown when a local recording is started
|
||||
// 'notify.chatMessages', // shown when receiving chat messages while the chat window is closed
|
||||
// 'notify.disconnected', // shown when a participant has left
|
||||
// 'notify.connectedOneMember', // show when a participant joined
|
||||
@@ -1308,6 +1392,7 @@ var config = {
|
||||
// 'notify.leftTwoMembers', // show when two participants left simultaneously
|
||||
// 'notify.leftThreePlusMembers', // show when more than 2 participants left simultaneously
|
||||
// 'notify.grantedTo', // shown when moderator rights were granted to a participant
|
||||
// 'notify.hostAskedUnmute', // shown to participant when host asks them to unmute
|
||||
// 'notify.invitedOneMember', // shown when 1 participant has been invited
|
||||
// 'notify.invitedThreePlusMembers', // shown when 3+ participants have been invited
|
||||
// 'notify.invitedTwoMembers', // shown when 2 participants have been invited
|
||||
@@ -1328,7 +1413,7 @@ var config = {
|
||||
// 'notify.raisedHand', // shown when a partcipant used raise hand,
|
||||
// 'notify.startSilentTitle', // shown when user joined with no audio
|
||||
// 'notify.unmute', // shown to moderator when user raises hand during AV moderation
|
||||
// 'notify.hostAskedUnmute', // shown to participant when host asks them to unmute
|
||||
// 'notify.videoMutedRemotelyTitle', // shown when user's video is muted by a remote party,
|
||||
// 'prejoin.errorDialOut',
|
||||
// 'prejoin.errorDialOutDisconnected',
|
||||
// 'prejoin.errorDialOutFailed',
|
||||
@@ -1341,9 +1426,12 @@ var config = {
|
||||
// 'toolbar.noAudioSignalTitle', // shown when a broken mic is detected
|
||||
// 'toolbar.noisyAudioInputTitle', // shown when noise is detected for the current microphone
|
||||
// 'toolbar.talkWhileMutedPopup', // shown when user tries to speak while muted
|
||||
// 'transcribing.failedToStart' // shown when transcribing fails to start
|
||||
// 'transcribing.failedToStart', // shown when transcribing fails to start
|
||||
// ],
|
||||
|
||||
// List of notifications to be disabled. Works in tandem with the above setting.
|
||||
// disabledNotifications: [],
|
||||
|
||||
// Prevent the filmstrip from autohiding when screen width is under a certain threshold
|
||||
// disableFilmstripAutohiding: false,
|
||||
|
||||
@@ -1354,14 +1442,21 @@ var config = {
|
||||
|
||||
// // Disables the stage filmstrip
|
||||
// // (displaying multiple participants on stage besides the vertical filmstrip)
|
||||
// disableStageFilmstrip: false
|
||||
// disableStageFilmstrip: false,
|
||||
|
||||
// // Disables the top panel (only shown when a user is sharing their screen).
|
||||
// disableTopPanel: false,
|
||||
|
||||
// // The minimum number of participants that must be in the call for
|
||||
// // the top panel layout to be used.
|
||||
// minParticipantCountForTopPanel: 50,
|
||||
// },
|
||||
|
||||
// Tile view related config options.
|
||||
// tileView: {
|
||||
// // The optimal number of tiles that are going to be shown in tile view. Depending on the screen size it may
|
||||
// // not be possible to show the exact number of participants specified here.
|
||||
// numberOfVisibleTiles: 25
|
||||
// numberOfVisibleTiles: 25,
|
||||
// },
|
||||
|
||||
// Specifies whether the chat emoticons are disabled or not
|
||||
@@ -1378,15 +1473,24 @@ var config = {
|
||||
// // - chat: show the GIF as a message in chat
|
||||
// // - all: all of the above. This is the default option
|
||||
// displayMode: 'all',
|
||||
// // How long the GIF should be displayed on the tile (in miliseconds).
|
||||
// tileTime: 5000
|
||||
// // How long the GIF should be displayed on the tile (in milliseconds).
|
||||
// tileTime: 5000,
|
||||
// },
|
||||
|
||||
// Allow all above example options to include a trailing comma and
|
||||
// prevent fear when commenting out the last value.
|
||||
makeJsonParserHappy: 'even if last key had a trailing comma'
|
||||
// Logging
|
||||
// logging: {
|
||||
// // Default log level for the app and lib-jitsi-meet.
|
||||
// defaultLogLevel: 'trace',
|
||||
// // Option to disable LogCollector (which stores the logs on CallStats).
|
||||
// //disableLogCollector: true,
|
||||
// // Individual loggers are customizable.
|
||||
// loggers: {
|
||||
// // The following are too verbose in their logging with the default level.
|
||||
// 'modules/RTC/TraceablePeerConnection.js': 'info',
|
||||
// 'modules/statistics/CallStats.js': 'info',
|
||||
// 'modules/xmpp/strophe.util.js': 'log',
|
||||
// },
|
||||
|
||||
// no configuration value should follow this line.
|
||||
// Application logo url
|
||||
// defaultLogoUrl: 'images/watermark.svg',
|
||||
};
|
||||
|
||||
/* eslint-enable no-unused-vars, no-var */
|
||||
|
||||
@@ -8,7 +8,8 @@ import { LoginDialog } from './react/features/authentication/components';
|
||||
import { isTokenAuthEnabled } from './react/features/authentication/functions';
|
||||
import {
|
||||
connectionEstablished,
|
||||
connectionFailed
|
||||
connectionFailed,
|
||||
constructOptions
|
||||
} from './react/features/base/connection/actions';
|
||||
import { openDialog } from './react/features/base/dialog/actions';
|
||||
import { setJWT } from './react/features/base/jwt';
|
||||
@@ -19,7 +20,9 @@ import {
|
||||
import { isFatalJitsiConnectionError } from './react/features/base/lib-jitsi-meet/functions';
|
||||
import { getCustomerDetails } from './react/features/jaas/actions.any';
|
||||
import { isVpaasMeeting, getJaasJWT } from './react/features/jaas/functions';
|
||||
import { setPrejoinDisplayNameRequired } from './react/features/prejoin/actions';
|
||||
import {
|
||||
setPrejoinDisplayNameRequired
|
||||
} from './react/features/prejoin/actions';
|
||||
const logger = Logger.getLogger(__filename);
|
||||
|
||||
/**
|
||||
@@ -81,12 +84,10 @@ function checkForAttachParametersAndConnect(id, password, connection) {
|
||||
* Try to open connection using provided credentials.
|
||||
* @param {string} [id]
|
||||
* @param {string} [password]
|
||||
* @param {string} [roomName]
|
||||
* @returns {Promise<JitsiConnection>} connection if
|
||||
* everything is ok, else error.
|
||||
*/
|
||||
export async function connect(id, password, roomName) {
|
||||
const connectionConfig = Object.assign({}, config);
|
||||
export async function connect(id, password) {
|
||||
const state = APP.store.getState();
|
||||
let { jwt } = state['features/base/jwt'];
|
||||
const { iAmRecorder, iAmSipGateway } = state['features/base/config'];
|
||||
@@ -100,19 +101,7 @@ export async function connect(id, password, roomName) {
|
||||
}
|
||||
}
|
||||
|
||||
// Use Websocket URL for the web app if configured. Note that there is no 'isWeb' check, because there's assumption
|
||||
// that this code executes only on web browsers/electron. This needs to be changed when mobile and web are unified.
|
||||
let serviceUrl = connectionConfig.websocket || connectionConfig.bosh;
|
||||
|
||||
serviceUrl += `?room=${roomName}`;
|
||||
|
||||
connectionConfig.serviceUrl = serviceUrl;
|
||||
|
||||
if (connectionConfig.websocketKeepAliveUrl) {
|
||||
connectionConfig.websocketKeepAliveUrl += `?room=${roomName}`;
|
||||
}
|
||||
|
||||
const connection = new JitsiMeetJS.JitsiConnection(null, jwt, connectionConfig);
|
||||
const connection = new JitsiMeetJS.JitsiConnection(null, jwt, constructOptions(state));
|
||||
|
||||
if (config.iAmRecorder) {
|
||||
connection.addFeature(DISCO_JIBRI_FEATURE);
|
||||
|
||||
@@ -30,12 +30,18 @@
|
||||
height: calc(100% - 70px);
|
||||
}
|
||||
|
||||
#chat-conversation-container {
|
||||
// extract message input height
|
||||
height: calc(100% - 68px);
|
||||
overflow: hidden;
|
||||
position: relative;
|
||||
}
|
||||
|
||||
#chatconversation {
|
||||
box-sizing: border-box;
|
||||
flex: 1;
|
||||
font-size: 10pt;
|
||||
// extract message input height
|
||||
height: calc(100% - 68px);
|
||||
height: 100%;
|
||||
line-height: 20px;
|
||||
overflow: auto;
|
||||
padding: 16px;
|
||||
@@ -119,63 +125,18 @@
|
||||
|
||||
.chat-input-container {
|
||||
padding: 0 16px 16px;
|
||||
|
||||
&.populated {
|
||||
#chat-input {
|
||||
.send-button {
|
||||
background: #1B67EC;
|
||||
cursor: pointer;
|
||||
margin-left: 0.3rem;
|
||||
|
||||
@media (hover: hover) and (pointer: fine) {
|
||||
&:hover {
|
||||
background: #3D82FB;
|
||||
}
|
||||
}
|
||||
|
||||
&:active {
|
||||
background: #0852D4;
|
||||
}
|
||||
|
||||
path {
|
||||
fill: #fff;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
#chat-input {
|
||||
border: 1px solid $chatInputSeparatorColor;
|
||||
display: flex;
|
||||
align-items: flex-end;
|
||||
padding: 4px;
|
||||
border-radius: 3px;
|
||||
|
||||
&:focus-within {
|
||||
border: 1px solid #619CF4;
|
||||
}
|
||||
|
||||
* {
|
||||
background-color: transparent;
|
||||
}
|
||||
position: relative;
|
||||
}
|
||||
|
||||
.send-button-container {
|
||||
display: flex;
|
||||
align-items: center;
|
||||
}
|
||||
|
||||
.send-button {
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
height: 40px;
|
||||
width: 40px;
|
||||
border-radius: 3px;
|
||||
|
||||
path {
|
||||
fill: $chatInputSeparatorColor;
|
||||
}
|
||||
.chat-input {
|
||||
flex: 1;
|
||||
margin-right: 8px;
|
||||
}
|
||||
|
||||
.smiley-button {
|
||||
@@ -395,7 +356,9 @@
|
||||
|
||||
.smiley-input {
|
||||
display: flex;
|
||||
position: relative;
|
||||
position: absolute;
|
||||
top: 0;
|
||||
left: 0;
|
||||
}
|
||||
|
||||
.smileys-panel {
|
||||
@@ -403,7 +366,7 @@
|
||||
box-sizing: border-box;
|
||||
background-color: rgba(0, 0, 0, .6) !important;
|
||||
height: auto;
|
||||
display: none;
|
||||
display: flex;
|
||||
overflow: hidden;
|
||||
position: absolute;
|
||||
width: calc(#{$sidebarWidth} - 32px);
|
||||
@@ -418,11 +381,6 @@
|
||||
*/
|
||||
transition: max-height 0.3s;
|
||||
|
||||
&.show-smileys {
|
||||
display: flex;
|
||||
max-height: 500%;
|
||||
}
|
||||
|
||||
#smileysContainer {
|
||||
background-color: $chatBackgroundColor;
|
||||
border-top: 1px solid $chatInputSeparatorColor;
|
||||
|
||||
112
css/_polls.scss
112
css/_polls.scss
@@ -28,32 +28,23 @@
|
||||
}
|
||||
|
||||
.poll-answer-container {
|
||||
display: flex;
|
||||
padding: 4px;
|
||||
background: #3D3D3D;
|
||||
border-radius: 3px;
|
||||
margin-bottom: 8px;
|
||||
|
||||
@media (max-width: 580px) {
|
||||
&> span {
|
||||
padding: 8px 0;
|
||||
}
|
||||
&> span {
|
||||
padding: 8px 0;
|
||||
}
|
||||
|
||||
svg {
|
||||
margin-top: 6px;
|
||||
}
|
||||
svg {
|
||||
margin-top: 6px;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
.poll-answer-option {
|
||||
font-weight: 400;
|
||||
display: block;
|
||||
margin: 4px;
|
||||
|
||||
@media (max-width: 580px) {
|
||||
font-size: 16px;
|
||||
margin: 11px 8px
|
||||
}
|
||||
}
|
||||
|
||||
.poll-answer-field-list, .poll-answer-list, .poll-result-list {
|
||||
list-style-type: none;
|
||||
padding: 0;
|
||||
@@ -84,11 +75,11 @@ ol.poll-result-list {
|
||||
}
|
||||
|
||||
.poll-create-option-row {
|
||||
display: 'flex';
|
||||
display: flex;
|
||||
margin-bottom: 4;
|
||||
}
|
||||
|
||||
// Needeed to override atlaskit default blue color
|
||||
// Needed to override atlaskit default blue color
|
||||
.poll-create-container .jsYMHu {
|
||||
background: #292929;
|
||||
border-color: #808090;
|
||||
@@ -291,6 +282,10 @@ ol.poll-result-list {
|
||||
h1, strong ,span {
|
||||
color: #fff;
|
||||
}
|
||||
|
||||
button > span {
|
||||
color: inherit;
|
||||
}
|
||||
}
|
||||
|
||||
.poll-create-label {
|
||||
@@ -363,82 +358,3 @@ ol.poll-result-list {
|
||||
.poll-answer-footer {
|
||||
padding: 8px 0 0 0;
|
||||
}
|
||||
|
||||
.poll-button {
|
||||
align-items: center;
|
||||
border: 0;
|
||||
border-radius: 6px;
|
||||
font-size: 14px;
|
||||
font-weight: 600;
|
||||
display: flex;
|
||||
justify-content: center;
|
||||
min-height: 40px;
|
||||
width: 100%;
|
||||
|
||||
&:disabled {
|
||||
cursor: initial;
|
||||
}
|
||||
|
||||
@media (max-width: 580px) {
|
||||
min-height: 48px;
|
||||
}
|
||||
}
|
||||
|
||||
.poll-button-primary {
|
||||
background-color: #0056E0;
|
||||
|
||||
&:hover {
|
||||
background-color: #246FE5;
|
||||
}
|
||||
|
||||
&:active {
|
||||
background-color: #0045B3;
|
||||
}
|
||||
|
||||
&:focus {
|
||||
background-color: #0045B3;
|
||||
border: 3px solid #99BBF3;
|
||||
}
|
||||
|
||||
&:disabled {
|
||||
background-color: #00225A;
|
||||
color: #858585;
|
||||
}
|
||||
}
|
||||
|
||||
.poll-button-secondary {
|
||||
background-color: #3D3D3D;
|
||||
|
||||
&:hover {
|
||||
background-color: #525252;
|
||||
}
|
||||
|
||||
&:active {
|
||||
background-color: #292929;
|
||||
}
|
||||
|
||||
&:focus {
|
||||
background-color: #292929;
|
||||
border: 3px solid #858585;
|
||||
}
|
||||
|
||||
&:disabled {
|
||||
background-color: #141414;
|
||||
color: #858585;
|
||||
}
|
||||
}
|
||||
|
||||
.poll-button-short {
|
||||
max-width: 132px;
|
||||
}
|
||||
|
||||
.poll-button-shortest {
|
||||
max-width: 117px;
|
||||
}
|
||||
|
||||
.poll-button-short,
|
||||
.poll-button-shortest {
|
||||
@media (max-width: 580px) {
|
||||
min-width: 49%;
|
||||
}
|
||||
}
|
||||
|
||||
@@ -19,11 +19,34 @@
|
||||
font-size: 14px;
|
||||
margin-left: 16px;
|
||||
}
|
||||
|
||||
&.space-top {
|
||||
margin-top: 10px;
|
||||
}
|
||||
}
|
||||
|
||||
.recording-header-line {
|
||||
border-top: 1px solid #5e6d7a;
|
||||
padding-top: 32px;
|
||||
padding-top: 16px;
|
||||
margin-top: 16px;
|
||||
}
|
||||
|
||||
.local-recording-warning {
|
||||
margin-top: 8px;
|
||||
display: block;
|
||||
font-size: 14px;
|
||||
line-height: 20px;
|
||||
padding: 8px 16px;
|
||||
|
||||
&.text {
|
||||
color: #fff;
|
||||
background-color: #3D3D3D;
|
||||
}
|
||||
|
||||
&.notification {
|
||||
color: #040404;
|
||||
background-color: #F8AE1A;
|
||||
}
|
||||
}
|
||||
|
||||
.recording-switch-disabled {
|
||||
@@ -40,7 +63,7 @@
|
||||
border-radius: 4px;
|
||||
height: 40px;
|
||||
justify-content: center;
|
||||
width: 56px;
|
||||
width: 42px;
|
||||
}
|
||||
|
||||
.cloud-content-recording-icon-container {
|
||||
@@ -52,7 +75,7 @@
|
||||
}
|
||||
|
||||
.jitsi-recording-header {
|
||||
margin-bottom: 32px;
|
||||
margin-bottom: 16px;
|
||||
}
|
||||
|
||||
.jitsi-content-recording-icon-container-with-switch {
|
||||
|
||||
@@ -12,6 +12,7 @@
|
||||
&#autoHide.with-always-on {
|
||||
overflow: hidden;
|
||||
animation: hideSubject forwards .6s ease-out;
|
||||
margin-left: 4px;
|
||||
|
||||
& > .subject-info-container {
|
||||
justify-content: flex-start;
|
||||
|
||||
@@ -134,6 +134,20 @@
|
||||
}
|
||||
}
|
||||
|
||||
.hangup-menu-button {
|
||||
background-color: $hangupMenuButtonColor;
|
||||
|
||||
@media (hover: hover) and (pointer: fine) {
|
||||
&:hover {
|
||||
background-color: $hangupMenuButtonHoverColor;
|
||||
}
|
||||
}
|
||||
|
||||
svg {
|
||||
fill: #fff;
|
||||
}
|
||||
}
|
||||
|
||||
.profile-button-avatar {
|
||||
align-items: center;
|
||||
}
|
||||
|
||||
@@ -6,6 +6,8 @@
|
||||
$baseFontFamily: -apple-system, BlinkMacSystemFont, 'open_sanslight', 'Helvetica Neue', Helvetica, Arial, sans-serif;
|
||||
$hangupColor:#DD3849;
|
||||
$hangupHoverColor: #F25363;
|
||||
$hangupMenuButtonColor:#0056E0;;
|
||||
$hangupMenuButtonHoverColor: #246FE5;
|
||||
$hangupFontSize: 2em;
|
||||
|
||||
/**
|
||||
|
||||
@@ -68,6 +68,12 @@
|
||||
}
|
||||
.buttons {
|
||||
margin-top: 16px;
|
||||
display: flex;
|
||||
align-items: center;
|
||||
|
||||
&>button:first-child {
|
||||
margin-right: 8px;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@@ -5,8 +5,6 @@
|
||||
.remote-videos {
|
||||
align-items: center;
|
||||
box-sizing: border-box;
|
||||
display: flex;
|
||||
flex-direction: column;
|
||||
overscroll-behavior: contain;
|
||||
}
|
||||
|
||||
|
||||
@@ -112,7 +112,7 @@
|
||||
}
|
||||
|
||||
/**
|
||||
* Remove unnecssary padding that is normally used to prevent horizontal
|
||||
* Remove unnecessary padding that is normally used to prevent horizontal
|
||||
* filmstrip from overlapping the left edge of the screen.
|
||||
*/
|
||||
#filmstripLocalVideo,
|
||||
|
||||
@@ -38,19 +38,6 @@
|
||||
color: #fff;
|
||||
}
|
||||
|
||||
.info-password-input {
|
||||
width: 100%;
|
||||
background-color: #0E1624;
|
||||
border-radius: 3px;
|
||||
border: 2px solid #202B3D;
|
||||
color: inherit;
|
||||
padding-left: 0;
|
||||
}
|
||||
.info-password-input:focus ,
|
||||
.info-password-input:active {
|
||||
border: 2px solid #B8C7E0;
|
||||
}
|
||||
|
||||
.info-password-local {
|
||||
user-select: text;
|
||||
}
|
||||
|
||||
@@ -3,9 +3,7 @@
|
||||
width: 100%;
|
||||
height: 90%;
|
||||
object-fit: contain;
|
||||
}
|
||||
input[type="checkbox"] + svg + span {
|
||||
color: #9FB0CC;
|
||||
margin-bottom: 10px;
|
||||
}
|
||||
|
||||
.separator-line {
|
||||
|
||||
@@ -13,12 +13,14 @@
|
||||
}
|
||||
|
||||
.password {
|
||||
align-items: center;
|
||||
align-items: flex-start;
|
||||
display: flex;
|
||||
justify-content: space-between;
|
||||
justify-content: flex-start;
|
||||
margin-top: 15px;
|
||||
flex-direction: column;
|
||||
|
||||
&-actions {
|
||||
margin-top: 10px;
|
||||
a {
|
||||
cursor: pointer;
|
||||
text-decoration: none;
|
||||
@@ -26,8 +28,8 @@
|
||||
color: #6FB1EA;
|
||||
}
|
||||
|
||||
& > :first-child:not(:last-child) {
|
||||
margin-right: 24px;
|
||||
& > :first-child:not(:last-child) {
|
||||
margin-right: 24px;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@@ -1,5 +1,4 @@
|
||||
@import 'lobby';
|
||||
@import 'premeeting-screens';
|
||||
@import 'prejoin';
|
||||
@import 'prejoin-dialog';
|
||||
@import 'prejoin-third-party';
|
||||
|
||||
@@ -1,118 +0,0 @@
|
||||
.prejoin-dialog {
|
||||
background: #1C2025;
|
||||
box-shadow: 0px 2px 20px rgba(0, 0, 0, 0.5);
|
||||
border-radius: 5px;
|
||||
color: #fff;
|
||||
height: 400px;
|
||||
width: 375px;
|
||||
|
||||
&--small {
|
||||
height: 300;
|
||||
width: 400;
|
||||
}
|
||||
|
||||
&-label {
|
||||
font-size: 15px;
|
||||
line-height: 24px;
|
||||
|
||||
&-num {
|
||||
background: #2b3b4b;
|
||||
border: 1px solid #A4B8D1;
|
||||
border-radius: 50%;
|
||||
color: #fff;
|
||||
display: inline-block;
|
||||
height: 24px;
|
||||
margin-right: 8px;
|
||||
width: 24px;
|
||||
}
|
||||
}
|
||||
|
||||
&-container {
|
||||
align-items: center;
|
||||
background: rgba(0,0,0,0.6);
|
||||
display: flex;
|
||||
height: 100vh;
|
||||
justify-content: center;
|
||||
left: 0;
|
||||
position: absolute;
|
||||
top: 0;
|
||||
width: 100vw;
|
||||
z-index: 3;
|
||||
}
|
||||
|
||||
&-flag {
|
||||
display: inline-block;
|
||||
margin-right: 8px;
|
||||
transform: scale(1.2);
|
||||
}
|
||||
|
||||
&-title {
|
||||
display: inline-block;
|
||||
font-size: 24px;
|
||||
line-height: 32px;
|
||||
}
|
||||
|
||||
&-icon {
|
||||
cursor: pointer;
|
||||
|
||||
> svg {
|
||||
fill: #A4B8D1;
|
||||
}
|
||||
}
|
||||
|
||||
&-btn {
|
||||
width: 309px;
|
||||
}
|
||||
|
||||
&-dialin-container {
|
||||
text-align: center;
|
||||
}
|
||||
|
||||
&-delimiter {
|
||||
background: #5f6266;
|
||||
border: 0;
|
||||
height: 1px;
|
||||
margin: 0;
|
||||
padding: 0;
|
||||
width: 100%;
|
||||
|
||||
&-container {
|
||||
margin: 16px 0 24px 0;
|
||||
position: relative;
|
||||
}
|
||||
|
||||
&-txt-container {
|
||||
position: absolute;
|
||||
text-align: center;
|
||||
top: -8px;
|
||||
width: 100%;
|
||||
}
|
||||
|
||||
&-txt {
|
||||
background: #1C2025;
|
||||
color: #5f6266;
|
||||
font-size: 11px;
|
||||
text-transform: uppercase;
|
||||
padding: 0 8px;
|
||||
}
|
||||
}
|
||||
|
||||
.prejoin-dialog-btn.primary,
|
||||
.action-btn.prejoin-dialog-btn.text {
|
||||
width: 310px;
|
||||
}
|
||||
}
|
||||
|
||||
.prejoin-dialog-callout {
|
||||
padding: 16px;
|
||||
|
||||
&-header {
|
||||
display: flex;
|
||||
justify-content: space-between;
|
||||
margin-bottom: 24px;
|
||||
}
|
||||
|
||||
&-picker {
|
||||
margin: 8px 0 16px 0;
|
||||
}
|
||||
}
|
||||
@@ -3,6 +3,25 @@
|
||||
width: 100%;
|
||||
}
|
||||
|
||||
&-avatar {
|
||||
margin: 8px auto 16px;
|
||||
|
||||
&-name {
|
||||
color: white;
|
||||
font-size: 16px;
|
||||
font-weight: 600;
|
||||
line-height: 26px;
|
||||
margin-bottom: 32px;
|
||||
text-align: center;
|
||||
}
|
||||
|
||||
&-container {
|
||||
align-items: center;
|
||||
display: flex;
|
||||
flex-direction: column;
|
||||
}
|
||||
}
|
||||
|
||||
&-error {
|
||||
background-color: #E04757;
|
||||
border-radius: 6px;
|
||||
|
||||
@@ -101,7 +101,7 @@
|
||||
font-weight: 600;
|
||||
letter-spacing: -0.015;
|
||||
line-height: 36px;
|
||||
margin-bottom: 32px;
|
||||
margin-bottom: 16px;
|
||||
text-align: center;
|
||||
}
|
||||
|
||||
|
||||
4
custom.d.ts
vendored
Normal file
4
custom.d.ts
vendored
Normal file
@@ -0,0 +1,4 @@
|
||||
declare module '*.svg' {
|
||||
const content: any;
|
||||
export default content;
|
||||
}
|
||||
4
debian/control
vendored
4
debian/control
vendored
@@ -33,7 +33,7 @@ Description: Configuration for web serving of Jitsi Meet
|
||||
|
||||
Package: jitsi-meet-prosody
|
||||
Architecture: all
|
||||
Depends: openssl, prosody (>= 0.11.0) | prosody-trunk | prosody-0.12 | prosody-0.11, lua-sec
|
||||
Depends: openssl, prosody (>= 0.11.0) | prosody-trunk | prosody-0.12 | prosody-0.11, lua-sec, lua-basexx, lua-luaossl, lua-cjson, lua-inspect
|
||||
Replaces: jitsi-meet-tokens
|
||||
Description: Prosody configuration for Jitsi Meet
|
||||
Jitsi Meet is a WebRTC JavaScript application that uses Jitsi
|
||||
@@ -47,7 +47,7 @@ Description: Prosody configuration for Jitsi Meet
|
||||
|
||||
Package: jitsi-meet-tokens
|
||||
Architecture: all
|
||||
Depends: ${misc:Depends}, prosody-trunk | prosody-0.11 | prosody-0.12 | prosody (>= 0.11.2), libssl-dev, luarocks, jitsi-meet-prosody, git, lua-basexx
|
||||
Depends: ${misc:Depends}, prosody-trunk | prosody-0.11 | prosody-0.12 | prosody (>= 0.11.2), jitsi-meet-prosody
|
||||
Description: Prosody token authentication plugin for Jitsi Meet
|
||||
|
||||
Package: jitsi-meet-turnserver
|
||||
|
||||
21
debian/jitsi-meet-tokens.postinst
vendored
21
debian/jitsi-meet-tokens.postinst
vendored
@@ -48,34 +48,17 @@ case "$1" in
|
||||
db_stop
|
||||
|
||||
if [ -f "$PROSODY_HOST_CONFIG" ] ; then
|
||||
# Install luajwt (also on update, to make sure we get the latest version).
|
||||
if ! luarocks install luajwtjitsi 3.0-0; then
|
||||
echo "Failed to install luajwtjitsi - try installing it manually"
|
||||
fi
|
||||
|
||||
# search for the token auth, if this is not enabled this is the
|
||||
# first time we install tokens package and needs a config change
|
||||
if ! egrep -q '^\s*authentication\s*=\s*"token"' "$PROSODY_HOST_CONFIG"; then
|
||||
if ! egrep -q '^\s*authentication\s*=\s*"token" -- do not delete me' "$PROSODY_HOST_CONFIG"; then
|
||||
# enable tokens in prosody host config
|
||||
sed -i 's/--plugin_paths/plugin_paths/g' $PROSODY_HOST_CONFIG
|
||||
sed -i 's/authentication = "anonymous"/authentication = "token"/g' $PROSODY_HOST_CONFIG
|
||||
sed -i 's/ --allow_unencrypted_plain_auth/ allow_unencrypted_plain_auth/g' $PROSODY_HOST_CONFIG
|
||||
sed -i 's/authentication = "jitsi-anonymous" -- do not delete me/authentication = "token" -- do not delete me/g' $PROSODY_HOST_CONFIG
|
||||
sed -i "s/ --app_id=\"example_app_id\"/ app_id=\"$APP_ID\"/g" $PROSODY_HOST_CONFIG
|
||||
sed -i "s/ --app_secret=\"example_app_secret\"/ app_secret=\"$APP_SECRET\"/g" $PROSODY_HOST_CONFIG
|
||||
sed -i 's/ --modules_enabled = { "token_verification" }/ modules_enabled = { "token_verification" }/g' $PROSODY_HOST_CONFIG
|
||||
sed -i '/^\s*--\s*"token_verification"/ s/--\s*//' $PROSODY_HOST_CONFIG
|
||||
|
||||
PR10_INSTALL_CHECK="$(dpkg-query -f '${Status}' -W 'prosody-0.10' 2>/dev/null | awk '{print $3}' || true)"
|
||||
PRTRUNK_INSTALL_CHECK="$(dpkg-query -f '${Status}' -W 'prosody-trunk' 2>/dev/null | awk '{print $3}' || true)"
|
||||
PR_VER_INSTALLED=$(dpkg-query -f='${Version}\n' --show prosody 2>/dev/null || true)
|
||||
if [ "$PR10_INSTALL_CHECK" = "installed" ] \
|
||||
|| [ "$PR10_INSTALL_CHECK" = "unpacked" ] \
|
||||
|| [ "$PRTRUNK_INSTALL_CHECK" = "installed" ] \
|
||||
|| [ "$PRTRUNK_INSTALL_CHECK" = "unpacked" ] \
|
||||
|| dpkg --compare-versions "$PR_VER_INSTALLED" lt "0.11" ; then
|
||||
sed -i 's/module:hook_global(/module:hook(/g' /usr/share/jitsi-meet/prosody-plugins/mod_auth_token.lua
|
||||
fi
|
||||
|
||||
if [ -x "/etc/init.d/prosody" ]; then
|
||||
invoke-rc.d prosody restart || true
|
||||
fi
|
||||
|
||||
2
debian/jitsi-meet-tokens.postrm
vendored
2
debian/jitsi-meet-tokens.postrm
vendored
@@ -37,7 +37,7 @@ case "$1" in
|
||||
APP_SECRET=$RET
|
||||
|
||||
# Revert prosody config
|
||||
sed -i 's/authentication = "token"/authentication = "anonymous"/g' $PROSODY_HOST_CONFIG
|
||||
sed -i 's/authentication = "token" -- do not delete me/authentication = "jitsi-anonymous" -- do not delete me/g' $PROSODY_HOST_CONFIG
|
||||
sed -i "s/ app_id=\"$APP_ID\"/ --app_id=\"example_app_id\"/g" $PROSODY_HOST_CONFIG
|
||||
sed -i "s/ app_secret=\"$APP_SECRET\"/ --app_secret=\"example_app_secret\"/g" $PROSODY_HOST_CONFIG
|
||||
sed -i '/^\s*"token_verification"/ s/"token_verification"/-- "token_verification"/' $PROSODY_HOST_CONFIG
|
||||
|
||||
22
debian/jitsi-meet-web-config.postinst
vendored
22
debian/jitsi-meet-web-config.postinst
vendored
@@ -246,6 +246,28 @@ case "$1" in
|
||||
echo ""
|
||||
echo "----------------"
|
||||
|
||||
echo ""
|
||||
echo ""
|
||||
echo " ;dOocd;"
|
||||
echo " .dNMM0dKO."
|
||||
echo " lNMMMKd0K,"
|
||||
echo " .xMMMMNxkNc"
|
||||
echo " dMMMMMkxXc"
|
||||
echo " cNMMMNl.."
|
||||
echo " .kMMMX; Interested in adding telephony to your Jitsi meetings?"
|
||||
echo " ;XMMMO'"
|
||||
echo " lNMMWO' Sign up on https://jaas.8x8.vc/#/components"
|
||||
echo " lNMMM0, and follow the guide in the dev console."
|
||||
echo " lXMMMK:."
|
||||
echo " ;KMMMNKd. 'oo,"
|
||||
echo " 'xNMMMMXkkkkOKOl'"
|
||||
echo " :0WMMMMMMNOkk0Kk,"
|
||||
echo " .cdOWMMMMMWXOkOl"
|
||||
echo " .;dKWMMMMMXc."
|
||||
echo " .,:cll:'"
|
||||
echo ""
|
||||
echo ""
|
||||
|
||||
# and we're done with debconf
|
||||
db_stop
|
||||
;;
|
||||
|
||||
1
debian/jitsi-meet-web.install
vendored
1
debian/jitsi-meet-web.install
vendored
@@ -1,5 +1,4 @@
|
||||
interface_config.js /usr/share/jitsi-meet/
|
||||
logging_config.js /usr/share/jitsi-meet/
|
||||
*.html /usr/share/jitsi-meet/
|
||||
*.ico /usr/share/jitsi-meet/
|
||||
libs /usr/share/jitsi-meet/
|
||||
|
||||
@@ -36,8 +36,7 @@ unlimited_jids = {
|
||||
}
|
||||
|
||||
VirtualHost "jitmeet.example.com"
|
||||
-- enabled = false -- Remove this line to enable this host
|
||||
authentication = "anonymous"
|
||||
authentication = "jitsi-anonymous" -- do not delete me
|
||||
-- Properties below are modified by jitsi-meet-tokens package config
|
||||
-- and authentication above is switched to "token"
|
||||
--app_id="example_app_id"
|
||||
@@ -53,6 +52,7 @@ VirtualHost "jitmeet.example.com"
|
||||
av_moderation_component = "avmoderation.jitmeet.example.com"
|
||||
speakerstats_component = "speakerstats.jitmeet.example.com"
|
||||
conference_duration_component = "conferenceduration.jitmeet.example.com"
|
||||
end_conference_component = "endconference.jitmeet.example.com"
|
||||
-- we need bosh
|
||||
modules_enabled = {
|
||||
"bosh";
|
||||
@@ -61,6 +61,7 @@ VirtualHost "jitmeet.example.com"
|
||||
"speakerstats";
|
||||
"external_services";
|
||||
"conference_duration";
|
||||
"end_conference";
|
||||
"muc_lobby_rooms";
|
||||
"muc_breakout_rooms";
|
||||
"av_moderation";
|
||||
@@ -91,7 +92,6 @@ Component "breakout.jitmeet.example.com" "muc"
|
||||
modules_enabled = {
|
||||
"muc_meeting_id";
|
||||
"muc_domain_mapper";
|
||||
--"token_verification";
|
||||
"muc_rate_limit";
|
||||
"polls";
|
||||
}
|
||||
@@ -125,6 +125,9 @@ Component "speakerstats.jitmeet.example.com" "speakerstats_component"
|
||||
Component "conferenceduration.jitmeet.example.com" "conference_duration_component"
|
||||
muc_component = "conference.jitmeet.example.com"
|
||||
|
||||
Component "endconference.jitmeet.example.com" "end_conference"
|
||||
muc_component = "conference.jitmeet.example.com"
|
||||
|
||||
Component "avmoderation.jitmeet.example.com" "av_moderation_component"
|
||||
muc_component = "conference.jitmeet.example.com"
|
||||
|
||||
@@ -138,14 +141,15 @@ Component "lobby.jitmeet.example.com" "muc"
|
||||
"polls";
|
||||
}
|
||||
|
||||
-- Enabled dial-in for JaaS customers
|
||||
-- Enables dial-in for Jitsi meet components customers
|
||||
-- Note: make sure you have the following packages installed: lua-basexx, liblua5.3-dev, libssl-dev, luarocks
|
||||
-- and execute $ sudo luarocks install luajwtjitsi 3.0-0
|
||||
VirtualHost "jigasi.meet.jitsi"
|
||||
enabled = false -- JaaS customers remove this line
|
||||
enabled = false -- Jitsi meet components customers remove this line
|
||||
modules_enabled = {
|
||||
"ping";
|
||||
"bosh";
|
||||
"muc_password_check";
|
||||
}
|
||||
authentication = "token"
|
||||
app_id = "jitsi";
|
||||
|
||||
@@ -1,8 +1,9 @@
|
||||
server_names_hash_bucket_size 64;
|
||||
|
||||
types {
|
||||
# nginx's default mime.types doesn't include a mapping for wasm
|
||||
# nginx's default mime.types doesn't include a mapping for wasm or wav.
|
||||
application/wasm wasm;
|
||||
audio/wav wav;
|
||||
}
|
||||
upstream prosody {
|
||||
zone upstreams 64K;
|
||||
@@ -73,6 +74,13 @@ server {
|
||||
alias /usr/share/jitsi-meet/libs/external_api.min.js;
|
||||
}
|
||||
|
||||
location = /_api/room-info {
|
||||
proxy_pass http://prosody/room-info?prefix=$prefix&$args;
|
||||
proxy_http_version 1.1;
|
||||
proxy_set_header X-Forwarded-For $remote_addr;
|
||||
proxy_set_header Host $http_host;
|
||||
}
|
||||
|
||||
# ensure all static content can always be found first
|
||||
location ~ ^/(libs|css|static|images|fonts|lang|sounds|connection_optimization|.well-known)/(.*)$
|
||||
{
|
||||
@@ -156,6 +164,14 @@ server {
|
||||
rewrite ^/(.*)$ /xmpp-websocket;
|
||||
}
|
||||
|
||||
location ~ ^/([^/?&:'"]+)/_api/room-info {
|
||||
set $subdomain "$1.";
|
||||
set $subdir "$1/";
|
||||
set $prefix "$1";
|
||||
|
||||
rewrite ^/(.*)$ /_api/room-info;
|
||||
}
|
||||
|
||||
# Anything that didn't match above, and isn't a real file, assume it's a room name and redirect to /
|
||||
location ~ ^/([^/?&:'"]+)/(.*)$ {
|
||||
set $subdomain "$1.";
|
||||
|
||||
BIN
images/downloadLocalRecording.png
Normal file
BIN
images/downloadLocalRecording.png
Normal file
Binary file not shown.
|
After Width: | Height: | Size: 490 B |
@@ -67,7 +67,6 @@
|
||||
"utils.js",
|
||||
"do_external_connect.js",
|
||||
"interface_config.js",
|
||||
"logging_config.js",
|
||||
"lib-jitsi-meet.min.js",
|
||||
"app.bundle.min.js",
|
||||
"all.css"
|
||||
@@ -185,7 +184,6 @@
|
||||
<!--#include virtual="connection_optimization/connection_optimization.html" -->
|
||||
<script src="libs/do_external_connect.min.js?v=1"></script>
|
||||
<script><!--#include virtual="/interface_config.js" --></script>
|
||||
<script><!--#include virtual="/logging_config.js" --></script>
|
||||
<script src="libs/lib-jitsi-meet.min.js?v=139"></script>
|
||||
<script src="libs/app.bundle.min.js?v=139"></script>
|
||||
<!--#include virtual="title.html" -->
|
||||
|
||||
@@ -27,7 +27,6 @@ var interfaceConfig = {
|
||||
CLOSE_PAGE_GUEST_HINT: false, // A html text to be shown to guests on the close page, false disables it
|
||||
|
||||
DEFAULT_BACKGROUND: '#040404',
|
||||
DEFAULT_LOGO_URL: 'images/watermark.svg',
|
||||
DEFAULT_WELCOME_PAGE_LOGO_URL: 'images/watermark.svg',
|
||||
|
||||
DISABLE_DOMINANT_SPEAKER_INDICATOR: false,
|
||||
@@ -90,7 +89,6 @@ var interfaceConfig = {
|
||||
JITSI_WATERMARK_LINK: 'https://jitsi.org',
|
||||
|
||||
LANG_DETECTION: true, // Allow i18n to detect the system language
|
||||
LIVE_STREAMING_HELP_LINK: 'https://jitsi.org/live', // Documentation reference for the live streaming feature.
|
||||
LOCAL_THUMBNAIL_RATIO: 16 / 9, // 16:9
|
||||
|
||||
/**
|
||||
@@ -144,7 +142,7 @@ var interfaceConfig = {
|
||||
RECENT_LIST_ENABLED: true,
|
||||
REMOTE_THUMBNAIL_RATIO: 1, // 1:1
|
||||
|
||||
SETTINGS_SECTIONS: [ 'devices', 'language', 'moderator', 'profile', 'calendar', 'sounds' ],
|
||||
SETTINGS_SECTIONS: [ 'devices', 'language', 'moderator', 'profile', 'calendar', 'sounds', 'more' ],
|
||||
|
||||
/**
|
||||
* Specify which sharing features should be displayed. If the value is not set
|
||||
@@ -242,12 +240,19 @@ var interfaceConfig = {
|
||||
// Please use defaultLocalDisplayName from config.js
|
||||
// DEFAULT_LOCAL_DISPLAY_NAME: 'me',
|
||||
|
||||
// Please use defaultLogoUrl from config.js
|
||||
// DEFAULT_LOGO_URL: 'images/watermark.svg',
|
||||
|
||||
// Please use defaultRemoteDisplayName from config.js
|
||||
// DEFAULT_REMOTE_DISPLAY_NAME: 'Fellow Jitster',
|
||||
|
||||
// Moved to config.js as `toolbarConfig.initialTimeout`.
|
||||
// INITIAL_TOOLBAR_TIMEOUT: 20000,
|
||||
|
||||
// Please use `liveStreaming.helpLink` from config.js
|
||||
// Documentation reference for the live streaming feature.
|
||||
// LIVE_STREAMING_HELP_LINK: 'https://jitsi.org/live',
|
||||
|
||||
// Moved to config.js as `toolbarConfig.alwaysVisible`.
|
||||
// TOOLBAR_ALWAYS_VISIBLE: false,
|
||||
|
||||
|
||||
38
ios/Podfile
38
ios/Podfile
@@ -9,9 +9,9 @@ install! 'cocoapods', :deterministic_uuids => false
|
||||
target 'JitsiMeet' do
|
||||
project 'app/app.xcodeproj'
|
||||
|
||||
pod 'Firebase/Analytics', '~> 6.33.0'
|
||||
pod 'Firebase/Crashlytics', '~> 6.33.0'
|
||||
pod 'Firebase/DynamicLinks', '~> 6.33.0'
|
||||
pod 'Firebase/Analytics', '~> 8.0'
|
||||
pod 'Firebase/Crashlytics', '~> 8.0'
|
||||
pod 'Firebase/DynamicLinks', '~> 8.0'
|
||||
end
|
||||
|
||||
target 'JitsiMeetSDK' do
|
||||
@@ -29,6 +29,14 @@ target 'JitsiMeetSDK' do
|
||||
:app_path => "#{Pod::Config.instance.installation_root}/.."
|
||||
)
|
||||
|
||||
# We use auto linking, but some dependencies are excluded from the lite build
|
||||
# (see react-native.config.js) so we add them here.
|
||||
|
||||
pod 'giphy-react-native-sdk', :path => '../node_modules/@giphy/react-native-sdk'
|
||||
pod 'RNCalendarEvents', :path => '../node_modules/react-native-calendar-events'
|
||||
pod 'RNGoogleSignin', :path => '../node_modules/@react-native-google-signin/google-signin'
|
||||
pod 'RNWatch', :path => '../node_modules/react-native-watch-connectivity'
|
||||
|
||||
# Native pod dependencies
|
||||
#
|
||||
|
||||
@@ -36,6 +44,30 @@ target 'JitsiMeetSDK' do
|
||||
pod 'ObjectiveDropboxOfficial', '6.2.3'
|
||||
end
|
||||
|
||||
target 'JitsiMeetSDKLite' do
|
||||
project 'sdk/sdk.xcodeproj'
|
||||
|
||||
# This is a more lightweight target, which removes some functionality.
|
||||
# Check the react-native.config.js for the list of excluded packages.
|
||||
|
||||
# React Native and its dependencies
|
||||
#
|
||||
|
||||
config = use_native_modules!
|
||||
use_react_native!(
|
||||
:path => config["reactNativePath"],
|
||||
:hermes_enabled => false,
|
||||
:fabric_enabled => false,
|
||||
# An absolute path to your application root.
|
||||
:app_path => "#{Pod::Config.instance.installation_root}/.."
|
||||
)
|
||||
|
||||
# Native pod dependencies
|
||||
#
|
||||
|
||||
pod 'CocoaLumberjack', '3.7.2'
|
||||
end
|
||||
|
||||
post_install do |installer|
|
||||
react_native_post_install(installer)
|
||||
__apply_Xcode_12_5_M1_post_install_workaround(installer)
|
||||
|
||||
223
ios/Podfile.lock
223
ios/Podfile.lock
@@ -21,50 +21,60 @@ PODS:
|
||||
- React-Core (= 0.68.1)
|
||||
- React-jsi (= 0.68.1)
|
||||
- ReactCommon/turbomodule/core (= 0.68.1)
|
||||
- Firebase/Analytics (6.33.0):
|
||||
- Firebase/Analytics (8.15.0):
|
||||
- Firebase/Core
|
||||
- Firebase/Core (6.33.0):
|
||||
- Firebase/Core (8.15.0):
|
||||
- Firebase/CoreOnly
|
||||
- FirebaseAnalytics (= 6.8.3)
|
||||
- Firebase/CoreOnly (6.33.0):
|
||||
- FirebaseCore (= 6.10.3)
|
||||
- Firebase/Crashlytics (6.33.0):
|
||||
- FirebaseAnalytics (~> 8.15.0)
|
||||
- Firebase/CoreOnly (8.15.0):
|
||||
- FirebaseCore (= 8.15.0)
|
||||
- Firebase/Crashlytics (8.15.0):
|
||||
- Firebase/CoreOnly
|
||||
- FirebaseCrashlytics (~> 4.6.1)
|
||||
- Firebase/DynamicLinks (6.33.0):
|
||||
- FirebaseCrashlytics (~> 8.15.0)
|
||||
- Firebase/DynamicLinks (8.15.0):
|
||||
- Firebase/CoreOnly
|
||||
- FirebaseDynamicLinks (~> 4.3.1)
|
||||
- FirebaseAnalytics (6.8.3):
|
||||
- FirebaseCore (~> 6.10)
|
||||
- FirebaseInstallations (~> 1.6)
|
||||
- GoogleAppMeasurement (= 6.8.3)
|
||||
- GoogleUtilities/AppDelegateSwizzler (~> 6.7)
|
||||
- GoogleUtilities/MethodSwizzler (~> 6.7)
|
||||
- GoogleUtilities/Network (~> 6.7)
|
||||
- "GoogleUtilities/NSData+zlib (~> 6.7)"
|
||||
- nanopb (~> 1.30906.0)
|
||||
- FirebaseCore (6.10.3):
|
||||
- FirebaseCoreDiagnostics (~> 1.6)
|
||||
- GoogleUtilities/Environment (~> 6.7)
|
||||
- GoogleUtilities/Logger (~> 6.7)
|
||||
- FirebaseCoreDiagnostics (1.7.0):
|
||||
- GoogleDataTransport (~> 7.4)
|
||||
- GoogleUtilities/Environment (~> 6.7)
|
||||
- GoogleUtilities/Logger (~> 6.7)
|
||||
- nanopb (~> 1.30906.0)
|
||||
- FirebaseCrashlytics (4.6.2):
|
||||
- FirebaseCore (~> 6.10)
|
||||
- FirebaseInstallations (~> 1.6)
|
||||
- GoogleDataTransport (~> 7.2)
|
||||
- nanopb (~> 1.30906.0)
|
||||
- PromisesObjC (~> 1.2)
|
||||
- FirebaseDynamicLinks (4.3.1):
|
||||
- FirebaseCore (~> 6.10)
|
||||
- FirebaseInstallations (1.7.0):
|
||||
- FirebaseCore (~> 6.10)
|
||||
- GoogleUtilities/Environment (~> 6.7)
|
||||
- GoogleUtilities/UserDefaults (~> 6.7)
|
||||
- PromisesObjC (~> 1.2)
|
||||
- FirebaseDynamicLinks (~> 8.15.0)
|
||||
- FirebaseAnalytics (8.15.0):
|
||||
- FirebaseAnalytics/AdIdSupport (= 8.15.0)
|
||||
- FirebaseCore (~> 8.0)
|
||||
- FirebaseInstallations (~> 8.0)
|
||||
- GoogleUtilities/AppDelegateSwizzler (~> 7.7)
|
||||
- GoogleUtilities/MethodSwizzler (~> 7.7)
|
||||
- GoogleUtilities/Network (~> 7.7)
|
||||
- "GoogleUtilities/NSData+zlib (~> 7.7)"
|
||||
- nanopb (~> 2.30908.0)
|
||||
- FirebaseAnalytics/AdIdSupport (8.15.0):
|
||||
- FirebaseCore (~> 8.0)
|
||||
- FirebaseInstallations (~> 8.0)
|
||||
- GoogleAppMeasurement (= 8.15.0)
|
||||
- GoogleUtilities/AppDelegateSwizzler (~> 7.7)
|
||||
- GoogleUtilities/MethodSwizzler (~> 7.7)
|
||||
- GoogleUtilities/Network (~> 7.7)
|
||||
- "GoogleUtilities/NSData+zlib (~> 7.7)"
|
||||
- nanopb (~> 2.30908.0)
|
||||
- FirebaseCore (8.15.0):
|
||||
- FirebaseCoreDiagnostics (~> 8.0)
|
||||
- GoogleUtilities/Environment (~> 7.7)
|
||||
- GoogleUtilities/Logger (~> 7.7)
|
||||
- FirebaseCoreDiagnostics (8.15.0):
|
||||
- GoogleDataTransport (~> 9.1)
|
||||
- GoogleUtilities/Environment (~> 7.7)
|
||||
- GoogleUtilities/Logger (~> 7.7)
|
||||
- nanopb (~> 2.30908.0)
|
||||
- FirebaseCrashlytics (8.15.0):
|
||||
- FirebaseCore (~> 8.0)
|
||||
- FirebaseInstallations (~> 8.0)
|
||||
- GoogleDataTransport (~> 9.1)
|
||||
- GoogleUtilities/Environment (~> 7.7)
|
||||
- nanopb (~> 2.30908.0)
|
||||
- PromisesObjC (< 3.0, >= 1.2)
|
||||
- FirebaseDynamicLinks (8.15.0):
|
||||
- FirebaseCore (~> 8.0)
|
||||
- FirebaseInstallations (8.15.0):
|
||||
- FirebaseCore (~> 8.0)
|
||||
- GoogleUtilities/Environment (~> 7.7)
|
||||
- GoogleUtilities/UserDefaults (~> 7.7)
|
||||
- PromisesObjC (< 3.0, >= 1.2)
|
||||
- fmt (6.2.1)
|
||||
- Giphy (2.1.20):
|
||||
- libwebp
|
||||
@@ -72,36 +82,52 @@ PODS:
|
||||
- Giphy (= 2.1.20)
|
||||
- React-Core
|
||||
- glog (0.3.5)
|
||||
- GoogleAppMeasurement (6.8.3):
|
||||
- GoogleUtilities/AppDelegateSwizzler (~> 6.7)
|
||||
- GoogleUtilities/MethodSwizzler (~> 6.7)
|
||||
- GoogleUtilities/Network (~> 6.7)
|
||||
- "GoogleUtilities/NSData+zlib (~> 6.7)"
|
||||
- nanopb (~> 1.30906.0)
|
||||
- GoogleDataTransport (7.5.1):
|
||||
- nanopb (~> 1.30906.0)
|
||||
- GoogleAppMeasurement (8.15.0):
|
||||
- GoogleAppMeasurement/AdIdSupport (= 8.15.0)
|
||||
- GoogleUtilities/AppDelegateSwizzler (~> 7.7)
|
||||
- GoogleUtilities/MethodSwizzler (~> 7.7)
|
||||
- GoogleUtilities/Network (~> 7.7)
|
||||
- "GoogleUtilities/NSData+zlib (~> 7.7)"
|
||||
- nanopb (~> 2.30908.0)
|
||||
- GoogleAppMeasurement/AdIdSupport (8.15.0):
|
||||
- GoogleAppMeasurement/WithoutAdIdSupport (= 8.15.0)
|
||||
- GoogleUtilities/AppDelegateSwizzler (~> 7.7)
|
||||
- GoogleUtilities/MethodSwizzler (~> 7.7)
|
||||
- GoogleUtilities/Network (~> 7.7)
|
||||
- "GoogleUtilities/NSData+zlib (~> 7.7)"
|
||||
- nanopb (~> 2.30908.0)
|
||||
- GoogleAppMeasurement/WithoutAdIdSupport (8.15.0):
|
||||
- GoogleUtilities/AppDelegateSwizzler (~> 7.7)
|
||||
- GoogleUtilities/MethodSwizzler (~> 7.7)
|
||||
- GoogleUtilities/Network (~> 7.7)
|
||||
- "GoogleUtilities/NSData+zlib (~> 7.7)"
|
||||
- nanopb (~> 2.30908.0)
|
||||
- GoogleDataTransport (9.1.4):
|
||||
- GoogleUtilities/Environment (~> 7.7)
|
||||
- nanopb (< 2.30910.0, >= 2.30908.0)
|
||||
- PromisesObjC (< 3.0, >= 1.2)
|
||||
- GoogleSignIn (6.0.2):
|
||||
- AppAuth (~> 1.4)
|
||||
- GTMAppAuth (~> 1.0)
|
||||
- GTMSessionFetcher/Core (~> 1.1)
|
||||
- GoogleUtilities/AppDelegateSwizzler (6.7.2):
|
||||
- GoogleUtilities/AppDelegateSwizzler (7.7.0):
|
||||
- GoogleUtilities/Environment
|
||||
- GoogleUtilities/Logger
|
||||
- GoogleUtilities/Network
|
||||
- GoogleUtilities/Environment (6.7.2):
|
||||
- PromisesObjC (~> 1.2)
|
||||
- GoogleUtilities/Logger (6.7.2):
|
||||
- GoogleUtilities/Environment (7.7.0):
|
||||
- PromisesObjC (< 3.0, >= 1.2)
|
||||
- GoogleUtilities/Logger (7.7.0):
|
||||
- GoogleUtilities/Environment
|
||||
- GoogleUtilities/MethodSwizzler (6.7.2):
|
||||
- GoogleUtilities/MethodSwizzler (7.7.0):
|
||||
- GoogleUtilities/Logger
|
||||
- GoogleUtilities/Network (6.7.2):
|
||||
- GoogleUtilities/Network (7.7.0):
|
||||
- GoogleUtilities/Logger
|
||||
- "GoogleUtilities/NSData+zlib"
|
||||
- GoogleUtilities/Reachability
|
||||
- "GoogleUtilities/NSData+zlib (6.7.2)"
|
||||
- GoogleUtilities/Reachability (6.7.2):
|
||||
- "GoogleUtilities/NSData+zlib (7.7.0)"
|
||||
- GoogleUtilities/Reachability (7.7.0):
|
||||
- GoogleUtilities/Logger
|
||||
- GoogleUtilities/UserDefaults (6.7.2):
|
||||
- GoogleUtilities/UserDefaults (7.7.0):
|
||||
- GoogleUtilities/Logger
|
||||
- GTMAppAuth (1.2.2):
|
||||
- AppAuth/Core (~> 1.4)
|
||||
@@ -116,13 +142,15 @@ PODS:
|
||||
- libwebp/mux (1.2.1):
|
||||
- libwebp/demux
|
||||
- libwebp/webp (1.2.1)
|
||||
- nanopb (1.30906.0):
|
||||
- nanopb/decode (= 1.30906.0)
|
||||
- nanopb/encode (= 1.30906.0)
|
||||
- nanopb/decode (1.30906.0)
|
||||
- nanopb/encode (1.30906.0)
|
||||
- nanopb (2.30908.0):
|
||||
- nanopb/decode (= 2.30908.0)
|
||||
- nanopb/encode (= 2.30908.0)
|
||||
- nanopb/decode (2.30908.0)
|
||||
- nanopb/encode (2.30908.0)
|
||||
- ObjectiveDropboxOfficial (6.2.3)
|
||||
- PromisesObjC (1.2.12)
|
||||
- PromisesObjC (2.1.1)
|
||||
- PromisesSwift (2.1.1):
|
||||
- PromisesObjC (= 2.1.1)
|
||||
- RCT-Folly (2021.06.28.00-v2):
|
||||
- boost
|
||||
- DoubleConversion
|
||||
@@ -348,12 +376,13 @@ PODS:
|
||||
- React-Core
|
||||
- react-native-splash-screen (3.3.0):
|
||||
- React-Core
|
||||
- react-native-video (5.2.0):
|
||||
- react-native-video (6.0.0-alpha.1):
|
||||
- React-Core
|
||||
- react-native-video/Video (= 5.2.0)
|
||||
- react-native-video/Video (5.2.0):
|
||||
- react-native-video/Video (= 6.0.0-alpha.1)
|
||||
- react-native-video/Video (6.0.0-alpha.1):
|
||||
- PromisesSwift
|
||||
- React-Core
|
||||
- react-native-webrtc (1.100.0):
|
||||
- react-native-webrtc (1.100.1):
|
||||
- React-Core
|
||||
- react-native-webview (11.15.1):
|
||||
- React-Core
|
||||
@@ -439,9 +468,7 @@ PODS:
|
||||
- RNGoogleSignin (7.0.4):
|
||||
- GoogleSignIn (~> 6.0.0)
|
||||
- React-Core
|
||||
- RNReanimated (1.13.4):
|
||||
- React-Core
|
||||
- RNScreens (3.10.1):
|
||||
- RNScreens (3.13.1):
|
||||
- React-Core
|
||||
- React-RCTImage
|
||||
- RNSound (0.11.1):
|
||||
@@ -449,9 +476,9 @@ PODS:
|
||||
- RNSound/Core (= 0.11.1)
|
||||
- RNSound/Core (0.11.1):
|
||||
- React-Core
|
||||
- RNSVG (12.1.0):
|
||||
- React
|
||||
- RNWatch (1.0.4):
|
||||
- RNSVG (12.4.3):
|
||||
- React-Core
|
||||
- RNWatch (1.0.11):
|
||||
- React
|
||||
- Yoga (1.14.0)
|
||||
|
||||
@@ -462,9 +489,9 @@ DEPENDENCIES:
|
||||
- DoubleConversion (from `../node_modules/react-native/third-party-podspecs/DoubleConversion.podspec`)
|
||||
- FBLazyVector (from `../node_modules/react-native/Libraries/FBLazyVector`)
|
||||
- FBReactNativeSpec (from `../node_modules/react-native/React/FBReactNativeSpec`)
|
||||
- Firebase/Analytics (~> 6.33.0)
|
||||
- Firebase/Crashlytics (~> 6.33.0)
|
||||
- Firebase/DynamicLinks (~> 6.33.0)
|
||||
- Firebase/Analytics (~> 8.0)
|
||||
- Firebase/Crashlytics (~> 8.0)
|
||||
- Firebase/DynamicLinks (~> 8.0)
|
||||
- "giphy-react-native-sdk (from `../node_modules/@giphy/react-native-sdk`)"
|
||||
- glog (from `../node_modules/react-native/third-party-podspecs/glog.podspec`)
|
||||
- ObjectiveDropboxOfficial (= 6.2.3)
|
||||
@@ -515,7 +542,6 @@ DEPENDENCIES:
|
||||
- RNDeviceInfo (from `../node_modules/react-native-device-info`)
|
||||
- RNGestureHandler (from `../node_modules/react-native-gesture-handler`)
|
||||
- "RNGoogleSignin (from `../node_modules/@react-native-google-signin/google-signin`)"
|
||||
- RNReanimated (from `../node_modules/react-native-reanimated`)
|
||||
- RNScreens (from `../node_modules/react-native-screens`)
|
||||
- RNSound (from `../node_modules/react-native-sound`)
|
||||
- RNSVG (from `../node_modules/react-native-svg`)
|
||||
@@ -546,6 +572,7 @@ SPEC REPOS:
|
||||
- nanopb
|
||||
- ObjectiveDropboxOfficial
|
||||
- PromisesObjC
|
||||
- PromisesSwift
|
||||
|
||||
EXTERNAL SOURCES:
|
||||
amplitude-react-native:
|
||||
@@ -652,8 +679,6 @@ EXTERNAL SOURCES:
|
||||
:path: "../node_modules/react-native-gesture-handler"
|
||||
RNGoogleSignin:
|
||||
:path: "../node_modules/@react-native-google-signin/google-signin"
|
||||
RNReanimated:
|
||||
:path: "../node_modules/react-native-reanimated"
|
||||
RNScreens:
|
||||
:path: "../node_modules/react-native-screens"
|
||||
RNSound:
|
||||
@@ -674,27 +699,28 @@ SPEC CHECKSUMS:
|
||||
DoubleConversion: 831926d9b8bf8166fd87886c4abab286c2422662
|
||||
FBLazyVector: 2c76493a346ef8cacf1f442926a39f805fffec1f
|
||||
FBReactNativeSpec: 371350f24afa87b6aba606972ec959dcd4a95c9a
|
||||
Firebase: 8db6f2d1b2c5e2984efba4949a145875a8f65fe5
|
||||
FirebaseAnalytics: 5dd088bd2e67bb9d13dbf792d1164ceaf3052193
|
||||
FirebaseCore: d889d9e12535b7f36ac8bfbf1713a0836a3012cd
|
||||
FirebaseCoreDiagnostics: 770ac5958e1372ce67959ae4b4f31d8e127c3ac1
|
||||
FirebaseCrashlytics: 1a747c9cc084a24dc6d9511c991db1cd078154eb
|
||||
FirebaseDynamicLinks: 6eac37d86910382eafb6315d952cc44c9e176094
|
||||
FirebaseInstallations: 466c7b4d1f58fe16707693091da253726a731ed2
|
||||
Firebase: 5f8193dff4b5b7c5d5ef72ae54bb76c08e2b841d
|
||||
FirebaseAnalytics: 7761cbadb00a717d8d0939363eb46041526474fa
|
||||
FirebaseCore: 5743c5785c074a794d35f2fff7ecc254a91e08b1
|
||||
FirebaseCoreDiagnostics: 92e07a649aeb66352b319d43bdd2ee3942af84cb
|
||||
FirebaseCrashlytics: feb07e4e9187be3c23c6a846cce4824e5ce2dd0b
|
||||
FirebaseDynamicLinks: 1dc816ef789c5adac6fede0b46d11478175c70e4
|
||||
FirebaseInstallations: 40bd9054049b2eae9a2c38ef1c3dd213df3605cd
|
||||
fmt: ff9d55029c625d3757ed641535fd4a75fedc7ce9
|
||||
Giphy: b6d5087521d251bb8c99cdc0eb07bbdf86d142d5
|
||||
giphy-react-native-sdk: 7abccf2b52123a0f30ce99da895ab6288023680c
|
||||
glog: 476ee3e89abb49e07f822b48323c51c57124b572
|
||||
GoogleAppMeasurement: 966e88df9d19c15715137bb2ddaf52373f111436
|
||||
GoogleDataTransport: f56af7caa4ed338dc8e138a5d7c5973e66440833
|
||||
GoogleAppMeasurement: 4c19f031220c72464d460c9daa1fb5d1acce958e
|
||||
GoogleDataTransport: 5fffe35792f8b96ec8d6775f5eccd83c998d5a3b
|
||||
GoogleSignIn: fd381840dbe7c1137aa6dc30849a5c3e070c034a
|
||||
GoogleUtilities: 7f2f5a07f888cdb145101d6042bc4422f57e70b3
|
||||
GoogleUtilities: e0913149f6b0625b553d70dae12b49fc62914fd1
|
||||
GTMAppAuth: ad5c2b70b9a8689e1a04033c9369c4915bfcbe89
|
||||
GTMSessionFetcher: 43748f93435c2aa068b1cbe39655aaf600652e91
|
||||
libwebp: 98a37e597e40bfdb4c911fc98f2c53d0b12d05fc
|
||||
nanopb: 59317e09cf1f1a0af72f12af412d54edf52603fc
|
||||
nanopb: a0ba3315591a9ae0a16a309ee504766e90db0c96
|
||||
ObjectiveDropboxOfficial: fe206ce8c0bc49976c249d472db7fdbc53ebbd53
|
||||
PromisesObjC: 3113f7f76903778cf4a0586bd1ab89329a0b7b97
|
||||
PromisesObjC: ab77feca74fa2823e7af4249b8326368e61014cb
|
||||
PromisesSwift: 99fddfe4a0ec88a56486644c0da106694c92a604
|
||||
RCT-Folly: 4d8508a426467c48885f1151029bc15fa5d7b3b8
|
||||
RCTRequired: 00581111c53531e39e3c6346ef0d2c0cf52a5a37
|
||||
RCTTypeSafety: 07e03ee7800e7dd65cba8e52ad0c2edb06c96604
|
||||
@@ -717,8 +743,8 @@ SPEC CHECKSUMS:
|
||||
react-native-safe-area-context: 584dc04881deb49474363f3be89e4ca0e854c057
|
||||
react-native-slider: 6e9b86e76cce4b9e35b3403193a6432ed07e0c81
|
||||
react-native-splash-screen: 4312f786b13a81b5169ef346d76d33bc0c6dc457
|
||||
react-native-video: a4c2635d0802f983594b7057e1bce8f442f0ad28
|
||||
react-native-webrtc: b8f2769386d51a6a8c89778478618fe311226bc3
|
||||
react-native-video: bb6f12a7198db53b261fefb5d609dc77417acc8b
|
||||
react-native-webrtc: 206a0ac12a5633d2ec4605174d7c9f12f0d674b2
|
||||
react-native-webview: ea4899a1056c782afa96dd082179a66cbebf5504
|
||||
React-perflogger: 30ab8d6db10e175626069e742eead3ebe8f24fd5
|
||||
React-RCTActionSheet: 4b45da334a175b24dabe75f856b98fed3dfd6201
|
||||
@@ -740,13 +766,12 @@ SPEC CHECKSUMS:
|
||||
RNDeviceInfo: 0400a6d0c94186d1120c3cbd97b23abc022187a9
|
||||
RNGestureHandler: e5c7cab5f214503dcefd6b2b0cefb050e1f51c4a
|
||||
RNGoogleSignin: c4381751eefd73c552b923ba347a9bfc6f18771c
|
||||
RNReanimated: c1b56d030d1616239861534d9adb531f8cffab68
|
||||
RNScreens: 522705f2e5c9d27efb17f24aceb2bf8335bc7b8e
|
||||
RNScreens: 40a2cb40a02a609938137a1e0acfbf8fc9eebf19
|
||||
RNSound: 27e8268bdb0a1f191f219a33267f7e0445e8d62f
|
||||
RNSVG: ce9d996113475209013317e48b05c21ee988d42e
|
||||
RNWatch: 99637948ec9b5c9ec5a41920642594ad5ba07e80
|
||||
RNSVG: f3b60aeeaa81960e2e0536c3a9eef50b667ef3a9
|
||||
RNWatch: dae6c858a2051dbdcfb00b9a86cf4d90400263b4
|
||||
Yoga: 17cd9a50243093b547c1e539c749928dd68152da
|
||||
|
||||
PODFILE CHECKSUM: bef1335067eaa4e8c558b1248f8ab3948de855bc
|
||||
PODFILE CHECKSUM: a437875b597d999a137c671b1da54153fe31d23f
|
||||
|
||||
COCOAPODS: 1.11.2
|
||||
COCOAPODS: 1.11.3
|
||||
|
||||
@@ -8,11 +8,11 @@
|
||||
<string>applinks:beta.meet.jit.si</string>
|
||||
<string>applinks:meet.jit.si</string>
|
||||
</array>
|
||||
<key>com.apple.developer.siri</key>
|
||||
<true/>
|
||||
<key>com.apple.security.application-groups</key>
|
||||
<array>
|
||||
<string>group.org.jitsi.meet.appgroup</string>
|
||||
</array>
|
||||
<key>com.apple.developer.siri</key>
|
||||
<true/>
|
||||
</dict>
|
||||
</plist>
|
||||
|
||||
@@ -369,6 +369,7 @@
|
||||
DEF4813D224925A2002AD03A /* Copy Google Plist file */,
|
||||
DE11877A21EE09640078D059 /* Setup Google reverse URL handler */,
|
||||
DE4F6D6E22005C0400DE699E /* Setup Dropbox */,
|
||||
4E81688528A408E600F8FA9E /* Update App Entitlements */,
|
||||
0BEA5C491F7B8F73000D0AB4 /* Embed Watch Content */,
|
||||
4EC49B9025BED71300E76218 /* Embed App Extensions */,
|
||||
);
|
||||
@@ -522,6 +523,24 @@
|
||||
shellPath = /bin/sh;
|
||||
shellScript = "../scripts/run-packager.sh\n";
|
||||
};
|
||||
4E81688528A408E600F8FA9E /* Update App Entitlements */ = {
|
||||
isa = PBXShellScriptBuildPhase;
|
||||
buildActionMask = 2147483647;
|
||||
files = (
|
||||
);
|
||||
inputFileListPaths = (
|
||||
);
|
||||
inputPaths = (
|
||||
);
|
||||
name = "Update App Entitlements";
|
||||
outputFileListPaths = (
|
||||
);
|
||||
outputPaths = (
|
||||
);
|
||||
runOnlyForDeploymentPostprocessing = 0;
|
||||
shellPath = /bin/sh;
|
||||
shellScript = "if test \"$PRODUCT_BUNDLE_IDENTIFIER\" = \"com.atlassian.JitsiMeet.ios\"; then\n ENTITLEMENTS_PLIST=\"$PROJECT_DIR/app.entitlements\"\n \n /usr/libexec/PlistBuddy -c \"Add :com.apple.developer.avfoundation.multitasking-camera-access bool 1\" $ENTITLEMENTS_PLIST\nfi\n";
|
||||
};
|
||||
69BC5020DBE393B56BD76636 /* [CP] Check Pods Manifest.lock */ = {
|
||||
isa = PBXShellScriptBuildPhase;
|
||||
buildActionMask = 2147483647;
|
||||
|
||||
@@ -17,7 +17,7 @@
|
||||
<key>CFBundlePackageType</key>
|
||||
<string>$(PRODUCT_BUNDLE_PACKAGE_TYPE)</string>
|
||||
<key>CFBundleShortVersionString</key>
|
||||
<string>22.2.0</string>
|
||||
<string>22.5.1</string>
|
||||
<key>CFBundleVersion</key>
|
||||
<string>1</string>
|
||||
<key>NSExtension</key>
|
||||
|
||||
@@ -107,7 +107,7 @@ extension SocketConnection: StreamDelegate {
|
||||
streamHasSpaceAvailable?()
|
||||
}
|
||||
case .errorOccurred:
|
||||
print("client stream error occured: \(String(describing: aStream.streamError))")
|
||||
print("client stream error occurred: \(String(describing: aStream.streamError))")
|
||||
close()
|
||||
notifyDidClose(error: aStream.streamError)
|
||||
|
||||
|
||||
@@ -17,7 +17,7 @@
|
||||
<key>CFBundlePackageType</key>
|
||||
<string>APPL</string>
|
||||
<key>CFBundleShortVersionString</key>
|
||||
<string>22.2.0</string>
|
||||
<string>22.5.1</string>
|
||||
<key>CFBundleSignature</key>
|
||||
<string>????</string>
|
||||
<key>CFBundleURLTypes</key>
|
||||
|
||||
@@ -17,7 +17,7 @@
|
||||
<key>CFBundlePackageType</key>
|
||||
<string>APPL</string>
|
||||
<key>CFBundleShortVersionString</key>
|
||||
<string>22.2.0</string>
|
||||
<string>22.5.1</string>
|
||||
<key>CFBundleVersion</key>
|
||||
<string>1</string>
|
||||
<key>UISupportedInterfaceOrientations</key>
|
||||
|
||||
@@ -17,7 +17,7 @@
|
||||
<key>CFBundlePackageType</key>
|
||||
<string>XPC!</string>
|
||||
<key>CFBundleShortVersionString</key>
|
||||
<string>22.2.0</string>
|
||||
<string>22.5.1</string>
|
||||
<key>CFBundleVersion</key>
|
||||
<string>1</string>
|
||||
<key>CLKComplicationPrincipalClass</key>
|
||||
|
||||
75
ios/scripts/release-sdk-lite.sh
Executable file
75
ios/scripts/release-sdk-lite.sh
Executable file
@@ -0,0 +1,75 @@
|
||||
#!/bin/bash
|
||||
|
||||
set -e -u
|
||||
|
||||
THIS_DIR=$(cd -P "$(dirname "$(readlink "${BASH_SOURCE[0]}" || echo "${BASH_SOURCE[0]}")")" && pwd)
|
||||
PROJECT_REPO=$(realpath ${THIS_DIR}/../..)
|
||||
RELEASE_REPO=$(realpath ${THIS_DIR}/../../../jitsi-meet-ios-sdk-releases)
|
||||
DEFAULT_SDK_VERSION=$(/usr/libexec/PlistBuddy -c "Print CFBundleShortVersionString" ${THIS_DIR}/../sdk/src/Lite-Info.plist)
|
||||
SDK_VERSION=${OVERRIDE_SDK_VERSION:-${DEFAULT_SDK_VERSION}}
|
||||
DO_GIT_TAG=${GIT_TAG:-0}
|
||||
|
||||
|
||||
echo "Releasing Jitsi Meet SDK Lite ${SDK_VERSION}"
|
||||
|
||||
pushd ${RELEASE_REPO}
|
||||
|
||||
# Generate podspec file
|
||||
cat JitsiMeetSDKLite.podspec.tpl | sed -e s/VERSION/${SDK_VERSION}/g > JitsiMeetSDKLite.podspec
|
||||
|
||||
# Cleanup
|
||||
rm -rf lite/Frameworks/*
|
||||
|
||||
popd
|
||||
|
||||
# Build the SDK
|
||||
pushd ${PROJECT_REPO}
|
||||
rm -rf ios/sdk/out
|
||||
xcodebuild clean \
|
||||
-workspace ios/jitsi-meet.xcworkspace \
|
||||
-scheme JitsiMeetSDKLite
|
||||
xcodebuild archive \
|
||||
-workspace ios/jitsi-meet.xcworkspace \
|
||||
-scheme JitsiMeetSDKLite \
|
||||
-configuration Release \
|
||||
-sdk iphonesimulator \
|
||||
-destination='generic/platform=iOS Simulator' \
|
||||
-archivePath ios/sdk/out/ios-simulator \
|
||||
ENABLE_BITCODE=NO \
|
||||
SKIP_INSTALL=NO \
|
||||
BUILD_LIBRARY_FOR_DISTRIBUTION=YES
|
||||
xcodebuild archive \
|
||||
-workspace ios/jitsi-meet.xcworkspace \
|
||||
-scheme JitsiMeetSDKLite \
|
||||
-configuration Release \
|
||||
-sdk iphoneos \
|
||||
-destination='generic/platform=iOS' \
|
||||
-archivePath ios/sdk/out/ios-device \
|
||||
ENABLE_BITCODE=NO \
|
||||
SKIP_INSTALL=NO \
|
||||
BUILD_LIBRARY_FOR_DISTRIBUTION=YES
|
||||
xcodebuild -create-xcframework \
|
||||
-framework ios/sdk/out/ios-device.xcarchive/Products/Library/Frameworks/JitsiMeetSDK.framework \
|
||||
-framework ios/sdk/out/ios-simulator.xcarchive/Products/Library/Frameworks/JitsiMeetSDK.framework \
|
||||
-output ios/sdk/out/JitsiMeetSDK.xcframework
|
||||
if [[ $DO_GIT_TAG == 1 ]]; then
|
||||
git tag ios-sdk-lite-${SDK_VERSION}
|
||||
fi
|
||||
popd
|
||||
|
||||
pushd ${RELEASE_REPO}
|
||||
|
||||
# Put the new files in the repo
|
||||
cp -a ${PROJECT_REPO}/ios/sdk/out/JitsiMeetSDK.xcframework lite/Frameworks/
|
||||
|
||||
# Add all files to git
|
||||
if [[ $DO_GIT_TAG == 1 ]]; then
|
||||
git add -A .
|
||||
git commit -m "${SDK_VERSION} lite"
|
||||
git tag "lite-${SDK_VERSION}"
|
||||
fi
|
||||
|
||||
popd
|
||||
|
||||
echo "Finished! Don't forget to push the tags and releases repo artifacts."
|
||||
echo "The new pod can be pushed to CocoaPods by doing: pod trunk push JitsiMeetSDKLite.podspec"
|
||||
@@ -22,11 +22,19 @@
|
||||
0BCA49601EC4B6C600B793EE /* POSIX.m in Sources */ = {isa = PBXBuildFile; fileRef = 0BCA495D1EC4B6C600B793EE /* POSIX.m */; };
|
||||
0BCA49611EC4B6C600B793EE /* Proximity.m in Sources */ = {isa = PBXBuildFile; fileRef = 0BCA495E1EC4B6C600B793EE /* Proximity.m */; };
|
||||
0BD906EA1EC0C00300C8C18E /* JitsiMeet.h in Headers */ = {isa = PBXBuildFile; fileRef = 0BD906E81EC0C00300C8C18E /* JitsiMeet.h */; settings = {ATTRIBUTES = (Public, ); }; };
|
||||
3453F4A32680898C4A40E821 /* libPods-JitsiMeetSDK.a in Frameworks */ = {isa = PBXBuildFile; fileRef = 927ED7DF018DE5E12C4C3404 /* libPods-JitsiMeetSDK.a */; };
|
||||
4E51B76425E5345E0038575A /* ScheenshareEventEmiter.h in Headers */ = {isa = PBXBuildFile; fileRef = 4E51B76225E5345E0038575A /* ScheenshareEventEmiter.h */; };
|
||||
4E51B76525E5345E0038575A /* ScheenshareEventEmiter.m in Sources */ = {isa = PBXBuildFile; fileRef = 4E51B76325E5345E0038575A /* ScheenshareEventEmiter.m */; };
|
||||
4EBA6E61286072E300B31882 /* JitsiMeetViewController.h in Headers */ = {isa = PBXBuildFile; fileRef = 4EBA6E5F286072E300B31882 /* JitsiMeetViewController.h */; };
|
||||
4EBA6E62286072E300B31882 /* JitsiMeetViewController.m in Sources */ = {isa = PBXBuildFile; fileRef = 4EBA6E60286072E300B31882 /* JitsiMeetViewController.m */; };
|
||||
4EBA6E652860B1E800B31882 /* JitsiMeetRenderingView.h in Headers */ = {isa = PBXBuildFile; fileRef = 4EBA6E632860B1E800B31882 /* JitsiMeetRenderingView.h */; };
|
||||
4EBA6E662860B1E800B31882 /* JitsiMeetRenderingView.m in Sources */ = {isa = PBXBuildFile; fileRef = 4EBA6E642860B1E800B31882 /* JitsiMeetRenderingView.m */; };
|
||||
4ED4FFF32721B9B90074E620 /* JitsiAudioSession.h in Headers */ = {isa = PBXBuildFile; fileRef = 4ED4FFF12721B9B90074E620 /* JitsiAudioSession.h */; settings = {ATTRIBUTES = (Public, ); }; };
|
||||
4ED4FFF42721B9B90074E620 /* JitsiAudioSession.m in Sources */ = {isa = PBXBuildFile; fileRef = 4ED4FFF22721B9B90074E620 /* JitsiAudioSession.m */; };
|
||||
6F08DF7D4458EE3CF3F36F6D /* libPods-JitsiMeetSDK.a in Frameworks */ = {isa = PBXBuildFile; fileRef = E4376CA6886DE68FD7A4294B /* libPods-JitsiMeetSDK.a */; };
|
||||
4EEC9630286C73A2008705FA /* JitsiMeetView+Private.h in Headers */ = {isa = PBXBuildFile; fileRef = 4EEC962E286C73A2008705FA /* JitsiMeetView+Private.h */; };
|
||||
4EEC9631286C73A2008705FA /* JitsiMeetView+Private.m in Sources */ = {isa = PBXBuildFile; fileRef = 4EEC962F286C73A2008705FA /* JitsiMeetView+Private.m */; };
|
||||
6F08DF7D4458EE3CF3F36F6D /* BuildFile in Frameworks */ = {isa = PBXBuildFile; };
|
||||
9A8EE79C77C17743BB66E8BD /* libPods-JitsiMeetSDKLite.a in Frameworks */ = {isa = PBXBuildFile; fileRef = B46497DE9A95BDF5E312AF48 /* libPods-JitsiMeetSDKLite.a */; };
|
||||
A4A934E9212F3ADB001E9388 /* Dropbox.m in Sources */ = {isa = PBXBuildFile; fileRef = A4A934E8212F3ADB001E9388 /* Dropbox.m */; };
|
||||
C6245F5D2053091D0040BE68 /* image-resize@2x.png in Resources */ = {isa = PBXBuildFile; fileRef = C6245F5B2053091D0040BE68 /* image-resize@2x.png */; };
|
||||
C6245F5E2053091D0040BE68 /* image-resize@3x.png in Resources */ = {isa = PBXBuildFile; fileRef = C6245F5C2053091D0040BE68 /* image-resize@3x.png */; };
|
||||
@@ -41,6 +49,8 @@
|
||||
DE438CDA2350934700DD541D /* JavaScriptSandbox.m in Sources */ = {isa = PBXBuildFile; fileRef = DE438CD82350934700DD541D /* JavaScriptSandbox.m */; };
|
||||
DE65AACA2317FFCD00290BEC /* LogUtils.h in Headers */ = {isa = PBXBuildFile; fileRef = DE65AAC92317FFCD00290BEC /* LogUtils.h */; };
|
||||
DE65AACC2318028300290BEC /* JitsiMeetBaseLogHandler+Private.h in Headers */ = {isa = PBXBuildFile; fileRef = DE65AACB2318028300290BEC /* JitsiMeetBaseLogHandler+Private.h */; };
|
||||
DE66914428BCC1C7007C4533 /* JitsiMeetSDK-Swift.h in Headers */ = {isa = PBXBuildFile; fileRef = DE66914328BCC1C7007C4533 /* JitsiMeetSDK-Swift.h */; };
|
||||
DE66914528BCC1C7007C4533 /* JitsiMeetSDK-Swift.h in Headers */ = {isa = PBXBuildFile; fileRef = DE66914328BCC1C7007C4533 /* JitsiMeetSDK-Swift.h */; };
|
||||
DE762DB422AFDE76000DEBD6 /* JitsiMeetUserInfo.h in Headers */ = {isa = PBXBuildFile; fileRef = DE762DB322AFDE76000DEBD6 /* JitsiMeetUserInfo.h */; settings = {ATTRIBUTES = (Public, ); }; };
|
||||
DE762DB622AFDE8D000DEBD6 /* JitsiMeetUserInfo.m in Sources */ = {isa = PBXBuildFile; fileRef = DE762DB522AFDE8D000DEBD6 /* JitsiMeetUserInfo.m */; };
|
||||
DE81A2D42316AC4D00AE1940 /* JitsiMeetLogger.h in Headers */ = {isa = PBXBuildFile; fileRef = DE81A2D22316AC4D00AE1940 /* JitsiMeetLogger.h */; settings = {ATTRIBUTES = (Public, ); }; };
|
||||
@@ -48,6 +58,58 @@
|
||||
DE81A2D92316AC7600AE1940 /* LogBridge.m in Sources */ = {isa = PBXBuildFile; fileRef = DE81A2D72316AC7600AE1940 /* LogBridge.m */; };
|
||||
DE81A2DE2317ED5400AE1940 /* JitsiMeetBaseLogHandler.h in Headers */ = {isa = PBXBuildFile; fileRef = DE81A2DC2317ED5400AE1940 /* JitsiMeetBaseLogHandler.h */; settings = {ATTRIBUTES = (Public, ); }; };
|
||||
DE81A2DF2317ED5400AE1940 /* JitsiMeetBaseLogHandler.m in Sources */ = {isa = PBXBuildFile; fileRef = DE81A2DD2317ED5400AE1940 /* JitsiMeetBaseLogHandler.m */; };
|
||||
DE9A0130289A9A9A00E41CBB /* JitsiMeetUserInfo.h in Headers */ = {isa = PBXBuildFile; fileRef = DE762DB322AFDE76000DEBD6 /* JitsiMeetUserInfo.h */; settings = {ATTRIBUTES = (Public, ); }; };
|
||||
DE9A0131289A9A9A00E41CBB /* JitsiMeetView.h in Headers */ = {isa = PBXBuildFile; fileRef = 0B412F161EDEC65D00B1A0A6 /* JitsiMeetView.h */; settings = {ATTRIBUTES = (Public, ); }; };
|
||||
DE9A0132289A9A9A00E41CBB /* RCTBridgeWrapper.h in Headers */ = {isa = PBXBuildFile; fileRef = 0B93EF7C1EC9DDCD0030D24D /* RCTBridgeWrapper.h */; };
|
||||
DE9A0133289A9A9A00E41CBB /* JitsiMeetBaseLogHandler.h in Headers */ = {isa = PBXBuildFile; fileRef = DE81A2DC2317ED5400AE1940 /* JitsiMeetBaseLogHandler.h */; settings = {ATTRIBUTES = (Public, ); }; };
|
||||
DE9A0134289A9A9A00E41CBB /* JitsiMeetSDK.h in Headers */ = {isa = PBXBuildFile; fileRef = DEA9F283258A5D9900D4CD74 /* JitsiMeetSDK.h */; settings = {ATTRIBUTES = (Public, ); }; };
|
||||
DE9A0135289A9A9A00E41CBB /* ScheenshareEventEmiter.h in Headers */ = {isa = PBXBuildFile; fileRef = 4E51B76225E5345E0038575A /* ScheenshareEventEmiter.h */; };
|
||||
DE9A0136289A9A9A00E41CBB /* JitsiMeetBaseLogHandler+Private.h in Headers */ = {isa = PBXBuildFile; fileRef = DE65AACB2318028300290BEC /* JitsiMeetBaseLogHandler+Private.h */; };
|
||||
DE9A0137289A9A9A00E41CBB /* JitsiMeetRenderingView.h in Headers */ = {isa = PBXBuildFile; fileRef = 4EBA6E632860B1E800B31882 /* JitsiMeetRenderingView.h */; };
|
||||
DE9A0138289A9A9A00E41CBB /* JitsiMeetViewDelegate.h in Headers */ = {isa = PBXBuildFile; fileRef = 0B412F1B1EDEC80100B1A0A6 /* JitsiMeetViewDelegate.h */; settings = {ATTRIBUTES = (Public, ); }; };
|
||||
DE9A0139289A9A9A00E41CBB /* JitsiAudioSession.h in Headers */ = {isa = PBXBuildFile; fileRef = 4ED4FFF12721B9B90074E620 /* JitsiAudioSession.h */; settings = {ATTRIBUTES = (Public, ); }; };
|
||||
DE9A013A289A9A9A00E41CBB /* JitsiMeetView+Private.h in Headers */ = {isa = PBXBuildFile; fileRef = 4EEC962E286C73A2008705FA /* JitsiMeetView+Private.h */; };
|
||||
DE9A013B289A9A9A00E41CBB /* JitsiMeet.h in Headers */ = {isa = PBXBuildFile; fileRef = 0BD906E81EC0C00300C8C18E /* JitsiMeet.h */; settings = {ATTRIBUTES = (Public, ); }; };
|
||||
DE9A013C289A9A9A00E41CBB /* JitsiMeetLogger.h in Headers */ = {isa = PBXBuildFile; fileRef = DE81A2D22316AC4D00AE1940 /* JitsiMeetLogger.h */; settings = {ATTRIBUTES = (Public, ); }; };
|
||||
DE9A013D289A9A9A00E41CBB /* LogUtils.h in Headers */ = {isa = PBXBuildFile; fileRef = DE65AAC92317FFCD00290BEC /* LogUtils.h */; };
|
||||
DE9A013E289A9A9A00E41CBB /* JitsiMeetViewController.h in Headers */ = {isa = PBXBuildFile; fileRef = 4EBA6E5F286072E300B31882 /* JitsiMeetViewController.h */; };
|
||||
DE9A013F289A9A9A00E41CBB /* JitsiMeetConferenceOptions.h in Headers */ = {isa = PBXBuildFile; fileRef = DEAD3224220C497000E93636 /* JitsiMeetConferenceOptions.h */; settings = {ATTRIBUTES = (Public, ); }; };
|
||||
DE9A0140289A9A9A00E41CBB /* ExternalAPI.h in Headers */ = {isa = PBXBuildFile; fileRef = C81E9AB825AC5AD800B134D9 /* ExternalAPI.h */; };
|
||||
DE9A0141289A9A9A00E41CBB /* InfoPlistUtil.h in Headers */ = {isa = PBXBuildFile; fileRef = C8AFD27D2462C613000293D2 /* InfoPlistUtil.h */; settings = {ATTRIBUTES = (Public, ); }; };
|
||||
DE9A0143289A9A9A00E41CBB /* CallKit.m in Sources */ = {isa = PBXBuildFile; fileRef = 0BB9AD7A1F5EC8F4001C08DB /* CallKit.m */; };
|
||||
DE9A0144289A9A9A00E41CBB /* JitsiMeetBaseLogHandler.m in Sources */ = {isa = PBXBuildFile; fileRef = DE81A2DD2317ED5400AE1940 /* JitsiMeetBaseLogHandler.m */; };
|
||||
DE9A0145289A9A9A00E41CBB /* JitsiMeetRenderingView.m in Sources */ = {isa = PBXBuildFile; fileRef = 4EBA6E642860B1E800B31882 /* JitsiMeetRenderingView.m */; };
|
||||
DE9A0146289A9A9A00E41CBB /* JitsiAudioSession.m in Sources */ = {isa = PBXBuildFile; fileRef = 4ED4FFF22721B9B90074E620 /* JitsiAudioSession.m */; };
|
||||
DE9A0147289A9A9A00E41CBB /* AppInfo.m in Sources */ = {isa = PBXBuildFile; fileRef = 0BB9AD7C1F60356D001C08DB /* AppInfo.m */; };
|
||||
DE9A0148289A9A9A00E41CBB /* LogBridge.m in Sources */ = {isa = PBXBuildFile; fileRef = DE81A2D72316AC7600AE1940 /* LogBridge.m */; };
|
||||
DE9A0149289A9A9A00E41CBB /* RNRootView.m in Sources */ = {isa = PBXBuildFile; fileRef = DEAFA778229EAD520033A7FA /* RNRootView.m */; };
|
||||
DE9A014A289A9A9A00E41CBB /* JitsiMeetUserInfo.m in Sources */ = {isa = PBXBuildFile; fileRef = DE762DB522AFDE8D000DEBD6 /* JitsiMeetUserInfo.m */; };
|
||||
DE9A014B289A9A9A00E41CBB /* JitsiMeetConferenceOptions.m in Sources */ = {isa = PBXBuildFile; fileRef = DEAD3225220C497000E93636 /* JitsiMeetConferenceOptions.m */; };
|
||||
DE9A014C289A9A9A00E41CBB /* RCTBridgeWrapper.m in Sources */ = {isa = PBXBuildFile; fileRef = 0B93EF7D1EC9DDCD0030D24D /* RCTBridgeWrapper.m */; };
|
||||
DE9A014D289A9A9A00E41CBB /* ExternalAPI.m in Sources */ = {isa = PBXBuildFile; fileRef = 0BA13D301EE83FF8007BEF7F /* ExternalAPI.m */; };
|
||||
DE9A014E289A9A9A00E41CBB /* POSIX.m in Sources */ = {isa = PBXBuildFile; fileRef = 0BCA495D1EC4B6C600B793EE /* POSIX.m */; };
|
||||
DE9A014F289A9A9A00E41CBB /* InfoPlistUtil.m in Sources */ = {isa = PBXBuildFile; fileRef = C8AFD27E2462C613000293D2 /* InfoPlistUtil.m */; };
|
||||
DE9A0150289A9A9A00E41CBB /* PiPViewCoordinator.swift in Sources */ = {isa = PBXBuildFile; fileRef = C6CC49AE207412CF000DFA42 /* PiPViewCoordinator.swift */; };
|
||||
DE9A0151289A9A9A00E41CBB /* LocaleDetector.m in Sources */ = {isa = PBXBuildFile; fileRef = DEFC743D21B178FA00E4DD96 /* LocaleDetector.m */; };
|
||||
DE9A0152289A9A9A00E41CBB /* AudioMode.m in Sources */ = {isa = PBXBuildFile; fileRef = 0BCA495C1EC4B6C600B793EE /* AudioMode.m */; };
|
||||
DE9A0153289A9A9A00E41CBB /* Proximity.m in Sources */ = {isa = PBXBuildFile; fileRef = 0BCA495E1EC4B6C600B793EE /* Proximity.m */; };
|
||||
DE9A0154289A9A9A00E41CBB /* JMCallKitEmitter.swift in Sources */ = {isa = PBXBuildFile; fileRef = C69EFA09209A0F650027712B /* JMCallKitEmitter.swift */; };
|
||||
DE9A0155289A9A9A00E41CBB /* ReactUtils.m in Sources */ = {isa = PBXBuildFile; fileRef = DEFE535521FB2E8300011A3A /* ReactUtils.m */; };
|
||||
DE9A0156289A9A9A00E41CBB /* JitsiMeetView+Private.m in Sources */ = {isa = PBXBuildFile; fileRef = 4EEC962F286C73A2008705FA /* JitsiMeetView+Private.m */; };
|
||||
DE9A0157289A9A9A00E41CBB /* DragGestureController.swift in Sources */ = {isa = PBXBuildFile; fileRef = C6A3425E204EF76800E062DD /* DragGestureController.swift */; };
|
||||
DE9A0158289A9A9A00E41CBB /* ScheenshareEventEmiter.m in Sources */ = {isa = PBXBuildFile; fileRef = 4E51B76325E5345E0038575A /* ScheenshareEventEmiter.m */; };
|
||||
DE9A015A289A9A9A00E41CBB /* JitsiMeetViewController.m in Sources */ = {isa = PBXBuildFile; fileRef = 4EBA6E60286072E300B31882 /* JitsiMeetViewController.m */; };
|
||||
DE9A015B289A9A9A00E41CBB /* JMCallKitProxy.swift in Sources */ = {isa = PBXBuildFile; fileRef = C69EFA0A209A0F660027712B /* JMCallKitProxy.swift */; };
|
||||
DE9A015C289A9A9A00E41CBB /* JitsiMeetLogger.m in Sources */ = {isa = PBXBuildFile; fileRef = DE81A2D32316AC4D00AE1940 /* JitsiMeetLogger.m */; };
|
||||
DE9A015D289A9A9A00E41CBB /* JMCallKitListener.swift in Sources */ = {isa = PBXBuildFile; fileRef = C69EFA0B209A0F660027712B /* JMCallKitListener.swift */; };
|
||||
DE9A015E289A9A9A00E41CBB /* JitsiMeetView.m in Sources */ = {isa = PBXBuildFile; fileRef = 0B412F171EDEC65D00B1A0A6 /* JitsiMeetView.m */; };
|
||||
DE9A015F289A9A9A00E41CBB /* JitsiMeet.m in Sources */ = {isa = PBXBuildFile; fileRef = DEFE535321FB1BF800011A3A /* JitsiMeet.m */; };
|
||||
DE9A0160289A9A9A00E41CBB /* JavaScriptSandbox.m in Sources */ = {isa = PBXBuildFile; fileRef = DE438CD82350934700DD541D /* JavaScriptSandbox.m */; };
|
||||
DE9A0162289A9A9A00E41CBB /* Intents.framework in Frameworks */ = {isa = PBXBuildFile; fileRef = 0BB9AD781F5EC6D7001C08DB /* Intents.framework */; settings = {ATTRIBUTES = (Weak, ); }; };
|
||||
DE9A0163289A9A9A00E41CBB /* CallKit.framework in Frameworks */ = {isa = PBXBuildFile; fileRef = 0BB9AD761F5EC6CE001C08DB /* CallKit.framework */; settings = {ATTRIBUTES = (Weak, ); }; };
|
||||
DE9A0166289A9A9A00E41CBB /* CallKitIcon.png in Resources */ = {isa = PBXBuildFile; fileRef = 0BC4B8681F8C01E100CE8B21 /* CallKitIcon.png */; };
|
||||
DE9A0167289A9A9A00E41CBB /* image-resize@2x.png in Resources */ = {isa = PBXBuildFile; fileRef = C6245F5B2053091D0040BE68 /* image-resize@2x.png */; };
|
||||
DE9A0168289A9A9A00E41CBB /* image-resize@3x.png in Resources */ = {isa = PBXBuildFile; fileRef = C6245F5C2053091D0040BE68 /* image-resize@3x.png */; };
|
||||
DEA9F284258A5D9900D4CD74 /* JitsiMeetSDK.h in Headers */ = {isa = PBXBuildFile; fileRef = DEA9F283258A5D9900D4CD74 /* JitsiMeetSDK.h */; settings = {ATTRIBUTES = (Public, ); }; };
|
||||
DEAD3226220C497000E93636 /* JitsiMeetConferenceOptions.h in Headers */ = {isa = PBXBuildFile; fileRef = DEAD3224220C497000E93636 /* JitsiMeetConferenceOptions.h */; settings = {ATTRIBUTES = (Public, ); }; };
|
||||
DEAD3227220C497000E93636 /* JitsiMeetConferenceOptions.m in Sources */ = {isa = PBXBuildFile; fileRef = DEAD3225220C497000E93636 /* JitsiMeetConferenceOptions.m */; };
|
||||
@@ -79,14 +141,24 @@
|
||||
0BD906E91EC0C00300C8C18E /* Info.plist */ = {isa = PBXFileReference; lastKnownFileType = text.plist.xml; path = Info.plist; sourceTree = "<group>"; };
|
||||
4E51B76225E5345E0038575A /* ScheenshareEventEmiter.h */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.c.h; path = ScheenshareEventEmiter.h; sourceTree = "<group>"; };
|
||||
4E51B76325E5345E0038575A /* ScheenshareEventEmiter.m */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.c.objc; path = ScheenshareEventEmiter.m; sourceTree = "<group>"; };
|
||||
4EBA6E5F286072E300B31882 /* JitsiMeetViewController.h */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.c.h; path = JitsiMeetViewController.h; sourceTree = "<group>"; };
|
||||
4EBA6E60286072E300B31882 /* JitsiMeetViewController.m */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.c.objc; path = JitsiMeetViewController.m; sourceTree = "<group>"; };
|
||||
4EBA6E632860B1E800B31882 /* JitsiMeetRenderingView.h */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.c.h; path = JitsiMeetRenderingView.h; sourceTree = "<group>"; };
|
||||
4EBA6E642860B1E800B31882 /* JitsiMeetRenderingView.m */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.c.objc; path = JitsiMeetRenderingView.m; sourceTree = "<group>"; };
|
||||
4ED4FFF12721B9B90074E620 /* JitsiAudioSession.h */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.c.h; path = JitsiAudioSession.h; sourceTree = "<group>"; };
|
||||
4ED4FFF22721B9B90074E620 /* JitsiAudioSession.m */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.c.objc; path = JitsiAudioSession.m; sourceTree = "<group>"; };
|
||||
4ED4FFF52721BAE10074E620 /* JitsiAudioSession+Private.h */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.c.h; path = "JitsiAudioSession+Private.h"; sourceTree = "<group>"; };
|
||||
4EEC962E286C73A2008705FA /* JitsiMeetView+Private.h */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.c.h; path = "JitsiMeetView+Private.h"; sourceTree = "<group>"; };
|
||||
4EEC962F286C73A2008705FA /* JitsiMeetView+Private.m */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.c.objc; path = "JitsiMeetView+Private.m"; sourceTree = "<group>"; };
|
||||
86389F55993FAAF6AEB3FA3E /* Pods-JitsiMeetSDKLite.release.xcconfig */ = {isa = PBXFileReference; includeInIndex = 1; lastKnownFileType = text.xcconfig; name = "Pods-JitsiMeetSDKLite.release.xcconfig"; path = "../Pods/Target Support Files/Pods-JitsiMeetSDKLite/Pods-JitsiMeetSDKLite.release.xcconfig"; sourceTree = "<group>"; };
|
||||
891FE43DAD30BC8976683100 /* Pods-JitsiMeetSDK.release.xcconfig */ = {isa = PBXFileReference; includeInIndex = 1; lastKnownFileType = text.xcconfig; name = "Pods-JitsiMeetSDK.release.xcconfig"; path = "../Pods/Target Support Files/Pods-JitsiMeetSDK/Pods-JitsiMeetSDK.release.xcconfig"; sourceTree = "<group>"; };
|
||||
8F48C340DE0D91D1012976C5 /* Pods-JitsiMeetSDKLite.debug.xcconfig */ = {isa = PBXFileReference; includeInIndex = 1; lastKnownFileType = text.xcconfig; name = "Pods-JitsiMeetSDKLite.debug.xcconfig"; path = "../Pods/Target Support Files/Pods-JitsiMeetSDKLite/Pods-JitsiMeetSDKLite.debug.xcconfig"; sourceTree = "<group>"; };
|
||||
927ED7DF018DE5E12C4C3404 /* libPods-JitsiMeetSDK.a */ = {isa = PBXFileReference; explicitFileType = archive.ar; includeInIndex = 0; path = "libPods-JitsiMeetSDK.a"; sourceTree = BUILT_PRODUCTS_DIR; };
|
||||
98E09B5C73D9036B4ED252FC /* Pods-JitsiMeet.debug.xcconfig */ = {isa = PBXFileReference; includeInIndex = 1; lastKnownFileType = text.xcconfig; name = "Pods-JitsiMeet.debug.xcconfig"; path = "../Pods/Target Support Files/Pods-JitsiMeet/Pods-JitsiMeet.debug.xcconfig"; sourceTree = "<group>"; };
|
||||
9C77CA3CC919B081F1A52982 /* Pods-JitsiMeet.release.xcconfig */ = {isa = PBXFileReference; includeInIndex = 1; lastKnownFileType = text.xcconfig; name = "Pods-JitsiMeet.release.xcconfig"; path = "../Pods/Target Support Files/Pods-JitsiMeet/Pods-JitsiMeet.release.xcconfig"; sourceTree = "<group>"; };
|
||||
A4A934E8212F3ADB001E9388 /* Dropbox.m */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.c.objc; path = Dropbox.m; sourceTree = "<group>"; };
|
||||
A4A934EB21349A06001E9388 /* Dropbox.h */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.c.h; path = Dropbox.h; sourceTree = "<group>"; };
|
||||
B46497DE9A95BDF5E312AF48 /* libPods-JitsiMeetSDKLite.a */ = {isa = PBXFileReference; explicitFileType = archive.ar; includeInIndex = 0; path = "libPods-JitsiMeetSDKLite.a"; sourceTree = BUILT_PRODUCTS_DIR; };
|
||||
C6245F5B2053091D0040BE68 /* image-resize@2x.png */ = {isa = PBXFileReference; lastKnownFileType = image.png; name = "image-resize@2x.png"; path = "src/picture-in-picture/image-resize@2x.png"; sourceTree = "<group>"; };
|
||||
C6245F5C2053091D0040BE68 /* image-resize@3x.png */ = {isa = PBXFileReference; lastKnownFileType = image.png; name = "image-resize@3x.png"; path = "src/picture-in-picture/image-resize@3x.png"; sourceTree = "<group>"; };
|
||||
C69EFA09209A0F650027712B /* JMCallKitEmitter.swift */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.swift; path = JMCallKitEmitter.swift; sourceTree = "<group>"; };
|
||||
@@ -94,13 +166,13 @@
|
||||
C69EFA0B209A0F660027712B /* JMCallKitListener.swift */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.swift; path = JMCallKitListener.swift; sourceTree = "<group>"; };
|
||||
C6A3425E204EF76800E062DD /* DragGestureController.swift */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.swift; path = DragGestureController.swift; sourceTree = "<group>"; };
|
||||
C6CC49AE207412CF000DFA42 /* PiPViewCoordinator.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = PiPViewCoordinator.swift; sourceTree = "<group>"; };
|
||||
C6F99C13204DB63D0001F710 /* JitsiMeetView+Private.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = "JitsiMeetView+Private.h"; sourceTree = "<group>"; };
|
||||
C81E9AB825AC5AD800B134D9 /* ExternalAPI.h */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.c.h; path = ExternalAPI.h; sourceTree = "<group>"; };
|
||||
C8AFD27D2462C613000293D2 /* InfoPlistUtil.h */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.c.h; path = InfoPlistUtil.h; sourceTree = "<group>"; };
|
||||
C8AFD27E2462C613000293D2 /* InfoPlistUtil.m */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.c.objc; path = InfoPlistUtil.m; sourceTree = "<group>"; };
|
||||
DE438CD82350934700DD541D /* JavaScriptSandbox.m */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.c.objc; path = JavaScriptSandbox.m; sourceTree = "<group>"; };
|
||||
DE65AAC92317FFCD00290BEC /* LogUtils.h */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.c.h; path = LogUtils.h; sourceTree = "<group>"; };
|
||||
DE65AACB2318028300290BEC /* JitsiMeetBaseLogHandler+Private.h */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.c.h; path = "JitsiMeetBaseLogHandler+Private.h"; sourceTree = "<group>"; };
|
||||
DE66914328BCC1C7007C4533 /* JitsiMeetSDK-Swift.h */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.c.h; path = "JitsiMeetSDK-Swift.h"; sourceTree = "<group>"; };
|
||||
DE762DB322AFDE76000DEBD6 /* JitsiMeetUserInfo.h */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.c.h; path = JitsiMeetUserInfo.h; sourceTree = "<group>"; };
|
||||
DE762DB522AFDE8D000DEBD6 /* JitsiMeetUserInfo.m */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.c.objc; path = JitsiMeetUserInfo.m; sourceTree = "<group>"; };
|
||||
DE762DB722AFE166000DEBD6 /* JitsiMeetUserInfo+Private.h */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.c.h; path = "JitsiMeetUserInfo+Private.h"; sourceTree = "<group>"; };
|
||||
@@ -109,6 +181,8 @@
|
||||
DE81A2D72316AC7600AE1940 /* LogBridge.m */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.c.objc; path = LogBridge.m; sourceTree = "<group>"; };
|
||||
DE81A2DC2317ED5400AE1940 /* JitsiMeetBaseLogHandler.h */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.c.h; path = JitsiMeetBaseLogHandler.h; sourceTree = "<group>"; };
|
||||
DE81A2DD2317ED5400AE1940 /* JitsiMeetBaseLogHandler.m */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.c.objc; path = JitsiMeetBaseLogHandler.m; sourceTree = "<group>"; };
|
||||
DE9A016F289A9A9A00E41CBB /* JitsiMeetSDK.framework */ = {isa = PBXFileReference; explicitFileType = wrapper.framework; includeInIndex = 0; path = JitsiMeetSDK.framework; sourceTree = BUILT_PRODUCTS_DIR; };
|
||||
DE9A0170289A9A9A00E41CBB /* Lite-Info.plist */ = {isa = PBXFileReference; lastKnownFileType = text.plist.xml; name = "Lite-Info.plist"; path = "/Users/saghul/work/jitsi/jitsi-meet-prs/ios/sdk/src/Lite-Info.plist"; sourceTree = "<absolute>"; };
|
||||
DEA9F283258A5D9900D4CD74 /* JitsiMeetSDK.h */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.c.h; path = JitsiMeetSDK.h; sourceTree = "<group>"; };
|
||||
DEAD3224220C497000E93636 /* JitsiMeetConferenceOptions.h */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.c.h; path = JitsiMeetConferenceOptions.h; sourceTree = "<group>"; };
|
||||
DEAD3225220C497000E93636 /* JitsiMeetConferenceOptions.m */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.c.objc; path = JitsiMeetConferenceOptions.m; sourceTree = "<group>"; };
|
||||
@@ -120,7 +194,6 @@
|
||||
DEFE535521FB2E8300011A3A /* ReactUtils.m */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.c.objc; path = ReactUtils.m; sourceTree = "<group>"; };
|
||||
DEFE535721FB2E9E00011A3A /* ReactUtils.h */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.c.h; path = ReactUtils.h; sourceTree = "<group>"; };
|
||||
DEFE535821FB311F00011A3A /* JitsiMeet+Private.h */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.c.h; path = "JitsiMeet+Private.h"; sourceTree = "<group>"; };
|
||||
E4376CA6886DE68FD7A4294B /* libPods-JitsiMeetSDK.a */ = {isa = PBXFileReference; explicitFileType = archive.ar; includeInIndex = 0; path = "libPods-JitsiMeetSDK.a"; sourceTree = BUILT_PRODUCTS_DIR; };
|
||||
/* End PBXFileReference section */
|
||||
|
||||
/* Begin PBXFrameworksBuildPhase section */
|
||||
@@ -130,7 +203,18 @@
|
||||
files = (
|
||||
0BB9AD791F5EC6D7001C08DB /* Intents.framework in Frameworks */,
|
||||
0BB9AD771F5EC6CE001C08DB /* CallKit.framework in Frameworks */,
|
||||
6F08DF7D4458EE3CF3F36F6D /* libPods-JitsiMeetSDK.a in Frameworks */,
|
||||
6F08DF7D4458EE3CF3F36F6D /* BuildFile in Frameworks */,
|
||||
3453F4A32680898C4A40E821 /* libPods-JitsiMeetSDK.a in Frameworks */,
|
||||
);
|
||||
runOnlyForDeploymentPostprocessing = 0;
|
||||
};
|
||||
DE9A0161289A9A9A00E41CBB /* Frameworks */ = {
|
||||
isa = PBXFrameworksBuildPhase;
|
||||
buildActionMask = 2147483647;
|
||||
files = (
|
||||
DE9A0162289A9A9A00E41CBB /* Intents.framework in Frameworks */,
|
||||
DE9A0163289A9A9A00E41CBB /* CallKit.framework in Frameworks */,
|
||||
9A8EE79C77C17743BB66E8BD /* libPods-JitsiMeetSDKLite.a in Frameworks */,
|
||||
);
|
||||
runOnlyForDeploymentPostprocessing = 0;
|
||||
};
|
||||
@@ -162,6 +246,7 @@
|
||||
isa = PBXGroup;
|
||||
children = (
|
||||
0BD906E51EC0C00300C8C18E /* JitsiMeetSDK.framework */,
|
||||
DE9A016F289A9A9A00E41CBB /* JitsiMeetSDK.framework */,
|
||||
);
|
||||
name = Products;
|
||||
sourceTree = "<group>";
|
||||
@@ -194,12 +279,17 @@
|
||||
DE65AACB2318028300290BEC /* JitsiMeetBaseLogHandler+Private.h */,
|
||||
DE81A2DD2317ED5400AE1940 /* JitsiMeetBaseLogHandler.m */,
|
||||
0B412F161EDEC65D00B1A0A6 /* JitsiMeetView.h */,
|
||||
4EEC962E286C73A2008705FA /* JitsiMeetView+Private.h */,
|
||||
4EEC962F286C73A2008705FA /* JitsiMeetView+Private.m */,
|
||||
0B412F171EDEC65D00B1A0A6 /* JitsiMeetView.m */,
|
||||
4EBA6E632860B1E800B31882 /* JitsiMeetRenderingView.h */,
|
||||
4EBA6E642860B1E800B31882 /* JitsiMeetRenderingView.m */,
|
||||
4EBA6E5F286072E300B31882 /* JitsiMeetViewController.h */,
|
||||
4EBA6E60286072E300B31882 /* JitsiMeetViewController.m */,
|
||||
DE81A2D72316AC7600AE1940 /* LogBridge.m */,
|
||||
DE65AAC92317FFCD00290BEC /* LogUtils.h */,
|
||||
DEAFA777229EAD3B0033A7FA /* RNRootView.h */,
|
||||
DEAFA778229EAD520033A7FA /* RNRootView.m */,
|
||||
C6F99C13204DB63D0001F710 /* JitsiMeetView+Private.h */,
|
||||
0B412F1B1EDEC80100B1A0A6 /* JitsiMeetViewDelegate.h */,
|
||||
DEFC743D21B178FA00E4DD96 /* LocaleDetector.m */,
|
||||
C6A3426B204F127900E062DD /* picture-in-picture */,
|
||||
@@ -215,6 +305,8 @@
|
||||
0BA13D301EE83FF8007BEF7F /* ExternalAPI.m */,
|
||||
4E51B76225E5345E0038575A /* ScheenshareEventEmiter.h */,
|
||||
4E51B76325E5345E0038575A /* ScheenshareEventEmiter.m */,
|
||||
DE9A0170289A9A9A00E41CBB /* Lite-Info.plist */,
|
||||
DE66914328BCC1C7007C4533 /* JitsiMeetSDK-Swift.h */,
|
||||
);
|
||||
path = src;
|
||||
sourceTree = "<group>";
|
||||
@@ -225,7 +317,8 @@
|
||||
0BB9AD761F5EC6CE001C08DB /* CallKit.framework */,
|
||||
0B93EF7A1EC608550030D24D /* CoreText.framework */,
|
||||
0BB9AD781F5EC6D7001C08DB /* Intents.framework */,
|
||||
E4376CA6886DE68FD7A4294B /* libPods-JitsiMeetSDK.a */,
|
||||
B46497DE9A95BDF5E312AF48 /* libPods-JitsiMeetSDKLite.a */,
|
||||
927ED7DF018DE5E12C4C3404 /* libPods-JitsiMeetSDK.a */,
|
||||
);
|
||||
name = Frameworks;
|
||||
sourceTree = "<group>";
|
||||
@@ -246,6 +339,8 @@
|
||||
9C77CA3CC919B081F1A52982 /* Pods-JitsiMeet.release.xcconfig */,
|
||||
09A78016288AF50ACD28A10D /* Pods-JitsiMeetSDK.debug.xcconfig */,
|
||||
891FE43DAD30BC8976683100 /* Pods-JitsiMeetSDK.release.xcconfig */,
|
||||
8F48C340DE0D91D1012976C5 /* Pods-JitsiMeetSDKLite.debug.xcconfig */,
|
||||
86389F55993FAAF6AEB3FA3E /* Pods-JitsiMeetSDKLite.release.xcconfig */,
|
||||
);
|
||||
name = Pods;
|
||||
sourceTree = "<group>";
|
||||
@@ -284,17 +379,47 @@
|
||||
DEA9F284258A5D9900D4CD74 /* JitsiMeetSDK.h in Headers */,
|
||||
4E51B76425E5345E0038575A /* ScheenshareEventEmiter.h in Headers */,
|
||||
DE65AACC2318028300290BEC /* JitsiMeetBaseLogHandler+Private.h in Headers */,
|
||||
DE66914428BCC1C7007C4533 /* JitsiMeetSDK-Swift.h in Headers */,
|
||||
4EBA6E652860B1E800B31882 /* JitsiMeetRenderingView.h in Headers */,
|
||||
0B412F221EDEF6EA00B1A0A6 /* JitsiMeetViewDelegate.h in Headers */,
|
||||
4ED4FFF32721B9B90074E620 /* JitsiAudioSession.h in Headers */,
|
||||
4EEC9630286C73A2008705FA /* JitsiMeetView+Private.h in Headers */,
|
||||
0BD906EA1EC0C00300C8C18E /* JitsiMeet.h in Headers */,
|
||||
DE81A2D42316AC4D00AE1940 /* JitsiMeetLogger.h in Headers */,
|
||||
DE65AACA2317FFCD00290BEC /* LogUtils.h in Headers */,
|
||||
4EBA6E61286072E300B31882 /* JitsiMeetViewController.h in Headers */,
|
||||
DEAD3226220C497000E93636 /* JitsiMeetConferenceOptions.h in Headers */,
|
||||
C81E9AB925AC5AD800B134D9 /* ExternalAPI.h in Headers */,
|
||||
C8AFD27F2462C613000293D2 /* InfoPlistUtil.h in Headers */,
|
||||
);
|
||||
runOnlyForDeploymentPostprocessing = 0;
|
||||
};
|
||||
DE9A012F289A9A9A00E41CBB /* Headers */ = {
|
||||
isa = PBXHeadersBuildPhase;
|
||||
buildActionMask = 2147483647;
|
||||
files = (
|
||||
DE9A0130289A9A9A00E41CBB /* JitsiMeetUserInfo.h in Headers */,
|
||||
DE9A0131289A9A9A00E41CBB /* JitsiMeetView.h in Headers */,
|
||||
DE9A0132289A9A9A00E41CBB /* RCTBridgeWrapper.h in Headers */,
|
||||
DE9A0133289A9A9A00E41CBB /* JitsiMeetBaseLogHandler.h in Headers */,
|
||||
DE9A0134289A9A9A00E41CBB /* JitsiMeetSDK.h in Headers */,
|
||||
DE9A0135289A9A9A00E41CBB /* ScheenshareEventEmiter.h in Headers */,
|
||||
DE9A0136289A9A9A00E41CBB /* JitsiMeetBaseLogHandler+Private.h in Headers */,
|
||||
DE66914528BCC1C7007C4533 /* JitsiMeetSDK-Swift.h in Headers */,
|
||||
DE9A0137289A9A9A00E41CBB /* JitsiMeetRenderingView.h in Headers */,
|
||||
DE9A0138289A9A9A00E41CBB /* JitsiMeetViewDelegate.h in Headers */,
|
||||
DE9A0139289A9A9A00E41CBB /* JitsiAudioSession.h in Headers */,
|
||||
DE9A013A289A9A9A00E41CBB /* JitsiMeetView+Private.h in Headers */,
|
||||
DE9A013B289A9A9A00E41CBB /* JitsiMeet.h in Headers */,
|
||||
DE9A013C289A9A9A00E41CBB /* JitsiMeetLogger.h in Headers */,
|
||||
DE9A013D289A9A9A00E41CBB /* LogUtils.h in Headers */,
|
||||
DE9A013E289A9A9A00E41CBB /* JitsiMeetViewController.h in Headers */,
|
||||
DE9A013F289A9A9A00E41CBB /* JitsiMeetConferenceOptions.h in Headers */,
|
||||
DE9A0140289A9A9A00E41CBB /* ExternalAPI.h in Headers */,
|
||||
DE9A0141289A9A9A00E41CBB /* InfoPlistUtil.h in Headers */,
|
||||
);
|
||||
runOnlyForDeploymentPostprocessing = 0;
|
||||
};
|
||||
/* End PBXHeadersBuildPhase section */
|
||||
|
||||
/* Begin PBXNativeTarget section */
|
||||
@@ -320,6 +445,28 @@
|
||||
productReference = 0BD906E51EC0C00300C8C18E /* JitsiMeetSDK.framework */;
|
||||
productType = "com.apple.product-type.framework";
|
||||
};
|
||||
DE9A012D289A9A9A00E41CBB /* JitsiMeetSDKLite */ = {
|
||||
isa = PBXNativeTarget;
|
||||
buildConfigurationList = DE9A016C289A9A9A00E41CBB /* Build configuration list for PBXNativeTarget "JitsiMeetSDKLite" */;
|
||||
buildPhases = (
|
||||
DE9A012E289A9A9A00E41CBB /* [CP] Check Pods Manifest.lock */,
|
||||
DE9A012F289A9A9A00E41CBB /* Headers */,
|
||||
DE9A0142289A9A9A00E41CBB /* Sources */,
|
||||
DE9A0161289A9A9A00E41CBB /* Frameworks */,
|
||||
DE9A0165289A9A9A00E41CBB /* Resources */,
|
||||
DE9A0169289A9A9A00E41CBB /* Copy sounds */,
|
||||
DE9A016A289A9A9A00E41CBB /* Package React bundle */,
|
||||
DE9A016B289A9A9A00E41CBB /* [CP] Copy Pods Resources */,
|
||||
);
|
||||
buildRules = (
|
||||
);
|
||||
dependencies = (
|
||||
);
|
||||
name = JitsiMeetSDKLite;
|
||||
productName = "Jitsi Meet SDK";
|
||||
productReference = DE9A016F289A9A9A00E41CBB /* JitsiMeetSDK.framework */;
|
||||
productType = "com.apple.product-type.framework";
|
||||
};
|
||||
/* End PBXNativeTarget section */
|
||||
|
||||
/* Begin PBXProject section */
|
||||
@@ -350,6 +497,7 @@
|
||||
projectRoot = "";
|
||||
targets = (
|
||||
0BD906E41EC0C00300C8C18E /* JitsiMeetSDK */,
|
||||
DE9A012D289A9A9A00E41CBB /* JitsiMeetSDKLite */,
|
||||
);
|
||||
};
|
||||
/* End PBXProject section */
|
||||
@@ -365,6 +513,16 @@
|
||||
);
|
||||
runOnlyForDeploymentPostprocessing = 0;
|
||||
};
|
||||
DE9A0165289A9A9A00E41CBB /* Resources */ = {
|
||||
isa = PBXResourcesBuildPhase;
|
||||
buildActionMask = 2147483647;
|
||||
files = (
|
||||
DE9A0166289A9A9A00E41CBB /* CallKitIcon.png in Resources */,
|
||||
DE9A0167289A9A9A00E41CBB /* image-resize@2x.png in Resources */,
|
||||
DE9A0168289A9A9A00E41CBB /* image-resize@3x.png in Resources */,
|
||||
);
|
||||
runOnlyForDeploymentPostprocessing = 0;
|
||||
};
|
||||
/* End PBXResourcesBuildPhase section */
|
||||
|
||||
/* Begin PBXShellScriptBuildPhase section */
|
||||
@@ -440,6 +598,76 @@
|
||||
shellPath = /bin/sh;
|
||||
shellScript = "SOUNDS_DIR=\"${PROJECT_DIR}/../../sounds\"\n\ncp $SOUNDS_DIR/* ${CONFIGURATION_BUILD_DIR}/${UNLOCALIZED_RESOURCES_FOLDER_PATH}/\n";
|
||||
};
|
||||
DE9A012E289A9A9A00E41CBB /* [CP] Check Pods Manifest.lock */ = {
|
||||
isa = PBXShellScriptBuildPhase;
|
||||
buildActionMask = 2147483647;
|
||||
files = (
|
||||
);
|
||||
inputPaths = (
|
||||
"${PODS_PODFILE_DIR_PATH}/Podfile.lock",
|
||||
"${PODS_ROOT}/Manifest.lock",
|
||||
);
|
||||
name = "[CP] Check Pods Manifest.lock";
|
||||
outputPaths = (
|
||||
"$(DERIVED_FILE_DIR)/Pods-JitsiMeetSDKLite-checkManifestLockResult.txt",
|
||||
);
|
||||
runOnlyForDeploymentPostprocessing = 0;
|
||||
shellPath = /bin/sh;
|
||||
shellScript = "diff \"${PODS_PODFILE_DIR_PATH}/Podfile.lock\" \"${PODS_ROOT}/Manifest.lock\" > /dev/null\nif [ $? != 0 ] ; then\n # print error to STDERR\n echo \"error: The sandbox is not in sync with the Podfile.lock. Run 'pod install' or update your CocoaPods installation.\" >&2\n exit 1\nfi\n# This output is used by Xcode 'outputs' to avoid re-running this script phase.\necho \"SUCCESS\" > \"${SCRIPT_OUTPUT_FILE_0}\"\n";
|
||||
showEnvVarsInLog = 0;
|
||||
};
|
||||
DE9A0169289A9A9A00E41CBB /* Copy sounds */ = {
|
||||
isa = PBXShellScriptBuildPhase;
|
||||
buildActionMask = 2147483647;
|
||||
files = (
|
||||
);
|
||||
inputFileListPaths = (
|
||||
);
|
||||
inputPaths = (
|
||||
);
|
||||
name = "Copy sounds";
|
||||
outputFileListPaths = (
|
||||
);
|
||||
outputPaths = (
|
||||
);
|
||||
runOnlyForDeploymentPostprocessing = 0;
|
||||
shellPath = /bin/sh;
|
||||
shellScript = "SOUNDS_DIR=\"${PROJECT_DIR}/../../sounds\"\n\ncp $SOUNDS_DIR/* ${CONFIGURATION_BUILD_DIR}/${UNLOCALIZED_RESOURCES_FOLDER_PATH}/\n";
|
||||
};
|
||||
DE9A016A289A9A9A00E41CBB /* Package React bundle */ = {
|
||||
isa = PBXShellScriptBuildPhase;
|
||||
buildActionMask = 2147483647;
|
||||
files = (
|
||||
);
|
||||
inputPaths = (
|
||||
);
|
||||
name = "Package React bundle";
|
||||
outputPaths = (
|
||||
);
|
||||
runOnlyForDeploymentPostprocessing = 0;
|
||||
shellPath = /bin/sh;
|
||||
shellScript = "export NODE_BINARY=node\nexport NODE_ARGS=\"--max_old_space_size=4096\"\n../../node_modules/react-native/scripts/react-native-xcode.sh\n";
|
||||
};
|
||||
DE9A016B289A9A9A00E41CBB /* [CP] Copy Pods Resources */ = {
|
||||
isa = PBXShellScriptBuildPhase;
|
||||
buildActionMask = 2147483647;
|
||||
files = (
|
||||
);
|
||||
inputPaths = (
|
||||
"${PODS_ROOT}/Target Support Files/Pods-JitsiMeetSDKLite/Pods-JitsiMeetSDKLite-resources.sh",
|
||||
"${PODS_ROOT}/Amplitude/Sources/Resources/ComodoRsaDomainValidationCA.der",
|
||||
"${PODS_CONFIGURATION_BUILD_DIR}/React-Core/AccessibilityResources.bundle",
|
||||
);
|
||||
name = "[CP] Copy Pods Resources";
|
||||
outputPaths = (
|
||||
"${TARGET_BUILD_DIR}/${UNLOCALIZED_RESOURCES_FOLDER_PATH}/ComodoRsaDomainValidationCA.der",
|
||||
"${TARGET_BUILD_DIR}/${UNLOCALIZED_RESOURCES_FOLDER_PATH}/AccessibilityResources.bundle",
|
||||
);
|
||||
runOnlyForDeploymentPostprocessing = 0;
|
||||
shellPath = /bin/sh;
|
||||
shellScript = "\"${PODS_ROOT}/Target Support Files/Pods-JitsiMeetSDKLite/Pods-JitsiMeetSDKLite-resources.sh\"\n";
|
||||
showEnvVarsInLog = 0;
|
||||
};
|
||||
/* End PBXShellScriptBuildPhase section */
|
||||
|
||||
/* Begin PBXSourcesBuildPhase section */
|
||||
@@ -449,6 +677,7 @@
|
||||
files = (
|
||||
0BB9AD7B1F5EC8F4001C08DB /* CallKit.m in Sources */,
|
||||
DE81A2DF2317ED5400AE1940 /* JitsiMeetBaseLogHandler.m in Sources */,
|
||||
4EBA6E662860B1E800B31882 /* JitsiMeetRenderingView.m in Sources */,
|
||||
4ED4FFF42721B9B90074E620 /* JitsiAudioSession.m in Sources */,
|
||||
0BB9AD7D1F60356D001C08DB /* AppInfo.m in Sources */,
|
||||
DE81A2D92316AC7600AE1940 /* LogBridge.m in Sources */,
|
||||
@@ -465,9 +694,11 @@
|
||||
0BCA49611EC4B6C600B793EE /* Proximity.m in Sources */,
|
||||
C69EFA0C209A0F660027712B /* JMCallKitEmitter.swift in Sources */,
|
||||
DEFE535621FB2E8300011A3A /* ReactUtils.m in Sources */,
|
||||
4EEC9631286C73A2008705FA /* JitsiMeetView+Private.m in Sources */,
|
||||
C6A34261204EF76800E062DD /* DragGestureController.swift in Sources */,
|
||||
4E51B76525E5345E0038575A /* ScheenshareEventEmiter.m in Sources */,
|
||||
A4A934E9212F3ADB001E9388 /* Dropbox.m in Sources */,
|
||||
4EBA6E62286072E300B31882 /* JitsiMeetViewController.m in Sources */,
|
||||
C69EFA0D209A0F660027712B /* JMCallKitProxy.swift in Sources */,
|
||||
DE81A2D52316AC4D00AE1940 /* JitsiMeetLogger.m in Sources */,
|
||||
C69EFA0E209A0F660027712B /* JMCallKitListener.swift in Sources */,
|
||||
@@ -477,6 +708,42 @@
|
||||
);
|
||||
runOnlyForDeploymentPostprocessing = 0;
|
||||
};
|
||||
DE9A0142289A9A9A00E41CBB /* Sources */ = {
|
||||
isa = PBXSourcesBuildPhase;
|
||||
buildActionMask = 2147483647;
|
||||
files = (
|
||||
DE9A0143289A9A9A00E41CBB /* CallKit.m in Sources */,
|
||||
DE9A0144289A9A9A00E41CBB /* JitsiMeetBaseLogHandler.m in Sources */,
|
||||
DE9A0145289A9A9A00E41CBB /* JitsiMeetRenderingView.m in Sources */,
|
||||
DE9A0146289A9A9A00E41CBB /* JitsiAudioSession.m in Sources */,
|
||||
DE9A0147289A9A9A00E41CBB /* AppInfo.m in Sources */,
|
||||
DE9A0148289A9A9A00E41CBB /* LogBridge.m in Sources */,
|
||||
DE9A0149289A9A9A00E41CBB /* RNRootView.m in Sources */,
|
||||
DE9A014A289A9A9A00E41CBB /* JitsiMeetUserInfo.m in Sources */,
|
||||
DE9A014B289A9A9A00E41CBB /* JitsiMeetConferenceOptions.m in Sources */,
|
||||
DE9A014C289A9A9A00E41CBB /* RCTBridgeWrapper.m in Sources */,
|
||||
DE9A014D289A9A9A00E41CBB /* ExternalAPI.m in Sources */,
|
||||
DE9A014E289A9A9A00E41CBB /* POSIX.m in Sources */,
|
||||
DE9A014F289A9A9A00E41CBB /* InfoPlistUtil.m in Sources */,
|
||||
DE9A0150289A9A9A00E41CBB /* PiPViewCoordinator.swift in Sources */,
|
||||
DE9A0151289A9A9A00E41CBB /* LocaleDetector.m in Sources */,
|
||||
DE9A0152289A9A9A00E41CBB /* AudioMode.m in Sources */,
|
||||
DE9A0153289A9A9A00E41CBB /* Proximity.m in Sources */,
|
||||
DE9A0154289A9A9A00E41CBB /* JMCallKitEmitter.swift in Sources */,
|
||||
DE9A0155289A9A9A00E41CBB /* ReactUtils.m in Sources */,
|
||||
DE9A0156289A9A9A00E41CBB /* JitsiMeetView+Private.m in Sources */,
|
||||
DE9A0157289A9A9A00E41CBB /* DragGestureController.swift in Sources */,
|
||||
DE9A0158289A9A9A00E41CBB /* ScheenshareEventEmiter.m in Sources */,
|
||||
DE9A015A289A9A9A00E41CBB /* JitsiMeetViewController.m in Sources */,
|
||||
DE9A015B289A9A9A00E41CBB /* JMCallKitProxy.swift in Sources */,
|
||||
DE9A015C289A9A9A00E41CBB /* JitsiMeetLogger.m in Sources */,
|
||||
DE9A015D289A9A9A00E41CBB /* JMCallKitListener.swift in Sources */,
|
||||
DE9A015E289A9A9A00E41CBB /* JitsiMeetView.m in Sources */,
|
||||
DE9A015F289A9A9A00E41CBB /* JitsiMeet.m in Sources */,
|
||||
DE9A0160289A9A9A00E41CBB /* JavaScriptSandbox.m in Sources */,
|
||||
);
|
||||
runOnlyForDeploymentPostprocessing = 0;
|
||||
};
|
||||
/* End PBXSourcesBuildPhase section */
|
||||
|
||||
/* Begin XCBuildConfiguration section */
|
||||
@@ -624,7 +891,8 @@
|
||||
PROVISIONING_PROFILE_SPECIFIER = "";
|
||||
SKIP_INSTALL = YES;
|
||||
SUPPORTS_MACCATALYST = NO;
|
||||
SWIFT_OBJC_BRIDGING_HEADER = "";
|
||||
SWIFT_INSTALL_OBJC_HEADER = NO;
|
||||
SWIFT_OBJC_INTERFACE_HEADER_NAME = "";
|
||||
SWIFT_OPTIMIZATION_LEVEL = "-Onone";
|
||||
SWIFT_VERSION = 5.0;
|
||||
};
|
||||
@@ -653,7 +921,77 @@
|
||||
PROVISIONING_PROFILE_SPECIFIER = "";
|
||||
SKIP_INSTALL = YES;
|
||||
SUPPORTS_MACCATALYST = NO;
|
||||
SWIFT_OBJC_BRIDGING_HEADER = "";
|
||||
SWIFT_INSTALL_OBJC_HEADER = NO;
|
||||
SWIFT_OBJC_INTERFACE_HEADER_NAME = "";
|
||||
SWIFT_VERSION = 5.0;
|
||||
};
|
||||
name = Release;
|
||||
};
|
||||
DE9A016D289A9A9A00E41CBB /* Debug */ = {
|
||||
isa = XCBuildConfiguration;
|
||||
baseConfigurationReference = 8F48C340DE0D91D1012976C5 /* Pods-JitsiMeetSDKLite.debug.xcconfig */;
|
||||
buildSettings = {
|
||||
ALWAYS_EMBED_SWIFT_STANDARD_LIBRARIES = NO;
|
||||
ARCHS = "$(ARCHS_STANDARD_64_BIT)";
|
||||
CLANG_ENABLE_MODULES = YES;
|
||||
CODE_SIGN_IDENTITY = "";
|
||||
"CODE_SIGN_IDENTITY[sdk=iphoneos*]" = "";
|
||||
DEFINES_MODULE = YES;
|
||||
DEVELOPMENT_TEAM = "";
|
||||
DYLIB_COMPATIBILITY_VERSION = 1;
|
||||
DYLIB_CURRENT_VERSION = 1;
|
||||
DYLIB_INSTALL_NAME_BASE = "@rpath";
|
||||
ENABLE_BITCODE = NO;
|
||||
"EXCLUDED_ARCHS[sdk=iphonesimulator*]" = "";
|
||||
GCC_PREPROCESSOR_DEFINITIONS = (
|
||||
"$(inherited)",
|
||||
"COCOAPODS=1",
|
||||
"JITSI_MEET_SDK_LITE=1",
|
||||
);
|
||||
INFOPLIST_FILE = "src/Lite-Info.plist";
|
||||
LD_RUNPATH_SEARCH_PATHS = "$(inherited) @executable_path/Frameworks @loader_path/Frameworks";
|
||||
PRODUCT_BUNDLE_IDENTIFIER = org.jitsi.JitsiMeetSDK.ios;
|
||||
PRODUCT_NAME = JitsiMeetSDK;
|
||||
PROVISIONING_PROFILE_SPECIFIER = "";
|
||||
SKIP_INSTALL = YES;
|
||||
SUPPORTS_MACCATALYST = NO;
|
||||
SWIFT_INSTALL_OBJC_HEADER = NO;
|
||||
SWIFT_OBJC_INTERFACE_HEADER_NAME = "";
|
||||
SWIFT_OPTIMIZATION_LEVEL = "-Onone";
|
||||
SWIFT_VERSION = 5.0;
|
||||
};
|
||||
name = Debug;
|
||||
};
|
||||
DE9A016E289A9A9A00E41CBB /* Release */ = {
|
||||
isa = XCBuildConfiguration;
|
||||
baseConfigurationReference = 86389F55993FAAF6AEB3FA3E /* Pods-JitsiMeetSDKLite.release.xcconfig */;
|
||||
buildSettings = {
|
||||
ALWAYS_EMBED_SWIFT_STANDARD_LIBRARIES = NO;
|
||||
ARCHS = "$(ARCHS_STANDARD_64_BIT)";
|
||||
CLANG_ENABLE_MODULES = YES;
|
||||
CODE_SIGN_IDENTITY = "";
|
||||
"CODE_SIGN_IDENTITY[sdk=iphoneos*]" = "";
|
||||
DEFINES_MODULE = YES;
|
||||
DEVELOPMENT_TEAM = "";
|
||||
DYLIB_COMPATIBILITY_VERSION = 1;
|
||||
DYLIB_CURRENT_VERSION = 1;
|
||||
DYLIB_INSTALL_NAME_BASE = "@rpath";
|
||||
ENABLE_BITCODE = YES;
|
||||
"EXCLUDED_ARCHS[sdk=iphonesimulator*]" = "";
|
||||
GCC_PREPROCESSOR_DEFINITIONS = (
|
||||
"$(inherited)",
|
||||
"COCOAPODS=1",
|
||||
JITSI_MEET_SDK_LITE,
|
||||
);
|
||||
INFOPLIST_FILE = "src/Lite-Info.plist";
|
||||
LD_RUNPATH_SEARCH_PATHS = "$(inherited) @executable_path/Frameworks @loader_path/Frameworks";
|
||||
PRODUCT_BUNDLE_IDENTIFIER = org.jitsi.JitsiMeetSDK.ios;
|
||||
PRODUCT_NAME = JitsiMeetSDK;
|
||||
PROVISIONING_PROFILE_SPECIFIER = "";
|
||||
SKIP_INSTALL = YES;
|
||||
SUPPORTS_MACCATALYST = NO;
|
||||
SWIFT_INSTALL_OBJC_HEADER = NO;
|
||||
SWIFT_OBJC_INTERFACE_HEADER_NAME = "";
|
||||
SWIFT_VERSION = 5.0;
|
||||
};
|
||||
name = Release;
|
||||
@@ -679,6 +1017,15 @@
|
||||
defaultConfigurationIsVisible = 0;
|
||||
defaultConfigurationName = Release;
|
||||
};
|
||||
DE9A016C289A9A9A00E41CBB /* Build configuration list for PBXNativeTarget "JitsiMeetSDKLite" */ = {
|
||||
isa = XCConfigurationList;
|
||||
buildConfigurations = (
|
||||
DE9A016D289A9A9A00E41CBB /* Debug */,
|
||||
DE9A016E289A9A9A00E41CBB /* Release */,
|
||||
);
|
||||
defaultConfigurationIsVisible = 0;
|
||||
defaultConfigurationName = Release;
|
||||
};
|
||||
/* End XCConfigurationList section */
|
||||
};
|
||||
rootObject = 0BD906DC1EC0C00300C8C18E /* Project object */;
|
||||
|
||||
@@ -0,0 +1,67 @@
|
||||
<?xml version="1.0" encoding="UTF-8"?>
|
||||
<Scheme
|
||||
LastUpgradeVersion = "1340"
|
||||
version = "1.3">
|
||||
<BuildAction
|
||||
parallelizeBuildables = "YES"
|
||||
buildImplicitDependencies = "YES">
|
||||
<BuildActionEntries>
|
||||
<BuildActionEntry
|
||||
buildForTesting = "YES"
|
||||
buildForRunning = "YES"
|
||||
buildForProfiling = "YES"
|
||||
buildForArchiving = "YES"
|
||||
buildForAnalyzing = "YES">
|
||||
<BuildableReference
|
||||
BuildableIdentifier = "primary"
|
||||
BlueprintIdentifier = "DE9A012D289A9A9A00E41CBB"
|
||||
BuildableName = "JitsiMeetSDK.framework"
|
||||
BlueprintName = "JitsiMeetSDKLite"
|
||||
ReferencedContainer = "container:sdk.xcodeproj">
|
||||
</BuildableReference>
|
||||
</BuildActionEntry>
|
||||
</BuildActionEntries>
|
||||
</BuildAction>
|
||||
<TestAction
|
||||
buildConfiguration = "Debug"
|
||||
selectedDebuggerIdentifier = "Xcode.DebuggerFoundation.Debugger.LLDB"
|
||||
selectedLauncherIdentifier = "Xcode.DebuggerFoundation.Launcher.LLDB"
|
||||
shouldUseLaunchSchemeArgsEnv = "YES">
|
||||
<Testables>
|
||||
</Testables>
|
||||
</TestAction>
|
||||
<LaunchAction
|
||||
buildConfiguration = "Debug"
|
||||
selectedDebuggerIdentifier = "Xcode.DebuggerFoundation.Debugger.LLDB"
|
||||
selectedLauncherIdentifier = "Xcode.DebuggerFoundation.Launcher.LLDB"
|
||||
launchStyle = "0"
|
||||
useCustomWorkingDirectory = "NO"
|
||||
ignoresPersistentStateOnLaunch = "NO"
|
||||
debugDocumentVersioning = "YES"
|
||||
debugServiceExtension = "internal"
|
||||
allowLocationSimulation = "YES">
|
||||
</LaunchAction>
|
||||
<ProfileAction
|
||||
buildConfiguration = "Release"
|
||||
shouldUseLaunchSchemeArgsEnv = "YES"
|
||||
savedToolIdentifier = ""
|
||||
useCustomWorkingDirectory = "NO"
|
||||
debugDocumentVersioning = "YES">
|
||||
<MacroExpansion>
|
||||
<BuildableReference
|
||||
BuildableIdentifier = "primary"
|
||||
BlueprintIdentifier = "DE9A012D289A9A9A00E41CBB"
|
||||
BuildableName = "JitsiMeetSDK.framework"
|
||||
BlueprintName = "JitsiMeetSDKLite"
|
||||
ReferencedContainer = "container:sdk.xcodeproj">
|
||||
</BuildableReference>
|
||||
</MacroExpansion>
|
||||
</ProfileAction>
|
||||
<AnalyzeAction
|
||||
buildConfiguration = "Debug">
|
||||
</AnalyzeAction>
|
||||
<ArchiveAction
|
||||
buildConfiguration = "Release"
|
||||
revealArchiveInOrganizer = "YES">
|
||||
</ArchiveAction>
|
||||
</Scheme>
|
||||
@@ -37,8 +37,10 @@ RCT_EXPORT_MODULE();
|
||||
= [[NSBundle mainBundle] infoDictionary];
|
||||
|
||||
// calendarEnabled
|
||||
BOOL calendarEnabled
|
||||
= infoDictionary[@"NSCalendarsUsageDescription"] != nil;
|
||||
BOOL calendarEnabled = NO;
|
||||
#if !defined(JITSI_MEET_SDK_LITE)
|
||||
calendarEnabled = infoDictionary[@"NSCalendarsUsageDescription"] != nil;
|
||||
#endif
|
||||
|
||||
// name
|
||||
NSString *name = infoDictionary[@"CFBundleDisplayName"];
|
||||
@@ -63,19 +65,39 @@ RCT_EXPORT_MODULE();
|
||||
}
|
||||
}
|
||||
|
||||
// SDK version
|
||||
NSDictionary<NSString *, id> *sdkInfoDictionary
|
||||
= [[NSBundle bundleForClass:self.class] infoDictionary];
|
||||
NSString *sdkVersion = sdkInfoDictionary[@"CFBundleShortVersionString"];
|
||||
if (sdkVersion == nil) {
|
||||
sdkVersion = sdkInfoDictionary[@"CFBundleVersion"];
|
||||
if (sdkVersion == nil) {
|
||||
sdkVersion = @"";
|
||||
}
|
||||
}
|
||||
|
||||
// build number
|
||||
NSString *buildNumber = infoDictionary[@"CFBundleVersion"];
|
||||
if (buildNumber == nil) {
|
||||
buildNumber = @"";
|
||||
}
|
||||
|
||||
// google services (sign in)
|
||||
BOOL isGoogleServiceEnabled = [InfoPlistUtil containsRealServiceInfoPlistInBundle:[NSBundle mainBundle]];
|
||||
|
||||
// lite SDK
|
||||
BOOL isLiteSDK = NO;
|
||||
#if defined(JITSI_MEET_SDK_LITE)
|
||||
isLiteSDK = YES;
|
||||
#endif
|
||||
|
||||
return @{
|
||||
@"calendarEnabled": [NSNumber numberWithBool:calendarEnabled],
|
||||
@"buildNumber": buildNumber,
|
||||
@"isLiteSDK": [NSNumber numberWithBool:isLiteSDK],
|
||||
@"name": name,
|
||||
@"sdkBundlePath": sdkBundlePath,
|
||||
@"sdkVersion": sdkVersion,
|
||||
@"version": version,
|
||||
@"GOOGLE_SERVICES_ENABLED": [NSNumber numberWithBool:isGoogleServiceEnabled]
|
||||
};
|
||||
|
||||
@@ -21,7 +21,6 @@
|
||||
#import <WebRTC/WebRTC.h>
|
||||
|
||||
#import "JitsiAudioSession+Private.h"
|
||||
#import "LogUtils.h"
|
||||
|
||||
|
||||
// Audio mode
|
||||
@@ -178,7 +177,7 @@ RCT_EXPORT_METHOD(setMode:(int)mode
|
||||
RCT_EXPORT_METHOD(setAudioDevice:(NSString *)device
|
||||
resolve:(RCTPromiseResolveBlock)resolve
|
||||
reject:(RCTPromiseRejectBlock)reject) {
|
||||
DDLogInfo(@"[AudioMode] Selected device: %@", device);
|
||||
RCTLogInfo(@"[AudioMode] Selected device: %@", device);
|
||||
|
||||
RTCAudioSession *session = JitsiAudioSession.rtcAudioSession;
|
||||
[session lockForConfiguration];
|
||||
@@ -248,6 +247,8 @@ RCT_EXPORT_METHOD(updateDeviceList) {
|
||||
- (void)audioSessionDidChangeRoute:(RTCAudioSession *)session
|
||||
reason:(AVAudioSessionRouteChangeReason)reason
|
||||
previousRoute:(AVAudioSessionRouteDescription *)previousRoute {
|
||||
RCTLogInfo(@"[AudioMode] Route changed, reason: %lu", (unsigned long)reason);
|
||||
|
||||
// Update JS about the changes.
|
||||
[self notifyDevicesChanged];
|
||||
|
||||
@@ -259,16 +260,12 @@ RCT_EXPORT_METHOD(updateDeviceList) {
|
||||
self->forceSpeaker = NO;
|
||||
self->forceEarpiece = NO;
|
||||
break;
|
||||
case AVAudioSessionRouteChangeReasonCategoryChange: {
|
||||
// The category has changed. Check if it's the one we want and adjust as
|
||||
// needed.
|
||||
RTCAudioSessionConfiguration *currentConfig = [self configForMode:self->activeMode];
|
||||
if ([session.category isEqualToString:currentConfig.category]) {
|
||||
// We are in the desired category, nothing to do here.
|
||||
return;
|
||||
}
|
||||
case AVAudioSessionRouteChangeReasonCategoryChange:
|
||||
// The category has changed, re-apply our config.
|
||||
// NB: It's tempting to doa category check here and skip the processing,
|
||||
// but that won't work. If the config changes but the category remains
|
||||
// the same we'll still find ourselves here.
|
||||
break;
|
||||
}
|
||||
default:
|
||||
return;
|
||||
}
|
||||
@@ -277,7 +274,7 @@ RCT_EXPORT_METHOD(updateDeviceList) {
|
||||
// This is to play well with other components which could be integrated
|
||||
// into the final application.
|
||||
if (self->activeMode != kAudioModeDefault) {
|
||||
DDLogInfo(@"[AudioMode] Route changed, reapplying RTCAudioSession config");
|
||||
RCTLogInfo(@"[AudioMode] Route changed, reapplying RTCAudioSession config");
|
||||
RTCAudioSessionConfiguration *config = [self configForMode:self->activeMode];
|
||||
[self setConfig:config error:nil];
|
||||
if (self->forceSpeaker && !self->isSpeakerOn) {
|
||||
@@ -290,7 +287,7 @@ RCT_EXPORT_METHOD(updateDeviceList) {
|
||||
}
|
||||
|
||||
- (void)audioSession:(RTCAudioSession *)audioSession didSetActive:(BOOL)active {
|
||||
DDLogInfo(@"[AudioMode] Audio session didSetActive:%d", active);
|
||||
RCTLogInfo(@"[AudioMode] Audio session didSetActive:%d", active);
|
||||
}
|
||||
|
||||
#pragma mark - Helper methods
|
||||
|
||||
@@ -16,6 +16,8 @@
|
||||
#import <React/RCTBridgeModule.h>
|
||||
#import <React/RCTEventEmitter.h>
|
||||
|
||||
static NSString * const sendEventNotificationName = @"org.jitsi.meet.SendEvent";
|
||||
|
||||
@interface ExternalAPI : RCTEventEmitter<RCTBridgeModule>
|
||||
|
||||
- (void)sendHangUp;
|
||||
@@ -27,5 +29,6 @@
|
||||
- (void)closeChat;
|
||||
- (void)sendChatMessage:(NSString*)message :(NSString*)to ;
|
||||
- (void)sendSetVideoMuted:(BOOL)muted;
|
||||
- (void)sendSetClosedCaptionsEnabled:(BOOL)enabled;
|
||||
|
||||
@end
|
||||
|
||||
@@ -15,7 +15,6 @@
|
||||
*/
|
||||
|
||||
#import "ExternalAPI.h"
|
||||
#import "JitsiMeetView+Private.h"
|
||||
|
||||
// Events
|
||||
static NSString * const hangUpAction = @"org.jitsi.meet.HANG_UP";
|
||||
@@ -27,6 +26,7 @@ static NSString * const openChatAction = @"org.jitsi.meet.OPEN_CHAT";
|
||||
static NSString * const closeChatAction = @"org.jitsi.meet.CLOSE_CHAT";
|
||||
static NSString * const sendChatMessageAction = @"org.jitsi.meet.SEND_CHAT_MESSAGE";
|
||||
static NSString * const setVideoMutedAction = @"org.jitsi.meet.SET_VIDEO_MUTED";
|
||||
static NSString * const setClosedCaptionsEnabledAction = @"org.jitsi.meet.SET_CLOSED_CAPTIONS_ENABLED";
|
||||
|
||||
@implementation ExternalAPI
|
||||
|
||||
@@ -49,7 +49,8 @@ RCT_EXPORT_MODULE();
|
||||
@"OPEN_CHAT": openChatAction,
|
||||
@"CLOSE_CHAT": closeChatAction,
|
||||
@"SEND_CHAT_MESSAGE": sendChatMessageAction,
|
||||
@"SET_VIDEO_MUTED" : setVideoMutedAction
|
||||
@"SET_VIDEO_MUTED" : setVideoMutedAction,
|
||||
@"SET_CLOSED_CAPTIONS_ENABLED": setClosedCaptionsEnabledAction
|
||||
};
|
||||
};
|
||||
|
||||
@@ -73,7 +74,8 @@ RCT_EXPORT_MODULE();
|
||||
openChatAction,
|
||||
closeChatAction,
|
||||
sendChatMessageAction,
|
||||
setVideoMutedAction
|
||||
setVideoMutedAction,
|
||||
setClosedCaptionsEnabledAction
|
||||
];
|
||||
}
|
||||
|
||||
@@ -86,33 +88,15 @@ RCT_EXPORT_MODULE();
|
||||
* @param scope
|
||||
*/
|
||||
RCT_EXPORT_METHOD(sendEvent:(NSString *)name
|
||||
data:(NSDictionary *)data
|
||||
scope:(NSString *)scope) {
|
||||
// The JavaScript App needs to provide uniquely identifying information to
|
||||
// the native ExternalAPI module so that the latter may match the former
|
||||
// to the native JitsiMeetView which hosts it.
|
||||
JitsiMeetView *view = [JitsiMeetView viewForExternalAPIScope:scope];
|
||||
|
||||
if (!view) {
|
||||
return;
|
||||
}
|
||||
|
||||
id delegate = view.delegate;
|
||||
|
||||
if (!delegate) {
|
||||
return;
|
||||
}
|
||||
|
||||
data:(NSDictionary *)data) {
|
||||
if ([name isEqual: @"PARTICIPANTS_INFO_RETRIEVED"]) {
|
||||
[self onParticipantsInfoRetrieved: data];
|
||||
return;
|
||||
}
|
||||
|
||||
SEL sel = NSSelectorFromString([self methodNameFromEventName:name]);
|
||||
|
||||
if (sel && [delegate respondsToSelector:sel]) {
|
||||
[delegate performSelector:sel withObject:data];
|
||||
}
|
||||
|
||||
[[NSNotificationCenter defaultCenter] postNotificationName:sendEventNotificationName
|
||||
object:nil
|
||||
userInfo:@{@"name": name, @"data": data}];
|
||||
}
|
||||
|
||||
- (void) onParticipantsInfoRetrieved:(NSDictionary *)data {
|
||||
@@ -124,28 +108,6 @@ RCT_EXPORT_METHOD(sendEvent:(NSString *)name
|
||||
[participantInfoCompletionHandlers removeObjectForKey:completionHandlerId];
|
||||
}
|
||||
|
||||
/**
|
||||
* Converts a specific event name i.e. redux action type description to a
|
||||
* method name.
|
||||
*
|
||||
* @param eventName The event name to convert to a method name.
|
||||
* @return A method name constructed from the specified `eventName`.
|
||||
*/
|
||||
- (NSString *)methodNameFromEventName:(NSString *)eventName {
|
||||
NSMutableString *methodName
|
||||
= [NSMutableString stringWithCapacity:eventName.length];
|
||||
|
||||
for (NSString *c in [eventName componentsSeparatedByString:@"_"]) {
|
||||
if (c.length) {
|
||||
[methodName appendString:
|
||||
methodName.length ? c.capitalizedString : c.lowercaseString];
|
||||
}
|
||||
}
|
||||
[methodName appendString:@":"];
|
||||
|
||||
return methodName;
|
||||
}
|
||||
|
||||
- (void)sendHangUp {
|
||||
[self sendEventWithName:hangUpAction body:nil];
|
||||
}
|
||||
@@ -205,5 +167,10 @@ RCT_EXPORT_METHOD(sendEvent:(NSString *)name
|
||||
[self sendEventWithName:setVideoMutedAction body:data];
|
||||
}
|
||||
|
||||
- (void)sendSetClosedCaptionsEnabled:(BOOL)enabled {
|
||||
NSDictionary *data = @{ @"enabled": [NSNumber numberWithBool:enabled]};
|
||||
|
||||
[self sendEventWithName:setClosedCaptionsEnabledAction body:data];
|
||||
}
|
||||
|
||||
@end
|
||||
|
||||
@@ -15,7 +15,7 @@
|
||||
<key>CFBundlePackageType</key>
|
||||
<string>FMWK</string>
|
||||
<key>CFBundleShortVersionString</key>
|
||||
<string>5.1.0</string>
|
||||
<string>6.1.0</string>
|
||||
<key>CFBundleVersion</key>
|
||||
<string>$(CURRENT_PROJECT_VERSION)</string>
|
||||
<key>NSPrincipalClass</key>
|
||||
|
||||
@@ -15,8 +15,8 @@
|
||||
*/
|
||||
|
||||
#import <Intents/Intents.h>
|
||||
#import <WebRTC/RTCLogging.h>
|
||||
|
||||
#import "Dropbox.h"
|
||||
#import "JitsiMeet+Private.h"
|
||||
#import "JitsiMeetConferenceOptions+Private.h"
|
||||
#import "JitsiMeetView+Private.h"
|
||||
@@ -25,8 +25,10 @@
|
||||
#import "RNSplashScreen.h"
|
||||
#import "ScheenshareEventEmiter.h"
|
||||
|
||||
#if !defined(JITSI_MEET_SDK_LITE)
|
||||
#import <RNGoogleSignin/RNGoogleSignin.h>
|
||||
#import <WebRTC/RTCLogging.h>
|
||||
#import "Dropbox.h"
|
||||
#endif
|
||||
|
||||
@implementation JitsiMeet {
|
||||
RCTBridgeWrapper *_bridgeWrapper;
|
||||
@@ -77,7 +79,9 @@
|
||||
|
||||
_launchOptions = [launchOptions copy];
|
||||
|
||||
#if !defined(JITSI_MEET_SDK_LITE)
|
||||
[Dropbox setAppKey];
|
||||
#endif
|
||||
|
||||
return YES;
|
||||
}
|
||||
@@ -87,14 +91,19 @@
|
||||
restorationHandler:(void (^)(NSArray<id<UIUserActivityRestoring>> *))restorationHandler {
|
||||
|
||||
JitsiMeetConferenceOptions *options = [self optionsFromUserActivity:userActivity];
|
||||
if (options) {
|
||||
[JitsiMeetView updateProps:[options asProps]];
|
||||
return true;
|
||||
}
|
||||
|
||||
return options && [JitsiMeetView setPropsInViews:[options asProps]];
|
||||
return false;
|
||||
}
|
||||
|
||||
- (BOOL)application:(UIApplication *)app
|
||||
openURL:(NSURL *)url
|
||||
options:(NSDictionary<UIApplicationOpenURLOptionsKey,id> *)options {
|
||||
|
||||
#if !defined(JITSI_MEET_SDK_LITE)
|
||||
if ([Dropbox application:app openURL:url options:options]) {
|
||||
return YES;
|
||||
}
|
||||
@@ -104,6 +113,7 @@
|
||||
options:options]) {
|
||||
return YES;
|
||||
}
|
||||
#endif
|
||||
|
||||
if (_customUrlScheme == nil || ![_customUrlScheme isEqualToString:url.scheme]) {
|
||||
return NO;
|
||||
@@ -112,8 +122,9 @@
|
||||
JitsiMeetConferenceOptions *conferenceOptions = [JitsiMeetConferenceOptions fromBuilder:^(JitsiMeetConferenceOptionsBuilder *builder) {
|
||||
builder.room = [url absoluteString];
|
||||
}];
|
||||
[JitsiMeetView updateProps:[conferenceOptions asProps]];
|
||||
|
||||
return [JitsiMeetView setPropsInViews:[conferenceOptions asProps]];
|
||||
return true;
|
||||
}
|
||||
|
||||
#pragma mark - Utility methods
|
||||
|
||||
30
ios/sdk/src/JitsiMeetRenderingView.h
Normal file
30
ios/sdk/src/JitsiMeetRenderingView.h
Normal file
@@ -0,0 +1,30 @@
|
||||
/*
|
||||
* Copyright @ 2022-present 8x8, Inc.
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
* You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*/
|
||||
|
||||
#import <UIKit/UIKit.h>
|
||||
#import "JitsiMeetViewDelegate.h"
|
||||
|
||||
NS_ASSUME_NONNULL_BEGIN
|
||||
|
||||
@interface JitsiMeetRenderingView : UIView
|
||||
|
||||
@property (nonatomic, assign) BOOL isPiPEnabled;
|
||||
|
||||
- (void)setProps:(NSDictionary *_Nonnull)newProps;
|
||||
|
||||
@end
|
||||
|
||||
NS_ASSUME_NONNULL_END
|
||||
83
ios/sdk/src/JitsiMeetRenderingView.m
Normal file
83
ios/sdk/src/JitsiMeetRenderingView.m
Normal file
@@ -0,0 +1,83 @@
|
||||
/*
|
||||
* Copyright @ 2022-present 8x8, Inc.
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
* You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*/
|
||||
#include <mach/mach_time.h>
|
||||
|
||||
#import "JitsiMeetRenderingView.h"
|
||||
#import "ReactUtils.h"
|
||||
#import "RNRootView.h"
|
||||
#import "JitsiMeet+Private.h"
|
||||
|
||||
/**
|
||||
* Backwards compatibility: turn the boolean prop into a feature flag.
|
||||
*/
|
||||
static NSString *const PiPEnabledFeatureFlag = @"pip.enabled";
|
||||
|
||||
@interface JitsiMeetRenderingView ()
|
||||
@end
|
||||
|
||||
@implementation JitsiMeetRenderingView {
|
||||
/**
|
||||
* React Native view where the entire content will be rendered.
|
||||
*/
|
||||
RNRootView *rootView;
|
||||
}
|
||||
|
||||
/**
|
||||
* Passes the given props to the React Native application. The props which we pass
|
||||
* are a combination of 3 different sources:
|
||||
*
|
||||
* - JitsiMeet.defaultConferenceOptions
|
||||
* - This function's parameters
|
||||
* - Some extras which are added by this function
|
||||
*/
|
||||
- (void)setProps:(NSDictionary *_Nonnull)newProps {
|
||||
NSMutableDictionary *props = mergeProps([[JitsiMeet sharedInstance] getDefaultProps], newProps);
|
||||
|
||||
// Set the PiP flag if it wasn't manually set.
|
||||
NSMutableDictionary *featureFlags = props[@"flags"];
|
||||
// TODO: temporary implementation
|
||||
if (featureFlags[PiPEnabledFeatureFlag] == nil) {
|
||||
featureFlags[PiPEnabledFeatureFlag] = @(self.isPiPEnabled);
|
||||
}
|
||||
|
||||
// This method is supposed to be imperative i.e. a second
|
||||
// invocation with one and the same URL is expected to join the respective
|
||||
// conference again if the first invocation was followed by leaving the
|
||||
// conference. However, React and, respectively,
|
||||
// appProperties/initialProperties are declarative expressions i.e. one and
|
||||
// the same URL will not trigger an automatic re-render in the JavaScript
|
||||
// source code. The workaround implemented below introduces imperativeness
|
||||
// in React Component props by defining a unique value per invocation.
|
||||
props[@"timestamp"] = @(mach_absolute_time());
|
||||
|
||||
if (rootView) {
|
||||
// Update props with the new URL.
|
||||
rootView.appProperties = props;
|
||||
} else {
|
||||
RCTBridge *bridge = [[JitsiMeet sharedInstance] getReactBridge];
|
||||
rootView = [[RNRootView alloc] initWithBridge:bridge
|
||||
moduleName:@"App"
|
||||
initialProperties:props];
|
||||
rootView.backgroundColor = self.backgroundColor;
|
||||
|
||||
// Add rootView as a subview which completely covers this one.
|
||||
[rootView setFrame:[self bounds]];
|
||||
rootView.autoresizingMask = UIViewAutoresizingFlexibleWidth | UIViewAutoresizingFlexibleHeight;
|
||||
[self addSubview:rootView];
|
||||
}
|
||||
}
|
||||
|
||||
@end
|
||||
271
ios/sdk/src/JitsiMeetSDK-Swift.h
Normal file
271
ios/sdk/src/JitsiMeetSDK-Swift.h
Normal file
@@ -0,0 +1,271 @@
|
||||
// IMPORTANT!
|
||||
// This file was once auto-generated by Xcode, and this is a copy of it. If any of the following
|
||||
// classes is modified this file needs to be regenerated.
|
||||
// - JMCallKitListener
|
||||
// - JMCallKitProxy
|
||||
#ifndef JITSIMEETSDK_SWIFT_H
|
||||
#define JITSIMEETSDK_SWIFT_H
|
||||
#pragma clang diagnostic push
|
||||
#pragma clang diagnostic ignored "-Wgcc-compat"
|
||||
|
||||
#if !defined(__has_include)
|
||||
# define __has_include(x) 0
|
||||
#endif
|
||||
#if !defined(__has_attribute)
|
||||
# define __has_attribute(x) 0
|
||||
#endif
|
||||
#if !defined(__has_feature)
|
||||
# define __has_feature(x) 0
|
||||
#endif
|
||||
#if !defined(__has_warning)
|
||||
# define __has_warning(x) 0
|
||||
#endif
|
||||
|
||||
#if __has_include(<swift/objc-prologue.h>)
|
||||
# include <swift/objc-prologue.h>
|
||||
#endif
|
||||
|
||||
#pragma clang diagnostic ignored "-Wauto-import"
|
||||
#include <Foundation/Foundation.h>
|
||||
#include <stdint.h>
|
||||
#include <stddef.h>
|
||||
#include <stdbool.h>
|
||||
|
||||
#if !defined(SWIFT_TYPEDEFS)
|
||||
# define SWIFT_TYPEDEFS 1
|
||||
# if __has_include(<uchar.h>)
|
||||
# include <uchar.h>
|
||||
# elif !defined(__cplusplus)
|
||||
typedef uint_least16_t char16_t;
|
||||
typedef uint_least32_t char32_t;
|
||||
# endif
|
||||
typedef float swift_float2 __attribute__((__ext_vector_type__(2)));
|
||||
typedef float swift_float3 __attribute__((__ext_vector_type__(3)));
|
||||
typedef float swift_float4 __attribute__((__ext_vector_type__(4)));
|
||||
typedef double swift_double2 __attribute__((__ext_vector_type__(2)));
|
||||
typedef double swift_double3 __attribute__((__ext_vector_type__(3)));
|
||||
typedef double swift_double4 __attribute__((__ext_vector_type__(4)));
|
||||
typedef int swift_int2 __attribute__((__ext_vector_type__(2)));
|
||||
typedef int swift_int3 __attribute__((__ext_vector_type__(3)));
|
||||
typedef int swift_int4 __attribute__((__ext_vector_type__(4)));
|
||||
typedef unsigned int swift_uint2 __attribute__((__ext_vector_type__(2)));
|
||||
typedef unsigned int swift_uint3 __attribute__((__ext_vector_type__(3)));
|
||||
typedef unsigned int swift_uint4 __attribute__((__ext_vector_type__(4)));
|
||||
#endif
|
||||
|
||||
#if !defined(SWIFT_PASTE)
|
||||
# define SWIFT_PASTE_HELPER(x, y) x##y
|
||||
# define SWIFT_PASTE(x, y) SWIFT_PASTE_HELPER(x, y)
|
||||
#endif
|
||||
#if !defined(SWIFT_METATYPE)
|
||||
# define SWIFT_METATYPE(X) Class
|
||||
#endif
|
||||
#if !defined(SWIFT_CLASS_PROPERTY)
|
||||
# if __has_feature(objc_class_property)
|
||||
# define SWIFT_CLASS_PROPERTY(...) __VA_ARGS__
|
||||
# else
|
||||
# define SWIFT_CLASS_PROPERTY(...)
|
||||
# endif
|
||||
#endif
|
||||
|
||||
#if __has_attribute(objc_runtime_name)
|
||||
# define SWIFT_RUNTIME_NAME(X) __attribute__((objc_runtime_name(X)))
|
||||
#else
|
||||
# define SWIFT_RUNTIME_NAME(X)
|
||||
#endif
|
||||
#if __has_attribute(swift_name)
|
||||
# define SWIFT_COMPILE_NAME(X) __attribute__((swift_name(X)))
|
||||
#else
|
||||
# define SWIFT_COMPILE_NAME(X)
|
||||
#endif
|
||||
#if __has_attribute(objc_method_family)
|
||||
# define SWIFT_METHOD_FAMILY(X) __attribute__((objc_method_family(X)))
|
||||
#else
|
||||
# define SWIFT_METHOD_FAMILY(X)
|
||||
#endif
|
||||
#if __has_attribute(noescape)
|
||||
# define SWIFT_NOESCAPE __attribute__((noescape))
|
||||
#else
|
||||
# define SWIFT_NOESCAPE
|
||||
#endif
|
||||
#if __has_attribute(ns_consumed)
|
||||
# define SWIFT_RELEASES_ARGUMENT __attribute__((ns_consumed))
|
||||
#else
|
||||
# define SWIFT_RELEASES_ARGUMENT
|
||||
#endif
|
||||
#if __has_attribute(warn_unused_result)
|
||||
# define SWIFT_WARN_UNUSED_RESULT __attribute__((warn_unused_result))
|
||||
#else
|
||||
# define SWIFT_WARN_UNUSED_RESULT
|
||||
#endif
|
||||
#if __has_attribute(noreturn)
|
||||
# define SWIFT_NORETURN __attribute__((noreturn))
|
||||
#else
|
||||
# define SWIFT_NORETURN
|
||||
#endif
|
||||
#if !defined(SWIFT_CLASS_EXTRA)
|
||||
# define SWIFT_CLASS_EXTRA
|
||||
#endif
|
||||
#if !defined(SWIFT_PROTOCOL_EXTRA)
|
||||
# define SWIFT_PROTOCOL_EXTRA
|
||||
#endif
|
||||
#if !defined(SWIFT_ENUM_EXTRA)
|
||||
# define SWIFT_ENUM_EXTRA
|
||||
#endif
|
||||
#if !defined(SWIFT_CLASS)
|
||||
# if __has_attribute(objc_subclassing_restricted)
|
||||
# define SWIFT_CLASS(SWIFT_NAME) SWIFT_RUNTIME_NAME(SWIFT_NAME) __attribute__((objc_subclassing_restricted)) SWIFT_CLASS_EXTRA
|
||||
# define SWIFT_CLASS_NAMED(SWIFT_NAME) __attribute__((objc_subclassing_restricted)) SWIFT_COMPILE_NAME(SWIFT_NAME) SWIFT_CLASS_EXTRA
|
||||
# else
|
||||
# define SWIFT_CLASS(SWIFT_NAME) SWIFT_RUNTIME_NAME(SWIFT_NAME) SWIFT_CLASS_EXTRA
|
||||
# define SWIFT_CLASS_NAMED(SWIFT_NAME) SWIFT_COMPILE_NAME(SWIFT_NAME) SWIFT_CLASS_EXTRA
|
||||
# endif
|
||||
#endif
|
||||
#if !defined(SWIFT_RESILIENT_CLASS)
|
||||
# if __has_attribute(objc_class_stub)
|
||||
# define SWIFT_RESILIENT_CLASS(SWIFT_NAME) SWIFT_CLASS(SWIFT_NAME) __attribute__((objc_class_stub))
|
||||
# define SWIFT_RESILIENT_CLASS_NAMED(SWIFT_NAME) __attribute__((objc_class_stub)) SWIFT_CLASS_NAMED(SWIFT_NAME)
|
||||
# else
|
||||
# define SWIFT_RESILIENT_CLASS(SWIFT_NAME) SWIFT_CLASS(SWIFT_NAME)
|
||||
# define SWIFT_RESILIENT_CLASS_NAMED(SWIFT_NAME) SWIFT_CLASS_NAMED(SWIFT_NAME)
|
||||
# endif
|
||||
#endif
|
||||
|
||||
#if !defined(SWIFT_PROTOCOL)
|
||||
# define SWIFT_PROTOCOL(SWIFT_NAME) SWIFT_RUNTIME_NAME(SWIFT_NAME) SWIFT_PROTOCOL_EXTRA
|
||||
# define SWIFT_PROTOCOL_NAMED(SWIFT_NAME) SWIFT_COMPILE_NAME(SWIFT_NAME) SWIFT_PROTOCOL_EXTRA
|
||||
#endif
|
||||
|
||||
#if !defined(SWIFT_EXTENSION)
|
||||
# define SWIFT_EXTENSION(M) SWIFT_PASTE(M##_Swift_, __LINE__)
|
||||
#endif
|
||||
|
||||
#if !defined(OBJC_DESIGNATED_INITIALIZER)
|
||||
# if __has_attribute(objc_designated_initializer)
|
||||
# define OBJC_DESIGNATED_INITIALIZER __attribute__((objc_designated_initializer))
|
||||
# else
|
||||
# define OBJC_DESIGNATED_INITIALIZER
|
||||
# endif
|
||||
#endif
|
||||
#if !defined(SWIFT_ENUM_ATTR)
|
||||
# if defined(__has_attribute) && __has_attribute(enum_extensibility)
|
||||
# define SWIFT_ENUM_ATTR(_extensibility) __attribute__((enum_extensibility(_extensibility)))
|
||||
# else
|
||||
# define SWIFT_ENUM_ATTR(_extensibility)
|
||||
# endif
|
||||
#endif
|
||||
#if !defined(SWIFT_ENUM)
|
||||
# define SWIFT_ENUM(_type, _name, _extensibility) enum _name : _type _name; enum SWIFT_ENUM_ATTR(_extensibility) SWIFT_ENUM_EXTRA _name : _type
|
||||
# if __has_feature(generalized_swift_name)
|
||||
# define SWIFT_ENUM_NAMED(_type, _name, SWIFT_NAME, _extensibility) enum _name : _type _name SWIFT_COMPILE_NAME(SWIFT_NAME); enum SWIFT_COMPILE_NAME(SWIFT_NAME) SWIFT_ENUM_ATTR(_extensibility) SWIFT_ENUM_EXTRA _name : _type
|
||||
# else
|
||||
# define SWIFT_ENUM_NAMED(_type, _name, SWIFT_NAME, _extensibility) SWIFT_ENUM(_type, _name, _extensibility)
|
||||
# endif
|
||||
#endif
|
||||
#if !defined(SWIFT_UNAVAILABLE)
|
||||
# define SWIFT_UNAVAILABLE __attribute__((unavailable))
|
||||
#endif
|
||||
#if !defined(SWIFT_UNAVAILABLE_MSG)
|
||||
# define SWIFT_UNAVAILABLE_MSG(msg) __attribute__((unavailable(msg)))
|
||||
#endif
|
||||
#if !defined(SWIFT_AVAILABILITY)
|
||||
# define SWIFT_AVAILABILITY(plat, ...) __attribute__((availability(plat, __VA_ARGS__)))
|
||||
#endif
|
||||
#if !defined(SWIFT_WEAK_IMPORT)
|
||||
# define SWIFT_WEAK_IMPORT __attribute__((weak_import))
|
||||
#endif
|
||||
#if !defined(SWIFT_DEPRECATED)
|
||||
# define SWIFT_DEPRECATED __attribute__((deprecated))
|
||||
#endif
|
||||
#if !defined(SWIFT_DEPRECATED_MSG)
|
||||
# define SWIFT_DEPRECATED_MSG(...) __attribute__((deprecated(__VA_ARGS__)))
|
||||
#endif
|
||||
#if __has_feature(attribute_diagnose_if_objc)
|
||||
# define SWIFT_DEPRECATED_OBJC(Msg) __attribute__((diagnose_if(1, Msg, "warning")))
|
||||
#else
|
||||
# define SWIFT_DEPRECATED_OBJC(Msg) SWIFT_DEPRECATED_MSG(Msg)
|
||||
#endif
|
||||
#if !defined(IBSegueAction)
|
||||
# define IBSegueAction
|
||||
#endif
|
||||
#if !defined(SWIFT_EXTERN)
|
||||
# if defined(__cplusplus)
|
||||
# define SWIFT_EXTERN extern "C"
|
||||
# else
|
||||
# define SWIFT_EXTERN extern
|
||||
# endif
|
||||
#endif
|
||||
#if __has_feature(modules)
|
||||
#if __has_warning("-Watimport-in-framework-header")
|
||||
#pragma clang diagnostic ignored "-Watimport-in-framework-header"
|
||||
#endif
|
||||
@import CallKit;
|
||||
@import ObjectiveC;
|
||||
#endif
|
||||
|
||||
#pragma clang diagnostic ignored "-Wproperty-attribute-mismatch"
|
||||
#pragma clang diagnostic ignored "-Wduplicate-method-arg"
|
||||
#if __has_warning("-Wpragma-clang-attribute")
|
||||
# pragma clang diagnostic ignored "-Wpragma-clang-attribute"
|
||||
#endif
|
||||
#pragma clang diagnostic ignored "-Wunknown-pragmas"
|
||||
#pragma clang diagnostic ignored "-Wnullability"
|
||||
|
||||
#if __has_attribute(external_source_symbol)
|
||||
# pragma push_macro("any")
|
||||
# undef any
|
||||
# pragma clang attribute push(__attribute__((external_source_symbol(language="Swift", defined_in="JitsiMeetSDK",generated_declaration))), apply_to=any(function,enum,objc_interface,objc_category,objc_protocol))
|
||||
# pragma pop_macro("any")
|
||||
#endif
|
||||
|
||||
|
||||
|
||||
@class NSUUID;
|
||||
@class AVAudioSession;
|
||||
@class CXAction;
|
||||
|
||||
SWIFT_PROTOCOL("_TtP12JitsiMeetSDK17JMCallKitListener_")
|
||||
@protocol JMCallKitListener <NSObject>
|
||||
@optional
|
||||
- (void)providerDidReset;
|
||||
- (void)performAnswerCallWithUUID:(NSUUID * _Nonnull)UUID;
|
||||
- (void)performEndCallWithUUID:(NSUUID * _Nonnull)UUID;
|
||||
- (void)performSetMutedCallWithUUID:(NSUUID * _Nonnull)UUID isMuted:(BOOL)isMuted;
|
||||
- (void)performStartCallWithUUID:(NSUUID * _Nonnull)UUID isVideo:(BOOL)isVideo;
|
||||
- (void)providerDidActivateAudioSessionWithSession:(AVAudioSession * _Nonnull)session;
|
||||
- (void)providerDidDeactivateAudioSessionWithSession:(AVAudioSession * _Nonnull)session;
|
||||
- (void)providerTimedOutPerformingActionWithAction:(CXAction * _Nonnull)action;
|
||||
@end
|
||||
|
||||
@class NSString;
|
||||
@class NSData;
|
||||
@class NSDate;
|
||||
@class CXTransaction;
|
||||
|
||||
SWIFT_CLASS("_TtC12JitsiMeetSDK14JMCallKitProxy")
|
||||
@interface JMCallKitProxy : NSObject
|
||||
- (nonnull instancetype)init SWIFT_UNAVAILABLE;
|
||||
+ (nonnull instancetype)new SWIFT_UNAVAILABLE_MSG("-init is unavailable");
|
||||
/// Enables the proxy in between CallKit and the consumers of the SDK.
|
||||
/// Defaults to disabled. Set to true when you want to use CallKit.
|
||||
SWIFT_CLASS_PROPERTY(@property (nonatomic, class) BOOL enabled;)
|
||||
+ (BOOL)enabled SWIFT_WARN_UNUSED_RESULT;
|
||||
+ (void)setEnabled:(BOOL)value;
|
||||
+ (void)configureProviderWithLocalizedName:(NSString * _Nonnull)localizedName ringtoneSound:(NSString * _Nullable)ringtoneSound iconTemplateImageData:(NSData * _Nullable)iconTemplateImageData;
|
||||
+ (BOOL)isProviderConfigured SWIFT_WARN_UNUSED_RESULT;
|
||||
+ (void)addListener:(id <JMCallKitListener> _Nonnull)listener;
|
||||
+ (void)removeListener:(id <JMCallKitListener> _Nonnull)listener;
|
||||
+ (BOOL)hasActiveCallForUUID:(NSString * _Nonnull)callUUID SWIFT_WARN_UNUSED_RESULT;
|
||||
+ (void)reportNewIncomingCallWithUUID:(NSUUID * _Nonnull)UUID handle:(NSString * _Nullable)handle displayName:(NSString * _Nullable)displayName hasVideo:(BOOL)hasVideo completion:(void (^ _Nonnull)(NSError * _Nullable))completion;
|
||||
+ (void)reportCallUpdateWith:(NSUUID * _Nonnull)UUID handle:(NSString * _Nullable)handle displayName:(NSString * _Nullable)displayName hasVideo:(BOOL)hasVideo;
|
||||
+ (void)reportCallWith:(NSUUID * _Nonnull)UUID endedAt:(NSDate * _Nullable)dateEnded reason:(CXCallEndedReason)endedReason;
|
||||
+ (void)reportOutgoingCallWith:(NSUUID * _Nonnull)UUID startedConnectingAt:(NSDate * _Nullable)dateStartedConnecting;
|
||||
+ (void)reportOutgoingCallWith:(NSUUID * _Nonnull)UUID connectedAt:(NSDate * _Nullable)dateConnected;
|
||||
+ (void)request:(CXTransaction * _Nonnull)transaction completion:(void (^ _Nonnull)(NSError * _Nullable))completion;
|
||||
@end
|
||||
|
||||
#if __has_attribute(external_source_symbol)
|
||||
# pragma clang attribute pop
|
||||
#endif
|
||||
#pragma clang diagnostic pop
|
||||
#endif
|
||||
@@ -1,6 +1,5 @@
|
||||
/*
|
||||
* Copyright @ 2018-present 8x8, Inc.
|
||||
* Copyright @ 2017-2018 Atlassian Pty Ltd
|
||||
* Copyright @ 2022-present 8x8, Inc.
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
@@ -15,11 +14,16 @@
|
||||
* limitations under the License.
|
||||
*/
|
||||
|
||||
#import "JitsiMeetView.h"
|
||||
#import <JitsiMeetSDK/JitsiMeetSDK.h>
|
||||
|
||||
@interface JitsiMeetView ()
|
||||
NS_ASSUME_NONNULL_BEGIN
|
||||
|
||||
+ (instancetype _Nullable)viewForExternalAPIScope:(NSString *_Nonnull)externalAPIScope;
|
||||
+ (BOOL)setPropsInViews:(NSDictionary *_Nonnull)newProps;
|
||||
static NSString * const updateViewPropsNotificationName = @"org.jitsi.meet.UpdateViewProps";
|
||||
|
||||
@interface JitsiMeetView (Private)
|
||||
|
||||
+ (void)updateProps:(NSDictionary *_Nonnull)newProps;
|
||||
|
||||
@end
|
||||
|
||||
NS_ASSUME_NONNULL_END
|
||||
|
||||
25
ios/sdk/src/JitsiMeetView+Private.m
Normal file
25
ios/sdk/src/JitsiMeetView+Private.m
Normal file
@@ -0,0 +1,25 @@
|
||||
/*
|
||||
* Copyright @ 2022-present 8x8, Inc.
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
* You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*/
|
||||
|
||||
#import "JitsiMeetView+Private.h"
|
||||
|
||||
@implementation JitsiMeetView (Private)
|
||||
|
||||
+ (void)updateProps:(NSDictionary *_Nonnull)newProps {
|
||||
[[NSNotificationCenter defaultCenter] postNotificationName:updateViewPropsNotificationName object:nil userInfo:@{@"props": newProps}];
|
||||
}
|
||||
|
||||
@end
|
||||
@@ -45,5 +45,6 @@
|
||||
- (void)closeChat;
|
||||
- (void)sendChatMessage:(NSString * _Nonnull)message :(NSString * _Nullable)to;
|
||||
- (void)setVideoMuted:(BOOL)muted;
|
||||
- (void)setClosedCaptionsEnabled:(BOOL)enabled;
|
||||
|
||||
@end
|
||||
|
||||
@@ -20,43 +20,22 @@
|
||||
#import "ExternalAPI.h"
|
||||
#import "JitsiMeet+Private.h"
|
||||
#import "JitsiMeetConferenceOptions+Private.h"
|
||||
#import "JitsiMeetView+Private.h"
|
||||
#import "JitsiMeetView.h"
|
||||
#import "JitsiMeetViewController.h"
|
||||
#import "ReactUtils.h"
|
||||
#import "RNRootView.h"
|
||||
|
||||
@interface JitsiMeetView ()
|
||||
|
||||
/**
|
||||
* Backwards compatibility: turn the boolean prop into a feature flag.
|
||||
*/
|
||||
static NSString *const PiPEnabledFeatureFlag = @"pip.enabled";
|
||||
@property (nonatomic, strong) JitsiMeetViewController *jitsiMeetViewController;
|
||||
@property (nonatomic, strong) UINavigationController *navController;
|
||||
@property (nonatomic, readonly) BOOL isPiPEnabled;
|
||||
|
||||
@end
|
||||
|
||||
@implementation JitsiMeetView {
|
||||
/**
|
||||
* The unique identifier of this `JitsiMeetView` within the process for the
|
||||
* purposes of `ExternalAPI`. The name scope was inspired by postis which we
|
||||
* use on Web for the similar purposes of the iframe-based external API.
|
||||
*/
|
||||
NSString *externalAPIScope;
|
||||
@implementation JitsiMeetView
|
||||
|
||||
/**
|
||||
* React Native view where the entire content will be rendered.
|
||||
*/
|
||||
RNRootView *rootView;
|
||||
}
|
||||
|
||||
/**
|
||||
* The `JitsiMeetView`s associated with their `ExternalAPI` scopes (i.e. unique
|
||||
* identifiers within the process).
|
||||
*/
|
||||
static NSMapTable<NSString *, JitsiMeetView *> *views;
|
||||
/**
|
||||
* This gets called automagically when the program starts.
|
||||
*/
|
||||
__attribute__((constructor))
|
||||
static void initializeViewsMap() {
|
||||
views = [NSMapTable strongToWeakObjectsMapTable];
|
||||
}
|
||||
@dynamic isPiPEnabled;
|
||||
|
||||
#pragma mark Initializers
|
||||
|
||||
@@ -87,6 +66,10 @@ static void initializeViewsMap() {
|
||||
return self;
|
||||
}
|
||||
|
||||
- (void)dealloc {
|
||||
[[NSNotificationCenter defaultCenter] removeObserver:self];
|
||||
}
|
||||
|
||||
/**
|
||||
* Internal initialization:
|
||||
*
|
||||
@@ -94,145 +77,105 @@ static void initializeViewsMap() {
|
||||
* - initializes the external API scope
|
||||
*/
|
||||
- (void)initWithXXX {
|
||||
// Hook this JitsiMeetView into ExternalAPI.
|
||||
externalAPIScope = [NSUUID UUID].UUIDString;
|
||||
[views setObject:self forKey:externalAPIScope];
|
||||
|
||||
// Set a background color which is in accord with the JavaScript and Android
|
||||
// parts of the application and causes less perceived visual flicker than
|
||||
// the default background color.
|
||||
self.backgroundColor
|
||||
= [UIColor colorWithRed:.07f green:.07f blue:.07f alpha:1];
|
||||
self.jitsiMeetViewController = [[JitsiMeetViewController alloc] init];
|
||||
self.jitsiMeetViewController.view.frame = [self bounds];
|
||||
[self addSubview:self.jitsiMeetViewController.view];
|
||||
|
||||
[self registerObservers];
|
||||
}
|
||||
|
||||
#pragma mark API
|
||||
|
||||
- (void)join:(JitsiMeetConferenceOptions *)options {
|
||||
[self setProps:options == nil ? @{} : [options asProps]];
|
||||
[self.jitsiMeetViewController join:options withPiP:self.isPiPEnabled];
|
||||
}
|
||||
|
||||
- (void)leave {
|
||||
[self setProps:@{}];
|
||||
[self.jitsiMeetViewController leave];
|
||||
}
|
||||
|
||||
- (void)hangUp {
|
||||
ExternalAPI *externalAPI = [[JitsiMeet sharedInstance] getExternalAPI];
|
||||
[externalAPI sendHangUp];
|
||||
[self.jitsiMeetViewController hangUp];
|
||||
}
|
||||
|
||||
- (void)setAudioMuted:(BOOL)muted {
|
||||
ExternalAPI *externalAPI = [[JitsiMeet sharedInstance] getExternalAPI];
|
||||
[externalAPI sendSetAudioMuted:muted];
|
||||
[self.jitsiMeetViewController setAudioMuted:muted];
|
||||
}
|
||||
|
||||
- (void)sendEndpointTextMessage:(NSString * _Nonnull)message :(NSString * _Nullable)to {
|
||||
ExternalAPI *externalAPI = [[JitsiMeet sharedInstance] getExternalAPI];
|
||||
[externalAPI sendEndpointTextMessage:message :to];
|
||||
[self.jitsiMeetViewController sendEndpointTextMessage:message :to];
|
||||
}
|
||||
|
||||
- (void)toggleScreenShare:(BOOL)enabled {
|
||||
ExternalAPI *externalAPI = [[JitsiMeet sharedInstance] getExternalAPI];
|
||||
[externalAPI toggleScreenShare:enabled];
|
||||
[self.jitsiMeetViewController toggleScreenShare:enabled];
|
||||
}
|
||||
|
||||
- (void)retrieveParticipantsInfo:(void (^ _Nonnull)(NSArray * _Nullable))completionHandler {
|
||||
ExternalAPI *externalAPI = [[JitsiMeet sharedInstance] getExternalAPI];
|
||||
[externalAPI retrieveParticipantsInfo:completionHandler];
|
||||
[self.jitsiMeetViewController retrieveParticipantsInfo:completionHandler];
|
||||
}
|
||||
|
||||
- (void)openChat:(NSString*)to {
|
||||
ExternalAPI *externalAPI = [[JitsiMeet sharedInstance] getExternalAPI];
|
||||
[externalAPI openChat:to];
|
||||
[self.jitsiMeetViewController openChat:to];
|
||||
}
|
||||
|
||||
- (void)closeChat {
|
||||
ExternalAPI *externalAPI = [[JitsiMeet sharedInstance] getExternalAPI];
|
||||
[externalAPI closeChat];
|
||||
[self.jitsiMeetViewController closeChat];
|
||||
}
|
||||
|
||||
- (void)sendChatMessage:(NSString * _Nonnull)message :(NSString * _Nullable)to {
|
||||
ExternalAPI *externalAPI = [[JitsiMeet sharedInstance] getExternalAPI];
|
||||
[externalAPI sendChatMessage:message :to];
|
||||
[self.jitsiMeetViewController sendChatMessage:message :to];
|
||||
}
|
||||
|
||||
- (void)setVideoMuted:(BOOL)muted {
|
||||
ExternalAPI *externalAPI = [[JitsiMeet sharedInstance] getExternalAPI];
|
||||
[externalAPI sendSetVideoMuted:muted];
|
||||
[self.jitsiMeetViewController setVideoMuted:muted];
|
||||
}
|
||||
|
||||
#pragma mark Private methods
|
||||
- (void)setClosedCaptionsEnabled:(BOOL)enabled {
|
||||
ExternalAPI *externalAPI = [[JitsiMeet sharedInstance] getExternalAPI];
|
||||
[externalAPI sendSetClosedCaptionsEnabled:enabled];
|
||||
}
|
||||
|
||||
#pragma mark Private
|
||||
|
||||
- (BOOL)isPiPEnabled {
|
||||
return self.delegate && [self.delegate respondsToSelector:@selector(enterPictureInPicture:)];
|
||||
}
|
||||
|
||||
- (void)registerObservers {
|
||||
[[NSNotificationCenter defaultCenter] addObserver:self selector:@selector(handleSendEventNotification:) name:sendEventNotificationName object:nil];
|
||||
}
|
||||
|
||||
- (void)handleSendEventNotification:(NSNotification *)notification {
|
||||
NSString *eventName = notification.userInfo[@"name"];
|
||||
NSString *eventData = notification.userInfo[@"data"];
|
||||
|
||||
SEL sel = NSSelectorFromString([self methodNameFromEventName:eventName]);
|
||||
|
||||
if (sel && [self.delegate respondsToSelector:sel]) {
|
||||
[self.delegate performSelector:sel withObject:eventData];
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Passes the given props to the React Native application. The props which we pass
|
||||
* are a combination of 3 different sources:
|
||||
* Converts a specific event name i.e. redux action type description to a
|
||||
* method name.
|
||||
*
|
||||
* - JitsiMeet.defaultConferenceOptions
|
||||
* - This function's parameters
|
||||
* - Some extras which are added by this function
|
||||
* @param eventName The event name to convert to a method name.
|
||||
* @return A method name constructed from the specified `eventName`.
|
||||
*/
|
||||
- (void)setProps:(NSDictionary *_Nonnull)newProps {
|
||||
NSMutableDictionary *props = mergeProps([[JitsiMeet sharedInstance] getDefaultProps], newProps);
|
||||
- (NSString *)methodNameFromEventName:(NSString *)eventName {
|
||||
NSMutableString *methodName
|
||||
= [NSMutableString stringWithCapacity:eventName.length];
|
||||
|
||||
// Set the PiP flag if it wasn't manually set.
|
||||
NSMutableDictionary *featureFlags = props[@"flags"];
|
||||
if (featureFlags[PiPEnabledFeatureFlag] == nil) {
|
||||
featureFlags[PiPEnabledFeatureFlag]
|
||||
= [NSNumber numberWithBool:
|
||||
self.delegate && [self.delegate respondsToSelector:@selector(enterPictureInPicture:)]];
|
||||
}
|
||||
for (NSString *c in [eventName componentsSeparatedByString:@"_"]) {
|
||||
if (c.length) {
|
||||
[methodName appendString:
|
||||
methodName.length ? c.capitalizedString : c.lowercaseString];
|
||||
}
|
||||
}
|
||||
[methodName appendString:@":"];
|
||||
|
||||
props[@"externalAPIScope"] = externalAPIScope;
|
||||
|
||||
// This method is supposed to be imperative i.e. a second
|
||||
// invocation with one and the same URL is expected to join the respective
|
||||
// conference again if the first invocation was followed by leaving the
|
||||
// conference. However, React and, respectively,
|
||||
// appProperties/initialProperties are declarative expressions i.e. one and
|
||||
// the same URL will not trigger an automatic re-render in the JavaScript
|
||||
// source code. The workaround implemented below introduces imperativeness
|
||||
// in React Component props by defining a unique value per invocation.
|
||||
props[@"timestamp"] = @(mach_absolute_time());
|
||||
|
||||
if (rootView) {
|
||||
// Update props with the new URL.
|
||||
rootView.appProperties = props;
|
||||
} else {
|
||||
RCTBridge *bridge = [[JitsiMeet sharedInstance] getReactBridge];
|
||||
rootView
|
||||
= [[RNRootView alloc] initWithBridge:bridge
|
||||
moduleName:@"App"
|
||||
initialProperties:props];
|
||||
rootView.backgroundColor = self.backgroundColor;
|
||||
|
||||
// Add rootView as a subview which completely covers this one.
|
||||
[rootView setFrame:[self bounds]];
|
||||
rootView.autoresizingMask
|
||||
= UIViewAutoresizingFlexibleWidth
|
||||
| UIViewAutoresizingFlexibleHeight;
|
||||
[self addSubview:rootView];
|
||||
}
|
||||
}
|
||||
|
||||
+ (BOOL)setPropsInViews:(NSDictionary *_Nonnull)newProps {
|
||||
BOOL handled = NO;
|
||||
|
||||
if (views) {
|
||||
for (NSString *externalAPIScope in views) {
|
||||
JitsiMeetView *view
|
||||
= [self viewForExternalAPIScope:externalAPIScope];
|
||||
|
||||
if (view) {
|
||||
[view setProps:newProps];
|
||||
handled = YES;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
return handled;
|
||||
}
|
||||
|
||||
+ (instancetype)viewForExternalAPIScope:(NSString *)externalAPIScope {
|
||||
return [views objectForKey:externalAPIScope];
|
||||
return methodName;
|
||||
}
|
||||
|
||||
@end
|
||||
|
||||
38
ios/sdk/src/JitsiMeetViewController.h
Normal file
38
ios/sdk/src/JitsiMeetViewController.h
Normal file
@@ -0,0 +1,38 @@
|
||||
/*
|
||||
* Copyright @ 2022-present 8x8, Inc.
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
* You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*/
|
||||
|
||||
#import <UIKit/UIKit.h>
|
||||
#import "JitsiMeetConferenceOptions.h"
|
||||
|
||||
NS_ASSUME_NONNULL_BEGIN
|
||||
|
||||
@interface JitsiMeetViewController : UIViewController
|
||||
|
||||
- (void)join:(JitsiMeetConferenceOptions *)options withPiP:(BOOL)enablePiP;
|
||||
- (void)leave;
|
||||
- (void)hangUp;
|
||||
- (void)setAudioMuted:(BOOL)muted;
|
||||
- (void)sendEndpointTextMessage:(NSString * _Nonnull)message :(NSString * _Nullable)to;
|
||||
- (void)toggleScreenShare:(BOOL)enabled;
|
||||
- (void)retrieveParticipantsInfo:(void (^ _Nonnull)(NSArray * _Nullable))completionHandler;
|
||||
- (void)openChat:(NSString*)to;
|
||||
- (void)closeChat;
|
||||
- (void)sendChatMessage:(NSString * _Nonnull)message :(NSString * _Nullable)to;
|
||||
- (void)setVideoMuted:(BOOL)muted;
|
||||
|
||||
@end
|
||||
|
||||
NS_ASSUME_NONNULL_END
|
||||
127
ios/sdk/src/JitsiMeetViewController.m
Normal file
127
ios/sdk/src/JitsiMeetViewController.m
Normal file
@@ -0,0 +1,127 @@
|
||||
/*
|
||||
* Copyright @ 2022-present 8x8, Inc.
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
* You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*/
|
||||
|
||||
#import "JitsiMeetViewController.h"
|
||||
#import "JitsiMeet+Private.h"
|
||||
#import "JitsiMeetConferenceOptions+Private.h"
|
||||
#import "JitsiMeetRenderingView.h"
|
||||
#import "JitsiMeetView+Private.h"
|
||||
|
||||
@interface JitsiMeetViewController ()
|
||||
|
||||
@property (strong, nonatomic) JitsiMeetRenderingView *view;
|
||||
|
||||
@end
|
||||
|
||||
@implementation JitsiMeetViewController
|
||||
|
||||
@dynamic view;
|
||||
|
||||
- (instancetype)init {
|
||||
self = [super init];
|
||||
if (self) {
|
||||
[self registerObservers];
|
||||
}
|
||||
|
||||
return self;
|
||||
}
|
||||
|
||||
- (void)dealloc {
|
||||
[[NSNotificationCenter defaultCenter] removeObserver:self];
|
||||
}
|
||||
|
||||
- (void)loadView {
|
||||
[super loadView];
|
||||
|
||||
self.view = [[JitsiMeetRenderingView alloc] init];
|
||||
self.view.autoresizingMask = UIViewAutoresizingFlexibleWidth | UIViewAutoresizingFlexibleHeight;
|
||||
}
|
||||
|
||||
- (void)viewDidLoad {
|
||||
[super viewDidLoad];
|
||||
|
||||
// Set a background color which is in accord with the JavaScript and Android
|
||||
// parts of the application and causes less perceived visual flicker than
|
||||
// the default background color.
|
||||
self.view.backgroundColor = [UIColor colorWithRed:.07f green:.07f blue:.07f alpha:1];
|
||||
}
|
||||
|
||||
- (void)join:(JitsiMeetConferenceOptions *)options withPiP:(BOOL)enablePiP {
|
||||
self.view.isPiPEnabled = enablePiP;
|
||||
[self.view setProps:options == nil ? @{} : [options asProps]];
|
||||
}
|
||||
|
||||
- (void)leave {
|
||||
[self.view setProps:@{}];
|
||||
}
|
||||
|
||||
- (void)hangUp {
|
||||
ExternalAPI *externalAPI = [[JitsiMeet sharedInstance] getExternalAPI];
|
||||
[externalAPI sendHangUp];
|
||||
}
|
||||
|
||||
- (void)setAudioMuted:(BOOL)muted {
|
||||
ExternalAPI *externalAPI = [[JitsiMeet sharedInstance] getExternalAPI];
|
||||
[externalAPI sendSetAudioMuted:muted];
|
||||
}
|
||||
|
||||
- (void)sendEndpointTextMessage:(NSString * _Nonnull)message :(NSString * _Nullable)to {
|
||||
ExternalAPI *externalAPI = [[JitsiMeet sharedInstance] getExternalAPI];
|
||||
[externalAPI sendEndpointTextMessage:message :to];
|
||||
}
|
||||
|
||||
- (void)toggleScreenShare:(BOOL)enabled {
|
||||
ExternalAPI *externalAPI = [[JitsiMeet sharedInstance] getExternalAPI];
|
||||
[externalAPI toggleScreenShare:enabled];
|
||||
}
|
||||
|
||||
- (void)retrieveParticipantsInfo:(void (^ _Nonnull)(NSArray * _Nullable))completionHandler {
|
||||
ExternalAPI *externalAPI = [[JitsiMeet sharedInstance] getExternalAPI];
|
||||
[externalAPI retrieveParticipantsInfo:completionHandler];
|
||||
}
|
||||
|
||||
- (void)openChat:(NSString*)to {
|
||||
ExternalAPI *externalAPI = [[JitsiMeet sharedInstance] getExternalAPI];
|
||||
[externalAPI openChat:to];
|
||||
}
|
||||
|
||||
- (void)closeChat {
|
||||
ExternalAPI *externalAPI = [[JitsiMeet sharedInstance] getExternalAPI];
|
||||
[externalAPI closeChat];
|
||||
}
|
||||
|
||||
- (void)sendChatMessage:(NSString * _Nonnull)message :(NSString * _Nullable)to {
|
||||
ExternalAPI *externalAPI = [[JitsiMeet sharedInstance] getExternalAPI];
|
||||
[externalAPI sendChatMessage:message :to];
|
||||
}
|
||||
|
||||
- (void)setVideoMuted:(BOOL)muted {
|
||||
ExternalAPI *externalAPI = [[JitsiMeet sharedInstance] getExternalAPI];
|
||||
[externalAPI sendSetVideoMuted:muted];
|
||||
}
|
||||
|
||||
#pragma mark Private
|
||||
|
||||
- (void)registerObservers {
|
||||
[[NSNotificationCenter defaultCenter] addObserver:self selector:@selector(handleUpdateViewPropsNotification:) name:updateViewPropsNotificationName object:nil];
|
||||
}
|
||||
|
||||
- (void)handleUpdateViewPropsNotification:(NSNotification *)notification {
|
||||
NSDictionary *props = [notification.userInfo objectForKey:@"props"];
|
||||
[self.view setProps:props];
|
||||
}
|
||||
|
||||
@end
|
||||
24
ios/sdk/src/Lite-Info.plist
Normal file
24
ios/sdk/src/Lite-Info.plist
Normal file
@@ -0,0 +1,24 @@
|
||||
<?xml version="1.0" encoding="UTF-8"?>
|
||||
<!DOCTYPE plist PUBLIC "-//Apple//DTD PLIST 1.0//EN" "http://www.apple.com/DTDs/PropertyList-1.0.dtd">
|
||||
<plist version="1.0">
|
||||
<dict>
|
||||
<key>CFBundleDevelopmentRegion</key>
|
||||
<string>en</string>
|
||||
<key>CFBundleExecutable</key>
|
||||
<string>$(EXECUTABLE_NAME)</string>
|
||||
<key>CFBundleIdentifier</key>
|
||||
<string>$(PRODUCT_BUNDLE_IDENTIFIER)</string>
|
||||
<key>CFBundleInfoDictionaryVersion</key>
|
||||
<string>6.0</string>
|
||||
<key>CFBundleName</key>
|
||||
<string>$(PRODUCT_NAME)</string>
|
||||
<key>CFBundlePackageType</key>
|
||||
<string>FMWK</string>
|
||||
<key>CFBundleShortVersionString</key>
|
||||
<string>99.0.0</string>
|
||||
<key>CFBundleVersion</key>
|
||||
<string>$(CURRENT_PROJECT_VERSION)</string>
|
||||
<key>NSPrincipalClass</key>
|
||||
<string></string>
|
||||
</dict>
|
||||
</plist>
|
||||
@@ -26,12 +26,11 @@
|
||||
#import <React/RCTBridge.h>
|
||||
#import <React/RCTEventEmitter.h>
|
||||
#import <React/RCTUtils.h>
|
||||
#import <React/RCTLog.h>
|
||||
#import <WebRTC/WebRTC.h>
|
||||
|
||||
#import <JitsiMeetSDK/JitsiMeetSDK-Swift.h>
|
||||
|
||||
#import "../LogUtils.h"
|
||||
#import "JitsiAudioSession.h"
|
||||
#import "../JitsiAudioSession.h"
|
||||
#import "../JitsiMeetSDK-Swift.h"
|
||||
|
||||
|
||||
// The events emitted/supported by RNCallKit:
|
||||
@@ -73,7 +72,7 @@ RCT_EXPORT_MODULE();
|
||||
RCT_EXPORT_METHOD(endCall:(NSString *)callUUID
|
||||
resolve:(RCTPromiseResolveBlock)resolve
|
||||
reject:(RCTPromiseRejectBlock)reject) {
|
||||
DDLogInfo(@"[RNCallKit][endCall] callUUID = %@", callUUID);
|
||||
RCTLogInfo(@"[RNCallKit][endCall] callUUID = %@", callUUID);
|
||||
|
||||
NSUUID *callUUID_ = [[NSUUID alloc] initWithUUIDString:callUUID];
|
||||
|
||||
@@ -94,7 +93,7 @@ RCT_EXPORT_METHOD(setMuted:(NSString *)callUUID
|
||||
muted:(BOOL)muted
|
||||
resolve:(RCTPromiseResolveBlock)resolve
|
||||
reject:(RCTPromiseRejectBlock)reject) {
|
||||
DDLogInfo(@"[RNCallKit][setMuted] callUUID = %@", callUUID);
|
||||
RCTLogInfo(@"[RNCallKit][setMuted] callUUID = %@", callUUID);
|
||||
|
||||
NSUUID *callUUID_ = [[NSUUID alloc] initWithUUIDString:callUUID];
|
||||
|
||||
@@ -111,7 +110,7 @@ RCT_EXPORT_METHOD(setMuted:(NSString *)callUUID
|
||||
}
|
||||
|
||||
RCT_EXPORT_METHOD(setProviderConfiguration:(NSDictionary *)dictionary) {
|
||||
DDLogInfo(@"[RNCallKit][setProviderConfiguration:] dictionary = %@", dictionary);
|
||||
RCTLogInfo(@"[RNCallKit][setProviderConfiguration:] dictionary = %@", dictionary);
|
||||
|
||||
if (![JMCallKitProxy isProviderConfigured]) {
|
||||
JMCallKitProxy.enabled = true;
|
||||
@@ -128,7 +127,7 @@ RCT_EXPORT_METHOD(startCall:(NSString *)callUUID
|
||||
video:(BOOL)video
|
||||
resolve:(RCTPromiseResolveBlock)resolve
|
||||
reject:(RCTPromiseRejectBlock)reject) {
|
||||
DDLogInfo(@"[RNCallKit][startCall] callUUID = %@", callUUID);
|
||||
RCTLogInfo(@"[RNCallKit][startCall] callUUID = %@", callUUID);
|
||||
|
||||
NSUUID *callUUID_ = [[NSUUID alloc] initWithUUIDString:callUUID];
|
||||
|
||||
@@ -192,7 +191,7 @@ RCT_EXPORT_METHOD(updateCall:(NSString *)callUUID
|
||||
options:(NSDictionary *)options
|
||||
resolve:(RCTPromiseResolveBlock)resolve
|
||||
reject:(RCTPromiseRejectBlock)reject) {
|
||||
DDLogInfo(@"[RNCallKit][updateCall] callUUID = %@ options = %@", callUUID, options);
|
||||
RCTLogInfo(@"[RNCallKit][updateCall] callUUID = %@ options = %@", callUUID, options);
|
||||
|
||||
NSUUID *callUUID_ = [[NSUUID alloc] initWithUUIDString:callUUID];
|
||||
|
||||
@@ -215,7 +214,7 @@ RCT_EXPORT_METHOD(updateCall:(NSString *)callUUID
|
||||
#pragma mark - Helper methods
|
||||
|
||||
- (void)configureProviderFromDictionary:(NSDictionary* )dictionary {
|
||||
DDLogInfo(@"[RNCallKit][providerConfigurationFromDictionary: %@]", dictionary);
|
||||
RCTLogInfo(@"[RNCallKit][providerConfigurationFromDictionary: %@]", dictionary);
|
||||
|
||||
if (!dictionary) {
|
||||
dictionary = @{};
|
||||
@@ -259,12 +258,12 @@ RCT_EXPORT_METHOD(updateCall:(NSString *)callUUID
|
||||
- (void)requestTransaction:(CXTransaction *)transaction
|
||||
resolve:(RCTPromiseResolveBlock)resolve
|
||||
reject:(RCTPromiseRejectBlock)reject {
|
||||
DDLogInfo(@"[RNCallKit][requestTransaction] transaction = %@", transaction);
|
||||
RCTLogInfo(@"[RNCallKit][requestTransaction] transaction = %@", transaction);
|
||||
|
||||
[JMCallKitProxy request:transaction
|
||||
completion:^(NSError * _Nullable error) {
|
||||
if (error) {
|
||||
DDLogError(@"[RNCallKit][requestTransaction] Error requesting transaction (%@): (%@)", transaction.actions, error);
|
||||
RCTLogError(@"[RNCallKit][requestTransaction] Error requesting transaction (%@): (%@)", transaction.actions, error);
|
||||
reject(nil, @"Error processing CallKit transaction", error);
|
||||
} else {
|
||||
resolve(nil);
|
||||
@@ -276,14 +275,14 @@ RCT_EXPORT_METHOD(updateCall:(NSString *)callUUID
|
||||
|
||||
// Called when the provider has been reset. We should terminate all calls.
|
||||
- (void)providerDidReset {
|
||||
DDLogInfo(@"[RNCallKit][CXProviderDelegate][providerDidReset:]");
|
||||
RCTLogInfo(@"[RNCallKit][CXProviderDelegate][providerDidReset:]");
|
||||
|
||||
[self sendEventWithName:RNCallKitProviderDidReset body:nil];
|
||||
}
|
||||
|
||||
// Answering incoming call
|
||||
- (void) performAnswerCallWithUUID:(NSUUID *)UUID {
|
||||
DDLogInfo(@"[RNCallKit][CXProviderDelegate][provider:performAnswerCallAction:]");
|
||||
RCTLogInfo(@"[RNCallKit][CXProviderDelegate][provider:performAnswerCallAction:]");
|
||||
|
||||
[self sendEventWithName:RNCallKitPerformAnswerCallAction
|
||||
body:@{ @"callUUID": UUID.UUIDString }];
|
||||
@@ -291,7 +290,7 @@ RCT_EXPORT_METHOD(updateCall:(NSString *)callUUID
|
||||
|
||||
// Call ended, user request
|
||||
- (void) performEndCallWithUUID:(NSUUID *)UUID {
|
||||
DDLogInfo(@"[RNCallKit][CXProviderDelegate][provider:performEndCallAction:]");
|
||||
RCTLogInfo(@"[RNCallKit][CXProviderDelegate][provider:performEndCallAction:]");
|
||||
|
||||
[self sendEventWithName:RNCallKitPerformEndCallAction
|
||||
body:@{ @"callUUID": UUID.UUIDString }];
|
||||
@@ -300,7 +299,7 @@ RCT_EXPORT_METHOD(updateCall:(NSString *)callUUID
|
||||
// Handle audio mute from CallKit view
|
||||
- (void) performSetMutedCallWithUUID:(NSUUID *)UUID
|
||||
isMuted:(BOOL)isMuted {
|
||||
DDLogInfo(@"[RNCallKit][CXProviderDelegate][provider:performSetMutedCallAction:]");
|
||||
RCTLogInfo(@"[RNCallKit][CXProviderDelegate][provider:performSetMutedCallAction:]");
|
||||
|
||||
[self sendEventWithName:RNCallKitPerformSetMutedCallAction
|
||||
body:@{
|
||||
@@ -312,26 +311,26 @@ RCT_EXPORT_METHOD(updateCall:(NSString *)callUUID
|
||||
// Starting outgoing call
|
||||
- (void) performStartCallWithUUID:(NSUUID *)UUID
|
||||
isVideo:(BOOL)isVideo {
|
||||
DDLogInfo(@"[RNCallKit][CXProviderDelegate][provider:performStartCallAction:]");
|
||||
RCTLogInfo(@"[RNCallKit][CXProviderDelegate][provider:performStartCallAction:]");
|
||||
|
||||
[JMCallKitProxy reportOutgoingCallWith:UUID
|
||||
startedConnectingAt:nil];
|
||||
}
|
||||
|
||||
- (void) providerDidActivateAudioSessionWithSession:(AVAudioSession *)session {
|
||||
DDLogInfo(@"[RNCallKit][CXProviderDelegate][provider:didActivateAudioSession:]");
|
||||
RCTLogInfo(@"[RNCallKit][CXProviderDelegate][provider:didActivateAudioSession:]");
|
||||
|
||||
[JitsiAudioSession activateWithAudioSession:session];
|
||||
}
|
||||
|
||||
- (void) providerDidDeactivateAudioSessionWithSession:(AVAudioSession *)session {
|
||||
DDLogInfo(@"[RNCallKit][CXProviderDelegate][provider:didDeactivateAudioSession:]");
|
||||
RCTLogInfo(@"[RNCallKit][CXProviderDelegate][provider:didDeactivateAudioSession:]");
|
||||
|
||||
[JitsiAudioSession deactivateWithAudioSession:session];
|
||||
}
|
||||
|
||||
- (void) providerTimedOutPerformingActionWithAction:(CXAction *)action {
|
||||
DDLogWarn(@"[RNCallKit][CXProviderDelegate][provider:timedOutPerformingAction:]");
|
||||
RCTLogWarn(@"[RNCallKit][CXProviderDelegate][provider:timedOutPerformingAction:]");
|
||||
}
|
||||
|
||||
|
||||
|
||||
@@ -17,14 +17,14 @@
|
||||
import UIKit
|
||||
|
||||
final class DragGestureController {
|
||||
|
||||
var insets: UIEdgeInsets = UIEdgeInsets.zero
|
||||
var currentPosition: PiPViewCoordinator.Position? = nil
|
||||
|
||||
private var frameBeforeDragging: CGRect = CGRect.zero
|
||||
private weak var view: UIView?
|
||||
private lazy var panGesture: UIPanGestureRecognizer = {
|
||||
return UIPanGestureRecognizer(target: self,
|
||||
action: #selector(handlePan(gesture:)))
|
||||
UIPanGestureRecognizer(target: self,
|
||||
action: #selector(handlePan(gesture:)))
|
||||
}()
|
||||
|
||||
func startDragListener(inView view: UIView) {
|
||||
@@ -40,7 +40,7 @@ final class DragGestureController {
|
||||
}
|
||||
|
||||
@objc private func handlePan(gesture: UIPanGestureRecognizer) {
|
||||
guard let view = self.view else { return }
|
||||
guard let view = view else { return }
|
||||
|
||||
let translation = gesture.translation(in: view.superview)
|
||||
let velocity = gesture.velocity(in: view.superview)
|
||||
@@ -65,7 +65,7 @@ final class DragGestureController {
|
||||
let velocityMagnitude = magnitude(vector: velocity)
|
||||
let animationDuration = 0.5
|
||||
let initialSpringVelocity =
|
||||
velocityMagnitude / distanceMagnitude / CGFloat(animationDuration)
|
||||
velocityMagnitude / distanceMagnitude / CGFloat(animationDuration)
|
||||
|
||||
frame.origin = CGPoint(x: finalPos.x, y: finalPos.y)
|
||||
|
||||
@@ -75,8 +75,7 @@ final class DragGestureController {
|
||||
initialSpringVelocity: initialSpringVelocity,
|
||||
options: .curveLinear,
|
||||
animations: {
|
||||
view.frame = frame
|
||||
}, completion: nil)
|
||||
view.frame = frame })
|
||||
|
||||
default:
|
||||
break
|
||||
@@ -85,9 +84,11 @@ final class DragGestureController {
|
||||
|
||||
private func calculateFinalPosition() -> CGPoint {
|
||||
guard
|
||||
let view = self.view,
|
||||
let view = view,
|
||||
let bounds = view.superview?.frame
|
||||
else { return CGPoint.zero }
|
||||
else {
|
||||
return CGPoint.zero
|
||||
}
|
||||
|
||||
let currentSize = view.frame.size
|
||||
let adjustedBounds = bounds.inset(by: insets)
|
||||
@@ -109,19 +110,26 @@ final class DragGestureController {
|
||||
goUp = location.y < bounds.midY
|
||||
}
|
||||
|
||||
let finalPosX: CGFloat =
|
||||
goLeft
|
||||
? adjustedBounds.origin.x
|
||||
: bounds.size.width - insets.right - currentSize.width
|
||||
let finalPosY: CGFloat =
|
||||
goUp
|
||||
? adjustedBounds.origin.y
|
||||
: bounds.size.height - insets.bottom - currentSize.height
|
||||
if (goLeft && goUp) {
|
||||
currentPosition = .upperLeftCorner
|
||||
}
|
||||
|
||||
return CGPoint(x: finalPosX, y: finalPosY)
|
||||
if (!goLeft && goUp) {
|
||||
currentPosition = .upperRightCorner
|
||||
}
|
||||
|
||||
if (!goLeft && !goUp) {
|
||||
currentPosition = .lowerRightCorner
|
||||
}
|
||||
|
||||
if (goLeft && !goUp) {
|
||||
currentPosition = .lowerLeftCorner
|
||||
}
|
||||
|
||||
return currentPosition!.getOriginIn(bounds: adjustedBounds, size: currentSize)
|
||||
}
|
||||
|
||||
private func magnitude(vector: CGPoint) -> CGFloat {
|
||||
return sqrt(pow(vector.x, 2) + pow(vector.y, 2))
|
||||
sqrt(pow(vector.x, 2) + pow(vector.y, 2))
|
||||
}
|
||||
}
|
||||
|
||||
@@ -19,16 +19,23 @@ import UIKit
|
||||
public typealias AnimationCompletion = (Bool) -> Void
|
||||
|
||||
public protocol PiPViewCoordinatorDelegate: class {
|
||||
|
||||
|
||||
func exitPictureInPicture()
|
||||
}
|
||||
|
||||
/// Coordinates the view state of a specified view to allow
|
||||
/// to be presented in full screen or in a custom Picture in Picture mode.
|
||||
/// This object will also provide the drag and tap interactions of the view
|
||||
/// when is presented in Picure in Picture mode.
|
||||
/// when is presented in Picture in Picture mode.
|
||||
public class PiPViewCoordinator {
|
||||
|
||||
|
||||
public enum Position {
|
||||
case lowerRightCorner
|
||||
case upperRightCorner
|
||||
case lowerLeftCorner
|
||||
case upperLeftCorner
|
||||
}
|
||||
|
||||
/// Limits the boundaries of view position on screen when minimized
|
||||
public var dragBoundInsets: UIEdgeInsets = UIEdgeInsets(top: 25,
|
||||
left: 5,
|
||||
@@ -39,23 +46,15 @@ public class PiPViewCoordinator {
|
||||
}
|
||||
}
|
||||
|
||||
public enum Position {
|
||||
case lowerRightCorner
|
||||
case upperRightCorner
|
||||
case lowerLeftCorner
|
||||
case upperLeftCorner
|
||||
}
|
||||
|
||||
public var initialPositionInSuperview = Position.lowerRightCorner
|
||||
|
||||
public let initialPositionInSuperView: Position = .lowerRightCorner
|
||||
|
||||
// Unused. Remove on the next major release.
|
||||
@available(*, deprecated, message: "The PiP window size is now fixed to 150px.")
|
||||
public var c: CGFloat = 0.0
|
||||
|
||||
|
||||
public weak var delegate: PiPViewCoordinatorDelegate?
|
||||
|
||||
private(set) var isInPiP: Bool = false // true if view is in PiP mode
|
||||
|
||||
private(set) var view: UIView
|
||||
private var currentBounds: CGRect = CGRect.zero
|
||||
|
||||
@@ -66,6 +65,13 @@ public class PiPViewCoordinator {
|
||||
|
||||
public init(withView view: UIView) {
|
||||
self.view = view
|
||||
// Required because otherwise the view will not rotate correctly.
|
||||
view.autoresizingMask = [.flexibleWidth, .flexibleHeight]
|
||||
|
||||
// Otherwise the enter/exit pip animation looks odd
|
||||
// when pip window is bottom left, top left or top right,
|
||||
// because the jitsi view content does not animate, but jumps to the new size immediately.
|
||||
view.clipsToBounds = true
|
||||
}
|
||||
|
||||
/// Configure the view to be always on top of all the contents
|
||||
@@ -74,7 +80,9 @@ public class PiPViewCoordinator {
|
||||
public func configureAsStickyView(withParentView parentView: UIView? = nil) {
|
||||
guard
|
||||
let parentView = parentView ?? UIApplication.shared.keyWindow
|
||||
else { return }
|
||||
else {
|
||||
return
|
||||
}
|
||||
|
||||
parentView.addSubview(view)
|
||||
currentBounds = parentView.bounds
|
||||
@@ -109,6 +117,9 @@ public class PiPViewCoordinator {
|
||||
/// around screen, and add a button of top of the view to be able to exit mode
|
||||
public func enterPictureInPicture() {
|
||||
isInPiP = true
|
||||
// Resizing is done by hand when in pip.
|
||||
view.autoresizingMask = []
|
||||
|
||||
animateViewChange()
|
||||
dragController.startDragListener(inView: view)
|
||||
dragController.insets = dragBoundInsets
|
||||
@@ -125,6 +136,9 @@ public class PiPViewCoordinator {
|
||||
/// exit pip button, and disable the drag gesture
|
||||
@objc public func exitPictureInPicture() {
|
||||
isInPiP = false
|
||||
// Enable autoresizing again, which got disabled for pip.
|
||||
view.autoresizingMask = [.flexibleWidth, .flexibleHeight]
|
||||
|
||||
animateViewChange()
|
||||
dragController.stopDragListener()
|
||||
|
||||
@@ -136,7 +150,7 @@ public class PiPViewCoordinator {
|
||||
let exitSelector = #selector(toggleExitPiP)
|
||||
tapGestureRecognizer?.removeTarget(self, action: exitSelector)
|
||||
tapGestureRecognizer = nil
|
||||
|
||||
|
||||
delegate?.exitPictureInPicture()
|
||||
}
|
||||
|
||||
@@ -144,6 +158,12 @@ public class PiPViewCoordinator {
|
||||
/// screen size changes
|
||||
public func resetBounds(bounds: CGRect) {
|
||||
currentBounds = bounds
|
||||
|
||||
// Is required because otherwise the pip window is buggy when rotating the device.
|
||||
// When not in pip then autoresize will do the job.
|
||||
if (isInPiP) {
|
||||
view.frame = changeViewRect()
|
||||
}
|
||||
}
|
||||
|
||||
/// Stop the dragging gesture of the root view
|
||||
@@ -169,7 +189,6 @@ public class PiPViewCoordinator {
|
||||
}
|
||||
|
||||
// MARK: - Interactions
|
||||
|
||||
@objc private func toggleExitPiP() {
|
||||
if exitPiPButton == nil {
|
||||
// show button
|
||||
@@ -186,44 +205,28 @@ public class PiPViewCoordinator {
|
||||
}
|
||||
}
|
||||
|
||||
// MARK: - Size calculation
|
||||
|
||||
private func animateViewChange() {
|
||||
func animateViewChange() {
|
||||
UIView.animate(withDuration: 0.25) {
|
||||
self.view.frame = self.changeViewRect()
|
||||
self.view.setNeedsLayout()
|
||||
}
|
||||
}
|
||||
|
||||
private func changeViewRect() -> CGRect {
|
||||
let bounds = currentBounds
|
||||
|
||||
guard isInPiP else {
|
||||
if !isInPiP {
|
||||
return bounds
|
||||
}
|
||||
|
||||
// resize to suggested ratio and position to the bottom right
|
||||
let adjustedBounds = bounds.inset(by: dragBoundInsets)
|
||||
let size = CGSize(width: 150, height: 150)
|
||||
let origin = initialPositionFor(pipSize: size, bounds: adjustedBounds)
|
||||
let origin = (dragController.currentPosition ?? initialPositionInSuperView).getOriginIn(bounds: adjustedBounds, size: size)
|
||||
|
||||
return CGRect(x: origin.x, y: origin.y, width: size.width, height: size.height)
|
||||
}
|
||||
|
||||
private func initialPositionFor(pipSize size: CGSize, bounds: CGRect) -> CGPoint {
|
||||
switch initialPositionInSuperview {
|
||||
case .lowerLeftCorner:
|
||||
return CGPoint(x: bounds.minX, y: bounds.maxY - size.height)
|
||||
case .lowerRightCorner:
|
||||
return CGPoint(x: bounds.maxX - size.width, y: bounds.maxY - size.height)
|
||||
case .upperLeftCorner:
|
||||
return CGPoint(x: bounds.minX, y: bounds.minY)
|
||||
case .upperRightCorner:
|
||||
return CGPoint(x: bounds.maxX - size.width, y: bounds.minY)
|
||||
}
|
||||
}
|
||||
|
||||
// MARK: - Animation helpers
|
||||
|
||||
private func animateTransition(animations: @escaping () -> Void,
|
||||
completion: AnimationCompletion?) {
|
||||
UIView.animate(withDuration: 0.1,
|
||||
@@ -234,3 +237,19 @@ public class PiPViewCoordinator {
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
// MARK: -
|
||||
extension PiPViewCoordinator.Position {
|
||||
func getOriginIn(bounds: CGRect, size: CGSize) -> CGPoint {
|
||||
switch self {
|
||||
case .lowerLeftCorner:
|
||||
return CGPoint(x: bounds.minX, y: bounds.maxY - size.height)
|
||||
case .lowerRightCorner:
|
||||
return CGPoint(x: bounds.maxX - size.width, y: bounds.maxY - size.height)
|
||||
case .upperLeftCorner:
|
||||
return CGPoint(x: bounds.minX, y: bounds.minY)
|
||||
case .upperRightCorner:
|
||||
return CGPoint(x: bounds.maxX - size.width, y: bounds.minY)
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@@ -22,6 +22,7 @@
|
||||
"sl": "Sloweens",
|
||||
"sv": "Sweeds",
|
||||
"tr": "Turks",
|
||||
"uk": "Oekraïens",
|
||||
"vi": "Viëtnamees",
|
||||
"zhCN": "Sjinees (Sjina)"
|
||||
}
|
||||
|
||||
@@ -28,6 +28,7 @@
|
||||
"ru": "Расійская",
|
||||
"sv": "Шведская",
|
||||
"tr": "Турэцкая",
|
||||
"uk": "Украінская",
|
||||
"vi": "В'етнамская",
|
||||
"zhCN": "Кітайская (Кітай)",
|
||||
"zhTW": "Кітайская (Тайвань)"
|
||||
|
||||
@@ -26,6 +26,7 @@
|
||||
"ru": "Руски",
|
||||
"sv": "Шведски",
|
||||
"tr": "Турски",
|
||||
"uk": "Украински",
|
||||
"vi": "Виетнамски",
|
||||
"zhCN": "Китайски (Китай)",
|
||||
"zhTW": "Тайвански"
|
||||
|
||||
@@ -27,6 +27,7 @@
|
||||
"ru": "Russisk",
|
||||
"sv": "Svensk",
|
||||
"tr": "Tyrkisk",
|
||||
"uk": "Ukrainsk",
|
||||
"vi": "Vietnamesisk",
|
||||
"zhCN": "Kinesisk (China)",
|
||||
"zhTW": "Kinesisk (Taiwan)"
|
||||
|
||||
@@ -17,6 +17,7 @@
|
||||
"fr": "Französisch",
|
||||
"frCA": "Französisch (Kanada)",
|
||||
"hr": "Kroatisch",
|
||||
"hsb": "Obersorbisch",
|
||||
"hu": "Ungarisch",
|
||||
"hy": "Armenisch",
|
||||
"it": "Italienisch",
|
||||
@@ -33,6 +34,7 @@
|
||||
"sr": "Serbish",
|
||||
"sv": "Schwedisch",
|
||||
"tr": "Türkisch",
|
||||
"uk": "Ukrainisch",
|
||||
"vi": "Vietnamesisch",
|
||||
"zhCN": "Chinesisch (China)",
|
||||
"zhTW": "Chinesisch (Taiwan)"
|
||||
|
||||
@@ -17,6 +17,7 @@
|
||||
"fr": "French",
|
||||
"frCA": "French (Canadian)",
|
||||
"hr": "Croatian",
|
||||
"hsb": "Upper Sorbian",
|
||||
"hu": "Hungarian",
|
||||
"hy": "Armenian",
|
||||
"it": "Italian",
|
||||
@@ -33,6 +34,7 @@
|
||||
"sr": "Serbian",
|
||||
"sv": "Swedish",
|
||||
"tr": "Turkish",
|
||||
"uk": "Ukrainian",
|
||||
"vi": "Vietnamese",
|
||||
"zhCN": "Chinese (China)",
|
||||
"zhTW": "Chinese (Taiwan)"
|
||||
|
||||
@@ -22,6 +22,7 @@
|
||||
"sl": "Slovena",
|
||||
"sv": "Sveda",
|
||||
"tr": "Turka",
|
||||
"uk": "Ukraina",
|
||||
"vi": "Vjetnama",
|
||||
"zhCN": "Ĉina (Ĉinuja)"
|
||||
}
|
||||
|
||||
@@ -30,6 +30,7 @@
|
||||
"sk": "Eslovaco",
|
||||
"sv": "Sueco",
|
||||
"tr": "Turco",
|
||||
"uk": "Ucraniano",
|
||||
"vi": "Vietnamita",
|
||||
"zhCN": "Chino (China)",
|
||||
"zhTW": "Chino (Taiwán)"
|
||||
|
||||
@@ -28,6 +28,7 @@
|
||||
"sk": "Eslovaco",
|
||||
"sv": "Sueco",
|
||||
"tr": "Turco",
|
||||
"uk": "Ucraniano",
|
||||
"vi": "Vietnamita",
|
||||
"zhCN": "Chino (China)",
|
||||
"zhTW": "Chino (Taiwan)"
|
||||
|
||||
@@ -27,6 +27,7 @@
|
||||
"ru": "Vene keel",
|
||||
"sv": "Roosi keel",
|
||||
"tr": "Türgi keel",
|
||||
"uk": "Ukraina keel",
|
||||
"vi": "Vietnami keel",
|
||||
"zhCN": "Hiina keel (Hiina)",
|
||||
"zhTW": "Hiina keel (Tai)"
|
||||
|
||||
@@ -32,6 +32,7 @@
|
||||
"sl": "",
|
||||
"sv": "ruotsi",
|
||||
"tr": "turkki",
|
||||
"uk": "ukraina",
|
||||
"vi": "vietnam",
|
||||
"zhCN": "kiina (Kiina)",
|
||||
"zhTW": "kiina (Taiwan)"
|
||||
|
||||
@@ -29,6 +29,7 @@
|
||||
"sk": "Slovaque",
|
||||
"sv": "Suédois",
|
||||
"tr": "Turc",
|
||||
"uk": "Ukrainien",
|
||||
"vi": "Vietnamien",
|
||||
"zhCN": "Chinois (Chine)",
|
||||
"zhTW": "Chinois (Taiwan)"
|
||||
|
||||
@@ -29,6 +29,7 @@
|
||||
"sk": "Slovaque",
|
||||
"sv": "Suédois",
|
||||
"tr": "Turc",
|
||||
"uk": "Ukrainien",
|
||||
"vi": "Vietnamien",
|
||||
"zhCN": "Chinois (Chine)",
|
||||
"zhTW": "Chinois (Taiwan)"
|
||||
|
||||
@@ -1,28 +1,56 @@
|
||||
{
|
||||
"af": "Afrikanski",
|
||||
"az": "Ažerbejdžanski",
|
||||
"ar": "Arapski",
|
||||
"bg": "Bugarski",
|
||||
"ca": "Katalanski",
|
||||
"cs": "Češki",
|
||||
"da": "Danski",
|
||||
"de": "Njemački",
|
||||
"el": "Grčki",
|
||||
"en": "Engleski",
|
||||
"enGB": "Engleski (Ujedinjeno Kraljevstvo)",
|
||||
"eo": "Esperanto",
|
||||
"es": "Španjolski",
|
||||
"esUS": "Španjolski (Latinska Amerika)",
|
||||
"et": "Estonski",
|
||||
"eu": "Baskijski",
|
||||
"fa": "Perzijski",
|
||||
"fi": "Finski",
|
||||
"fr": "Francuski",
|
||||
"frCA": "Francuski (Canada)",
|
||||
"he": "Hebrejski",
|
||||
"hi": "Hindski",
|
||||
"hr": "Hrvatski",
|
||||
"hsb": "Gornjolužičkosrpski",
|
||||
"hu": "Mađarski",
|
||||
"hy": "Armenski",
|
||||
"id": "Indonezijski",
|
||||
"it": "Talijanski",
|
||||
"ja": "Japanski",
|
||||
"ko": "Korejski",
|
||||
"lt": "Litvanski",
|
||||
"lv": "Latvijski",
|
||||
"ml": "Malayalam",
|
||||
"mr": "Marathi",
|
||||
"nb": "Norveški Bokmal",
|
||||
"nl": "Nizozemski",
|
||||
"oc": "Okcitanski",
|
||||
"pl": "Poljski",
|
||||
"pt": "Portugalski",
|
||||
"ptBR": "Portugalski (Brazil)",
|
||||
"ro": "Rumunjski",
|
||||
"ru": "Ruski",
|
||||
"sc": "Sardijski",
|
||||
"sk": "Slovački",
|
||||
"sl": "Slovenski",
|
||||
"sq": "Albanski",
|
||||
"sr": "Srpski",
|
||||
"sv": "Švedski",
|
||||
"te": "Teluški",
|
||||
"th": "Tajski",
|
||||
"tr": "Turski",
|
||||
"uk": "Ukrajinski",
|
||||
"vi": "Vijetnamski",
|
||||
"zhCN": "Kineski (Kina)"
|
||||
"zhCN": "Kineski (Kina)",
|
||||
"zhTW": "Kineski (Taiwan)"
|
||||
}
|
||||
|
||||
47
lang/languages-hsb.json
Normal file
47
lang/languages-hsb.json
Normal file
@@ -0,0 +1,47 @@
|
||||
{
|
||||
"ar": "arabšćina",
|
||||
"bg": "bołharšćina",
|
||||
"cs": "čěšćina",
|
||||
"da": "danšćina",
|
||||
"de": "němčina",
|
||||
"el": "grjekšćina",
|
||||
"en": "jendźelšćina",
|
||||
"enGB": "jendźelšćina (Wulka Britaniska)",
|
||||
"eo": "esperanto",
|
||||
"es": "španišćina",
|
||||
"esUS": "španišćina (Łaćonska)",
|
||||
"et": "estišćina",
|
||||
"eu": "baskišćina",
|
||||
"fa": "persišćina",
|
||||
"fi": "finšćina",
|
||||
"fr": "francošćina",
|
||||
"frCA": "francošćina (Kanada)",
|
||||
"he": "hebrejšćina",
|
||||
"hi": "hindišćina",
|
||||
"hr": "chorwatšćina",
|
||||
"hsb": "hornjoserbšćina",
|
||||
"hu": "madźaršćina",
|
||||
"hy": "armenšćina",
|
||||
"id": "indonešćina",
|
||||
"it": "italšćina",
|
||||
"ja": "japanšćina",
|
||||
"ko": "korejšćina",
|
||||
"lt": "litawšćina",
|
||||
"lv": "letišćina",
|
||||
"nl": "nižozemšćina",
|
||||
"pl": "pólšćina",
|
||||
"pt": "portugalšćina",
|
||||
"ptBR": "portugalšćina (Brazilska)",
|
||||
"ro": "rumunšćina",
|
||||
"ru": "rušćina",
|
||||
"sk": "słowakšćina",
|
||||
"sl": "słowjenšćina",
|
||||
"sq": "albanšćina",
|
||||
"sr": "serbišćina",
|
||||
"sv": "šwedšćina",
|
||||
"tr": "turkowšćina",
|
||||
"uk": "ukrainšćina",
|
||||
"vi": "vietnamšćina",
|
||||
"zhCN": "chinšćina (China)",
|
||||
"zhTW": "chinšćina (Taiwan)"
|
||||
}
|
||||
@@ -29,6 +29,7 @@
|
||||
"sk": "Szlovákul",
|
||||
"sv": "Svéd",
|
||||
"tr": "Török",
|
||||
"uk": "Ukrán",
|
||||
"vi": "Vietnámi",
|
||||
"zhCN": "Kínai (Kína)",
|
||||
"zhTW": "Kínai (Tajvan)"
|
||||
|
||||
@@ -22,6 +22,7 @@
|
||||
"sl": "Սլովեներեն ",
|
||||
"sv": "Շվեդերեն ",
|
||||
"tr": "Թուրքերեն",
|
||||
"uk": "Ուկրաիներեն",
|
||||
"vi": "",
|
||||
"zhCN": "Չիներեն"
|
||||
}
|
||||
|
||||
@@ -33,6 +33,7 @@
|
||||
"sk": "Bahasa Slovakia",
|
||||
"sv": "Bahasa Swedia",
|
||||
"tr": "Bahasa Turki",
|
||||
"uk": "Bahasa Ukraina",
|
||||
"vi": "Bahasa Vietnam",
|
||||
"zhCN": "Bahasa Mandarin",
|
||||
"zhTW": "Bahasa Mandarin - Taiwan"
|
||||
|
||||
Some files were not shown because too many files have changed in this diff Show More
Reference in New Issue
Block a user