Compare commits
1 Commits
1850
...
move_loggi
| Author | SHA1 | Date | |
|---|---|---|---|
|
|
cf83b4142a |
@@ -3,7 +3,6 @@ build/*
|
||||
|
||||
# Third-party source code which we (1) do not want to modify or (2) try to
|
||||
# modify as little as possible.
|
||||
flow-typed/*
|
||||
libs/*
|
||||
|
||||
# ESLint will by default ignore its own configuration file. However, there does
|
||||
|
||||
@@ -4,10 +4,7 @@ module.exports = {
|
||||
'commonjs': true,
|
||||
'es6': true
|
||||
},
|
||||
'extends': [
|
||||
'eslint:recommended',
|
||||
'plugin:flowtype/recommended'
|
||||
],
|
||||
'extends': 'eslint:recommended',
|
||||
'globals': {
|
||||
// The globals that (1) are accessed but not defined within many of our
|
||||
// files, (2) are certainly defined, and (3) we would like to use
|
||||
@@ -15,16 +12,12 @@ module.exports = {
|
||||
// files.
|
||||
'__filename': false
|
||||
},
|
||||
'parser': 'babel-eslint',
|
||||
'parserOptions': {
|
||||
'ecmaFeatures': {
|
||||
'experimentalObjectRestSpread': true
|
||||
},
|
||||
'sourceType': 'module'
|
||||
},
|
||||
'plugins': [
|
||||
'flowtype'
|
||||
],
|
||||
'rules': {
|
||||
'new-cap': [
|
||||
'error',
|
||||
|
||||
65
.flowconfig
@@ -1,65 +0,0 @@
|
||||
[ignore]
|
||||
; We fork some components by platform
|
||||
.*/*[.]android.js
|
||||
|
||||
; Ignore "BUCK" generated dirs
|
||||
<PROJECT_ROOT>/\.buckd/
|
||||
|
||||
; Ignore unexpected extra "@providesModule"
|
||||
.*/node_modules/.*/node_modules/fbjs/.*
|
||||
|
||||
; Ignore duplicate module providers
|
||||
; For RN Apps installed via npm, "Libraries" folder is inside
|
||||
; "node_modules/react-native" but in the source repo it is in the root
|
||||
.*/Libraries/react-native/React.js
|
||||
.*/Libraries/react-native/ReactNative.js
|
||||
|
||||
; Ignore packages in node_modules which we (i.e. the jitsi-meet project) have
|
||||
; seen to cause errors and we have chosen not to fix.
|
||||
.*/node_modules/babel-core/.*
|
||||
.*/node_modules/bower/.*
|
||||
.*/node_modules/jsonlint/.*
|
||||
.*/node_modules/styled-components/.*
|
||||
|
||||
[include]
|
||||
|
||||
[libs]
|
||||
node_modules/react-native/Libraries/react-native/react-native-interface.js
|
||||
node_modules/react-native/flow
|
||||
flow/
|
||||
|
||||
[options]
|
||||
emoji=true
|
||||
|
||||
module.system=haste
|
||||
|
||||
experimental.strict_type_args=true
|
||||
|
||||
munge_underscores=true
|
||||
|
||||
module.name_mapper='^[./a-zA-Z0-9$_-]+\.\(bmp\|gif\|jpg\|jpeg\|png\|psd\|svg\|webp\|m4v\|mov\|mp4\|mpeg\|mpg\|webm\|aac\|aiff\|caf\|m4a\|mp3\|wav\|html\|pdf\)$' -> 'RelativeImageStub'
|
||||
|
||||
suppress_type=$FlowIssue
|
||||
suppress_type=$FlowFixMe
|
||||
suppress_type=$FixMe
|
||||
|
||||
suppress_comment=\\(.\\|\n\\)*\\$FlowFixMe\\($\\|[^(]\\|(\\(>=0\\.\\(3[0-8]\\|[1-2][0-9]\\|[0-9]\\).[0-9]\\)? *\\(site=[a-z,_]*react_native[a-z,_]*\\)?)\\)
|
||||
suppress_comment=\\(.\\|\n\\)*\\$FlowIssue\\((\\(>=0\\.\\(3[0-8]\\|1[0-9]\\|[1-2][0-9]\\).[0-9]\\)? *\\(site=[a-z,_]*react_native[a-z,_]*\\)?)\\)?:? #[0-9]+
|
||||
suppress_comment=\\(.\\|\n\\)*\\$FlowFixedInNextDeploy
|
||||
|
||||
unsafe.enable_getters_and_setters=true
|
||||
|
||||
; We (i.e. the jitsi-meet project) are using the haste module system on Web as
|
||||
; well, not only on React Native. Unfortunately, Flow does not support .web.js
|
||||
; by default. Override Flow's defaults to include .web.js as well. Technically,
|
||||
; we have .native.js as well so the choice of .web.js may lead to errors.
|
||||
; Practically though, it is a potential future problem that we do not have at
|
||||
; the time of this writing.
|
||||
module.file_ext=.web.js
|
||||
; Flow's defaults:
|
||||
module.file_ext=.js
|
||||
module.file_ext=.jsx
|
||||
module.file_ext=.json
|
||||
|
||||
[version]
|
||||
^0.38.0
|
||||
1
.gitattributes
vendored
@@ -1,3 +1,2 @@
|
||||
*.bundle.js -text -diff
|
||||
*.pbxproj -text
|
||||
lib-jitsi-meet.js -text -diff
|
||||
|
||||
21
.gitignore
vendored
@@ -4,6 +4,7 @@ deploy-local.sh
|
||||
libs/
|
||||
all.css
|
||||
*css.map
|
||||
unsupported_browser.css
|
||||
.remote-sync.json
|
||||
.sync-config.cson
|
||||
|
||||
@@ -35,33 +36,21 @@ DerivedData
|
||||
*.xcuserstate
|
||||
project.xcworkspace
|
||||
|
||||
# Android/IntelliJ
|
||||
# Android/IJ
|
||||
#
|
||||
build/
|
||||
*.iml
|
||||
.idea
|
||||
.gradle
|
||||
local.properties
|
||||
*.iml
|
||||
|
||||
# node.js
|
||||
#
|
||||
node_modules/
|
||||
npm-debug.log
|
||||
yarn-error.log
|
||||
|
||||
# BUCK
|
||||
#
|
||||
buck-out/
|
||||
\.buckd/
|
||||
*.keystore
|
||||
|
||||
# fastlane
|
||||
#
|
||||
# It is recommended to not store the screenshots in the git repo. Instead, use
|
||||
# fastlane to re-generate the screenshots whenever they are needed. For more
|
||||
# information about the recommended setup visit:
|
||||
# https://github.com/fastlane/fastlane/blob/master/fastlane/docs/Gitignore.md
|
||||
#
|
||||
fastlane/report.xml
|
||||
fastlane/Preview.html
|
||||
fastlane/screenshots
|
||||
android/app/libs
|
||||
android/keystores/debug.keystore
|
||||
|
||||
@@ -1,18 +1,7 @@
|
||||
# The following do not need to be checked because they do not represent JS
|
||||
# source code.
|
||||
build/
|
||||
debian/
|
||||
libs/
|
||||
node_modules/
|
||||
|
||||
# The following are checked by ESLint with the maximum configuration which
|
||||
# supersedes JSHint.
|
||||
flow-typed/
|
||||
react/
|
||||
|
||||
# The following are checked by ESLint with the minimum configuration which does
|
||||
# not supersede JSHint but take advantage of advanced language features such as
|
||||
# Facebook Flow which are not supported by JSHint.
|
||||
modules/translation/translation.js
|
||||
|
||||
analytics.js
|
||||
webpack.config.babel.js
|
||||
|
||||
@@ -1,7 +1,7 @@
|
||||
<html>
|
||||
<head>
|
||||
<link rel="stylesheet" href="../css/all.css"/>
|
||||
<!--#include virtual="/title.html" -->
|
||||
<link rel="stylesheet" href="css/all.css"/>
|
||||
<!--#include virtual="title.html" -->
|
||||
</head>
|
||||
<body>
|
||||
<div class="error_page">
|
||||
@@ -1,33 +0,0 @@
|
||||
# How to contribute
|
||||
We would love to have your help. Before you start working however, please read
|
||||
and follow this short guide.
|
||||
|
||||
# Reporting Issues
|
||||
Before you open an issue on GitHub, please discuss it on one of our
|
||||
[mailing lists](https://jitsi.org/Development/MailingLists) and wait for
|
||||
confirmation from one of the committers. Once you have that confirmation,
|
||||
please proceed to reporting the issue on GitHub, while providing as much
|
||||
information as possible. Mention the version of Jitsi Meet, Jicofo and JVB
|
||||
you are using, and explain (as detailed as you can) how the problem can
|
||||
be reproduced.
|
||||
|
||||
# Code contributions
|
||||
Found a bug and know how to fix it? Great! Please read on.
|
||||
|
||||
## Contributor License Agreement
|
||||
While the Jitsi projects are released under the
|
||||
[Apache License 2.0](https://github.com/jitsi/jitsi-meet/blob/master/LICENSE), the copyright
|
||||
holder and principal creator is [Atlassian](https://www.atlassian.com/). To
|
||||
ensure that we can continue making these projects available under an Open Source license,
|
||||
we need you to sign our Apache-based contributor
|
||||
license agreement as either a [corporation](https://jitsi.org/ccla) or an
|
||||
[individual](https://jitsi.org/icla). If you cannot accept the terms laid out
|
||||
in the agreement, unfortunately, we cannot accept your contribution.
|
||||
|
||||
## Creating Pull Requests
|
||||
- Make sure your code passes the linter rules beforehand. The linter is exeuted
|
||||
automatically when committing code.
|
||||
- Perform **one** logical change per pull request.
|
||||
- Maintain a clean list of commits, squash them if necessary.
|
||||
- Rebase your topic branch on top of the master branch before creating the pull
|
||||
request.
|
||||
@@ -1,4 +0,0 @@
|
||||
/**
|
||||
* Notifies interested parties that hangup procedure will start.
|
||||
*/
|
||||
export const BEFORE_HANGUP = "conference.before_hangup";
|
||||
13
Makefile
@@ -8,9 +8,16 @@ OUTPUT_DIR = .
|
||||
STYLES_BUNDLE = css/all.bundle.css
|
||||
STYLES_DESTINATION = css/all.css
|
||||
STYLES_MAIN = css/main.scss
|
||||
STYLES_UNSUPPORTED_BROWSER = css/unsupported_browser.scss
|
||||
WEBPACK = ./node_modules/.bin/webpack
|
||||
|
||||
all: compile deploy clean
|
||||
all: update-deps compile deploy clean
|
||||
|
||||
# FIXME: there is a problem with node-sass not correctly installed (compiled)
|
||||
# a quick fix to make sure it is installed on every update
|
||||
# the problem appears on linux and not on macosx
|
||||
update-deps:
|
||||
$(NPM) update && $(NPM) install node-sass
|
||||
|
||||
compile:
|
||||
$(WEBPACK) -p
|
||||
@@ -40,6 +47,7 @@ deploy-lib-jitsi-meet:
|
||||
$(DEPLOY_DIR)
|
||||
|
||||
deploy-css:
|
||||
$(NODE_SASS) css/unsupported_browser.scss css/unsupported_browser.css ; \
|
||||
$(NODE_SASS) $(STYLES_MAIN) $(STYLES_BUNDLE) && \
|
||||
$(CLEANCSS) $(STYLES_BUNDLE) > $(STYLES_DESTINATION) ; \
|
||||
rm $(STYLES_BUNDLE)
|
||||
@@ -49,7 +57,8 @@ deploy-local:
|
||||
|
||||
source-package:
|
||||
mkdir -p source_package/jitsi-meet/css && \
|
||||
cp -r *.js *.html connection_optimization favicon.ico fonts images libs static sounds LICENSE lang source_package/jitsi-meet && \
|
||||
cp -r *.js *.html connection_optimization favicon.ico fonts images libs sounds LICENSE lang source_package/jitsi-meet && \
|
||||
cp css/all.css source_package/jitsi-meet/css && \
|
||||
cp css/unsupported_browser.css source_package/jitsi-meet/css && \
|
||||
(cd source_package ; tar cjf ../jitsi-meet.tar.bz2 jitsi-meet) && \
|
||||
rm -rf source_package
|
||||
|
||||
30
README.md
@@ -1,5 +1,5 @@
|
||||
# Jitsi Meet - Secure, Simple and Scalable Video Conferences
|
||||
|
||||
Jitsi Meet - Secure, Simple and Scalable Video Conferences
|
||||
====
|
||||
Jitsi Meet is an open-source (Apache) WebRTC JavaScript application that uses [Jitsi Videobridge](https://jitsi.org/videobridge) to provide high quality, scalable video conferences. You can see [Jitsi Meet in action](http://youtu.be/7vFUVClsNh0) here at the session #482 of the VoIP Users Conference.
|
||||
|
||||
You can also try it out yourself at https://meet.jit.si .
|
||||
@@ -12,17 +12,6 @@ Installing Jitsi Meet is quite a simple experience. For Debian-based systems, we
|
||||
|
||||
For other systems, or if you wish to install all components manually, see the [detailed manual installation instructions](https://github.com/jitsi/jitsi-meet/blob/master/doc/manual-install.md).
|
||||
|
||||
## Download
|
||||
|
||||
You can download Debian/Ubuntu binaries:
|
||||
* [stable](https://download.jitsi.org/stable/) ([instructions](https://jitsi.org/Main/InstallJitsiMeetDebianStableRepository))
|
||||
* [testing](https://download.jitsi.org/testing/) ([instructions](https://jitsi.org/Main/InstallJitsiMeetDebianTestingRepository))
|
||||
* [nightly](https://download.jitsi.org/unstable/) ([instructions](https://jitsi.org/Main/InstallJitsiMeetDebianNightlyRepository))
|
||||
|
||||
You can get our mobile versions from here:
|
||||
* [Android](https://play.google.com/store/apps/details?id=org.jitsi.meet)
|
||||
* [iOS](https://itunes.apple.com/us/app/jitsi-meet/id1165103905)
|
||||
|
||||
## Building the sources
|
||||
|
||||
Jitsi Meet uses [Browserify](http://browserify.org). If you want to make changes in the code you need to [install Browserify](http://browserify.org/#install). Browserify requires [nodejs](http://nodejs.org).
|
||||
@@ -39,7 +28,7 @@ To build the Jitsi Meet application, just type
|
||||
make
|
||||
```
|
||||
|
||||
## Working with the library sources (lib-jitsi-meet)
|
||||
## Working with the library sources(lib-jitsi-meet).
|
||||
|
||||
By default the library is build from its git repository sources. The default dependency path in package.json is :
|
||||
```json
|
||||
@@ -86,19 +75,6 @@ npm unlink lib-jitsi-meet
|
||||
npm install
|
||||
```
|
||||
|
||||
## Contributing
|
||||
|
||||
If you are looking to contribute to Jitsi Meet, first of all, thank you! Please
|
||||
see our [guidelines for contributing](CONTRIBUTING.md).
|
||||
|
||||
## Embedding in external applications
|
||||
|
||||
Jitsi Meet provides a very flexible way of embedding it in external applications by using the [Jitsi Meet API](doc/api.md).
|
||||
|
||||
## Mobile app
|
||||
Jitsi Meet is also available as a React Native application for Android and iOS.
|
||||
Instructions on how to build it can be found [here](doc/mobile.md).
|
||||
|
||||
## Discuss
|
||||
Please use the [Jitsi dev mailing list](http://lists.jitsi.org/pipermail/dev/) to discuss feature requests before opening an issue on Github.
|
||||
|
||||
|
||||
@@ -46,13 +46,13 @@ android_library(
|
||||
|
||||
android_build_config(
|
||||
name = 'build_config',
|
||||
package = 'org.jitsi.meet',
|
||||
package = 'org.jitsi.jitsi_meet_react',
|
||||
)
|
||||
|
||||
android_resource(
|
||||
name = 'res',
|
||||
res = 'src/main/res',
|
||||
package = 'org.jitsi.meet',
|
||||
package = 'org.jitsi.jitsi_meet_react',
|
||||
)
|
||||
|
||||
android_binary(
|
||||
|
||||
@@ -1,4 +1,15 @@
|
||||
buildscript {
|
||||
repositories {
|
||||
maven { url 'https://maven.fabric.io/public' }
|
||||
}
|
||||
|
||||
dependencies {
|
||||
classpath 'io.fabric.tools:gradle:1.+'
|
||||
}
|
||||
}
|
||||
|
||||
apply plugin: 'com.android.application'
|
||||
apply plugin: 'io.fabric'
|
||||
|
||||
import com.android.build.OutputFile
|
||||
|
||||
@@ -87,11 +98,11 @@ android {
|
||||
buildToolsVersion '23.0.1'
|
||||
|
||||
defaultConfig {
|
||||
applicationId 'org.jitsi.meet'
|
||||
applicationId 'org.jitsi.jitsi_meet_react'
|
||||
minSdkVersion 16
|
||||
targetSdkVersion 22
|
||||
versionCode Integer.parseInt("${version}")
|
||||
versionName "1.3.${version}"
|
||||
versionCode 1
|
||||
versionName '1.0'
|
||||
ndk {
|
||||
abiFilters 'armeabi-v7a', 'x86'
|
||||
}
|
||||
@@ -138,15 +149,18 @@ if (project.hasProperty('JITSI_SIGNING')
|
||||
apply from: project.property('JITSI_SIGNING');
|
||||
}
|
||||
|
||||
repositories {
|
||||
maven { url 'https://maven.fabric.io/public' }
|
||||
}
|
||||
dependencies {
|
||||
compile project(':react-native-background-timer')
|
||||
compile project(':react-native-immersive')
|
||||
compile project(':react-native-keep-awake')
|
||||
compile project(':react-native-vector-icons')
|
||||
compile project(':react-native-webrtc')
|
||||
compile fileTree(dir: 'libs', include: ['*.jar'])
|
||||
compile 'com.android.support:appcompat-v7:23.0.1'
|
||||
compile 'com.facebook.react:react-native:+' // From node_modules
|
||||
compile 'com.facebook.react:react-native:+'
|
||||
compile('com.crashlytics.sdk.android:crashlytics:2.6.5@aar') {
|
||||
transitive = true
|
||||
}
|
||||
}
|
||||
|
||||
apply from: '../../node_modules/react-native-vector-icons/fonts.gradle'
|
||||
@@ -154,6 +168,6 @@ apply from: '../../node_modules/react-native-vector-icons/fonts.gradle'
|
||||
// Run this once to be able to run the application with BUCK
|
||||
// puts all compile dependencies into folder libs for BUCK to use
|
||||
task copyDownloadableDepsToLibs(type: Copy) {
|
||||
from configurations.compile
|
||||
into 'libs'
|
||||
from configurations.compile
|
||||
into 'libs'
|
||||
}
|
||||
|
||||
@@ -1,14 +1,11 @@
|
||||
<manifest xmlns:android="http://schemas.android.com/apk/res/android"
|
||||
package="org.jitsi.meet"
|
||||
package="org.jitsi.jitsi_meet_react"
|
||||
android:versionCode="1"
|
||||
android:versionName="1.0">
|
||||
|
||||
<!-- XXX: ACCESS_NETWORK_STATE is required by WebRTC. -->
|
||||
<uses-permission android:name="android.permission.ACCESS_NETWORK_STATE" />
|
||||
<uses-permission android:name="android.permission.BLUETOOTH" />
|
||||
<uses-permission android:name="android.permission.ACCESS_NETWORK_STATE" /><!-- WebRTC -->
|
||||
<uses-permission android:name="android.permission.CAMERA" />
|
||||
<uses-permission android:name="android.permission.INTERNET" />
|
||||
<uses-permission android:name="android.permission.MODIFY_AUDIO_SETTINGS" />
|
||||
<uses-permission android:name="android.permission.RECORD_AUDIO" />
|
||||
<uses-permission android:name="android.permission.SYSTEM_ALERT_WINDOW"/>
|
||||
|
||||
@@ -16,8 +13,8 @@
|
||||
<uses-feature android:name="android.hardware.camera.autofocus"/>
|
||||
|
||||
<uses-sdk
|
||||
android:minSdkVersion="19"
|
||||
android:targetSdkVersion="23" />
|
||||
android:minSdkVersion="16"
|
||||
android:targetSdkVersion="22" />
|
||||
|
||||
<application
|
||||
android:allowBackup="true"
|
||||
@@ -29,8 +26,7 @@
|
||||
android:configChanges="keyboard|keyboardHidden|orientation|screenSize"
|
||||
android:label="@string/app_name"
|
||||
android:launchMode="singleTask"
|
||||
android:name=".MainActivity"
|
||||
android:windowSoftInputMode="adjustResize">
|
||||
android:name=".MainActivity">
|
||||
<intent-filter>
|
||||
<action android:name="android.intent.action.MAIN" />
|
||||
<category android:name="android.intent.category.LAUNCHER" />
|
||||
@@ -39,21 +35,16 @@
|
||||
<action android:name="android.intent.action.VIEW" />
|
||||
<category android:name="android.intent.category.BROWSABLE" />
|
||||
<category android:name="android.intent.category.DEFAULT" />
|
||||
<data android:host="beta.hipchat.me" android:scheme="https" />
|
||||
<data android:host="beta.meet.jit.si" android:scheme="https" />
|
||||
<data android:host="chaos.hipchat.me" android:scheme="https" />
|
||||
<data android:host="enso.me" android:scheme="https" />
|
||||
<data android:host="hipchat.me" android:scheme="https" />
|
||||
<data android:host="meet.jit.si" android:scheme="https" />
|
||||
</intent-filter>
|
||||
<intent-filter>
|
||||
<action android:name="android.intent.action.VIEW" />
|
||||
<category android:name="android.intent.category.BROWSABLE" />
|
||||
<category android:name="android.intent.category.DEFAULT" />
|
||||
<data android:scheme="org.jitsi.meet" />
|
||||
</intent-filter>
|
||||
</activity>
|
||||
<activity
|
||||
android:name="com.facebook.react.devsupport.DevSettingsActivity" />
|
||||
<meta-data
|
||||
android:name="io.fabric.ApiKey"
|
||||
android:value="a8ae24a58302ba79da1d312138e941f6b86e3242" />
|
||||
</application>
|
||||
</manifest>
|
||||
|
||||
@@ -1,8 +1,11 @@
|
||||
package org.jitsi.meet;
|
||||
package org.jitsi.jitsi_meet_react;
|
||||
|
||||
import android.os.Bundle;
|
||||
import com.crashlytics.android.Crashlytics;
|
||||
import com.facebook.react.ReactActivity;
|
||||
import com.facebook.react.ReactActivityDelegate;
|
||||
import com.facebook.react.ReactRootView;
|
||||
import io.fabric.sdk.android.Fabric;
|
||||
|
||||
public class MainActivity extends ReactActivity {
|
||||
/**
|
||||
@@ -43,4 +46,11 @@ public class MainActivity extends ReactActivity {
|
||||
protected String getMainComponentName() {
|
||||
return "App";
|
||||
}
|
||||
|
||||
@Override
|
||||
protected void onCreate(Bundle savedInstanceState) {
|
||||
super.onCreate(savedInstanceState);
|
||||
|
||||
Fabric.with(this, new Crashlytics());
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,39 @@
|
||||
package org.jitsi.jitsi_meet_react;
|
||||
|
||||
import android.app.Application;
|
||||
import android.util.Log;
|
||||
|
||||
import com.facebook.react.ReactApplication;
|
||||
import com.facebook.react.ReactInstanceManager;
|
||||
import com.facebook.react.ReactNativeHost;
|
||||
import com.facebook.react.ReactPackage;
|
||||
import com.facebook.react.shell.MainReactPackage;
|
||||
import com.oblador.vectoricons.VectorIconsPackage;
|
||||
import com.oney.WebRTCModule.WebRTCModulePackage;
|
||||
|
||||
import java.util.Arrays;
|
||||
import java.util.List;
|
||||
|
||||
public class MainApplication extends Application implements ReactApplication {
|
||||
|
||||
private final ReactNativeHost mReactNativeHost = new ReactNativeHost(this) {
|
||||
@Override
|
||||
protected boolean getUseDeveloperSupport() {
|
||||
return BuildConfig.DEBUG;
|
||||
}
|
||||
|
||||
@Override
|
||||
protected List<ReactPackage> getPackages() {
|
||||
return Arrays.<ReactPackage>asList(
|
||||
new MainReactPackage(),
|
||||
new VectorIconsPackage(),
|
||||
new WebRTCModulePackage()
|
||||
);
|
||||
}
|
||||
};
|
||||
|
||||
@Override
|
||||
public ReactNativeHost getReactNativeHost() {
|
||||
return mReactNativeHost;
|
||||
}
|
||||
}
|
||||
@@ -1,64 +0,0 @@
|
||||
package org.jitsi.meet;
|
||||
|
||||
import android.app.Application;
|
||||
|
||||
import com.facebook.react.ReactApplication;
|
||||
import com.facebook.react.ReactNativeHost;
|
||||
import com.facebook.react.ReactPackage;
|
||||
import com.facebook.soloader.SoLoader;
|
||||
|
||||
import java.util.Arrays;
|
||||
import java.util.List;
|
||||
|
||||
public class MainApplication extends Application implements ReactApplication {
|
||||
private final ReactNativeHost mReactNativeHost = new ReactNativeHost(this) {
|
||||
/**
|
||||
* {@inheritDoc}
|
||||
*/
|
||||
@Override
|
||||
public boolean getUseDeveloperSupport() {
|
||||
return BuildConfig.DEBUG;
|
||||
}
|
||||
|
||||
/**
|
||||
* {@inheritDoc}
|
||||
*/
|
||||
@Override
|
||||
protected List<ReactPackage> getPackages() {
|
||||
return Arrays.<ReactPackage>asList(
|
||||
new com.corbt.keepawake.KCKeepAwakePackage(),
|
||||
new com.facebook.react.shell.MainReactPackage(),
|
||||
new com.oblador.vectoricons.VectorIconsPackage(),
|
||||
new com.ocetnik.timer.BackgroundTimerPackage(),
|
||||
new com.oney.WebRTCModule.WebRTCModulePackage(),
|
||||
new com.rnimmersive.RNImmersivePackage(),
|
||||
new org.jitsi.meet.audiomode.AudioModePackage()
|
||||
);
|
||||
}
|
||||
};
|
||||
|
||||
/**
|
||||
* {@inheritDoc}
|
||||
*/
|
||||
@Override
|
||||
public ReactNativeHost getReactNativeHost() {
|
||||
return mReactNativeHost;
|
||||
}
|
||||
|
||||
/**
|
||||
* {@inheritDoc}
|
||||
*/
|
||||
@Override
|
||||
public void onCreate() {
|
||||
super.onCreate();
|
||||
|
||||
SoLoader.init(this, /* native exopackage */ false);
|
||||
|
||||
if (!getReactNativeHost()
|
||||
.getReactInstanceManager()
|
||||
.getDevSupportManager()
|
||||
.getDevSupportEnabled()) {
|
||||
// TODO Auto-generated method stub
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -1,322 +0,0 @@
|
||||
package org.jitsi.meet.audiomode;
|
||||
|
||||
import android.annotation.TargetApi;
|
||||
import android.content.BroadcastReceiver;
|
||||
import android.content.Context;
|
||||
import android.content.Intent;
|
||||
import android.content.IntentFilter;
|
||||
import android.media.AudioDeviceInfo;
|
||||
import android.media.AudioManager;
|
||||
import android.os.Build;
|
||||
import android.os.Handler;
|
||||
import android.os.Looper;
|
||||
import android.util.Log;
|
||||
|
||||
import com.facebook.react.bridge.Promise;
|
||||
import com.facebook.react.bridge.ReactApplicationContext;
|
||||
import com.facebook.react.bridge.ReactContextBaseJavaModule;
|
||||
import com.facebook.react.bridge.ReactMethod;
|
||||
|
||||
import java.util.HashMap;
|
||||
import java.util.Map;
|
||||
|
||||
/**
|
||||
* Module implementing a simple API to select the appropriate audio device for a
|
||||
* conference call.
|
||||
*
|
||||
* Audio calls should use <tt>AudioModeModule.AUDIO_CALL</tt>, which uses the
|
||||
* builtin earpiece, wired headset or bluetooth headset. The builtin earpiece is
|
||||
* the default audio device.
|
||||
*
|
||||
* Video calls should should use <tt>AudioModeModule.VIDEO_CALL</tt>, which uses
|
||||
* the builtin speaker, earpiece, wired headset or bluetooth headset. The
|
||||
* builtin speaker is the default audio device.
|
||||
*
|
||||
* Before a call has started and after it has ended the
|
||||
* <tt>AudioModeModule.DEFAULT</tt> mode should be used.
|
||||
*/
|
||||
public class AudioModeModule extends ReactContextBaseJavaModule {
|
||||
/**
|
||||
* Constants representing the audio mode.
|
||||
* - DEFAULT: Used before and after every call. It represents the default
|
||||
* audio routing scheme.
|
||||
* - AUDIO_CALL: Used for audio only calls. It will use the earpiece by
|
||||
* default, unless a wired or Bluetooth headset is connected.
|
||||
* - VIDEO_CALL: Used for video calls. It will use the speaker by default,
|
||||
* unless a wired or Bluetooth headset is connected.
|
||||
*/
|
||||
private static final int DEFAULT = 0;
|
||||
private static final int AUDIO_CALL = 1;
|
||||
private static final int VIDEO_CALL = 2;
|
||||
|
||||
/**
|
||||
*
|
||||
*/
|
||||
private static final String ACTION_HEADSET_PLUG
|
||||
= (Build.VERSION.SDK_INT >= 21)
|
||||
? AudioManager.ACTION_HEADSET_PLUG
|
||||
: Intent.ACTION_HEADSET_PLUG;
|
||||
|
||||
/**
|
||||
* React Native module name.
|
||||
*/
|
||||
private static final String MODULE_NAME = "AudioMode";
|
||||
|
||||
/**
|
||||
* Tag used when logging messages.
|
||||
*/
|
||||
static final String TAG = MODULE_NAME;
|
||||
|
||||
/**
|
||||
* {@link AudioManager} instance used to interact with the Android audio
|
||||
* subsystem.
|
||||
*/
|
||||
private final AudioManager audioManager;
|
||||
|
||||
/**
|
||||
* {@link BluetoothHeadsetMonitor} for detecting Bluetooth device changes in
|
||||
* old (< M) Android versions.
|
||||
*/
|
||||
private BluetoothHeadsetMonitor bluetoothHeadsetMonitor;
|
||||
|
||||
/**
|
||||
* {@link Handler} for running all operations on the main thread.
|
||||
*/
|
||||
private final Handler mainThreadHandler
|
||||
= new Handler(Looper.getMainLooper());
|
||||
|
||||
/**
|
||||
* {@link Runnable} for running update operation on the main thread.
|
||||
*/
|
||||
private final Runnable mainThreadRunner
|
||||
= new Runnable() {
|
||||
@Override
|
||||
public void run() {
|
||||
if (mode != -1) {
|
||||
updateAudioRoute(mode);
|
||||
}
|
||||
}
|
||||
};
|
||||
|
||||
/**
|
||||
* Audio mode currently in use.
|
||||
*/
|
||||
private int mode = -1;
|
||||
|
||||
/**
|
||||
* Initializes a new module instance. There shall be a single instance of
|
||||
* this module throughout the lifetime of the application.
|
||||
*
|
||||
* @param reactContext the {@link ReactApplicationContext} where this module
|
||||
* is created.
|
||||
*/
|
||||
public AudioModeModule(ReactApplicationContext reactContext) {
|
||||
super(reactContext);
|
||||
|
||||
audioManager
|
||||
= (AudioManager)
|
||||
reactContext.getSystemService(Context.AUDIO_SERVICE);
|
||||
|
||||
// Setup runtime device change detection.
|
||||
setupAudioRouteChangeDetection();
|
||||
}
|
||||
|
||||
/**
|
||||
* Gets a mapping with the constants this module is exporting.
|
||||
*
|
||||
* @return a {@link Map} mapping the constants to be exported with their
|
||||
* values.
|
||||
*/
|
||||
@Override
|
||||
public Map<String, Object> getConstants() {
|
||||
Map<String, Object> constants = new HashMap<>();
|
||||
|
||||
constants.put("AUDIO_CALL", AUDIO_CALL);
|
||||
constants.put("DEFAULT", DEFAULT);
|
||||
constants.put("VIDEO_CALL", VIDEO_CALL);
|
||||
|
||||
return constants;
|
||||
}
|
||||
|
||||
/**
|
||||
* Gets the name for this module, to be used in the React Native bridge.
|
||||
*
|
||||
* @return a string with the module name.
|
||||
*/
|
||||
@Override
|
||||
public String getName() {
|
||||
return MODULE_NAME;
|
||||
}
|
||||
|
||||
/**
|
||||
* Helper method to trigger an audio route update when devices change. It
|
||||
* makes sure the operation is performed on the main thread.
|
||||
*/
|
||||
void onAudioDeviceChange() {
|
||||
mainThreadHandler.post(mainThreadRunner);
|
||||
}
|
||||
|
||||
/**
|
||||
* Helper method to set the output route to a Bluetooth device.
|
||||
*
|
||||
* @param enabled true if Bluetooth should use used, false otherwise.
|
||||
*/
|
||||
private void setBluetoothAudioRoute(boolean enabled) {
|
||||
if (enabled) {
|
||||
audioManager.startBluetoothSco();
|
||||
audioManager.setBluetoothScoOn(true);
|
||||
} else {
|
||||
audioManager.setBluetoothScoOn(false);
|
||||
audioManager.stopBluetoothSco();
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Public method to set the current audio mode.
|
||||
*
|
||||
* @param mode the desired audio mode.
|
||||
* @param promise a {@link Promise} which will be resolved if the audio mode
|
||||
* could be updated successfully, and it will be rejected otherwise.
|
||||
*/
|
||||
@ReactMethod
|
||||
public void setMode(final int mode, final Promise promise) {
|
||||
if (mode != DEFAULT && mode != AUDIO_CALL && mode != VIDEO_CALL) {
|
||||
promise.reject("setMode", "Invalid audio mode " + mode);
|
||||
return;
|
||||
}
|
||||
|
||||
Runnable r = new Runnable() {
|
||||
@Override
|
||||
public void run() {
|
||||
if (updateAudioRoute(mode)) {
|
||||
AudioModeModule.this.mode = mode;
|
||||
promise.resolve(null);
|
||||
} else {
|
||||
promise.reject(
|
||||
"setMode",
|
||||
"Failed to set the requested audio mode");
|
||||
}
|
||||
}
|
||||
};
|
||||
mainThreadHandler.post(r);
|
||||
}
|
||||
|
||||
/**
|
||||
* Setup the audio route change detection mechanism. We use the
|
||||
* {@link android.media.AudioDeviceCallback} API on Android >= 23 only.
|
||||
*/
|
||||
private void setupAudioRouteChangeDetection() {
|
||||
if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.M) {
|
||||
setupAudioRouteChangeDetectionM();
|
||||
} else {
|
||||
setupAudioRouteChangeDetectionPreM();
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Audio route change detection mechanism for Android API >= 23.
|
||||
*/
|
||||
@TargetApi(Build.VERSION_CODES.M)
|
||||
private void setupAudioRouteChangeDetectionM() {
|
||||
android.media.AudioDeviceCallback audioDeviceCallback =
|
||||
new android.media.AudioDeviceCallback() {
|
||||
@Override
|
||||
public void onAudioDevicesAdded(
|
||||
AudioDeviceInfo[] addedDevices) {
|
||||
Log.d(TAG, "Audio devices added");
|
||||
onAudioDeviceChange();
|
||||
}
|
||||
|
||||
@Override
|
||||
public void onAudioDevicesRemoved(
|
||||
AudioDeviceInfo[] removedDevices) {
|
||||
Log.d(TAG, "Audio devices removed");
|
||||
onAudioDeviceChange();
|
||||
}
|
||||
};
|
||||
|
||||
audioManager.registerAudioDeviceCallback(audioDeviceCallback, null);
|
||||
}
|
||||
|
||||
/**
|
||||
* Audio route change detection mechanism for Android API < 23.
|
||||
*/
|
||||
private void setupAudioRouteChangeDetectionPreM() {
|
||||
Context context = getReactApplicationContext();
|
||||
|
||||
// Detect changes in wired headset connections.
|
||||
IntentFilter wiredHeadSetFilter = new IntentFilter(ACTION_HEADSET_PLUG);
|
||||
BroadcastReceiver wiredHeadsetReceiver = new BroadcastReceiver() {
|
||||
@Override
|
||||
public void onReceive(Context context, Intent intent) {
|
||||
Log.d(TAG, "Wired headset added / removed");
|
||||
onAudioDeviceChange();
|
||||
}
|
||||
};
|
||||
context.registerReceiver(wiredHeadsetReceiver, wiredHeadSetFilter);
|
||||
|
||||
// Detect Bluetooth device changes.
|
||||
bluetoothHeadsetMonitor = new BluetoothHeadsetMonitor(this, context);
|
||||
}
|
||||
|
||||
/**
|
||||
* Updates the audio route for the given mode.
|
||||
*
|
||||
* @param mode the audio mode to be used when computing the audio route.
|
||||
* @return true if the audio route was updated successfully, false
|
||||
* otherwise.
|
||||
*/
|
||||
private boolean updateAudioRoute(int mode) {
|
||||
Log.d(TAG, "Update audio route for mode: " + mode);
|
||||
|
||||
if (mode == DEFAULT) {
|
||||
audioManager.setMode(AudioManager.MODE_NORMAL);
|
||||
audioManager.abandonAudioFocus(null);
|
||||
audioManager.setSpeakerphoneOn(false);
|
||||
audioManager.setMicrophoneMute(true);
|
||||
setBluetoothAudioRoute(false);
|
||||
|
||||
return true;
|
||||
}
|
||||
|
||||
audioManager.setMode(AudioManager.MODE_IN_COMMUNICATION);
|
||||
audioManager.setMicrophoneMute(false);
|
||||
|
||||
if (audioManager.requestAudioFocus(
|
||||
null,
|
||||
AudioManager.STREAM_VOICE_CALL,
|
||||
AudioManager.AUDIOFOCUS_GAIN)
|
||||
== AudioManager.AUDIOFOCUS_REQUEST_FAILED) {
|
||||
Log.d(TAG, "Audio focus request failed");
|
||||
return false;
|
||||
}
|
||||
|
||||
boolean useSpeaker = (mode == VIDEO_CALL);
|
||||
|
||||
if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.M) {
|
||||
// On Android >= M we use the AudioDeviceCallback API, so turn on
|
||||
// Bluetooth SCO from the start.
|
||||
if (audioManager.isBluetoothScoAvailableOffCall()) {
|
||||
audioManager.startBluetoothSco();
|
||||
}
|
||||
} else {
|
||||
// On older Android versions we must set the Bluetooth route
|
||||
// manually. Also disable the speaker in that case.
|
||||
setBluetoothAudioRoute(
|
||||
bluetoothHeadsetMonitor.isHeadsetAvailable());
|
||||
if (bluetoothHeadsetMonitor.isHeadsetAvailable()) {
|
||||
useSpeaker = false;
|
||||
}
|
||||
}
|
||||
|
||||
// XXX: isWiredHeadsetOn is not deprecated when used just for knowing if
|
||||
// there is a wired headset connected, regardless of audio being routed
|
||||
// to it.
|
||||
audioManager.setSpeakerphoneOn(
|
||||
useSpeaker
|
||||
&& !(audioManager.isWiredHeadsetOn()
|
||||
|| audioManager.isBluetoothScoOn()));
|
||||
|
||||
return true;
|
||||
}
|
||||
}
|
||||
@@ -1,48 +0,0 @@
|
||||
package org.jitsi.meet.audiomode;
|
||||
|
||||
import com.facebook.react.ReactPackage;
|
||||
import com.facebook.react.bridge.JavaScriptModule;
|
||||
import com.facebook.react.bridge.NativeModule;
|
||||
import com.facebook.react.bridge.ReactApplicationContext;
|
||||
import com.facebook.react.uimanager.ViewManager;
|
||||
|
||||
import java.util.ArrayList;
|
||||
import java.util.Collections;
|
||||
import java.util.List;
|
||||
|
||||
/**
|
||||
* Implements {@link ReactPackage} for {@link AudioModeModule}.
|
||||
*/
|
||||
public class AudioModePackage implements ReactPackage {
|
||||
/**
|
||||
* {@inheritDoc}
|
||||
*/
|
||||
@Override
|
||||
public List<Class<? extends JavaScriptModule>> createJSModules() {
|
||||
return Collections.emptyList();
|
||||
}
|
||||
|
||||
/**
|
||||
* {@inheritDoc}
|
||||
*
|
||||
* @return List of native modules to be exposed by React Native.
|
||||
*/
|
||||
@Override
|
||||
public List<NativeModule> createNativeModules(
|
||||
ReactApplicationContext reactContext) {
|
||||
List<NativeModule> modules = new ArrayList<>();
|
||||
|
||||
modules.add(new AudioModeModule(reactContext));
|
||||
|
||||
return modules;
|
||||
}
|
||||
|
||||
/**
|
||||
* {@inheritDoc}
|
||||
*/
|
||||
@Override
|
||||
public List<ViewManager> createViewManagers(
|
||||
ReactApplicationContext reactContext) {
|
||||
return Collections.emptyList();
|
||||
}
|
||||
}
|
||||
@@ -1,189 +0,0 @@
|
||||
package org.jitsi.meet.audiomode;
|
||||
|
||||
import android.bluetooth.BluetoothAdapter;
|
||||
import android.bluetooth.BluetoothDevice;
|
||||
import android.bluetooth.BluetoothHeadset;
|
||||
import android.bluetooth.BluetoothProfile;
|
||||
import android.content.BroadcastReceiver;
|
||||
import android.content.Context;
|
||||
import android.content.Intent;
|
||||
import android.content.IntentFilter;
|
||||
import android.media.AudioManager;
|
||||
import android.os.Handler;
|
||||
import android.os.Looper;
|
||||
import android.util.Log;
|
||||
|
||||
/**
|
||||
* Helper class to detect and handle Bluetooth device changes. It monitors
|
||||
* Bluetooth headsets being connected / disconnected and notifies the module
|
||||
* about device changes when this occurs.
|
||||
*/
|
||||
public class BluetoothHeadsetMonitor {
|
||||
/**
|
||||
* {@link AudioModeModule} where this monitor reports.
|
||||
*/
|
||||
private final AudioModeModule audioModeModule;
|
||||
|
||||
/**
|
||||
* The {@link Context} in which {@link #audioModeModule} executes.
|
||||
*/
|
||||
private final Context context;
|
||||
|
||||
/**
|
||||
* Reference to a proxy object which allows us to query connected devices.
|
||||
*/
|
||||
private BluetoothHeadset headset;
|
||||
|
||||
/**
|
||||
* Flag indicating if there are any Bluetooth headset devices currently
|
||||
* available.
|
||||
*/
|
||||
private boolean headsetAvailable = false;
|
||||
|
||||
/**
|
||||
* {@link Handler} for running all operations on the main thread.
|
||||
*/
|
||||
private final Handler mainThreadHandler
|
||||
= new Handler(Looper.getMainLooper());
|
||||
|
||||
/**
|
||||
* Helper for running Bluetooth operations on the main thread.
|
||||
*/
|
||||
private final Runnable updateDevicesRunnable
|
||||
= new Runnable() {
|
||||
@Override
|
||||
public void run() {
|
||||
headsetAvailable
|
||||
= (headset != null)
|
||||
&& !headset.getConnectedDevices().isEmpty();
|
||||
audioModeModule.onAudioDeviceChange();
|
||||
}
|
||||
};
|
||||
|
||||
public BluetoothHeadsetMonitor(
|
||||
AudioModeModule audioModeModule,
|
||||
Context context) {
|
||||
this.audioModeModule = audioModeModule;
|
||||
this.context = context;
|
||||
|
||||
AudioManager audioManager
|
||||
= (AudioManager) context.getSystemService(Context.AUDIO_SERVICE);
|
||||
|
||||
if (!audioManager.isBluetoothScoAvailableOffCall()) {
|
||||
Log.w(AudioModeModule.TAG, "Bluetooth SCO is not available");
|
||||
return;
|
||||
}
|
||||
|
||||
if (getBluetoothHeadsetProfileProxy()) {
|
||||
registerBluetoothReceiver();
|
||||
|
||||
// Initial detection.
|
||||
updateDevices();
|
||||
}
|
||||
}
|
||||
|
||||
private boolean getBluetoothHeadsetProfileProxy() {
|
||||
BluetoothAdapter adapter = BluetoothAdapter.getDefaultAdapter();
|
||||
|
||||
if (adapter == null) {
|
||||
Log.w(AudioModeModule.TAG, "Device doesn't support Bluetooth");
|
||||
return false;
|
||||
}
|
||||
|
||||
// XXX: The profile listener listens for system services of the given
|
||||
// type being available to the application. That is, if our Bluetooth
|
||||
// adapter has the "headset" profile.
|
||||
BluetoothProfile.ServiceListener listener
|
||||
= new BluetoothProfile.ServiceListener() {
|
||||
@Override
|
||||
public void onServiceConnected(
|
||||
int profile,
|
||||
BluetoothProfile proxy) {
|
||||
if (profile == BluetoothProfile.HEADSET) {
|
||||
headset = (BluetoothHeadset) proxy;
|
||||
updateDevices();
|
||||
}
|
||||
}
|
||||
|
||||
@Override
|
||||
public void onServiceDisconnected(int profile) {
|
||||
// The logic is the same as the logic of onServiceConnected.
|
||||
onServiceConnected(profile, /* proxy */ null);
|
||||
}
|
||||
};
|
||||
|
||||
return
|
||||
adapter.getProfileProxy(
|
||||
context,
|
||||
listener,
|
||||
BluetoothProfile.HEADSET);
|
||||
}
|
||||
|
||||
/**
|
||||
* Returns the current headset availability.
|
||||
*
|
||||
* @return true if there is a Bluetooth headset connected, false otherwise.
|
||||
*/
|
||||
public boolean isHeadsetAvailable() {
|
||||
return headsetAvailable;
|
||||
}
|
||||
|
||||
private void onBluetoothReceiverReceive(Context context, Intent intent) {
|
||||
final String action = intent.getAction();
|
||||
|
||||
if (action.equals(BluetoothHeadset.ACTION_CONNECTION_STATE_CHANGED)) {
|
||||
// XXX: This action will be fired when a Bluetooth headset is
|
||||
// connected or disconnected to the system. This is not related to
|
||||
// audio routing.
|
||||
int state = intent.getIntExtra(BluetoothHeadset.EXTRA_STATE, -99);
|
||||
|
||||
switch (state) {
|
||||
case BluetoothHeadset.STATE_CONNECTED:
|
||||
case BluetoothHeadset.STATE_DISCONNECTED:
|
||||
Log.d(
|
||||
AudioModeModule.TAG,
|
||||
"BT headset connection state changed: " + state);
|
||||
updateDevices();
|
||||
break;
|
||||
}
|
||||
} else if (action.equals(AudioManager.ACTION_SCO_AUDIO_STATE_UPDATED)) {
|
||||
// XXX: This action will be fired when the connection established
|
||||
// with a Bluetooth headset (called a SCO connection) changes state.
|
||||
// When the SCO connection is active we route audio to it.
|
||||
int state
|
||||
= intent.getIntExtra(AudioManager.EXTRA_SCO_AUDIO_STATE, -99);
|
||||
|
||||
switch (state) {
|
||||
case AudioManager.SCO_AUDIO_STATE_CONNECTED:
|
||||
case AudioManager.SCO_AUDIO_STATE_DISCONNECTED:
|
||||
Log.d(
|
||||
AudioModeModule.TAG,
|
||||
"BT SCO connection state changed: " + state);
|
||||
updateDevices();
|
||||
break;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
private void registerBluetoothReceiver() {
|
||||
BroadcastReceiver receiver = new BroadcastReceiver() {
|
||||
@Override
|
||||
public void onReceive(Context context, Intent intent) {
|
||||
onBluetoothReceiverReceive(context, intent);
|
||||
}
|
||||
};
|
||||
IntentFilter filter = new IntentFilter();
|
||||
|
||||
filter.addAction(AudioManager.ACTION_SCO_AUDIO_STATE_UPDATED);
|
||||
filter.addAction(BluetoothHeadset.ACTION_CONNECTION_STATE_CHANGED);
|
||||
context.registerReceiver(receiver, filter);
|
||||
}
|
||||
|
||||
/**
|
||||
* Detects if there are new devices connected / disconnected and fires the
|
||||
* {@link AudioModeModule#onAudioDeviceChange()} callback.
|
||||
*/
|
||||
private void updateDevices() {
|
||||
mainThreadHandler.post(updateDevicesRunnable);
|
||||
}
|
||||
}
|
||||
|
Before Width: | Height: | Size: 8.7 KiB After Width: | Height: | Size: 5.2 KiB |
|
Before Width: | Height: | Size: 5.0 KiB After Width: | Height: | Size: 3.1 KiB |
|
Before Width: | Height: | Size: 13 KiB After Width: | Height: | Size: 7.7 KiB |
|
Before Width: | Height: | Size: 25 KiB After Width: | Height: | Size: 14 KiB |
|
Before Width: | Height: | Size: 38 KiB After Width: | Height: | Size: 20 KiB |
@@ -3,7 +3,6 @@
|
||||
<!-- Base application theme. -->
|
||||
<style name="AppTheme" parent="Theme.AppCompat.Light.NoActionBar">
|
||||
<!-- Customize your theme here. -->
|
||||
<item name="android:windowTranslucentStatus">true</item>
|
||||
</style>
|
||||
|
||||
</resources>
|
||||
|
||||
@@ -5,7 +5,7 @@ buildscript {
|
||||
jcenter()
|
||||
}
|
||||
dependencies {
|
||||
classpath 'com.android.tools.build:gradle:2.2.3'
|
||||
classpath 'com.android.tools.build:gradle:1.3.1'
|
||||
|
||||
// NOTE: Do not place your application dependencies here; they belong
|
||||
// in the individual module build.gradle files
|
||||
|
||||
@@ -18,4 +18,3 @@
|
||||
# org.gradle.parallel=true
|
||||
|
||||
android.useDeprecatedNdk=true
|
||||
version=1
|
||||
|
||||
@@ -2,4 +2,4 @@ distributionBase=GRADLE_USER_HOME
|
||||
distributionPath=wrapper/dists
|
||||
zipStoreBase=GRADLE_USER_HOME
|
||||
zipStorePath=wrapper/dists
|
||||
distributionUrl=https\://services.gradle.org/distributions/gradle-2.14.1-all.zip
|
||||
distributionUrl=https\://services.gradle.org/distributions/gradle-2.4-all.zip
|
||||
|
||||
@@ -1,12 +1,6 @@
|
||||
rootProject.name = 'jitsi-meet-react'
|
||||
|
||||
include ':app'
|
||||
include ':react-native-background-timer'
|
||||
project(':react-native-background-timer').projectDir = new File(rootProject.projectDir, '../node_modules/react-native-background-timer/android')
|
||||
include ':react-native-immersive'
|
||||
project(':react-native-immersive').projectDir = new File(rootProject.projectDir, '../node_modules/react-native-immersive/android')
|
||||
include ':react-native-keep-awake'
|
||||
project(':react-native-keep-awake').projectDir = new File(rootProject.projectDir, '../node_modules/react-native-keep-awake/android')
|
||||
include ':react-native-vector-icons'
|
||||
project(':react-native-vector-icons').projectDir = new File(rootProject.projectDir, '../node_modules/react-native-vector-icons/android')
|
||||
include ':react-native-webrtc'
|
||||
|
||||
258
app.js
@@ -1,10 +1,14 @@
|
||||
/* global $, config, getRoomName, loggingConfig, JitsiMeetJS */
|
||||
/* application specific logic */
|
||||
const logger = require("jitsi-meet-logger").getLogger(__filename);
|
||||
|
||||
import "babel-polyfill";
|
||||
import "jquery";
|
||||
import "jquery-contextmenu";
|
||||
import "jquery-ui";
|
||||
import "strophe";
|
||||
import "strophe-disco";
|
||||
import "strophe-caps";
|
||||
import "jQuery-Impromptu";
|
||||
import "autosize";
|
||||
|
||||
@@ -15,13 +19,101 @@ import 'aui-experimental-css';
|
||||
|
||||
window.toastr = require("toastr");
|
||||
|
||||
const Logger = require("jitsi-meet-logger");
|
||||
const LogCollector = Logger.LogCollector;
|
||||
import JitsiMeetLogStorage from "./modules/util/JitsiMeetLogStorage";
|
||||
|
||||
import URLProcessor from "./modules/config/URLProcessor";
|
||||
import RoomnameGenerator from './modules/util/RoomnameGenerator';
|
||||
|
||||
import UI from "./modules/UI/UI";
|
||||
import settings from "./modules/settings/Settings";
|
||||
import conference from './conference';
|
||||
import ConferenceUrl from './modules/URL/ConferenceUrl';
|
||||
import API from './modules/API/API';
|
||||
|
||||
import UIEvents from './service/UI/UIEvents';
|
||||
import getTokenData from "./modules/tokendata/TokenData";
|
||||
import translation from "./modules/translation/translation";
|
||||
import remoteControl from "./modules/remotecontrol/RemoteControl";
|
||||
|
||||
const ConferenceEvents = JitsiMeetJS.events.conference;
|
||||
|
||||
/**
|
||||
* Tries to push history state with the following parameters:
|
||||
* 'VideoChat', `Room: ${roomName}`, URL. If fail, prints the error and returns
|
||||
* it.
|
||||
*/
|
||||
function pushHistoryState(roomName, URL) {
|
||||
try {
|
||||
window.history.pushState(
|
||||
'VideoChat', `Room: ${roomName}`, URL
|
||||
);
|
||||
} catch (e) {
|
||||
logger.warn("Push history state failed with parameters:",
|
||||
'VideoChat', `Room: ${roomName}`, URL, e);
|
||||
return e;
|
||||
}
|
||||
return null;
|
||||
}
|
||||
|
||||
/**
|
||||
* Replaces current history state(replaces the URL displayed by the browser).
|
||||
* @param {string} newUrl the URL string which is to be displayed by the browser
|
||||
* to the user.
|
||||
*/
|
||||
function replaceHistoryState (newUrl) {
|
||||
if (window.history
|
||||
&& typeof window.history.replaceState === 'function') {
|
||||
window.history.replaceState({}, document.title, newUrl);
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Builds and returns the room name.
|
||||
*/
|
||||
function buildRoomName () {
|
||||
let roomName = getRoomName();
|
||||
|
||||
if(!roomName) {
|
||||
let word = RoomnameGenerator.generateRoomWithoutSeparator();
|
||||
roomName = word.toLowerCase();
|
||||
let historyURL = window.location.href + word;
|
||||
//Trying to push state with current URL + roomName
|
||||
pushHistoryState(word, historyURL);
|
||||
}
|
||||
|
||||
return roomName;
|
||||
}
|
||||
|
||||
/**
|
||||
* Adjusts the logging levels.
|
||||
* @private
|
||||
*/
|
||||
function configureLoggingLevels () {
|
||||
// NOTE The library Logger is separated from the app loggers, so the levels
|
||||
// have to be set in two places
|
||||
|
||||
// Set default logging level
|
||||
const defaultLogLevel
|
||||
= loggingConfig.defaultLogLevel || JitsiMeetJS.logLevels.TRACE;
|
||||
Logger.setLogLevel(defaultLogLevel);
|
||||
JitsiMeetJS.setLogLevel(defaultLogLevel);
|
||||
|
||||
// NOTE console was used on purpose here to go around the logging
|
||||
// and always print the default logging level to the console
|
||||
console.info("Default logging level set to: " + defaultLogLevel);
|
||||
|
||||
// Set log level for each logger
|
||||
if (loggingConfig) {
|
||||
Object.keys(loggingConfig).forEach(function(loggerName) {
|
||||
if ('defaultLogLevel' !== loggerName) {
|
||||
const level = loggingConfig[loggerName];
|
||||
Logger.setLogLevelById(level, loggerName);
|
||||
JitsiMeetJS.setLogLevelById(level, loggerName);
|
||||
}
|
||||
});
|
||||
}
|
||||
}
|
||||
|
||||
const APP = {
|
||||
// Used by do_external_connect.js if we receive the attach data after
|
||||
@@ -60,15 +152,163 @@ const APP = {
|
||||
ConferenceUrl : null,
|
||||
connection: null,
|
||||
API,
|
||||
remoteControl
|
||||
init () {
|
||||
this.initLogging();
|
||||
this.keyboardshortcut =
|
||||
require("./modules/keyboardshortcut/keyboardshortcut");
|
||||
this.configFetch = require("./modules/config/HttpConfigFetch");
|
||||
this.tokenData = getTokenData();
|
||||
},
|
||||
initLogging () {
|
||||
// Adjust logging level
|
||||
configureLoggingLevels();
|
||||
// Create the LogCollector and register it as the global log transport.
|
||||
// It is done early to capture as much logs as possible. Captured logs
|
||||
// will be cached, before the JitsiMeetLogStorage gets ready (statistics
|
||||
// module is initialized).
|
||||
if (!this.logCollector && !loggingConfig.disableLogCollector) {
|
||||
this.logCollector = new LogCollector(new JitsiMeetLogStorage());
|
||||
Logger.addGlobalTransport(this.logCollector);
|
||||
JitsiMeetJS.addGlobalLogTransport(this.logCollector);
|
||||
}
|
||||
}
|
||||
};
|
||||
|
||||
// TODO The execution of the mobile app starts from react/index.native.js.
|
||||
// Similarly, the execution of the Web app should start from react/index.web.js
|
||||
// for the sake of consistency and ease of understanding. Temporarily though
|
||||
// because we are at the beginning of introducing React into the Web app, allow
|
||||
// the execution of the Web app to start from app.js in order to reduce the
|
||||
// complexity of the beginning step.
|
||||
require('./react');
|
||||
/**
|
||||
* If JWT token data it will be used for local user settings
|
||||
*/
|
||||
function setTokenData() {
|
||||
let localUser = APP.tokenData.caller;
|
||||
if(localUser) {
|
||||
APP.settings.setEmail((localUser.getEmail() || "").trim(), true);
|
||||
APP.settings.setAvatarUrl((localUser.getAvatarUrl() || "").trim());
|
||||
APP.settings.setDisplayName((localUser.getName() || "").trim(), true);
|
||||
}
|
||||
}
|
||||
|
||||
function init() {
|
||||
setTokenData();
|
||||
// Initialize the conference URL handler
|
||||
APP.ConferenceUrl = new ConferenceUrl(window.location);
|
||||
// Clean up the URL displayed by the browser
|
||||
replaceHistoryState(APP.ConferenceUrl.getInviteUrl());
|
||||
|
||||
// TODO The execution of the mobile app starts from react/index.native.js.
|
||||
// Similarly, the execution of the Web app should start from
|
||||
// react/index.web.js for the sake of consistency and ease of understanding.
|
||||
// Temporarily though because we are at the beginning of introducing React
|
||||
// into the Web app, allow the execution of the Web app to start from app.js
|
||||
// in order to reduce the complexity of the beginning step.
|
||||
require('./react');
|
||||
|
||||
const isUIReady = APP.UI.start();
|
||||
if (isUIReady) {
|
||||
APP.conference.init({roomName: buildRoomName()}).then(() => {
|
||||
|
||||
if (APP.logCollector) {
|
||||
// Start the LogCollector's periodic "store logs" task only if
|
||||
// we're in the conference and not on the welcome page. This is
|
||||
// determined by the value of "isUIReady" const above.
|
||||
APP.logCollector.start();
|
||||
APP.logCollectorStarted = true;
|
||||
// Make an attempt to flush in case a lot of logs have been
|
||||
// cached, before the collector was started.
|
||||
APP.logCollector.flush();
|
||||
|
||||
// This event listener will flush the logs, before
|
||||
// the statistics module (CallStats) is stopped.
|
||||
//
|
||||
// NOTE The LogCollector is not stopped, because this event can
|
||||
// be triggered multiple times during single conference
|
||||
// (whenever statistics module is stopped). That includes
|
||||
// the case when Jicofo terminates the single person left in the
|
||||
// room. It will then restart the media session when someone
|
||||
// eventually join the room which will start the stats again.
|
||||
APP.conference.addConferenceListener(
|
||||
ConferenceEvents.BEFORE_STATISTICS_DISPOSED,
|
||||
() => {
|
||||
if (APP.logCollector) {
|
||||
APP.logCollector.flush();
|
||||
}
|
||||
}
|
||||
);
|
||||
}
|
||||
|
||||
APP.UI.initConference();
|
||||
|
||||
APP.UI.addListener(UIEvents.LANG_CHANGED, language => {
|
||||
APP.translation.setLanguage(language);
|
||||
APP.settings.setLanguage(language);
|
||||
});
|
||||
|
||||
APP.keyboardshortcut.init();
|
||||
}).catch(err => {
|
||||
APP.UI.hideRingOverLay();
|
||||
APP.API.notifyConferenceLeft(APP.conference.roomName);
|
||||
logger.error(err);
|
||||
});
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* If we have an HTTP endpoint for getting config.json configured we're going to
|
||||
* read it and override properties from config.js and interfaceConfig.js.
|
||||
* If there is no endpoint we'll just continue with initialization.
|
||||
* Keep in mind that if the endpoint has been configured and we fail to obtain
|
||||
* the config for any reason then the conference won't start and error message
|
||||
* will be displayed to the user.
|
||||
*/
|
||||
function obtainConfigAndInit() {
|
||||
let roomName = APP.conference.roomName;
|
||||
|
||||
if (config.configLocation) {
|
||||
APP.configFetch.obtainConfig(
|
||||
config.configLocation, roomName,
|
||||
// Get config result callback
|
||||
function(success, error) {
|
||||
if (success) {
|
||||
var now = APP.connectionTimes["configuration.fetched"] =
|
||||
window.performance.now();
|
||||
logger.log("(TIME) configuration fetched:\t", now);
|
||||
init();
|
||||
} else {
|
||||
// Show obtain config error,
|
||||
// pass the error object for report
|
||||
APP.UI.messageHandler.openReportDialog(
|
||||
null, "dialog.connectError", error);
|
||||
}
|
||||
});
|
||||
} else {
|
||||
require("./modules/config/BoshAddressChoice").chooseAddress(
|
||||
config, roomName);
|
||||
|
||||
init();
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
$(document).ready(function () {
|
||||
var now = APP.connectionTimes["document.ready"] = window.performance.now();
|
||||
logger.log("(TIME) document ready:\t", now);
|
||||
|
||||
URLProcessor.setConfigParametersFromUrl();
|
||||
|
||||
APP.init();
|
||||
|
||||
APP.translation.init(settings.getLanguage());
|
||||
|
||||
APP.API.init(APP.tokenData.externalAPISettings);
|
||||
|
||||
obtainConfigAndInit();
|
||||
});
|
||||
|
||||
$(window).bind('beforeunload', function () {
|
||||
// Stop the LogCollector
|
||||
if (APP.logCollectorStarted) {
|
||||
APP.logCollector.stop();
|
||||
APP.logCollectorStarted = false;
|
||||
}
|
||||
APP.API.dispose();
|
||||
});
|
||||
|
||||
module.exports = APP;
|
||||
|
||||
@@ -1,7 +1,7 @@
|
||||
<html>
|
||||
<head>
|
||||
<link rel="stylesheet" href="../css/all.css"/>
|
||||
<!--#include virtual="/title.html" -->
|
||||
<link rel="stylesheet" href="css/all.css"/>
|
||||
<!--#include virtual="title.html" -->
|
||||
</head>
|
||||
<body>
|
||||
<div class="redirectPageMessage">Sorry! You are not allowed to be here :(</div>
|
||||
@@ -1,7 +1,7 @@
|
||||
<html>
|
||||
<head>
|
||||
<link rel="stylesheet" href="../css/all.css"/>
|
||||
<!--#include virtual="/title.html" -->
|
||||
<link rel="stylesheet" href="css/all.css"/>
|
||||
<!--#include virtual="title.html" -->
|
||||
<script><!--#include virtual="/interface_config.js" --></script>
|
||||
<script src="close.js"></script>
|
||||
</head>
|
||||
@@ -12,7 +12,7 @@
|
||||
</div>
|
||||
<div class="hint-msg">
|
||||
<p>
|
||||
<span id="hintQuestion">Did you know?</span>
|
||||
<span>Did you know?</span>
|
||||
<span class="hint-msg__holder" id="hintMessage"></span>
|
||||
</p>
|
||||
<div class="happy-software"></div>
|
||||
@@ -32,7 +32,7 @@ function insertTextMsg(id, msg){
|
||||
var el = document.getElementById(id);
|
||||
|
||||
if (el)
|
||||
el.innerHTML = msg;
|
||||
el.innerText = msg;
|
||||
}
|
||||
|
||||
/**
|
||||
@@ -42,17 +42,6 @@ function onLoad() {
|
||||
//Works only for close2.html because close.html doesn't have this element.
|
||||
insertTextMsg('thanksMessage',
|
||||
'Thank you for using ' + interfaceConfig.APP_NAME);
|
||||
|
||||
// If there is a setting show a special message only for the guests
|
||||
if (interfaceConfig.CLOSE_PAGE_GUEST_HINT) {
|
||||
if ( window.sessionStorage.getItem('guest') === 'true' ) {
|
||||
var element = document.getElementById('hintQuestion');
|
||||
element.classList.add('hide');
|
||||
insertTextMsg('hintMessage', interfaceConfig.CLOSE_PAGE_GUEST_HINT);
|
||||
return;
|
||||
}
|
||||
}
|
||||
|
||||
insertTextMsg('hintMessage', getHint());
|
||||
}
|
||||
|
||||
@@ -1,7 +1,7 @@
|
||||
<html>
|
||||
<head>
|
||||
<link rel="stylesheet" href="../css/all.css"/>
|
||||
<!--#include virtual="/title.html" -->
|
||||
<link rel="stylesheet" href="css/all.css"/>
|
||||
<!--#include virtual="title.html" -->
|
||||
<script><!--#include virtual="/interface_config.js" --></script>
|
||||
<script src="close.js"></script>
|
||||
</head>
|
||||
@@ -12,7 +12,7 @@
|
||||
</div>
|
||||
<div class="hint-msg">
|
||||
<p>
|
||||
<span id="hintQuestion">Did you know?</span>
|
||||
<span>Did you know?</span>
|
||||
<span class="hint-msg__holder" id="hintMessage"></span>
|
||||
</p>
|
||||
<div class="happy-software"></div>
|
||||
735
conference.js
44
config.js
@@ -20,17 +20,10 @@ var config = { // eslint-disable-line no-unused-vars
|
||||
//focusUserJid: 'focus@auth.jitsi-meet.example.com', // The real JID of focus participant - can be overridden here
|
||||
//defaultSipNumber: '', // Default SIP number
|
||||
|
||||
// The STUN servers that will be used in the peer to peer connections
|
||||
p2pStunServers: [
|
||||
{ urls: "stun:stun.l.google.com:19302" },
|
||||
{ urls: "stun:stun1.l.google.com:19302" },
|
||||
{ urls: "stun:stun2.l.google.com:19302" }
|
||||
],
|
||||
|
||||
// Desktop sharing method. Can be set to 'ext', 'webrtc' or false to disable.
|
||||
desktopSharingChromeMethod: 'ext',
|
||||
// The ID of the jidesha extension for Chrome.
|
||||
desktopSharingChromeExtId: null,
|
||||
// Whether desktop sharing should be disabled on Chrome.
|
||||
desktopSharingChromeDisabled: true,
|
||||
desktopSharingChromeExtId: 'diibjkoicjeejcmhdnailmkgecihlobk',
|
||||
// The media sources to use when using screen sharing with the Chrome
|
||||
// extension.
|
||||
desktopSharingChromeSources: ['screen', 'window', 'tab'],
|
||||
@@ -47,7 +40,7 @@ var config = { // eslint-disable-line no-unused-vars
|
||||
// up to and including 41. On Firefox 42 and higher, we will run without the
|
||||
// extension.
|
||||
// If set to -1, an extension will be required for all versions of Firefox.
|
||||
desktopSharingFirefoxMaxVersionExtRequired: 51,
|
||||
desktopSharingFirefoxMaxVersionExtRequired: -1,
|
||||
// The URL to the Firefox extension for desktop sharing.
|
||||
desktopSharingFirefoxExtensionURL: null,
|
||||
|
||||
@@ -60,6 +53,8 @@ var config = { // eslint-disable-line no-unused-vars
|
||||
disableStats: false,
|
||||
disableAudioLevels: false,
|
||||
channelLastN: -1, // The default value of the channel attribute last-n.
|
||||
adaptiveLastN: false,
|
||||
//disableAdaptiveSimulcast: false,
|
||||
enableRecording: false,
|
||||
enableWelcomePage: true,
|
||||
//enableClosePage: false, // enabling the close page will ignore the welcome
|
||||
@@ -81,20 +76,15 @@ var config = { // eslint-disable-line no-unused-vars
|
||||
// If true - all users without token will be considered guests and all users
|
||||
// with token will be considered non-guests. Only guests will be allowed to
|
||||
// edit their profile.
|
||||
enableUserRolesBasedOnToken: false,
|
||||
// Suspending video might cause problems with audio playback. Disabling until these are fixed.
|
||||
disableSuspendVideo: true,
|
||||
// disables or enables RTX (RFC 4588) (defaults to false).
|
||||
disableRtx: false,
|
||||
// Sets the preferred resolution (height) for local video. Defaults to 360.
|
||||
resolution: 720,
|
||||
// Enables peer to peer mode. When enabled system will try to establish
|
||||
// direct connection given that there are exactly 2 participants in
|
||||
// the room. If that succeeds the conference will stop sending data through
|
||||
// the JVB and use the peer to peer connection instead. When 3rd participant
|
||||
// joins the conference will be moved back to the JVB connection.
|
||||
//enableP2P: true
|
||||
// How long we're going to wait, before going back to P2P after
|
||||
// the 3rd participant has left the conference (to filter out page reload)
|
||||
//backToP2PDelay: 5
|
||||
enableUserRolesBasedOnToken: false
|
||||
};
|
||||
|
||||
// Logging configuration
|
||||
var loggingConfig = { // eslint-disable-line no-unused-vars
|
||||
//default log level for the app and lib-jitsi-meet
|
||||
defaultLogLevel: 'trace',
|
||||
// Option to disable LogCollector (which stores the logs on CallStats)
|
||||
//disableLogCollector: true,
|
||||
// Logging level adjustments for verbose modules:
|
||||
'modules/xmpp/strophe.util.js': 'log'
|
||||
};
|
||||
|
||||
@@ -4,14 +4,6 @@ const logger = require("jitsi-meet-logger").getLogger(__filename);
|
||||
import AuthHandler from './modules/UI/authentication/AuthHandler';
|
||||
import jitsiLocalStorage from './modules/util/JitsiLocalStorage';
|
||||
|
||||
import {
|
||||
connectionEstablished,
|
||||
connectionFailed
|
||||
} from './react/features/base/connection';
|
||||
import {
|
||||
isFatalJitsiConnectionError
|
||||
} from './react/features/base/lib-jitsi-meet';
|
||||
|
||||
const ConnectionEvents = JitsiMeetJS.events.connection;
|
||||
const ConnectionErrors = JitsiMeetJS.errors.connection;
|
||||
|
||||
@@ -75,18 +67,6 @@ function connect(id, password, roomName) {
|
||||
connection.addEventListener(
|
||||
ConnectionEvents.CONNECTION_FAILED, handleConnectionFailed
|
||||
);
|
||||
connection.addEventListener(
|
||||
ConnectionEvents.CONNECTION_FAILED, connectionFailedHandler);
|
||||
|
||||
function connectionFailedHandler(error, errMsg) {
|
||||
APP.store.dispatch(connectionFailed(connection, error, errMsg));
|
||||
|
||||
if (isFatalJitsiConnectionError(error)) {
|
||||
connection.removeEventListener(
|
||||
ConnectionEvents.CONNECTION_FAILED,
|
||||
connectionFailedHandler);
|
||||
}
|
||||
}
|
||||
|
||||
function unsubscribe() {
|
||||
connection.removeEventListener(
|
||||
@@ -100,7 +80,6 @@ function connect(id, password, roomName) {
|
||||
}
|
||||
|
||||
function handleConnectionEstablished() {
|
||||
APP.store.dispatch(connectionEstablished(connection));
|
||||
unsubscribe();
|
||||
resolve(connection);
|
||||
}
|
||||
|
||||
@@ -3,25 +3,21 @@
|
||||
user-select: none;
|
||||
}
|
||||
|
||||
body {
|
||||
margin: 0px;
|
||||
width: 100%;
|
||||
height: 100%;
|
||||
html, body{
|
||||
margin:0px;
|
||||
height:100%;
|
||||
color: $defaultColor;
|
||||
font-size: 12px;
|
||||
font-weight: 400;
|
||||
background: #000000;
|
||||
overflow: hidden;
|
||||
color: $defaultColor;
|
||||
background: $defaultBackground;
|
||||
&.filmstrip-only {
|
||||
background: transparent;
|
||||
}
|
||||
}
|
||||
|
||||
p {
|
||||
margin: 0;
|
||||
}
|
||||
|
||||
body, input, textarea, keygen, select, button {
|
||||
html, body, input, textarea, keygen, select, button {
|
||||
font-family: $baseFontFamily !important;
|
||||
}
|
||||
|
||||
@@ -84,10 +80,11 @@ form {
|
||||
height: 74px;
|
||||
background-size: contain;
|
||||
background-repeat: no-repeat;
|
||||
z-index: $zindex2;
|
||||
z-index: 2;
|
||||
}
|
||||
|
||||
.leftwatermark {
|
||||
display: none;
|
||||
left: $defaultToolbarSize;
|
||||
margin-left: 10px;
|
||||
background-image: url($defaultWatermarkLink);
|
||||
@@ -95,18 +92,20 @@ form {
|
||||
}
|
||||
|
||||
.rightwatermark {
|
||||
display: none;
|
||||
right: 15;
|
||||
background-position: center right;
|
||||
}
|
||||
|
||||
.poweredby {
|
||||
display: none;
|
||||
position: absolute;
|
||||
left: 25;
|
||||
bottom: 7;
|
||||
font-size: 11pt;
|
||||
color: rgba(255,255,255,.50);
|
||||
text-decoration: none;
|
||||
z-index: $poweredByZ;
|
||||
z-index: 100;
|
||||
}
|
||||
|
||||
.connected {
|
||||
@@ -126,7 +125,6 @@ form {
|
||||
z-index: $tooltipsZ;
|
||||
&-inner {
|
||||
background-color: $tooltipBg;
|
||||
max-width: 350px;
|
||||
}
|
||||
|
||||
&-arrow {
|
||||
@@ -144,4 +142,4 @@ form {
|
||||
#inviteLinkRef {
|
||||
-webkit-user-select: text;
|
||||
user-select: text;
|
||||
}
|
||||
}
|
||||
@@ -212,24 +212,24 @@
|
||||
line-height: 30px;
|
||||
}
|
||||
|
||||
:not(.default-scrollbar)::-webkit-scrollbar {
|
||||
::-webkit-scrollbar {
|
||||
background: #06a5df;
|
||||
width: 7px;
|
||||
}
|
||||
|
||||
:not(.default-scrollbar)::-webkit-scrollbar-button {
|
||||
::-webkit-scrollbar-button {
|
||||
display: none;
|
||||
}
|
||||
|
||||
:not(.default-scrollbar)::-webkit-scrollbar-track {
|
||||
::-webkit-scrollbar-track {
|
||||
background: black;
|
||||
}
|
||||
|
||||
:not(.default-scrollbar)::-webkit-scrollbar-track-piece {
|
||||
::-webkit-scrollbar-track-piece {
|
||||
background: black;
|
||||
}
|
||||
|
||||
:not(.default-scrollbar)::-webkit-scrollbar-thumb {
|
||||
::-webkit-scrollbar-thumb {
|
||||
background: #06a5df;
|
||||
border-radius: 4px;
|
||||
}
|
||||
|
||||
@@ -17,7 +17,7 @@
|
||||
flex-direction: column-reverse;
|
||||
flex-wrap: nowrap;
|
||||
position: relative;
|
||||
z-index: $zindex1; // Set z-index to make element visible
|
||||
z-index: 1; // Set z-index to make element visible
|
||||
width: $hideFilmstripButtonWidth;
|
||||
|
||||
button {
|
||||
@@ -50,17 +50,14 @@
|
||||
position:relative;
|
||||
height:196px;
|
||||
padding: 0;
|
||||
/*The filmstrip should not be covered by the left toolbar*/
|
||||
padding-left: $defaultToolbarSize + 5;
|
||||
padding-left: 17px;
|
||||
bottom: 0;
|
||||
width:auto;
|
||||
border: $thumbnailsBorder solid transparent;
|
||||
z-index: $filmstripVideosZ;
|
||||
z-index: 5;
|
||||
transition: bottom 2s;
|
||||
overflow: visible !important;
|
||||
/*!!!Removes the gap between the local video container and the remote
|
||||
videos.*/
|
||||
font-size: 0pt;
|
||||
font-size: 0pt; /*!!!Removes the gap between the local video container and the remote videos.*/
|
||||
|
||||
&.hidden {
|
||||
bottom: -196px;
|
||||
@@ -71,7 +68,7 @@
|
||||
position: relative;
|
||||
background-size: contain;
|
||||
border: $thumbnailVideoBorder solid transparent;
|
||||
border-radius: $borderRadius;
|
||||
border-radius:1px;
|
||||
margin: 0 $thumbnailVideoMargin;
|
||||
|
||||
&.videoContainerFocused, &:hover {
|
||||
@@ -92,7 +89,7 @@
|
||||
0 0 3px $videoThumbnailSelected !important;
|
||||
}
|
||||
|
||||
.remotevideomenu > .icon-menu {
|
||||
.remotevideomenu {
|
||||
display: none;
|
||||
}
|
||||
|
||||
@@ -105,7 +102,7 @@
|
||||
box-shadow: inset 0 0 3px $videoThumbnailHovered,
|
||||
0 0 3px $videoThumbnailHovered;
|
||||
|
||||
.remotevideomenu > .icon-menu {
|
||||
.remotevideomenu {
|
||||
display: inline-block;
|
||||
}
|
||||
}
|
||||
@@ -115,10 +112,10 @@
|
||||
& > video,
|
||||
& > object {
|
||||
cursor: hand;
|
||||
border-radius: $borderRadius;
|
||||
border-radius:1px;
|
||||
object-fit: cover;
|
||||
overflow: hidden;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -25,9 +25,6 @@
|
||||
-moz-osx-font-smoothing: grayscale;
|
||||
}
|
||||
|
||||
.icon-mic-camera-combined:before {
|
||||
content: "\e903";
|
||||
}
|
||||
.icon-feedback:before {
|
||||
content: "\e91d";
|
||||
}
|
||||
@@ -37,15 +34,15 @@
|
||||
.icon-avatar:before {
|
||||
content: "\e901";
|
||||
}
|
||||
.icon-autorenew:before {
|
||||
content: "\e903";
|
||||
}
|
||||
.icon-hangup:before {
|
||||
content: "\e905";
|
||||
}
|
||||
.icon-chat:before {
|
||||
content: "\e906";
|
||||
}
|
||||
.icon-download:before {
|
||||
content: "\e902";
|
||||
}
|
||||
.icon-edit:before {
|
||||
content: "\e907";
|
||||
}
|
||||
@@ -58,6 +55,9 @@
|
||||
.icon-kick:before {
|
||||
content: "\e904";
|
||||
}
|
||||
.icon-menu:before {
|
||||
content: "\e91f";
|
||||
}
|
||||
.icon-menu-up:before {
|
||||
content: "\e91f";
|
||||
}
|
||||
@@ -70,6 +70,9 @@
|
||||
.icon-exit-full-screen:before {
|
||||
content: "\e90c";
|
||||
}
|
||||
.icon-star:before {
|
||||
content: "\e916";
|
||||
}
|
||||
.icon-star-full:before {
|
||||
content: "\e90a";
|
||||
}
|
||||
@@ -106,12 +109,6 @@
|
||||
.icon-settings:before {
|
||||
content: "\e915";
|
||||
}
|
||||
.icon-star:before {
|
||||
content: "\e916";
|
||||
}
|
||||
.icon-switch-camera:before {
|
||||
content: "\e921";
|
||||
}
|
||||
.icon-share-desktop:before {
|
||||
content: "\e917";
|
||||
}
|
||||
@@ -136,6 +133,7 @@
|
||||
.icon-recEnable:before {
|
||||
content: "\e614";
|
||||
}
|
||||
// FIXME not used anymore - consider removing in the next font update
|
||||
.icon-presentation:before {
|
||||
content: "\e603";
|
||||
}
|
||||
}
|
||||
|
||||
@@ -1,6 +1,6 @@
|
||||
.inlay {
|
||||
margin-top: 14%;
|
||||
@include border-radius(4px);
|
||||
@include border-radius(3px);
|
||||
padding: 40px 38px 44px;
|
||||
color: #fff;
|
||||
background: $inlayColorBg;
|
||||
@@ -27,86 +27,7 @@
|
||||
font-size: 50px;
|
||||
}
|
||||
|
||||
&-filmstrip-only {
|
||||
background-color: $inlayFilmstripOnlyBg;
|
||||
color: $inlayFilmstripOnlyColor;
|
||||
margin-left: 20px;
|
||||
margin-right: 20px;
|
||||
margin-top: 20px;
|
||||
bottom: 30px;
|
||||
position: absolute;
|
||||
display: flex;
|
||||
max-height: 120px;
|
||||
height: 80%;
|
||||
right: 0px;
|
||||
border-radius: 4px;
|
||||
overflow: hidden;
|
||||
&__content {
|
||||
padding: 20px;
|
||||
display: flex;
|
||||
justify-content: center;
|
||||
position: relative;
|
||||
> .button-control {
|
||||
align-self: center;
|
||||
}
|
||||
> #reloadProgressBar {
|
||||
position: absolute;
|
||||
left: 0px;
|
||||
bottom: 0px;
|
||||
margin-bottom: 0px;
|
||||
width: 100%;
|
||||
border-radius: 0px;
|
||||
> .aui-progress-indicator-value {
|
||||
border-radius: 0px;
|
||||
}
|
||||
}
|
||||
}
|
||||
&__title {
|
||||
font-size: 18px;
|
||||
font-weight: 600;
|
||||
}
|
||||
|
||||
&__container {
|
||||
align-self: center;
|
||||
}
|
||||
|
||||
&__text {
|
||||
margin-top: 10px;
|
||||
font-size: 14px;
|
||||
font-weight: 600;
|
||||
}
|
||||
|
||||
&__icon {
|
||||
font-size: 50px;
|
||||
align-self: center;
|
||||
color: $inlayIconColor;
|
||||
opacity: 0.6;
|
||||
}
|
||||
&__icon-container {
|
||||
text-align: center;
|
||||
display: flex;
|
||||
justify-content: center;
|
||||
position: absolute;
|
||||
width: 100%;
|
||||
height: 100%;
|
||||
top: 0px;
|
||||
}
|
||||
|
||||
&__avatar-container {
|
||||
position: relative;
|
||||
> img {
|
||||
height: 100%;
|
||||
}
|
||||
}
|
||||
|
||||
&__icon-background {
|
||||
background: $inlayIconBg;
|
||||
opacity: 0.6;
|
||||
position: absolute;
|
||||
width: 100%;
|
||||
height: 100%;
|
||||
top: 0px;
|
||||
}
|
||||
&__button {
|
||||
float: none !important;
|
||||
}
|
||||
|
||||
}
|
||||
}
|
||||
@@ -2,7 +2,7 @@
|
||||
position: absolute;
|
||||
top: 0;
|
||||
left: 0;
|
||||
z-index: $jitsipopoverZ;
|
||||
z-index: 1010;
|
||||
display: none;
|
||||
max-width: 300px;
|
||||
min-width: 100px;
|
||||
@@ -10,7 +10,7 @@
|
||||
color: $popoverFontColor;
|
||||
background-color: $popoverBg;
|
||||
background-clip: padding-box;
|
||||
border-radius: $borderRadius;
|
||||
border-radius: 3px;
|
||||
/*-webkit-box-shadow: 0 5px 10px rgba(0, 0, 0, 0.2);*/
|
||||
/*box-shadow: 0 5px 10px rgba(0, 0, 0, 0.4);*/
|
||||
white-space: normal;
|
||||
|
||||
@@ -1,18 +1,18 @@
|
||||
@charset "UTF-8";
|
||||
/*!
|
||||
* jQuery contextMenu - Plugin for simple contextMenu handling
|
||||
*
|
||||
* Version: v2.1.1
|
||||
*
|
||||
* Authors: Björn Brala (SWIS.nl), Rodney Rehm, Addy Osmani (patches for FF)
|
||||
* Web: http://swisnl.github.io/jQuery-contextMenu/
|
||||
*
|
||||
* Copyright (c) 2011-2016 SWIS BV and contributors
|
||||
*
|
||||
* Licensed under
|
||||
* MIT License http://www.opensource.org/licenses/mit-license
|
||||
*
|
||||
* Date: 2016-02-28T09:53:18.890Z
|
||||
/*!
|
||||
* jQuery contextMenu - Plugin for simple contextMenu handling
|
||||
*
|
||||
* Version: v2.1.1
|
||||
*
|
||||
* Authors: Björn Brala (SWIS.nl), Rodney Rehm, Addy Osmani (patches for FF)
|
||||
* Web: http://swisnl.github.io/jQuery-contextMenu/
|
||||
*
|
||||
* Copyright (c) 2011-2016 SWIS BV and contributors
|
||||
*
|
||||
* Licensed under
|
||||
* MIT License http://www.opensource.org/licenses/mit-license
|
||||
*
|
||||
* Date: 2016-02-28T09:53:18.890Z
|
||||
*/
|
||||
@font-face {
|
||||
font-family: "context-menu-icons";
|
||||
@@ -88,7 +88,7 @@
|
||||
list-style-type: none;
|
||||
background: #fff;
|
||||
border: 1px solid #bebebe;
|
||||
border-radius: $borderRadius;
|
||||
border-radius: 3px;
|
||||
-webkit-box-shadow: 0 2px 5px rgba(0, 0, 0, .5);
|
||||
box-shadow: 0 2px 5px rgba(0, 0, 0, .5);
|
||||
}
|
||||
@@ -143,7 +143,7 @@
|
||||
position: absolute;
|
||||
top: 50%;
|
||||
right: 8px;
|
||||
z-index: $zindex1;
|
||||
z-index: 1;
|
||||
width: 0;
|
||||
height: 0;
|
||||
content: '';
|
||||
@@ -156,8 +156,8 @@
|
||||
transform: translateY(-50%);
|
||||
}
|
||||
|
||||
/**
|
||||
* Inputs
|
||||
/**
|
||||
* Inputs
|
||||
*/
|
||||
.context-menu-item.context-menu-input {
|
||||
padding: 5px 10px;
|
||||
|
||||
@@ -6,7 +6,7 @@
|
||||
overflow: hidden;
|
||||
padding: 20px;
|
||||
margin-left: 10px;
|
||||
z-index: $zindex10;
|
||||
z-index: 10;
|
||||
border-radius: $borderRadius;
|
||||
background-attachment: scroll;
|
||||
background-size: auto auto;
|
||||
|
||||
@@ -1,10 +1,34 @@
|
||||
/*Initialize*/
|
||||
div.loginmenu {
|
||||
ul.loginmenu {
|
||||
font-family: $baseFontFamily;
|
||||
line-height: normal;
|
||||
display:none;
|
||||
position: absolute;
|
||||
margin: 0;
|
||||
padding: 5px;
|
||||
top: 40px;
|
||||
left: 20px;
|
||||
padding-bottom: 7px;
|
||||
top: 45px;
|
||||
left: -5px;
|
||||
background-color: rgba(0,0,0,0.9);
|
||||
border: 1px solid rgba(256, 256, 256, 0.2);
|
||||
border-radius:8px;
|
||||
}
|
||||
|
||||
ul.loginmenu li {
|
||||
list-style-type: none;
|
||||
padding: 7px;
|
||||
color: #fff;
|
||||
font-size: 11pt;
|
||||
cursor: default;
|
||||
white-space: pre;
|
||||
}
|
||||
|
||||
ul.loginmenu:after {
|
||||
content: url('../images/dropdownPointer.png');
|
||||
display: block;
|
||||
position: absolute;
|
||||
top: -7px;
|
||||
left: 18px;
|
||||
}
|
||||
|
||||
a.disabled {
|
||||
@@ -12,7 +36,23 @@ a.disabled {
|
||||
pointer-events: none;
|
||||
}
|
||||
|
||||
.loginmenuPadding {
|
||||
width: 50px;
|
||||
height: 30px;
|
||||
position: absolute;
|
||||
top: -30px;
|
||||
left: 0px;
|
||||
}
|
||||
|
||||
.loginmenu.extendedToolbarPopup {
|
||||
top: 20px;
|
||||
left: 40px;
|
||||
left: 55px;
|
||||
top: 0px;
|
||||
}
|
||||
|
||||
ul.loginmenu.extendedToolbarPopup:after {
|
||||
content: url('../images/leftDropdownPointer.png');
|
||||
display: block;
|
||||
position: absolute;
|
||||
top: 18px;
|
||||
left: -7px;
|
||||
}
|
||||
206
css/_mixins.scss
@@ -2,52 +2,52 @@
|
||||
* Animation mixin.
|
||||
*/
|
||||
@mixin animation($animate...) {
|
||||
$max: length($animate);
|
||||
$animations: '';
|
||||
$max: length($animate);
|
||||
$animations: '';
|
||||
|
||||
@for $i from 1 through $max {
|
||||
$animations: #{$animations + nth($animate, $i)};
|
||||
@for $i from 1 through $max {
|
||||
$animations: #{$animations + nth($animate, $i)};
|
||||
|
||||
@if $i < $max {
|
||||
$animations: #{$animations + ", "};
|
||||
}
|
||||
@if $i < $max {
|
||||
$animations: #{$animations + ", "};
|
||||
}
|
||||
-webkit-animation: $animations;
|
||||
-moz-animation: $animations;
|
||||
-o-animation: $animations;
|
||||
animation: $animations;
|
||||
}
|
||||
-webkit-animation: $animations;
|
||||
-moz-animation: $animations;
|
||||
-o-animation: $animations;
|
||||
animation: $animations;
|
||||
}
|
||||
|
||||
@mixin flex() {
|
||||
display: -webkit-box;
|
||||
display: -moz-box;
|
||||
display: -ms-flexbox;
|
||||
display: -webkit-flex;
|
||||
display: flex;
|
||||
display: -webkit-box;
|
||||
display: -moz-box;
|
||||
display: -ms-flexbox;
|
||||
display: -webkit-flex;
|
||||
display: flex;
|
||||
}
|
||||
|
||||
/**
|
||||
* Keyframes mixin.
|
||||
*/
|
||||
@mixin keyframes($animationName) {
|
||||
@-webkit-keyframes #{$animationName} {
|
||||
@content;
|
||||
}
|
||||
@-moz-keyframes #{$animationName} {
|
||||
@content;
|
||||
}
|
||||
@-o-keyframes #{$animationName} {
|
||||
@content;
|
||||
}
|
||||
@keyframes #{$animationName} {
|
||||
@content;
|
||||
}
|
||||
@-webkit-keyframes #{$animationName} {
|
||||
@content;
|
||||
}
|
||||
@-moz-keyframes #{$animationName} {
|
||||
@content;
|
||||
}
|
||||
@-o-keyframes #{$animationName} {
|
||||
@content;
|
||||
}
|
||||
@keyframes #{$animationName} {
|
||||
@content;
|
||||
}
|
||||
}
|
||||
|
||||
@mixin circle($diameter) {
|
||||
width: $diameter;
|
||||
height: $diameter;
|
||||
border-radius: 50%;
|
||||
width: $diameter;
|
||||
height: $diameter;
|
||||
border-radius: 50%;
|
||||
}
|
||||
|
||||
/**
|
||||
@@ -60,10 +60,10 @@
|
||||
}
|
||||
|
||||
@mixin absoluteAligning() {
|
||||
top: 50%;
|
||||
left: 50%;
|
||||
position: absolute;
|
||||
@include transform(translate(-50%, -50%));
|
||||
top: 50%;
|
||||
left: 50%;
|
||||
position: absolute;
|
||||
@include transform(translate(-50%, -50%));
|
||||
}
|
||||
|
||||
/**
|
||||
@@ -75,121 +75,79 @@
|
||||
}
|
||||
|
||||
@mixin transform($func) {
|
||||
-moz-transform: $func;
|
||||
-ms-transform: $func;
|
||||
-webkit-transform: $func;
|
||||
-o-transform: $func;
|
||||
transform: $func;
|
||||
-moz-transform: $func;
|
||||
-ms-transform: $func;
|
||||
-webkit-transform: $func;
|
||||
-o-transform: $func;
|
||||
transform: $func;
|
||||
}
|
||||
|
||||
@mixin transition($transition...) {
|
||||
-moz-transition: $transition;
|
||||
-o-transition: $transition;
|
||||
-webkit-transition: $transition;
|
||||
transition: $transition;
|
||||
-moz-transition: $transition;
|
||||
-o-transition: $transition;
|
||||
-webkit-transition: $transition;
|
||||
transition: $transition;
|
||||
}
|
||||
|
||||
/**
|
||||
* Mixin styling a placeholder.
|
||||
**/
|
||||
* Mixin styling placeholder
|
||||
**/
|
||||
@mixin placeholder() {
|
||||
$selectors: (
|
||||
"::-webkit-input-placeholder",
|
||||
"::-moz-placeholder",
|
||||
":-moz-placeholder",
|
||||
":-ms-input-placeholder"
|
||||
);
|
||||
$selectors: (
|
||||
"::-webkit-input-placeholder",
|
||||
"::-moz-placeholder",
|
||||
":-moz-placeholder",
|
||||
":-ms-input-placeholder"
|
||||
);
|
||||
|
||||
@each $selector in $selectors {
|
||||
#{$selector} {
|
||||
@content;
|
||||
}
|
||||
@each $selector in $selectors {
|
||||
#{$selector} {
|
||||
@content;
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Mixin styling a slider track for different browsers.
|
||||
**/
|
||||
@mixin slider() {
|
||||
$selectors: (
|
||||
"input[type=range]::-webkit-slider-runnable-track",
|
||||
"input[type=range]::-moz-range-track",
|
||||
"input[type=range]::-ms-track"
|
||||
);
|
||||
|
||||
@each $selector in $selectors {
|
||||
#{$selector} {
|
||||
@content;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Mixin styling a slider thumb for different browsers.
|
||||
**/
|
||||
@mixin slider-thumb() {
|
||||
$selectors: (
|
||||
"input[type=range]::-webkit-slider-thumb",
|
||||
"input[type=range]::-moz-range-thumb",
|
||||
"input[type=range]::-ms-thumb"
|
||||
);
|
||||
|
||||
@each $selector in $selectors {
|
||||
#{$selector} {
|
||||
@content;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@mixin box-shadow($h, $y, $blur, $color, $inset: false) {
|
||||
@if $inset {
|
||||
-webkit-box-shadow: inset $h $y $blur $color;
|
||||
-moz-box-shadow: inset $h $y $blur $color;
|
||||
box-shadow: inset $h $y $blur $color;
|
||||
} @else {
|
||||
-webkit-box-shadow: $h $y $blur $color;
|
||||
-moz-box-shadow: $h $y $blur $color;
|
||||
box-shadow: $h $y $blur $color;
|
||||
}
|
||||
@if $inset {
|
||||
-webkit-box-shadow: inset $h $y $blur $color;
|
||||
-moz-box-shadow: inset $h $y $blur $color;
|
||||
box-shadow: inset $h $y $blur $color;
|
||||
} @else {
|
||||
-webkit-box-shadow: $h $y $blur $color;
|
||||
-moz-box-shadow: $h $y $blur $color;
|
||||
box-shadow: $h $y $blur $color;
|
||||
}
|
||||
}
|
||||
|
||||
@mixin no-box-shadow {
|
||||
-webkit-box-shadow: none;
|
||||
-moz-box-shadow: none;
|
||||
box-shadow: none;
|
||||
-webkit-box-shadow: none;
|
||||
-moz-box-shadow: none;
|
||||
box-shadow: none;
|
||||
}
|
||||
|
||||
@mixin box-sizing($box-model) {
|
||||
-webkit-box-sizing: $box-model; // Safari <= 5
|
||||
-moz-box-sizing: $box-model; // Firefox <= 19
|
||||
box-sizing: $box-model;
|
||||
-webkit-box-sizing: $box-model; // Safari <= 5
|
||||
-moz-box-sizing: $box-model; // Firefox <= 19
|
||||
box-sizing: $box-model;
|
||||
}
|
||||
|
||||
@mixin border-radius($radius) {
|
||||
-webkit-border-radius: $radius;
|
||||
border-radius: $radius;
|
||||
/* stops bg color from leaking outside the border: */
|
||||
background-clip: padding-box;
|
||||
-webkit-border-radius: $radius;
|
||||
border-radius: $radius;
|
||||
/* stops bg color from leaking outside the border: */
|
||||
background-clip: padding-box;
|
||||
}
|
||||
|
||||
@mixin opacity($opacity) {
|
||||
opacity: $opacity;
|
||||
$opacity-ie: $opacity * 100;
|
||||
-ms-filter: progid:DXImageTransform.Microsoft.Alpha(Opacity=$opacity-ie);
|
||||
filter: alpha(opacity=$opacity-ie); //IE8
|
||||
opacity: $opacity;
|
||||
$opacity-ie: $opacity * 100;
|
||||
-ms-filter: progid:DXImageTransform.Microsoft.Alpha(Opacity=$opacity-ie);
|
||||
filter: alpha(opacity=$opacity-ie); //IE8
|
||||
}
|
||||
|
||||
@mixin text-truncate {
|
||||
display: block;
|
||||
overflow: hidden;
|
||||
text-overflow: ellipsis;
|
||||
white-space: nowrap;
|
||||
}
|
||||
|
||||
/**
|
||||
* Creates a semi-transparent background with the given color and alpha
|
||||
* (opacity) value.
|
||||
*/
|
||||
@mixin transparentBg($color, $alpha) {
|
||||
background-color: rgba(red($color), green($color), blue($color), $alpha);
|
||||
display: block;
|
||||
overflow: hidden;
|
||||
text-overflow: ellipsis;
|
||||
white-space: nowrap;
|
||||
}
|
||||
@@ -1,12 +1,11 @@
|
||||
.notice {
|
||||
#notice {
|
||||
position: relative;
|
||||
z-index: $zindex3;
|
||||
z-index: 3;
|
||||
margin-top: 6px;
|
||||
|
||||
&__message {
|
||||
background-color: #000000;
|
||||
color: white;
|
||||
padding: 3px;
|
||||
border-radius: 5px;
|
||||
}
|
||||
}
|
||||
#noticeText {
|
||||
background-color: #000000;
|
||||
color: white;
|
||||
padding: 3px;
|
||||
border-radius: 5px;
|
||||
}
|
||||
@@ -2,7 +2,7 @@
|
||||
position: absolute;
|
||||
top: 0;
|
||||
left: 0;
|
||||
z-index: $popoverZ;
|
||||
z-index: 1015;
|
||||
display: none;
|
||||
max-width: 300px;
|
||||
min-width: 100px;
|
||||
|
||||
@@ -6,6 +6,7 @@
|
||||
padding: 0;
|
||||
margin: 2px 0;
|
||||
bottom: 0;
|
||||
width: 100px;
|
||||
height: auto;
|
||||
|
||||
&:first-child {
|
||||
@@ -23,8 +24,7 @@
|
||||
}
|
||||
|
||||
// Link Appearance
|
||||
&__link,
|
||||
&__contents {
|
||||
&__link {
|
||||
display: block;
|
||||
box-sizing: border-box;
|
||||
text-decoration: none;
|
||||
@@ -41,16 +41,11 @@
|
||||
}
|
||||
}
|
||||
|
||||
&__text,
|
||||
&__slider {
|
||||
&__text {
|
||||
display: inline-block;
|
||||
vertical-align: middle;
|
||||
}
|
||||
|
||||
&__slider {
|
||||
width: 50px;
|
||||
}
|
||||
|
||||
&__icon {
|
||||
vertical-align: middle;
|
||||
position: relative;
|
||||
@@ -71,9 +66,4 @@
|
||||
|
||||
span.remotevideomenu:hover ul.popupmenu, ul.popupmenu:hover {
|
||||
display:block !important;
|
||||
}
|
||||
|
||||
.remote-control-spinner {
|
||||
top: 6px;
|
||||
left: 2px;
|
||||
}
|
||||
}
|
||||
@@ -1,3 +1,10 @@
|
||||
html, body {
|
||||
width: 100%;
|
||||
height:100%;
|
||||
color: $defaultColor;
|
||||
background: $defaultBackground;
|
||||
}
|
||||
|
||||
.redirectPageMessage {
|
||||
width: 30%;
|
||||
margin: 20% auto;
|
||||
|
||||
@@ -10,7 +10,7 @@
|
||||
position: absolute;
|
||||
top: 0;
|
||||
width: 0;
|
||||
z-index: $sideToolbarContainerZ;
|
||||
z-index: 800;
|
||||
|
||||
/**
|
||||
* Labels inside the side panel.
|
||||
|
||||
@@ -33,7 +33,7 @@
|
||||
|
||||
#subject {
|
||||
position: relative;
|
||||
z-index: $zindex3;
|
||||
z-index: 3;
|
||||
width: auto;
|
||||
padding: 5px;
|
||||
margin-left: 40%;
|
||||
@@ -106,7 +106,7 @@
|
||||
height: 50px;
|
||||
cursor: pointer;
|
||||
text-align: center;
|
||||
z-index: $zindex1;
|
||||
z-index: 1;
|
||||
font-size: $toolbarFontSize !important;
|
||||
line-height: 50px !important;
|
||||
vertical-align: middle;
|
||||
|
||||
@@ -14,8 +14,8 @@ $defaultToolbarSize: 50px;
|
||||
|
||||
// Video layout.
|
||||
$thumbnailToolbarHeight: 22px;
|
||||
$thumbnailIndicatorBorder: 2px;
|
||||
$thumbnailIndicatorSize: $thumbnailToolbarHeight;
|
||||
$thumbnailIndicatorBorder: 0;
|
||||
$thumbnailIndicatorSize: 3em;
|
||||
$thumbnailVideoMargin: 2px;
|
||||
$thumbnailsBorder: 2px;
|
||||
$thumbnailVideoBorder: 2px;
|
||||
@@ -43,14 +43,14 @@ $toolbarBadgeColor: #FFFFFF;
|
||||
$toolbarToggleBackground: #12499C;
|
||||
$splitterToolbarButtonMargin: 18px;
|
||||
|
||||
/**
|
||||
/*
|
||||
* Main controls
|
||||
* TODO: looks like we don't use it
|
||||
*/
|
||||
$inputSemiBackground: rgba(132, 132, 132, .8);
|
||||
$inputLightBackground: #EBEBEB;
|
||||
|
||||
/**
|
||||
/*
|
||||
* Video layout
|
||||
*/
|
||||
$videoThumbnailHovered: rgba(22, 94, 204, .4);
|
||||
@@ -95,7 +95,7 @@ $notificationWidth: 215px;
|
||||
/**
|
||||
* Misc.
|
||||
*/
|
||||
$borderRadius: 4px;
|
||||
$borderRadius: 3px;
|
||||
$defaultWatermarkLink: '../images/watermark.png';
|
||||
$sidebarWidth: 220px;
|
||||
$popoverMenuPadding: 13px;
|
||||
@@ -104,26 +104,13 @@ $happySoftwareBackground: transparent;
|
||||
/**
|
||||
* Z-indexes. TODO: Replace this by a function.
|
||||
*/
|
||||
$zindex0: 0;
|
||||
$zindex1: 1;
|
||||
$zindex2: 2;
|
||||
$zindex3: 3;
|
||||
$filmstripVideosZ: 5;
|
||||
$zindex10: 10;
|
||||
$reloadZ: 20;
|
||||
$poweredByZ: 100;
|
||||
$ringingZ: 300;
|
||||
$sideToolbarContainerZ: 300;
|
||||
$toolbarZ: 400;
|
||||
$tooltipsZ: 401;
|
||||
$dropdownMaskZ: 900;
|
||||
$dropdownZ: 901;
|
||||
$tooltipsZ: 901;
|
||||
$toolbarZ: 900;
|
||||
$overlayZ: 902;
|
||||
$jitsipopoverZ: 1010;
|
||||
$centeredVideoLabelZ: 1011;
|
||||
$notificationZ: 1012;
|
||||
$popoverZ: 1015;
|
||||
|
||||
$ringingZ: 800;
|
||||
$dropdownZ: 901;
|
||||
$dropdownMaskZ: 900;
|
||||
|
||||
/**
|
||||
* Font Colors
|
||||
@@ -139,16 +126,4 @@ $defaultDarkFontColor: #000;
|
||||
$inputControlEmColor: #f29424;
|
||||
//buttons
|
||||
$linkFontColor: #489afe;
|
||||
$linkHoverFontColor: #287ade;
|
||||
|
||||
/**
|
||||
* Unsupported browser
|
||||
*/
|
||||
$primaryUnsupportedBrowserButtonBgColor: #17a0db;
|
||||
$unsupportedBrowserButtonBgColor: #ff9a00;
|
||||
$unsupportedBrowserTextColor: #4a4a4a;
|
||||
$unsupportedBrowserTextSmallFontSize: 17px;
|
||||
$unsupportedBrowserTitleColor: #fff;
|
||||
$unsupportedBrowserTitleFontSize: 24px;
|
||||
$unsupportedDesktopBrowserTextColor: rgba(255, 255, 255, 0.7);
|
||||
$unsupportedDesktopBrowserTextFontSize: 21px;
|
||||
$linkHoverFontColor: #287ade;
|
||||
@@ -18,10 +18,9 @@
|
||||
|
||||
&__background {
|
||||
@include topLeft();
|
||||
background-color: black;
|
||||
border-radius: $borderRadius;
|
||||
width: 100%;
|
||||
height: 100%;
|
||||
background-color: black;
|
||||
}
|
||||
|
||||
/**
|
||||
@@ -31,7 +30,7 @@
|
||||
&__toptoolbar {
|
||||
position: absolute;
|
||||
left: 0;
|
||||
z-index: $zindex3;
|
||||
z-index: 3;
|
||||
width: 100%;
|
||||
box-sizing: border-box; // Includes the padding in the 100% width.
|
||||
}
|
||||
@@ -59,7 +58,7 @@
|
||||
float: left;
|
||||
@include circle($thumbnailIndicatorSize);
|
||||
box-sizing: border-box;
|
||||
z-index: $zindex3;
|
||||
z-index: 3;
|
||||
background: $dominantSpeakerBg;
|
||||
color: $thumbnailPictogramColor;
|
||||
border: $thumbnailIndicatorBorder solid $thumbnailPictogramColor;
|
||||
@@ -107,13 +106,12 @@
|
||||
}
|
||||
|
||||
&__hoverOverlay {
|
||||
background: rgba(0,0,0,.6);
|
||||
border-radius: $borderRadius;
|
||||
position: relative;
|
||||
width: 100%;
|
||||
height: 100%;
|
||||
visibility: hidden;
|
||||
z-index: $zindex2;
|
||||
background: rgba(0,0,0,.6);
|
||||
z-index: 2;
|
||||
}
|
||||
}
|
||||
|
||||
@@ -130,8 +128,8 @@
|
||||
|
||||
#localVideoWrapper>video,
|
||||
#localVideoWrapper>object {
|
||||
border-radius: $borderRadius !important;
|
||||
cursor: hand;
|
||||
border-radius:1px !important;
|
||||
object-fit: cover;
|
||||
}
|
||||
|
||||
@@ -161,7 +159,7 @@
|
||||
position: absolute;
|
||||
left: 0;
|
||||
top: 0;
|
||||
z-index: $zindex1;
|
||||
z-index: 1;
|
||||
width: 100%;
|
||||
height: 100%;
|
||||
}
|
||||
@@ -171,7 +169,7 @@
|
||||
}
|
||||
|
||||
#etherpad {
|
||||
z-index: $zindex0;
|
||||
z-index: 0;
|
||||
}
|
||||
|
||||
/**
|
||||
@@ -193,7 +191,7 @@
|
||||
overflow: hidden;
|
||||
white-space: nowrap;
|
||||
line-height: $thumbnailToolbarHeight;
|
||||
z-index: $zindex2;
|
||||
z-index: 2;
|
||||
}
|
||||
|
||||
/**
|
||||
@@ -213,7 +211,6 @@
|
||||
|
||||
.videocontainer .displayname {
|
||||
pointer-events: none;
|
||||
padding: 0 3px 0 3px;
|
||||
}
|
||||
|
||||
.videocontainer .editdisplayname {
|
||||
@@ -233,7 +230,7 @@
|
||||
padding: 3px 5px;
|
||||
font-size: 9pt;
|
||||
cursor: pointer;
|
||||
z-index: $zindex2;
|
||||
z-index: 2;
|
||||
}
|
||||
|
||||
/**
|
||||
@@ -283,7 +280,7 @@
|
||||
top: 0px;
|
||||
right: 0;
|
||||
margin: 7px;
|
||||
z-index: $zindex3;
|
||||
z-index: 3;
|
||||
width: 18px;
|
||||
height: 13px;
|
||||
color: #FFF;
|
||||
@@ -301,7 +298,7 @@
|
||||
margin-top: -17px;
|
||||
width: 6px;
|
||||
height: 35px;
|
||||
z-index: $zindex2;
|
||||
z-index: 2;
|
||||
border: none;
|
||||
|
||||
.audiodot-top,
|
||||
@@ -344,13 +341,13 @@
|
||||
background-clip: padding-box;
|
||||
-webkit-border-radius: 5px;
|
||||
-webkit-background-clip: padding-box;
|
||||
z-index: $reloadZ; /*The reload button should appear on top of the header!*/
|
||||
z-index: 20; /*The reload button should appear on top of the header!*/
|
||||
}
|
||||
|
||||
.audiolevel {
|
||||
display: inline-block;
|
||||
position: absolute;
|
||||
z-index: $zindex0;
|
||||
z-index: 0;
|
||||
border-radius:1px;
|
||||
pointer-events: none;
|
||||
}
|
||||
@@ -408,7 +405,7 @@
|
||||
.noMic {
|
||||
position: absolute;
|
||||
border-radius: 8px;
|
||||
z-index: $zindex1;
|
||||
z-index: 1;
|
||||
width: 100%;
|
||||
height: 100%;
|
||||
background-image: url("../images/noMic.png");
|
||||
@@ -420,7 +417,7 @@
|
||||
.noVideo {
|
||||
position: absolute;
|
||||
border-radius: 8px;
|
||||
z-index: $zindex1;
|
||||
z-index: 1;
|
||||
width: 100%;
|
||||
height: 100%;
|
||||
background-image: url("../images/noVideo.png");
|
||||
@@ -453,7 +450,7 @@
|
||||
display: none;
|
||||
position: absolute;
|
||||
width: auto;
|
||||
z-index: $zindex2;
|
||||
z-index: 2;
|
||||
font-weight: 600;
|
||||
font-size: 14px;
|
||||
text-align: center;
|
||||
@@ -474,10 +471,9 @@
|
||||
#localConnectionMessage {
|
||||
display: none;
|
||||
position: absolute;
|
||||
left: 0;
|
||||
width: 100%;
|
||||
top:50%;
|
||||
z-index: $zindex2;
|
||||
z-index: 2;
|
||||
font-weight: 600;
|
||||
font-size: 14px;
|
||||
text-align: center;
|
||||
@@ -506,7 +502,7 @@
|
||||
#videoResolutionLabel,
|
||||
.centeredVideoLabel {
|
||||
display: none;
|
||||
z-index: $centeredVideoLabelZ;
|
||||
z-index: 1011;
|
||||
}
|
||||
|
||||
.centeredVideoLabel {
|
||||
|
||||
@@ -22,7 +22,7 @@
|
||||
font-weight: 500;
|
||||
font-size: 16px;
|
||||
color: #acacac;
|
||||
z-index: $zindex2;
|
||||
z-index: 2;
|
||||
}
|
||||
|
||||
#disable_welcome:checked + label
|
||||
@@ -35,7 +35,7 @@
|
||||
font-weight: 500;
|
||||
font-size: 16px;
|
||||
color: #acacac;
|
||||
z-index: $zindex2;
|
||||
z-index: 2;
|
||||
}
|
||||
|
||||
#enter_room_form {
|
||||
@@ -50,7 +50,7 @@
|
||||
float: left;
|
||||
}
|
||||
|
||||
.domain-name
|
||||
#domain_name
|
||||
{
|
||||
float: left;
|
||||
height: 55px;
|
||||
@@ -61,51 +61,37 @@
|
||||
color: $defaultDarkColor;
|
||||
}
|
||||
|
||||
.enter-room {
|
||||
&__field {
|
||||
font-size: 15px;
|
||||
border: none;
|
||||
-webkit-appearance: none;
|
||||
width: 228px;
|
||||
height: 55px;
|
||||
line-height: 55px;
|
||||
font-weight: 500;
|
||||
box-shadow: none;
|
||||
float: left;
|
||||
background-color: #FFFFFF;
|
||||
position: relative;
|
||||
z-index: $zindex2;
|
||||
}
|
||||
#enter_room_field {
|
||||
font-size: 15px;
|
||||
border: none;
|
||||
-webkit-appearance: none;
|
||||
width: 228px;
|
||||
height: 55px;
|
||||
line-height: 55px;
|
||||
font-weight: 500;
|
||||
box-shadow: none;
|
||||
float: left;
|
||||
background-color: #FFFFFF;
|
||||
position: relative;
|
||||
z-index: 2;
|
||||
}
|
||||
|
||||
&__reload {
|
||||
display: block;
|
||||
width: 30px;
|
||||
color: #acacac;
|
||||
font-size: 1.9em;
|
||||
line-height: 55px;
|
||||
z-index: $zindex3;
|
||||
float: left;
|
||||
cursor: pointer;
|
||||
text-align: center;
|
||||
}
|
||||
|
||||
&__button {
|
||||
width: 73px;
|
||||
height: 45px;
|
||||
background-color: #21B9FC;
|
||||
moz-border-radius: 1px;
|
||||
-webkit-border-radius: 1px;
|
||||
color: #ffffff;
|
||||
font-weight: 600;
|
||||
border: none;
|
||||
margin-top: 5px;
|
||||
font-size: 19px;
|
||||
padding-top: 6px;
|
||||
outline: none;
|
||||
float:left;
|
||||
position: relative;
|
||||
z-index: $zindex2;
|
||||
}
|
||||
#enter_room_button {
|
||||
width: 73px;
|
||||
height: 45px;
|
||||
background-color: #21B9FC;
|
||||
moz-border-radius: 1px;
|
||||
-webkit-border-radius: 1px;
|
||||
color: #ffffff;
|
||||
font-weight: 600;
|
||||
border: none;
|
||||
margin-top: 5px;
|
||||
font-size: 19px;
|
||||
padding-top: 6px;
|
||||
outline: none;
|
||||
float:left;
|
||||
position: relative;
|
||||
z-index: 2;
|
||||
}
|
||||
|
||||
#enter_room_container {
|
||||
@@ -198,3 +184,16 @@
|
||||
line-height: 22px;
|
||||
font-weight: 200;
|
||||
}
|
||||
|
||||
#reload_roomname
|
||||
{
|
||||
width: 30px;
|
||||
color: #acacac;
|
||||
font-size: 1.9em;
|
||||
line-height: 55px;
|
||||
z-index: 3;
|
||||
float: left;
|
||||
cursor: pointer;
|
||||
text-align: center;
|
||||
display: none;
|
||||
}
|
||||
|
||||
@@ -57,18 +57,6 @@
|
||||
}
|
||||
}
|
||||
|
||||
&_overlay {
|
||||
color: $primaryButtonColor;
|
||||
background-color: $overlayButtonBg;
|
||||
border-radius: 2px;
|
||||
border: none;
|
||||
|
||||
&:hover {
|
||||
background-color: $primaryButtonBackground;
|
||||
border: none;
|
||||
}
|
||||
}
|
||||
|
||||
&_primary {
|
||||
background-color: $primaryButtonBackground;
|
||||
border: 1px solid $primaryButtonBackground;
|
||||
@@ -94,8 +82,4 @@
|
||||
color: $linkHoverFontColor;
|
||||
}
|
||||
}
|
||||
|
||||
&_center {
|
||||
float: none !important;
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -1,41 +0,0 @@
|
||||
/**
|
||||
* Disable the default webkit styles for range inputs (sliders).
|
||||
*/
|
||||
input[type=range]{
|
||||
-webkit-appearance: none;
|
||||
background: none;
|
||||
}
|
||||
|
||||
/**
|
||||
* Disable the default focus styles for webkit range inputs (sliders).
|
||||
*/
|
||||
input[type=range]:focus {
|
||||
outline: none;
|
||||
}
|
||||
|
||||
/**
|
||||
* Include the mixin for a range input style.
|
||||
*/
|
||||
@include slider {
|
||||
background: $sliderTrackBackground;
|
||||
border: none;
|
||||
border-radius: 3px;
|
||||
cursor: pointer;
|
||||
height: 6px;
|
||||
width: 100%;
|
||||
}
|
||||
|
||||
/**
|
||||
* Include the mixin for a range input thumb style.
|
||||
*/
|
||||
@include slider-thumb {
|
||||
-webkit-appearance: none;
|
||||
background: white;
|
||||
border: 1px solid $sliderThumbBackground;
|
||||
border-radius: 50%;
|
||||
box-shadow: 0px 0px 1px $sliderThumbBackground;
|
||||
cursor: pointer;
|
||||
height: 14px;
|
||||
margin-top: -4px;
|
||||
width: 14px;
|
||||
}
|
||||
@@ -8,13 +8,4 @@
|
||||
text-decoration: underline;
|
||||
@include transition(color .1s ease-in);
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Helper links are links that are meant to open a documentation page or more
|
||||
* detailed info.
|
||||
*/
|
||||
.helper-link {
|
||||
@extend .link;
|
||||
font-size: 12px;
|
||||
}
|
||||
@@ -37,10 +37,8 @@
|
||||
@import 'overlay/overlay';
|
||||
@import 'inlay';
|
||||
@import 'reload_overlay/reload_overlay';
|
||||
@import 'modals/desktop-picker/desktop-picker';
|
||||
@import 'modals/dialog';
|
||||
@import 'modals/feedback/feedback';
|
||||
@import 'modals/speaker_stats/speaker_stats';
|
||||
@import 'videolayout_default';
|
||||
@import 'notice';
|
||||
@import 'popup_menu';
|
||||
@@ -62,14 +60,12 @@
|
||||
@import 'components/link';
|
||||
@import 'shortcuts/main';
|
||||
@import 'components/button-control';
|
||||
@import 'components/input-control';
|
||||
@import 'components/input-slider';
|
||||
@import 'components/_input-control.scss';
|
||||
@import "modals/invite/invite";
|
||||
@import "connection-info";
|
||||
@import 'aui-components/dropdown';
|
||||
@import '404';
|
||||
@import 'policy';
|
||||
@import 'filmstrip';
|
||||
@import 'unsupported-browser/main';
|
||||
|
||||
/* Modules END */
|
||||
|
||||
@@ -1,59 +0,0 @@
|
||||
.desktop-picker-pane {
|
||||
height: 320px;
|
||||
overflow-x: hidden;
|
||||
overflow-y: auto;
|
||||
width: 100%;
|
||||
|
||||
&.source-type-screen {
|
||||
.desktop-picker-source {
|
||||
margin-left: auto;
|
||||
margin-right: auto;
|
||||
width: 50%;
|
||||
}
|
||||
|
||||
.desktop-source-preview-thumbnail {
|
||||
width: 100%;
|
||||
}
|
||||
|
||||
.desktop-source-preview-label {
|
||||
display: none;
|
||||
}
|
||||
}
|
||||
|
||||
&.source-type-window {
|
||||
.desktop-picker-source {
|
||||
display: inline-block;
|
||||
width: 30%;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
.desktop-picker-source {
|
||||
color: $defaultDarkFontColor;
|
||||
margin-top: 10px;
|
||||
text-align: center;
|
||||
|
||||
&.is-selected {
|
||||
.desktop-source-preview-image-container {
|
||||
background: rgba(0, 0, 0, 0.1);
|
||||
border-radius: $borderRadius;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
.desktop-source-preview-label {
|
||||
margin-top: 3px;
|
||||
overflow: hidden;
|
||||
text-overflow: ellipsis;
|
||||
white-space: nowrap;
|
||||
}
|
||||
|
||||
.desktop-source-preview-thumbnail {
|
||||
box-shadow: 5px 5px 5px grey;
|
||||
height: auto;
|
||||
max-width: 100%;
|
||||
}
|
||||
|
||||
.desktop-source-preview-image-container {
|
||||
padding: 10px;
|
||||
}
|
||||
@@ -1,56 +0,0 @@
|
||||
.speaker-stats {
|
||||
list-style: none;
|
||||
padding: 0;
|
||||
color: $auiDialogColor;
|
||||
width: 100%;
|
||||
font-weight: 500;
|
||||
|
||||
.speaker-stats-item__status-dot {
|
||||
position: relative;
|
||||
display: block;
|
||||
width: 9px;
|
||||
height: 9px;
|
||||
border-radius: 50%;
|
||||
margin: 0 auto;
|
||||
|
||||
&.status-active {
|
||||
background: green;
|
||||
}
|
||||
|
||||
&.status-inactive {
|
||||
background: gray;
|
||||
}
|
||||
}
|
||||
|
||||
.status-user-left {
|
||||
color: $placeHolderColor;
|
||||
}
|
||||
|
||||
.speaker-stats-item__status,
|
||||
.speaker-stats-item__name,
|
||||
.speaker-stats-item__time {
|
||||
display: inline-block;
|
||||
margin: 5px 0;
|
||||
vertical-align: middle;
|
||||
}
|
||||
.speaker-stats-item__status {
|
||||
width: 5%;
|
||||
}
|
||||
.speaker-stats-item__name {
|
||||
width: 40%;
|
||||
}
|
||||
.speaker-stats-item__time {
|
||||
width: 55%;
|
||||
}
|
||||
|
||||
.speaker-stats-item:nth-child(even) {
|
||||
background: whitesmoke;
|
||||
}
|
||||
|
||||
.speaker-stats-item__name,
|
||||
.speaker-stats-item__time {
|
||||
overflow: hidden;
|
||||
text-overflow: ellipsis;
|
||||
white-space: nowrap;
|
||||
}
|
||||
}
|
||||
@@ -1,6 +1,5 @@
|
||||
.overlay {
|
||||
&__container,
|
||||
&__container-light {
|
||||
&__container {
|
||||
top: 0;
|
||||
left: 0;
|
||||
width: 100%;
|
||||
@@ -8,16 +7,6 @@
|
||||
position: fixed;
|
||||
z-index: $overlayZ;
|
||||
background: $defaultBackground;
|
||||
&.filmstrip-only {
|
||||
@include transparentBg($filmStripOnlyOverlayBg, 0.8);
|
||||
}
|
||||
}
|
||||
|
||||
&__container-light {
|
||||
@include transparentBg($defaultBackground, 0.7);
|
||||
&.filmstrip-only {
|
||||
@include transparentBg($filmStripOnlyOverlayBg, 0.2);
|
||||
}
|
||||
}
|
||||
|
||||
&__content {
|
||||
@@ -27,11 +16,6 @@
|
||||
width: 56%;
|
||||
left: 50%;
|
||||
@include transform(translateX(-50%));
|
||||
&.filmstrip-only {
|
||||
left: 0px;
|
||||
width: 100%;
|
||||
@include transform(none);
|
||||
}
|
||||
|
||||
&_bottom {
|
||||
position: absolute;
|
||||
@@ -44,4 +28,4 @@
|
||||
bottom: 24px;
|
||||
width: 100%;
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -4,7 +4,7 @@
|
||||
line-height: 20px;
|
||||
}
|
||||
|
||||
.reload_overlay_text {
|
||||
.reload_overlay_msg {
|
||||
display: block;
|
||||
font-size: 12px;
|
||||
line-height: 30px;
|
||||
@@ -13,7 +13,4 @@
|
||||
#reloadProgressBar {
|
||||
width: 180px;
|
||||
margin: 5px auto;
|
||||
> .aui-progress-indicator-value {
|
||||
background: $reloadProgressBarBg;
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -8,8 +8,6 @@ $baseLight: #FFFFFF;
|
||||
*/
|
||||
$controlBackground: $baseLight;
|
||||
$controlColor: #333333;
|
||||
$sliderTrackBackground: #474747;
|
||||
$sliderThumbBackground: #3572b0;
|
||||
|
||||
/**
|
||||
* Buttons
|
||||
@@ -35,14 +33,10 @@ $primaryButtonFontWeight: 400;
|
||||
|
||||
$buttonShadowColor: #192d4f;
|
||||
|
||||
$overlayButtonBg: #0074E0;
|
||||
|
||||
/**
|
||||
* Color variables
|
||||
**/
|
||||
$defaultBackground: #474747;
|
||||
$filmStripOnlyOverlayBg: #000;
|
||||
$reloadProgressBarBg: #0074E0;
|
||||
|
||||
/**
|
||||
* Connection indicator
|
||||
@@ -64,10 +58,6 @@ $dialogTitleFontWeight: 400;
|
||||
**/
|
||||
$inlayColorBg: lighten($defaultBackground, 20%);
|
||||
$inlayBorderColor: lighten($auiDialogContentBg, 10%);
|
||||
$inlayIconBg: #000;
|
||||
$inlayIconColor: #fff;
|
||||
$inlayFilmstripOnlyColor: #474747;
|
||||
$inlayFilmstripOnlyBg: #fff;
|
||||
|
||||
// Main controls
|
||||
$inputBackground: $controlBackground;
|
||||
|
||||
@@ -1,3 +0,0 @@
|
||||
@import 'no-mobile-app';
|
||||
@import 'unsupported-desktop-browser';
|
||||
@import 'unsupported-mobile-browser';
|
||||
@@ -1,21 +0,0 @@
|
||||
.no-mobile-app {
|
||||
margin: 30% auto 0;
|
||||
max-width: 25em;
|
||||
text-align: center;
|
||||
width: auto;
|
||||
|
||||
&__title {
|
||||
border-bottom: 1px solid $auiBorderColor;
|
||||
color: $unsupportedBrowserTitleColor;
|
||||
font-weight: 400;
|
||||
letter-spacing: 0.5px;
|
||||
padding-bottom: em(17, 24);
|
||||
}
|
||||
|
||||
&__description {
|
||||
font-size: $unsupportedBrowserTextSmallFontSize;
|
||||
font-weight: 300;
|
||||
letter-spacing: 1px;
|
||||
margin-top: 1em;
|
||||
}
|
||||
}
|
||||
@@ -1,39 +0,0 @@
|
||||
.unsupported-desktop-browser {
|
||||
@include absoluteAligning();
|
||||
|
||||
display: block;
|
||||
text-align: center;
|
||||
|
||||
&__title {
|
||||
color: $unsupportedBrowserTitleColor;
|
||||
font-weight: 300;
|
||||
font-size: $unsupportedBrowserTitleFontSize;
|
||||
letter-spacing: 1px;
|
||||
}
|
||||
|
||||
&__description {
|
||||
color: $unsupportedDesktopBrowserTextColor;
|
||||
font-size: $unsupportedDesktopBrowserTextFontSize;
|
||||
font-weight: 300;
|
||||
letter-spacing: 1px;
|
||||
margin-top: 16px;
|
||||
|
||||
&_small {
|
||||
@extend .unsupported-desktop-browser__description;
|
||||
font-size: $unsupportedBrowserTextSmallFontSize;
|
||||
}
|
||||
}
|
||||
|
||||
&__link {
|
||||
color: $linkFontColor;
|
||||
@include transition(color .1s ease-out);
|
||||
|
||||
&:hover {
|
||||
color: $linkHoverFontColor;
|
||||
cursor: pointer;
|
||||
text-decoration: none;
|
||||
|
||||
@include transition(color .1s ease-in);
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -1,69 +0,0 @@
|
||||
.unsupported-mobile-browser {
|
||||
background-color: #fff;
|
||||
height: 100vh;
|
||||
padding: 35px 0;
|
||||
width: 100vw;
|
||||
|
||||
&__body {
|
||||
color: $unsupportedBrowserTextColor;
|
||||
margin: auto;
|
||||
max-width: 40em;
|
||||
text-align: center;
|
||||
width: 75%;
|
||||
|
||||
a:active {
|
||||
text-decoration: none;
|
||||
}
|
||||
}
|
||||
|
||||
&__text {
|
||||
font-size: 1.8em;
|
||||
line-height: em(29px, 21px);
|
||||
margin-bottom: 0.65em;
|
||||
|
||||
&_small {
|
||||
font-size: 1.5em;
|
||||
margin-bottom: 1em;
|
||||
margin-top: em(21, 18);
|
||||
|
||||
strong {
|
||||
font-size: em(21, 18);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
&__logo {
|
||||
height: 108px;
|
||||
width: 77px;
|
||||
}
|
||||
|
||||
&__button {
|
||||
border: 0;
|
||||
height: 42px;
|
||||
margin: 0 auto;
|
||||
max-width: 300px;
|
||||
width: 98%;
|
||||
@include border-radius(8px);
|
||||
background-color: $unsupportedBrowserButtonBgColor;
|
||||
font-size: 1.5em;
|
||||
font-weight: 300;
|
||||
letter-spacing: 0.5px;
|
||||
text-shadow: 0px 1px 2px $unsupportedBrowserTextColor;
|
||||
|
||||
// Disable standard button effects.
|
||||
box-shadow: none;
|
||||
outline: none;
|
||||
|
||||
&:active {
|
||||
background-color: $unsupportedBrowserButtonBgColor;
|
||||
}
|
||||
|
||||
&_primary {
|
||||
background-color: $primaryUnsupportedBrowserButtonBgColor;
|
||||
|
||||
&:active {
|
||||
background-color: $primaryUnsupportedBrowserButtonBgColor;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
138
css/unsupported_browser.scss
Normal file
@@ -0,0 +1,138 @@
|
||||
@import 'variables';
|
||||
|
||||
body {
|
||||
width:100%;
|
||||
height:100%;
|
||||
background-color: white;
|
||||
color: #424242;
|
||||
font-family: $baseFontFamily;
|
||||
font-size: 28px;
|
||||
margin:0;
|
||||
padding:0;
|
||||
}
|
||||
#wrap{
|
||||
display: block;
|
||||
position: absolute;
|
||||
width:500px;
|
||||
height: 565px;
|
||||
overflow:hidden;
|
||||
text-align: center;
|
||||
margin: auto;
|
||||
top: 0; left: 0; bottom: 0; right: 0;
|
||||
}
|
||||
.firefox{
|
||||
font-size: 11pt;
|
||||
color: #c8c8c8;
|
||||
width: 468px;
|
||||
text-align: center;
|
||||
margin: 30px auto 0px auto;
|
||||
padding-left: 15px;
|
||||
}
|
||||
#text{
|
||||
display:inline-block;
|
||||
font-size: 28px;
|
||||
/* width: 568px; */
|
||||
vertical-align:middle;
|
||||
padding-top: 25px;
|
||||
}
|
||||
|
||||
a {
|
||||
color: #087dba;
|
||||
text-decoration:none;
|
||||
}
|
||||
|
||||
.browser {
|
||||
width: 138px;
|
||||
height: 163px;
|
||||
margin-top: 5px;
|
||||
background-color: #e8e8e8;
|
||||
border: 1px solid #cfcfcf;
|
||||
border-radius: 10px;
|
||||
}
|
||||
|
||||
.browser_wrapper
|
||||
{
|
||||
width: 138px;
|
||||
/* height: 188px; */
|
||||
vertical-align: middle;
|
||||
color: #929391;
|
||||
font-size: 20px;
|
||||
float: left;
|
||||
margin-left: 15px;
|
||||
margin-top: 5px;
|
||||
}
|
||||
|
||||
.browser_text
|
||||
{
|
||||
height: 2em;
|
||||
}
|
||||
.supported_browsers
|
||||
{
|
||||
margin: 0px auto 0px auto;
|
||||
/* width: 660px; */
|
||||
}
|
||||
|
||||
.clear
|
||||
{
|
||||
clear: both;
|
||||
}
|
||||
|
||||
.button
|
||||
{
|
||||
background-color: #62c82a;
|
||||
border: 1px solid #3c8117;
|
||||
border-radius: 10px;
|
||||
color: #FFFFFF;
|
||||
font-size: 12px;
|
||||
text-align: center;
|
||||
width: 115px;
|
||||
height: 26px;
|
||||
padding-top: 13px;
|
||||
margin: 15px auto 0px auto;
|
||||
}
|
||||
|
||||
.logo
|
||||
{
|
||||
margin: 20px auto 0px auto;
|
||||
}
|
||||
|
||||
#chrome_logo
|
||||
{
|
||||
width: 78px;
|
||||
height: 78px;
|
||||
background-image: url('../images/chrome.png');
|
||||
}
|
||||
#chromium_logo
|
||||
{
|
||||
width: 77px;
|
||||
height: 78px;
|
||||
background-image: url('../images/chromium.png');
|
||||
}
|
||||
#firefox_logo
|
||||
{
|
||||
width: 86px;
|
||||
height: 80px;
|
||||
background-image: url('../images/firefox.png');
|
||||
}
|
||||
|
||||
#opera_logo
|
||||
{
|
||||
width: 73px;
|
||||
height: 78px;
|
||||
background-image: url('../images/opera.png');
|
||||
}
|
||||
|
||||
#safari_logo
|
||||
{
|
||||
width: 78px;
|
||||
height: 79px;
|
||||
background-image: url('../images/safari.png');
|
||||
}
|
||||
|
||||
#ie_logo
|
||||
{
|
||||
width: 80px;
|
||||
height: 78px;
|
||||
background-image: url('../images/ie.png');
|
||||
}
|
||||
|
||||
5
debian/control
vendored
@@ -21,7 +21,8 @@ Description: WebRTC JavaScript video conferences
|
||||
|
||||
Package: jitsi-meet-web-config
|
||||
Architecture: all
|
||||
Depends: openssl, openjdk-8-jre-headless | nginx | apache2
|
||||
Depends: openssl, openjdk-8-jre-headless | nginx | apache2,
|
||||
jitsi-meet-web
|
||||
Description: Configuration for web serving of Jitsi Meet
|
||||
Jitsi Meet is a WebRTC JavaScript application that uses Jitsi
|
||||
Videobridge to provide high quality, scalable video conferences.
|
||||
@@ -36,7 +37,7 @@ Description: Configuration for web serving of Jitsi Meet
|
||||
|
||||
Package: jitsi-meet-prosody
|
||||
Architecture: all
|
||||
Depends: openssl, prosody | prosody-trunk
|
||||
Depends: openssl, prosody | prosody-trunk, jitsi-meet-web
|
||||
Description: Prosody configuration for Jitsi Meet
|
||||
Jitsi Meet is a WebRTC JavaScript application that uses Jitsi
|
||||
Videobridge to provide high quality, scalable video conferences.
|
||||
|
||||
2
debian/jitsi-meet-tokens.install
vendored
@@ -1 +1 @@
|
||||
resources/prosody-plugins/ /usr/share/jitsi-meet/
|
||||
prosody-plugins/ /usr/share/jitsi-meet/
|
||||
|
||||
4
debian/jitsi-meet-web-config.docs
vendored
@@ -1,4 +0,0 @@
|
||||
doc/debian/jitsi-meet/jitsi-meet.example
|
||||
doc/debian/jitsi-meet/jitsi-meet.example-apache
|
||||
doc/debian/jitsi-meet/README
|
||||
config.js
|
||||
16
debian/jitsi-meet-web-config.postinst
vendored
@@ -65,7 +65,7 @@ case "$1" in
|
||||
# SSL for nginx
|
||||
db_get jitsi-meet/cert-choice
|
||||
CERT_CHOICE="$RET"
|
||||
UPLOADED_CERT_CHOICE="I want to use my own certificate"
|
||||
UPLOADED_CERT_CHOICE="A certificate is available and the files are uploaded on the server"
|
||||
|
||||
if [ "$CERT_CHOICE" = "$UPLOADED_CERT_CHOICE" ] ; then
|
||||
db_set jitsi-meet/cert-path-key "/etc/ssl/$JVB_HOSTNAME.key"
|
||||
@@ -94,7 +94,7 @@ case "$1" in
|
||||
# jitsi meet
|
||||
JITSI_MEET_CONFIG="/etc/jitsi/meet/$JVB_HOSTNAME-config.js"
|
||||
if [ ! -f $JITSI_MEET_CONFIG ] ; then
|
||||
cp /usr/share/doc/jitsi-meet-web-config/config.js $JITSI_MEET_CONFIG
|
||||
cp /usr/share/doc/jitsi-meet-web/config.js $JITSI_MEET_CONFIG
|
||||
sed -i "s/jitsi-meet.example.com/$JVB_HOSTNAME/g" $JITSI_MEET_CONFIG
|
||||
fi
|
||||
|
||||
@@ -127,7 +127,6 @@ case "$1" in
|
||||
echo "org.jitsi.videobridge.rest.jetty.ResourceHandler.resourceBase=/usr/share/jitsi-meet" >> $JVB_CONFIG
|
||||
echo "org.jitsi.videobridge.rest.jetty.ResourceHandler.alias./config.js=/etc/jitsi/meet/$JVB_HOSTNAME-config.js" >> $JVB_CONFIG
|
||||
echo "org.jitsi.videobridge.rest.jetty.ResourceHandler.alias./interface_config.js=/usr/share/jitsi-meet/interface_config.js" >> $JVB_CONFIG
|
||||
echo "org.jitsi.videobridge.rest.jetty.ResourceHandler.alias./logging_config.js=/usr/share/jitsi-meet/logging_config.js" >> $JVB_CONFIG
|
||||
echo "org.jitsi.videobridge.rest.jetty.RewriteHandler.regex=^/([a-zA-Z0-9]+)$" >> $JVB_CONFIG
|
||||
echo "org.jitsi.videobridge.rest.jetty.RewriteHandler.replacement=/" >> $JVB_CONFIG
|
||||
echo "org.jitsi.videobridge.rest.jetty.SSIResourceHandler.paths=/" >> $JVB_CONFIG
|
||||
@@ -172,7 +171,7 @@ case "$1" in
|
||||
|
||||
# nginx conf
|
||||
if [ ! -f /etc/nginx/sites-available/$JVB_HOSTNAME.conf ] ; then
|
||||
cp /usr/share/doc/jitsi-meet-web-config/jitsi-meet.example /etc/nginx/sites-available/$JVB_HOSTNAME.conf
|
||||
cp /usr/share/doc/jitsi-meet-web/jitsi-meet.example /etc/nginx/sites-available/$JVB_HOSTNAME.conf
|
||||
if [ ! -f /etc/nginx/sites-enabled/$JVB_HOSTNAME.conf ] ; then
|
||||
ln -s /etc/nginx/sites-available/$JVB_HOSTNAME.conf /etc/nginx/sites-enabled/$JVB_HOSTNAME.conf
|
||||
fi
|
||||
@@ -203,7 +202,7 @@ case "$1" in
|
||||
if [ ! -f /etc/apache2/sites-available/$JVB_HOSTNAME.conf ] ; then
|
||||
# when creating new config, make sure all needed modules are enabled
|
||||
a2enmod rewrite ssl headers proxy_http include
|
||||
cp /usr/share/doc/jitsi-meet-web-config/jitsi-meet.example-apache /etc/apache2/sites-available/$JVB_HOSTNAME.conf
|
||||
cp /usr/share/doc/jitsi-meet-web/jitsi-meet.example-apache /etc/apache2/sites-available/$JVB_HOSTNAME.conf
|
||||
a2ensite $JVB_HOSTNAME.conf
|
||||
sed -i "s/jitsi-meet.example.com/$JVB_HOSTNAME/g" /etc/apache2/sites-available/$JVB_HOSTNAME.conf
|
||||
fi
|
||||
@@ -223,13 +222,6 @@ case "$1" in
|
||||
invoke-rc.d apache2 reload
|
||||
fi
|
||||
|
||||
echo "----------------"
|
||||
echo ""
|
||||
echo "You can now switch to a Let’s Encrypt certificate. To do so, execute:"
|
||||
echo "/usr/share/jitsi-meet/scripts/install-letsencrypt-cert.sh"
|
||||
echo ""
|
||||
echo "----------------"
|
||||
|
||||
# and we're done with debconf
|
||||
db_stop
|
||||
;;
|
||||
|
||||
3
debian/jitsi-meet-web-config.templates
vendored
@@ -1,10 +1,9 @@
|
||||
Template: jitsi-meet/cert-choice
|
||||
Type: select
|
||||
__Choices: Generate a new self-signed certificate (You will later get a chance to obtain a Let's encrypt certificate), I want to use my own certificate
|
||||
__Choices: Self-signed certificate will be generated, A certificate is available and the files are uploaded on the server
|
||||
_Description: SSL certificate for the Jitsi Meet instance
|
||||
Jitsi Meet is best to be set up with an SSL certificate.
|
||||
Having no certificate, a self-signed one will be generated.
|
||||
By choosing self-signed you will later have a chance to install Let’s Encrypt certificates.
|
||||
Having a certificate signed by a recognised CA, it can be uploaded on the server
|
||||
and point its location. The default filenames will be /etc/ssl/--domain.name--.key
|
||||
for the key and /etc/ssl/--domain.name--.crt for the certificate.
|
||||
|
||||
4
debian/jitsi-meet-web.docs
vendored
@@ -1 +1,5 @@
|
||||
README.md
|
||||
doc/debian/jitsi-meet/jitsi-meet.example
|
||||
doc/debian/jitsi-meet/jitsi-meet.example-apache
|
||||
doc/debian/jitsi-meet/README
|
||||
config.js
|
||||
|
||||
6
debian/jitsi-meet-web.install
vendored
@@ -1,14 +1,12 @@
|
||||
interface_config.js /usr/share/jitsi-meet/
|
||||
logging_config.js /usr/share/jitsi-meet/
|
||||
*.js /usr/share/jitsi-meet/
|
||||
*.json /usr/share/jitsi-meet/
|
||||
*.html /usr/share/jitsi-meet/
|
||||
*.ico /usr/share/jitsi-meet/
|
||||
libs /usr/share/jitsi-meet/
|
||||
static /usr/share/jitsi-meet/
|
||||
css/all.css /usr/share/jitsi-meet/css/
|
||||
css/unsupported_browser.css /usr/share/jitsi-meet/css/
|
||||
sounds /usr/share/jitsi-meet/
|
||||
fonts /usr/share/jitsi-meet/
|
||||
images /usr/share/jitsi-meet/
|
||||
lang /usr/share/jitsi-meet/
|
||||
connection_optimization /usr/share/jitsi-meet/
|
||||
resources/*.sh /usr/share/jitsi-meet/scripts/
|
||||
|
||||
4
debian/po/templates.pot
vendored
@@ -20,13 +20,13 @@ msgstr ""
|
||||
#. Type: select
|
||||
#. Choices
|
||||
#: ../jitsi-meet-web-config.templates:1001
|
||||
msgid "Generate a new self-signed certificate (You will later get a chance to obtain a Let's encrypt certificate)"
|
||||
msgid "Self-signed certificate will be generated"
|
||||
msgstr ""
|
||||
|
||||
#. Type: select
|
||||
#. Choices
|
||||
#: ../jitsi-meet-web-config.templates:1001
|
||||
msgid "I want to use my own certificate"
|
||||
msgid "A certificate is available and the files are uploaded on the server"
|
||||
msgstr ""
|
||||
|
||||
#. Type: select
|
||||
|
||||
274
doc/api.md
@@ -1,213 +1,181 @@
|
||||
# Jitsi Meet API
|
||||
Jitsi Meet API
|
||||
============
|
||||
|
||||
You can use the Jitsi Meet API to embed Jitsi Meet in to your application.
|
||||
You can use Jitsi Meet API to embed Jitsi Meet in to your application.
|
||||
|
||||
## Installation
|
||||
|
||||
To embed Jitsi Meet in your application you need to add the Jitsi Meet API library:
|
||||
Installation
|
||||
==========
|
||||
|
||||
To embed Jitsi Meet in your application you need to add Jitsi Meet API library
|
||||
```javascript
|
||||
<script src="https://meet.jit.si/external_api.js"></script>
|
||||
```
|
||||
|
||||
## API
|
||||
|
||||
### `api = new JitsiMeetExternalAPI(domain, room, [width], [height], [htmlElement], [configOverwite], [interfaceConfigOverwrite], [noSsl], [jwt])`
|
||||
|
||||
The next step for embedding Jitsi Meet is to create the Jitsi Meet API object.
|
||||
Its constructor gets a number of options:
|
||||
|
||||
* **domain**: domain used to build the conference URL, "meet.jit.si" for
|
||||
example.
|
||||
* **room**: name of the room to join.
|
||||
* **width**: (optional) width for the iframe which will be created.
|
||||
* **height**: (optional) height for the iframe which will be created.
|
||||
* **htmlElement**: (optional) HTL DOM Element where the iframe will be added as
|
||||
a child.
|
||||
* **configOverwite**: (optional) JS object with overrides for options defined in
|
||||
[config.js].
|
||||
* **interfaceConfigOverwrite**: (optional) JS object with overrides for options
|
||||
defined in [interface_config.js].
|
||||
* **noSsl**: (optional, defaults to true) Boolean indicating if the server
|
||||
should be contacted using HTTP or HTTPS.
|
||||
* **jwt**: (optional) [JWT](https://jwt.io/) token.
|
||||
|
||||
Example:
|
||||
|
||||
The next step for embedding Jitsi Meet is to create the Jitsi Meet API object
|
||||
```javascript
|
||||
var domain = "meet.jit.si";
|
||||
var room = "JitsiMeetAPIExample";
|
||||
var width = 700;
|
||||
var height = 700;
|
||||
var htmlElement = document.querySelector('#meet');
|
||||
var api = new JitsiMeetExternalAPI(domain, room, width, height, htmlElement);
|
||||
<script>
|
||||
var domain = "meet.jit.si";
|
||||
var room = "JitsiMeetAPIExample";
|
||||
var width = 700;
|
||||
var height = 700;
|
||||
var api = new JitsiMeetExternalAPI(domain, room, width, height);
|
||||
</script>
|
||||
```
|
||||
You can paste that lines in your html code where you want to be placed the Jitsi Meet conference
|
||||
or you can specify the parent HTML element for the Jitsi Meet conference in the JitsiMeetExternalAPI
|
||||
constructor.
|
||||
```javascript
|
||||
var api = new JitsiMeetExternalAPI(domain, room, width, height, htmlElement);
|
||||
```
|
||||
If you don't specify room the user will enter in new conference with random room name.
|
||||
|
||||
You can overwrite options set in config.js and interface_config.js. For example, to enable the film-strip-only interface mode and disable simulcast, you can use:
|
||||
```javascript
|
||||
var configOverwrite = {enableSimulcast: false};
|
||||
var interfaceConfigOverwrite = {filmStripOnly: true};
|
||||
var api = new JitsiMeetExternalAPI(domain, room, width, height, htmlElement, configOverwrite, interfaceConfigOverwrite);
|
||||
```
|
||||
|
||||
You can overwrite options set in [config.js] and [interface_config.js].
|
||||
For example, to enable the film-strip-only interface mode, you can use:
|
||||
Controlling embedded Jitsi Meet Conference
|
||||
=========
|
||||
|
||||
```javascript
|
||||
var interfaceConfigOverwrite = {filmStripOnly: true};
|
||||
var api = new JitsiMeetExternalAPI(domain, room, width, height, undefined, undefined, interfaceConfigOverwrite);
|
||||
You can control the embedded Jitsi Meet conference using the JitsiMeetExternalAPI object.
|
||||
|
||||
You can send command to Jitsi Meet conference using ```executeCommand```.
|
||||
```
|
||||
|
||||
You can also pass a jwt token to Jitsi Meet:
|
||||
|
||||
```javascript
|
||||
var jwt = "<jwt_token>";
|
||||
var noSsl = false;
|
||||
var api = new JitsiMeetExternalAPI(domain, room, width, height, htmlElement, configOverwrite, interfaceConfigOverwrite, noSsl, jwt);
|
||||
```
|
||||
|
||||
### Controlling the embedded Jitsi Meet Conference
|
||||
|
||||
You can control the embedded Jitsi Meet conference using the `JitsiMeetExternalAPI` object by using `executeCommand`:
|
||||
|
||||
```javascript
|
||||
api.executeCommand(command, ...arguments)
|
||||
api.executeCommand(command, arguments)
|
||||
```
|
||||
The ```command``` parameter is String object with the name of the command.
|
||||
The ```arguments``` parameter is array with the arguments required by the command.
|
||||
If no arguments are required by the command this parameter can be omitted or you can pass empty array.
|
||||
Currently we support the following commands:
|
||||
|
||||
The `command` parameter is String object with the name of the command. The following commands are currently supported:
|
||||
|
||||
* **displayName** - Sets the display name of the local participant. This command requires one argument - the new display name to be set.
|
||||
```javascript
|
||||
* **displayName** - sets the display name of the local participant. This command requires one argument -
|
||||
the new display name to be set
|
||||
```
|
||||
api.executeCommand('displayName', 'New Nickname');
|
||||
```
|
||||
|
||||
* **toggleAudio** - Mutes / unmutes the audio for the local participant. No arguments are required.
|
||||
```javascript
|
||||
api.executeCommand('toggleAudio')
|
||||
* **toggleAudio** - mutes / unmutes the audio for the local participant. No arguments are required.
|
||||
```
|
||||
api.executeCommand('toggleAudio', [])
|
||||
```
|
||||
* **toggleVideo** - mutes / unmutes the video for the local participant. No arguments are required.
|
||||
```
|
||||
api.executeCommand('toggleVideo', [])
|
||||
```
|
||||
* **toggleFilmStrip** - hides / shows the film strip. No arguments are required.
|
||||
```
|
||||
api.executeCommand('filmStrip', [])
|
||||
```
|
||||
* **toggleChat** - hides / shows the chat. No arguments are required.
|
||||
```
|
||||
api.executeCommand('toggleChat', [])
|
||||
```
|
||||
* **toggleContactList** - hides / shows the contact list. No arguments are required.
|
||||
```
|
||||
api.executeCommand('toggleContactList', [])
|
||||
```
|
||||
|
||||
* **toggleVideo** - Mutes / unmutes the video for the local participant. No arguments are required.
|
||||
```javascript
|
||||
api.executeCommand('toggleVideo')
|
||||
* **toggleShareScreen** - starts / stops the screen sharing. No arguments are required.
|
||||
```
|
||||
|
||||
* **toggleFilmStrip** - Hides / shows the film strip. No arguments are required.
|
||||
```javascript
|
||||
api.executeCommand('toggleFilmStrip')
|
||||
```
|
||||
|
||||
* **toggleChat** - Hides / shows the chat. No arguments are required.
|
||||
```javascript
|
||||
api.executeCommand('toggleChat')
|
||||
```
|
||||
|
||||
* **toggleContactList** - Hides / shows the contact list. No arguments are required.
|
||||
```javascript
|
||||
api.executeCommand('toggleContactList')
|
||||
```
|
||||
|
||||
* **toggleShareScreen** - Starts / stops screen sharing. No arguments are required.
|
||||
```javascript
|
||||
api.executeCommand('toggleShareScreen')
|
||||
api.executeCommand('toggleShareScreen', [])
|
||||
```
|
||||
|
||||
* **hangup** - Hangups the call. No arguments are required.
|
||||
```javascript
|
||||
api.executeCommand('hangup')
|
||||
```
|
||||
api.executeCommand('hangup', [])
|
||||
```
|
||||
|
||||
* **email** - Changes the local email address. This command requires one argument - the new email address to be set.
|
||||
```javascript
|
||||
api.executeCommand('email', 'example@example.com')
|
||||
You can also execute multiple commands using the method ```executeCommands```.
|
||||
```
|
||||
|
||||
* **avatarUrl** - Changes the local avatar URL. This command requires one argument - the new avatar URL to be set.
|
||||
```javascript
|
||||
api.executeCommand('avatarUrl', 'https://avatars0.githubusercontent.com/u/3671647')
|
||||
```
|
||||
|
||||
You can also execute multiple commands using the `executeCommands` method:
|
||||
```javascript
|
||||
api.executeCommands(commands)
|
||||
```
|
||||
The `commands` parameter is an object with the names of the commands as keys and the arguments for the commands asvalues:
|
||||
```javascript
|
||||
The ```commands``` parameter is object with keys the names of the commands and values the arguments for the
|
||||
commands.
|
||||
|
||||
```
|
||||
api.executeCommands({displayName: ['nickname'], toggleAudio: []});
|
||||
```
|
||||
|
||||
You can add event listeners to the embedded Jitsi Meet using the `addEventListener` method.
|
||||
```javascript
|
||||
You can add event listeners to the embedded Jitsi Meet using ```addEventListener``` method.
|
||||
```
|
||||
api.addEventListener(event, listener)
|
||||
```
|
||||
The ```event``` parameter is String object with the name of the event.
|
||||
The ```listener``` paramenter is Function object with one argument that will be notified when the event occurs
|
||||
with data related to the event.
|
||||
|
||||
The `event` parameter is a String object with the name of the event.
|
||||
The `listener` parameter is a Function object with one argument that will be notified when the event occurs with data related to the event.
|
||||
Currently we support the following events:
|
||||
|
||||
The following events are currently supported:
|
||||
|
||||
* **incomingMessage** - Event notifications about incoming
|
||||
messages. The listener will receive an object with the following structure:
|
||||
```javascript
|
||||
* **incomingMessage** - event notifications about incoming
|
||||
messages. The listener will receive object with the following structure:
|
||||
```
|
||||
{
|
||||
"from": from, // JID of the user that sent the message
|
||||
"nick": nick, // the nickname of the user that sent the message
|
||||
"message": txt // the text of the message
|
||||
"from": from,//JID of the user that sent the message
|
||||
"nick": nick,//the nickname of the user that sent the message
|
||||
"message": txt//the text of the message
|
||||
}
|
||||
```
|
||||
|
||||
* **outgoingMessage** - Event notifications about outgoing
|
||||
messages. The listener will receive an object with the following structure:
|
||||
```javascript
|
||||
* **outgoingMessage** - event notifications about outgoing
|
||||
messages. The listener will receive object with the following structure:
|
||||
```
|
||||
{
|
||||
"message": txt // the text of the message
|
||||
"message": txt//the text of the message
|
||||
}
|
||||
```
|
||||
|
||||
* **displayNameChanged** - event notifications about display name
|
||||
changes. The listener will receive an object with the following structure:
|
||||
```javascript
|
||||
change. The listener will receive object with the following structure:
|
||||
```
|
||||
{
|
||||
"jid": jid, // the JID of the participant that changed his display name
|
||||
"displayname": displayName // the new display name
|
||||
jid: jid,//the JID of the participant that changed his display name
|
||||
displayname: displayName //the new display name
|
||||
}
|
||||
```
|
||||
|
||||
* **participantJoined** - event notifications about new participants who join the room. The listener will receive an object with the following structure:
|
||||
```javascript
|
||||
* **participantJoined** - event notifications about new participant.
|
||||
The listener will receive object with the following structure:
|
||||
```
|
||||
{
|
||||
"jid": jid // the JID of the participant
|
||||
jid: jid //the jid of the participant
|
||||
}
|
||||
```
|
||||
|
||||
* **participantLeft** - event notifications about participants that leave the room. The listener will receive an object with the following structure:
|
||||
```javascript
|
||||
* **participantLeft** - event notifications about participant that left room.
|
||||
The listener will receive object with the following structure:
|
||||
```
|
||||
{
|
||||
"jid": jid // the JID of the participant
|
||||
jid: jid //the jid of the participant
|
||||
}
|
||||
```
|
||||
|
||||
* **videoConferenceJoined** - event notifications fired when the local user has joined the video conference. The listener will receive an object with the following structure:
|
||||
```javascript
|
||||
* **video-conference-joined** - event notifications fired when the local user has joined the video conference.
|
||||
The listener will receive object with the following structure:
|
||||
```
|
||||
{
|
||||
"roomName": room // the room name of the conference
|
||||
roomName: room //the room name of the conference
|
||||
}
|
||||
```
|
||||
|
||||
* **videoConferenceLeft** - event notifications fired when the local user has left the video conference. The listener will receive an object with the following structure:
|
||||
```javascript
|
||||
* **video-conference-left** - event notifications fired when the local user has left the video conference.
|
||||
The listener will receive object with the following structure:
|
||||
```
|
||||
{
|
||||
"roomName": room // the room name of the conference
|
||||
roomName: room //the room name of the conference
|
||||
}
|
||||
```
|
||||
|
||||
* **readyToClose** - event notification fired when Jitsi Meet is ready to be closed (hangup operations are completed).
|
||||
|
||||
You can also add multiple event listeners by using `addEventListeners`.
|
||||
You can also add multiple event listeners by using ```addEventListeners```.
|
||||
This method requires one argument of type Object. The object argument must
|
||||
have the names of the events as keys and the listeners of the events as values.
|
||||
have keys with the names of the events and values the listeners of the events.
|
||||
|
||||
```javascript
|
||||
```
|
||||
function incomingMessageListener(object)
|
||||
{
|
||||
// ...
|
||||
...
|
||||
}
|
||||
|
||||
function outgoingMessageListener(object)
|
||||
{
|
||||
// ...
|
||||
...
|
||||
}
|
||||
|
||||
api.addEventListeners({
|
||||
@@ -215,28 +183,20 @@ api.addEventListeners({
|
||||
outgoingMessage: outgoingMessageListener})
|
||||
```
|
||||
|
||||
If you want to remove a listener you can use `removeEventListener` method with argument the name of the event.
|
||||
|
||||
```javascript
|
||||
If you want to remove a listener you can use ```removeEventListener``` method with argument the name of the event.
|
||||
```
|
||||
api.removeEventListener("incomingMessage");
|
||||
```
|
||||
|
||||
If you want to remove more than one event you can use `removeEventListeners` method with an Array with the names of the events as an argument.
|
||||
```javascript
|
||||
If you want to remove more than one event you can use ```removeEventListeners``` method with argument
|
||||
array with the names of the events.
|
||||
```
|
||||
api.removeEventListeners(["incomingMessage", "outgoingMessageListener"]);
|
||||
```
|
||||
|
||||
You can get the number of participants in the conference with the following API function:
|
||||
```javascript
|
||||
var numberOfParticipants = api.getNumberOfParticipants();
|
||||
You can remove the embedded Jitsi Meet Conference with the following code:
|
||||
```
|
||||
|
||||
You can remove the embedded Jitsi Meet Conference with the following API function:
|
||||
```javascript
|
||||
api.dispose()
|
||||
```
|
||||
|
||||
NOTE: It's a good practice to remove the conference before the page is unloaded.
|
||||
|
||||
[config.js]: https://github.com/jitsi/jitsi-meet/blob/master/config.js
|
||||
[interface_config.js]: https://github.com/jitsi/jitsi-meet/blob/master/interface_config.js
|
||||
It is a good practice to remove the conference before the page is unloaded.
|
||||
|
||||
@@ -20,7 +20,7 @@ server {
|
||||
|
||||
root /usr/share/jitsi-meet;
|
||||
index index.html index.htm;
|
||||
error_page 404 /static/404.html;
|
||||
error_page 404 /404.html;
|
||||
|
||||
location /config.js {
|
||||
alias /etc/jitsi/meet/jitsi-meet.example.com-config.js;
|
||||
|
||||
@@ -29,8 +29,6 @@
|
||||
Allow from all
|
||||
</Directory>
|
||||
|
||||
ErrorDocument 404 /static/404.html
|
||||
|
||||
Alias "/config.js" "/etc/jitsi/meet/jitsi-meet.example.com-config.js"
|
||||
<Location /config.js>
|
||||
Require all granted
|
||||
|
||||
@@ -1,22 +0,0 @@
|
||||
<html itemscope itemtype="http://schema.org/Product" prefix="og: http://ogp.me/ns#" xmlns="http://www.w3.org/1999/html">
|
||||
<head>
|
||||
<meta charset="utf-8">
|
||||
<meta http-equiv="content-type" content="text/html;charset=utf-8">
|
||||
</head>
|
||||
<body>
|
||||
<script src="https://meet.jit.si/external_api.js"></script>
|
||||
<script>
|
||||
var domain = "meet.jit.si";
|
||||
var room = "JitsiMeetAPIExample";
|
||||
var width = 700;
|
||||
var height = 180;
|
||||
var htmlElement = undefined;
|
||||
var configOverwrite = {};
|
||||
var interfaceConfigOverwrite = {
|
||||
filmStripOnly: true
|
||||
};
|
||||
var api = new JitsiMeetExternalAPI(domain, room, width, height,
|
||||
htmlElement, configOverwrite, interfaceConfigOverwrite);
|
||||
</script>
|
||||
</body>
|
||||
</html>
|
||||
29
doc/influxdb.md
Normal file
@@ -0,0 +1,29 @@
|
||||
# Overview
|
||||
Jitsi Meet supports logging to an [InfluxDB](http://influxdb.com/) database.
|
||||
|
||||
# Configuration
|
||||
The following needs to be done to enable this functionality.
|
||||
|
||||
## Install InfluxDB
|
||||
The details are outside the scope of the document, see http://influxdb.com/download/ .
|
||||
|
||||
## Create an InfluxDB database
|
||||
Use the InfluxDB admin interface (running on port 8083) and create a database. In this example we name it <code>jitsi_database</code>
|
||||
|
||||
## Enable logging for Jitsi Videobridge
|
||||
Add the following properties to <code>/usr/share/jitsi-videobridge/.sip-communicator/sip-communicator.properties</code>.
|
||||
|
||||
- org.jitsi.videobridge.log.INFLUX_DB_ENABLED=true
|
||||
- org.jitsi.videobridge.log.INFLUX_URL_BASE=http://influxdb.example.com:8086
|
||||
- org.jitsi.videobridge.log.INFLUX_DATABASE=jitsi_database
|
||||
- org.jitsi.videobridge.log.INFLUX_USER=user
|
||||
- org.jitsi.videobridge.log.INFLUX_PASS=pass
|
||||
|
||||
## Enable logging for Jicofo
|
||||
Add the same properties as above to <code>/usr/share/jicofo/.sip-communicator/sip-communicator.properties</code>.
|
||||
|
||||
## Enable logging for Jitsi Meet itself
|
||||
Change "logStats" to "true" in <code>/etc/jitsi/meet/you-domain.config.js</code> or the <code>config.js</code> file used in your installation.
|
||||
|
||||
# User interface
|
||||
You can explore the database using the [Jiloin](https://github.com/jitsi/jiloin) web interface.
|
||||
@@ -6,34 +6,6 @@ change references to that to match your host, and generate some passwords for
|
||||
|
||||
There are also some complete [example config files](https://github.com/jitsi/jitsi-meet/tree/master/doc/example-config-files/) available, mentioned in each section.
|
||||
|
||||
## Network description
|
||||
|
||||
This how the network look like:
|
||||
```
|
||||
+ +
|
||||
| |
|
||||
| |
|
||||
v |
|
||||
443 |
|
||||
+-------+ |
|
||||
| | |
|
||||
| NginX | |
|
||||
| | |
|
||||
+--+-+--+ |
|
||||
| | |
|
||||
+------------+ | | +--------------+ |
|
||||
| | | | | | |
|
||||
| jitsi-meet +<---+ +--->+ prosody/xmpp | |
|
||||
| |files 5280 | | |
|
||||
+------------+ +--------------+ v
|
||||
5222,5347^ ^5347 4443
|
||||
+--------+ | | +-------------+
|
||||
| | | | | |
|
||||
| jicofo +----^ ^----+ videobridge |
|
||||
| | | |
|
||||
+--------+ +-------------+
|
||||
```
|
||||
|
||||
## Install prosody
|
||||
```sh
|
||||
apt-get install prosody
|
||||
@@ -104,9 +76,7 @@ Add a new file `jitsi.example.com` in `/etc/nginx/sites-available` (see also the
|
||||
server_names_hash_bucket_size 64;
|
||||
|
||||
server {
|
||||
listen 443;
|
||||
# tls configuration that is not covered in this guide
|
||||
# we recommend the use of https://certbot.eff.org/
|
||||
listen 80;
|
||||
server_name jitsi.example.com;
|
||||
# set the root
|
||||
root /srv/jitsi.example.com;
|
||||
@@ -161,9 +131,9 @@ Or autostart it by adding the line in `/etc/rc.local`:
|
||||
|
||||
## Install Jitsi Conference Focus (jicofo)
|
||||
|
||||
Install JDK and Maven if missing:
|
||||
Install JDK and Ant if missing:
|
||||
```
|
||||
apt-get install default-jdk maven
|
||||
apt-get install default-jdk ant
|
||||
```
|
||||
|
||||
_NOTE: When installing on older Debian releases keep in mind that you need JDK >= 1.7._
|
||||
@@ -175,14 +145,12 @@ git clone https://github.com/jitsi/jicofo.git
|
||||
Build distribution package. Replace {os-name} with one of: 'lin', 'lin64', 'macosx', 'win', 'win64'.
|
||||
```sh
|
||||
cd jicofo
|
||||
mvn package -DskipTests -Dassembly.skipAssembly=false
|
||||
ant dist.{os-name}
|
||||
```
|
||||
Run jicofo:
|
||||
```sh
|
||||
=======
|
||||
unzip target/jicofo-{os-name}-1.0-SNAPSHOT.zip
|
||||
cd jicofo-{os-name}-1.0-SNAPSHOT'
|
||||
./jicofo.sh --host=localhost --domain=jitsi.example.com --secret=YOURSECRET2 --user_domain=auth.jitsi.example.com --user_name=focus --user_password=YOURSECRET3
|
||||
cd dist/{os-name}'
|
||||
./jicofo.sh --domain=jitsi.example.com --secret=YOURSECRET2 --user_domain=auth.jitsi.example.com --user_name=focus --user_password=YOURSECRET3
|
||||
```
|
||||
|
||||
## Deploy Jitsi Meet
|
||||
@@ -191,8 +159,6 @@ Checkout and configure Jitsi Meet:
|
||||
cd /srv
|
||||
git clone https://github.com/jitsi/jitsi-meet.git
|
||||
mv jitsi-meet/ jitsi.example.com
|
||||
npm install
|
||||
make
|
||||
```
|
||||
|
||||
Edit host names in `/srv/jitsi.example.com/config.js` (see also the example config file):
|
||||
@@ -201,11 +167,11 @@ var config = {
|
||||
hosts: {
|
||||
domain: 'jitsi.example.com',
|
||||
muc: 'conference.jitsi.example.com',
|
||||
bridge: 'jitsi-videobridge.jitsi.example.com',
|
||||
focus: 'focus.jitsi.example.com'
|
||||
bridge: 'jitsi-videobridge.jitsi.example.com'
|
||||
},
|
||||
useNicks: false,
|
||||
bosh: '//jitsi.example.com/http-bind', // FIXME: use xep-0156 for that
|
||||
desktopSharing: 'false' // Desktop sharing method. Can be set to 'ext', 'webrtc' or false to disable.
|
||||
//chromeExtensionId: 'diibjkoicjeejcmhdnailmkgecihlobk', // Id of desktop streamer Chrome extension
|
||||
//minChromeExtVersion: '0.1' // Required version of Chrome extension
|
||||
};
|
||||
|
||||
@@ -1,96 +0,0 @@
|
||||
# Jitsi Meet mobile apps
|
||||
|
||||
Jitsi Meet can also be built as a standalone mobile application for
|
||||
iOS and Android. It uses the [React Native] framework.
|
||||
|
||||
First make sure the [React Native dependencies] are installed.
|
||||
|
||||
**NOTE**: This document assumes the app is being built on a macOS system.
|
||||
|
||||
**NOTE**: The app must be built for an actual device since the simulators don't
|
||||
work properly with the native plugins we require.
|
||||
|
||||
|
||||
## iOS
|
||||
|
||||
1. Install some extra dependencies
|
||||
|
||||
- Install ios-deploy globally (in case you want to use the React Native CLI
|
||||
to deploy the app to the device)
|
||||
|
||||
```bash
|
||||
npm install -g ios-deploy
|
||||
```
|
||||
|
||||
You may need to add ```--unsafe-perm=true``` if you are running on [Mac OS 10.11 or greater](https://github.com/phonegap/ios-deploy#os-x-1011-el-capitan-or-greater).
|
||||
|
||||
2. Build the app
|
||||
|
||||
There are 2 ways to build the app: using the CLI or using Xcode.
|
||||
|
||||
Using the CLI:
|
||||
|
||||
```bash
|
||||
react-native run-ios --device
|
||||
```
|
||||
|
||||
When the app is launched from the CLI the output can be checked with the
|
||||
following command:
|
||||
|
||||
```bash
|
||||
react-native log-ios
|
||||
```
|
||||
|
||||
Using Xcode
|
||||
|
||||
- Open **ios/jitsi-meet-react.xcworkspace** in Xcode. Make sure it's the
|
||||
workspace file!
|
||||
|
||||
- Select your device from the top bar and hit the "play" button.
|
||||
|
||||
When the app is launched from Xcode the Debug console will show the output
|
||||
logs the application creates.
|
||||
|
||||
|
||||
3. Other remarks
|
||||
|
||||
It's likely you'll need to change the bundle ID for deploying to a device
|
||||
because the default bundle ID points to the application signed by Atlassian.
|
||||
|
||||
This can be changed in the "General" tab. Under "Identity" set
|
||||
"Bundle Identifier" to a different value, and adjust the "Team" in the
|
||||
"Signing" section to match your own.
|
||||
|
||||
|
||||
## Android
|
||||
|
||||
The [React Native dependencies] page has very detailed information on how to
|
||||
setup [Android Studio] and the required components for getting the necessary
|
||||
build environment. Make sure you follow it closely.
|
||||
|
||||
1. Building the app
|
||||
|
||||
The app can be built using the CLI utility as follows:
|
||||
|
||||
```bash
|
||||
react-native run-android
|
||||
```
|
||||
|
||||
It will be launched on the connected Android device.
|
||||
|
||||
|
||||
## Debugging
|
||||
|
||||
The official documentation on [debugging] is quite extensive, it is the
|
||||
preferred method for debugging.
|
||||
|
||||
**NOTE**: When using Chrome Developer Tools for debugging the JavaScript code
|
||||
is being interpreted by Chrome's V8 engine, instead of JSCore which
|
||||
React Native uses. It's important to keep this in mind due to potential
|
||||
differences in supported JavaScript features.
|
||||
|
||||
|
||||
[Android Studio]: https://developer.android.com/studio/index.html
|
||||
[debugging]: https://facebook.github.io/react-native/docs/debugging.html
|
||||
[React Native]: https://facebook.github.io/react-native/
|
||||
[React Native dependencies]: https://facebook.github.io/react-native/docs/getting-started.html#installing-dependencies
|
||||
6
flow-typed/npm/flow-bin_v0.x.x.js
vendored
@@ -1,6 +0,0 @@
|
||||
// flow-typed signature: 6a5610678d4b01e13bbfbbc62bdaf583
|
||||
// flow-typed version: 3817bc6980/flow-bin_v0.x.x/flow_>=v0.25.x
|
||||
|
||||
declare module "flow-bin" {
|
||||
declare module.exports: string;
|
||||
}
|
||||
36
flow-typed/npm/react-i18next_v2.x.x.js
vendored
@@ -1,36 +0,0 @@
|
||||
// flow-typed signature: 57cf34196930be78935a42e5c8ac3cb6
|
||||
// flow-typed version: ae6284e7b7/react-i18next_v2.x.x/flow_>=v0.36.x_<=v0.39.x
|
||||
|
||||
declare module 'react-i18next' {
|
||||
declare type TFunction = (key?: ?string, data?: ?Object) => string;
|
||||
declare type Locales = string | Array<string>;
|
||||
|
||||
declare type StatelessComponent<P> = (props: P) => ?React$Element<any>;
|
||||
|
||||
declare type Comp<P> = StatelessComponent<P> | Class<React$Component<*, P, *>>;
|
||||
|
||||
declare type Translator<OP, P> = {
|
||||
(component: StatelessComponent<P>): Class<React$Component<void, OP, void>>;
|
||||
<Def, St>(component: Class<React$Component<Def, P, St>>): Class<React$Component<Def, OP, St>>;
|
||||
}
|
||||
|
||||
declare function translate<OP, P>(locales: Locales): Translator<OP, P>;
|
||||
|
||||
declare type NamespacesProps = {
|
||||
components: Array<Comp<*>>,
|
||||
i18n: { loadNamespaces: Function },
|
||||
};
|
||||
|
||||
declare function loadNamespaces(props: NamespacesProps): Promise<void>;
|
||||
|
||||
declare type ProviderProps = { i18n: Object, children: React$Element<any> };
|
||||
|
||||
declare var I18nextProvider: Class<React$Component<void, ProviderProps, void>>;
|
||||
|
||||
declare type InterpolateProps = {
|
||||
children?: React$Element<any>,
|
||||
className?: string,
|
||||
};
|
||||
|
||||
declare var Interpolate: Class<React$Component<void, InterpolateProps, void>>;
|
||||
}
|
||||
89
flow-typed/npm/react-redux_v5.x.x.js
vendored
@@ -1,89 +0,0 @@
|
||||
// flow-typed signature: 0ed284c5a2e97a9e3c0e87af3dedc09d
|
||||
// flow-typed version: bdf1e66252/react-redux_v5.x.x/flow_>=v0.30.x
|
||||
|
||||
import type { Dispatch, Store } from 'redux'
|
||||
|
||||
declare module 'react-redux' {
|
||||
|
||||
/*
|
||||
|
||||
S = State
|
||||
A = Action
|
||||
OP = OwnProps
|
||||
SP = StateProps
|
||||
DP = DispatchProps
|
||||
|
||||
*/
|
||||
|
||||
declare type MapStateToProps<S, OP: Object, SP: Object> = (state: S, ownProps: OP) => SP | MapStateToProps<S, OP, SP>;
|
||||
|
||||
declare type MapDispatchToProps<A, OP: Object, DP: Object> = ((dispatch: Dispatch<A>, ownProps: OP) => DP) | DP;
|
||||
|
||||
declare type MergeProps<SP, DP: Object, OP: Object, P: Object> = (stateProps: SP, dispatchProps: DP, ownProps: OP) => P;
|
||||
|
||||
declare type StatelessComponent<P> = (props: P) => ?React$Element<any>;
|
||||
|
||||
declare class ConnectedComponent<OP, P, Def, St> extends React$Component<void, OP, void> {
|
||||
static WrappedComponent: Class<React$Component<Def, P, St>>;
|
||||
getWrappedInstance(): React$Component<Def, P, St>;
|
||||
static defaultProps: void;
|
||||
props: OP;
|
||||
state: void;
|
||||
}
|
||||
|
||||
declare type ConnectedComponentClass<OP, P, Def, St> = Class<ConnectedComponent<OP, P, Def, St>>;
|
||||
|
||||
declare type Connector<OP, P> = {
|
||||
(component: StatelessComponent<P>): ConnectedComponentClass<OP, P, void, void>;
|
||||
<Def, St>(component: Class<React$Component<Def, P, St>>): ConnectedComponentClass<OP, P, Def, St>;
|
||||
};
|
||||
|
||||
declare class Provider<S, A> extends React$Component<void, { store: Store<S, A>, children?: any }, void> { }
|
||||
|
||||
declare type ConnectOptions = {
|
||||
pure?: boolean,
|
||||
withRef?: boolean
|
||||
};
|
||||
|
||||
declare type Null = null | void;
|
||||
|
||||
declare function connect<A, OP>(
|
||||
...rest: Array<void> // <= workaround for https://github.com/facebook/flow/issues/2360
|
||||
): Connector<OP, $Supertype<{ dispatch: Dispatch<A> } & OP>>;
|
||||
|
||||
declare function connect<A, OP>(
|
||||
mapStateToProps: Null,
|
||||
mapDispatchToProps: Null,
|
||||
mergeProps: Null,
|
||||
options: ConnectOptions
|
||||
): Connector<OP, $Supertype<{ dispatch: Dispatch<A> } & OP>>;
|
||||
|
||||
declare function connect<S, A, OP, SP>(
|
||||
mapStateToProps: MapStateToProps<S, OP, SP>,
|
||||
mapDispatchToProps: Null,
|
||||
mergeProps: Null,
|
||||
options?: ConnectOptions
|
||||
): Connector<OP, $Supertype<SP & { dispatch: Dispatch<A> } & OP>>;
|
||||
|
||||
declare function connect<A, OP, DP>(
|
||||
mapStateToProps: Null,
|
||||
mapDispatchToProps: MapDispatchToProps<A, OP, DP>,
|
||||
mergeProps: Null,
|
||||
options?: ConnectOptions
|
||||
): Connector<OP, $Supertype<DP & OP>>;
|
||||
|
||||
declare function connect<S, A, OP, SP, DP>(
|
||||
mapStateToProps: MapStateToProps<S, OP, SP>,
|
||||
mapDispatchToProps: MapDispatchToProps<A, OP, DP>,
|
||||
mergeProps: Null,
|
||||
options?: ConnectOptions
|
||||
): Connector<OP, $Supertype<SP & DP & OP>>;
|
||||
|
||||
declare function connect<S, A, OP, SP, DP, P>(
|
||||
mapStateToProps: MapStateToProps<S, OP, SP>,
|
||||
mapDispatchToProps: MapDispatchToProps<A, OP, DP>,
|
||||
mergeProps: MergeProps<SP, DP, OP, P>,
|
||||
options?: ConnectOptions
|
||||
): Connector<OP, P>;
|
||||
|
||||
}
|
||||
56
flow-typed/npm/redux_v3.x.x.js
vendored
@@ -1,56 +0,0 @@
|
||||
// flow-typed signature: ba132c96664f1a05288f3eb2272a3c35
|
||||
// flow-typed version: c4bbd91cfc/redux_v3.x.x/flow_>=v0.33.x
|
||||
|
||||
declare module 'redux' {
|
||||
|
||||
/*
|
||||
|
||||
S = State
|
||||
A = Action
|
||||
|
||||
*/
|
||||
|
||||
declare type Dispatch<A: { type: $Subtype<string> }> = (action: A) => A;
|
||||
|
||||
declare type MiddlewareAPI<S, A> = {
|
||||
dispatch: Dispatch<A>;
|
||||
getState(): S;
|
||||
};
|
||||
|
||||
declare type Store<S, A> = {
|
||||
// rewrite MiddlewareAPI members in order to get nicer error messages (intersections produce long messages)
|
||||
dispatch: Dispatch<A>;
|
||||
getState(): S;
|
||||
subscribe(listener: () => void): () => void;
|
||||
replaceReducer(nextReducer: Reducer<S, A>): void
|
||||
};
|
||||
|
||||
declare type Reducer<S, A> = (state: S, action: A) => S;
|
||||
|
||||
declare type Middleware<S, A> =
|
||||
(api: MiddlewareAPI<S, A>) =>
|
||||
(next: Dispatch<A>) => Dispatch<A>;
|
||||
|
||||
declare type StoreCreator<S, A> = {
|
||||
(reducer: Reducer<S, A>, enhancer?: StoreEnhancer<S, A>): Store<S, A>;
|
||||
(reducer: Reducer<S, A>, preloadedState: S, enhancer?: StoreEnhancer<S, A>): Store<S, A>;
|
||||
};
|
||||
|
||||
declare type StoreEnhancer<S, A> = (next: StoreCreator<S, A>) => StoreCreator<S, A>;
|
||||
|
||||
declare function createStore<S, A>(reducer: Reducer<S, A>, enhancer?: StoreEnhancer<S, A>): Store<S, A>;
|
||||
declare function createStore<S, A>(reducer: Reducer<S, A>, preloadedState: S, enhancer?: StoreEnhancer<S, A>): Store<S, A>;
|
||||
|
||||
declare function applyMiddleware<S, A>(...middlewares: Array<Middleware<S, A>>): StoreEnhancer<S, A>;
|
||||
|
||||
declare type ActionCreator<A, B> = (...args: Array<B>) => A;
|
||||
declare type ActionCreators<K, A> = { [key: K]: ActionCreator<A, any> };
|
||||
|
||||
declare function bindActionCreators<A, C: ActionCreator<A, any>>(actionCreator: C, dispatch: Dispatch<A>): C;
|
||||
declare function bindActionCreators<A, K, C: ActionCreators<K, A>>(actionCreators: C, dispatch: Dispatch<A>): C;
|
||||
|
||||
declare function combineReducers<O: Object, A>(reducers: O): Reducer<$ObjMap<O, <S>(r: Reducer<S, any>) => S>, A>;
|
||||
|
||||
declare function compose<S, A>(...fns: Array<StoreEnhancer<S, A>>): Function;
|
||||
|
||||
}
|
||||
BIN
fonts/jitsi.eot
@@ -14,7 +14,7 @@
|
||||
<glyph unicode="" glyph-name="connection-lost" horiz-adv-x="1414" d="M0 299.153h196.337v-187.951h-196.337v187.951zM271.842 480.372h196.337v-369.169h-196.337v369.169zM543.656 661.562h196.337v-550.36h-196.337v550.36zM815.47 842.766v-731.564h119.56c-14.589 33.025-23.125 71.503-23.232 111.943 0.132 86.42 38.697 163.851 99.656 216.468l0.348 403.153h-196.332zM1087.292 1024v-533.672c28.874 10.572 62.222 16.73 97.009 16.825 35.717-0.129 69.823-6.614 101.322-18.371l-1.999 535.218h-196.332zM1192.868 439.852c-0.009 0-0.020 0-0.031 0-122.247 0-221.351-98.447-221.372-219.896 0-0.007 0-0.014 0-0.021 0-121.467 99.111-219.935 221.372-219.935 0.011 0 0.021 0 0.032 0 122.248 0.014 221.345 98.477 221.345 219.935 0 0.007 0 0.013 0 0.020-0.021 121.441-99.11 219.883-221.345 219.897zM1194.706 372.607c87.601-0.006 158.614-69.787 158.614-155.866 0-0.006 0-0.012 0-0.019-0.022-86.062-71.026-155.822-158.614-155.828-87.588 0.006-158.593 69.766-158.615 155.826 0 0.007 0 0.014 0 0.020 0 86.079 71.013 155.86 158.613 155.866zM1286.795 355.682l48.348-52.528-236.375-217.567-48.348 52.528 236.375 217.567z" />
|
||||
<glyph unicode="" glyph-name="avatar" d="M512 204c106 0 200 56 256 138-2 84-172 132-256 132-86 0-254-48-256-132 56-82 150-138 256-138zM512 810c-70 0-128-58-128-128s58-128 128-128 128 58 128 128-58 128-128 128zM512 938c236 0 426-190 426-426s-190-426-426-426-426 190-426 426 190 426 426 426z" />
|
||||
<glyph unicode="" glyph-name="download" d="M726 470h-128v170h-172v-170h-128l214-214zM826 596c110-8 198-100 198-212 0-118-96-214-214-214h-554c-142 0-256 114-256 256 0 132 100 240 228 254 54 102 160 174 284 174 156 0 284-110 314-258z" />
|
||||
<glyph unicode="" glyph-name="mic-camera-combined" d="M756.704 628.138l267.296 202.213v-635.075l-267.296 202.213v-191.923c0-12.085-11.296-21.863-25.216-21.863h-706.272c-13.92 0-25.216 9.777-25.216 21.863v612.25c0 12.085 11.296 21.863 25.216 21.863h706.272c13.92 0 25.216-9.777 25.216-21.863v-189.679zM371.338 376.228c47.817 0 86.529 40.232 86.529 89.811v184.835c0 49.651-38.713 89.883-86.529 89.883-47.788 0-86.515-40.232-86.515-89.883v-184.835c0-49.579 38.756-89.811 86.515-89.811v0zM356.754 314.070v-32.78h33.718v33.412c73.858 9.606 131.235 73.73 131.235 151.351v88.232h-30.636v-88.232c0-67.57-53.696-122.534-119.734-122.534-66.024 0-119.691 54.964-119.691 122.534v88.232h-30.636v-88.232c0-79.215 59.674-144.502 135.744-151.969v-0.014z" />
|
||||
<glyph unicode="" glyph-name="autorenew" d="M800 694c34-52 54-116 54-182 0-188-154-342-342-342v-128l-170 172 170 170v-128c142 0 256 114 256 256 0 44-12 84-30 120zM512 768c-142 0-256-114-256-256 0-44 10-84 30-120l-62-62c-34 52-54 116-54 182 0 188 154 342 342 342v128l170-172-170-170v128z" />
|
||||
<glyph unicode="" glyph-name="kick" d="M512 810l284-426h-568zM214 298h596v-84h-596v84z" />
|
||||
<glyph unicode="" glyph-name="hangup" d="M512 640c-68 0-134-10-196-30v-132c0-16-10-34-24-40-42-20-80-46-114-78-8-8-18-12-30-12s-22 4-30 12l-106 106c-8 8-12 18-12 30s4 22 12 30c130 124 306 200 500 200s370-76 500-200c8-8 12-18 12-30s-4-22-12-30l-106-106c-8-8-18-12-30-12s-22 4-30 12c-34 32-72 58-114 78-14 6-24 20-24 38v132c-62 20-128 32-196 32z" />
|
||||
<glyph unicode="" glyph-name="chat" d="M854 342v512h-684v-598l86 86h598zM854 938c46 0 84-38 84-84v-512c0-46-38-86-84-86h-598l-170-170v768c0 46 38 84 84 84h684z" />
|
||||
@@ -44,5 +44,4 @@
|
||||
<glyph unicode="" glyph-name="raised-hand" d="M982 790v-620c0-94-78-170-172-170h-310c-46 0-90 18-122 50l-336 342s54 52 56 52c10 8 22 12 34 12 10 0 18-2 26-6 2 0 184-104 184-104v508c0 36 28 64 64 64s64-28 64-64v-300h42v406c0 36 28 64 64 64s64-28 64-64v-406h42v364c0 36 28 64 64 64s64-28 64-64v-364h44v236c0 36 28 64 64 64s64-28 64-64z" />
|
||||
<glyph unicode="" glyph-name="menu-up" d="M512 682l256-256-60-60-196 196-196-196-60 60z" />
|
||||
<glyph unicode="" glyph-name="menu-down" d="M708 658l60-60-256-256-256 256 60 60 196-196z" />
|
||||
<glyph unicode="" glyph-name="switch-camera" d="M640 362l150 150-150 150v-108h-256v108l-150-150 150-150v108h256v-108zM854 854c46 0 84-40 84-86v-512c0-46-38-86-84-86h-684c-46 0-84 40-84 86v512c0 46 38 86 84 86h136l78 84h256l78-84h136z" />
|
||||
</font></defs></svg>
|
||||
|
Before Width: | Height: | Size: 15 KiB After Width: | Height: | Size: 15 KiB |
BIN
fonts/jitsi.ttf
BIN
fonts/jitsi.woff
@@ -1,35 +1,6 @@
|
||||
{
|
||||
"IcoMoonType": "selection",
|
||||
"icons": [
|
||||
{
|
||||
"icon": {
|
||||
"paths": [
|
||||
"M756.704 395.862l267.296-202.213v635.075l-267.296-202.213v191.923c0 12.085-11.296 21.863-25.216 21.863h-706.272c-13.92 0-25.216-9.777-25.216-21.863v-612.25c0-12.085 11.296-21.863 25.216-21.863h706.272c13.92 0 25.216 9.777 25.216 21.863v189.679zM371.338 647.772c47.817 0 86.529-40.232 86.529-89.811v-184.835c0-49.651-38.713-89.883-86.529-89.883-47.788 0-86.515 40.232-86.515 89.883v184.835c0 49.579 38.756 89.811 86.515 89.811v0zM356.754 709.93v32.78h33.718v-33.412c73.858-9.606 131.235-73.73 131.235-151.351v-88.232h-30.636v88.232c0 67.57-53.696 122.534-119.734 122.534-66.024 0-119.691-54.964-119.691-122.534v-88.232h-30.636v88.232c0 79.215 59.674 144.502 135.744 151.969v0.014z"
|
||||
],
|
||||
"attrs": [
|
||||
{}
|
||||
],
|
||||
"isMulticolor": false,
|
||||
"isMulticolor2": false,
|
||||
"grid": 0,
|
||||
"tags": [
|
||||
"Combined Shape"
|
||||
]
|
||||
},
|
||||
"attrs": [
|
||||
{}
|
||||
],
|
||||
"properties": {
|
||||
"order": 109,
|
||||
"id": 0,
|
||||
"name": "mic-camera-combined",
|
||||
"prevSize": 32,
|
||||
"code": 59651
|
||||
},
|
||||
"setIdx": 0,
|
||||
"setId": 2,
|
||||
"iconIdx": 0
|
||||
},
|
||||
{
|
||||
"icon": {
|
||||
"paths": [
|
||||
@@ -55,8 +26,8 @@
|
||||
"prevSize": 32,
|
||||
"code": 59677
|
||||
},
|
||||
"setIdx": 1,
|
||||
"setId": 1,
|
||||
"setIdx": 0,
|
||||
"setId": 2,
|
||||
"iconIdx": 0
|
||||
},
|
||||
{
|
||||
@@ -84,8 +55,8 @@
|
||||
"prevSize": 32,
|
||||
"code": 59676
|
||||
},
|
||||
"setIdx": 1,
|
||||
"setId": 1,
|
||||
"setIdx": 0,
|
||||
"setId": 2,
|
||||
"iconIdx": 1
|
||||
},
|
||||
{
|
||||
@@ -110,9 +81,35 @@
|
||||
"code": 59649,
|
||||
"name": "avatar"
|
||||
},
|
||||
"setIdx": 1,
|
||||
"setId": 1,
|
||||
"iconIdx": 2
|
||||
"setIdx": 0,
|
||||
"setId": 2,
|
||||
"iconIdx": 12
|
||||
},
|
||||
{
|
||||
"icon": {
|
||||
"paths": [
|
||||
"M800 330c34 52 54 116 54 182 0 188-154 342-342 342v128l-170-172 170-170v128c142 0 256-114 256-256 0-44-12-84-30-120zM512 256c-142 0-256 114-256 256 0 44 10 84 30 120l-62 62c-34-52-54-116-54-182 0-188 154-342 342-342v-128l170 172-170 170v-128z"
|
||||
],
|
||||
"isMulticolor": false,
|
||||
"isMulticolor2": false,
|
||||
"tags": [
|
||||
"autorenew"
|
||||
],
|
||||
"grid": 0,
|
||||
"attrs": []
|
||||
},
|
||||
"attrs": [],
|
||||
"properties": {
|
||||
"id": 68,
|
||||
"order": 84,
|
||||
"ligatures": "autorenew",
|
||||
"prevSize": 32,
|
||||
"code": 59651,
|
||||
"name": "autorenew"
|
||||
},
|
||||
"setIdx": 0,
|
||||
"setId": 2,
|
||||
"iconIdx": 69
|
||||
},
|
||||
{
|
||||
"icon": {
|
||||
@@ -136,9 +133,9 @@
|
||||
"code": 59653,
|
||||
"name": "hangup"
|
||||
},
|
||||
"setIdx": 1,
|
||||
"setId": 1,
|
||||
"iconIdx": 3
|
||||
"setIdx": 0,
|
||||
"setId": 2,
|
||||
"iconIdx": 123
|
||||
},
|
||||
{
|
||||
"icon": {
|
||||
@@ -162,9 +159,9 @@
|
||||
"code": 59654,
|
||||
"name": "chat"
|
||||
},
|
||||
"setIdx": 1,
|
||||
"setId": 1,
|
||||
"iconIdx": 4
|
||||
"setIdx": 0,
|
||||
"setId": 2,
|
||||
"iconIdx": 149
|
||||
},
|
||||
{
|
||||
"icon": {
|
||||
@@ -188,9 +185,9 @@
|
||||
"code": 59650,
|
||||
"name": "download"
|
||||
},
|
||||
"setIdx": 1,
|
||||
"setId": 1,
|
||||
"iconIdx": 5
|
||||
"setIdx": 0,
|
||||
"setId": 2,
|
||||
"iconIdx": 165
|
||||
},
|
||||
{
|
||||
"icon": {
|
||||
@@ -214,9 +211,9 @@
|
||||
"code": 59655,
|
||||
"name": "edit"
|
||||
},
|
||||
"setIdx": 1,
|
||||
"setId": 1,
|
||||
"iconIdx": 6
|
||||
"setIdx": 0,
|
||||
"setId": 2,
|
||||
"iconIdx": 186
|
||||
},
|
||||
{
|
||||
"icon": {
|
||||
@@ -240,9 +237,9 @@
|
||||
"code": 59656,
|
||||
"name": "share-doc"
|
||||
},
|
||||
"setIdx": 1,
|
||||
"setId": 1,
|
||||
"iconIdx": 7
|
||||
"setIdx": 0,
|
||||
"setId": 2,
|
||||
"iconIdx": 207
|
||||
},
|
||||
{
|
||||
"icon": {
|
||||
@@ -266,9 +263,9 @@
|
||||
"code": 59657,
|
||||
"name": "telephone"
|
||||
},
|
||||
"setIdx": 1,
|
||||
"setId": 1,
|
||||
"iconIdx": 8
|
||||
"setIdx": 0,
|
||||
"setId": 2,
|
||||
"iconIdx": 216
|
||||
},
|
||||
{
|
||||
"icon": {
|
||||
@@ -292,9 +289,9 @@
|
||||
"code": 59652,
|
||||
"name": "kick"
|
||||
},
|
||||
"setIdx": 1,
|
||||
"setId": 1,
|
||||
"iconIdx": 9
|
||||
"setIdx": 0,
|
||||
"setId": 2,
|
||||
"iconIdx": 243
|
||||
},
|
||||
{
|
||||
"icon": {
|
||||
@@ -318,9 +315,9 @@
|
||||
"code": 59679,
|
||||
"name": "menu-up"
|
||||
},
|
||||
"setIdx": 1,
|
||||
"setId": 1,
|
||||
"iconIdx": 10
|
||||
"setIdx": 0,
|
||||
"setId": 2,
|
||||
"iconIdx": 257
|
||||
},
|
||||
{
|
||||
"icon": {
|
||||
@@ -344,9 +341,9 @@
|
||||
"code": 59680,
|
||||
"name": "menu-down"
|
||||
},
|
||||
"setIdx": 1,
|
||||
"setId": 1,
|
||||
"iconIdx": 11
|
||||
"setIdx": 0,
|
||||
"setId": 2,
|
||||
"iconIdx": 258
|
||||
},
|
||||
{
|
||||
"icon": {
|
||||
@@ -370,9 +367,9 @@
|
||||
"code": 59659,
|
||||
"name": "full-screen"
|
||||
},
|
||||
"setIdx": 1,
|
||||
"setId": 1,
|
||||
"iconIdx": 12
|
||||
"setIdx": 0,
|
||||
"setId": 2,
|
||||
"iconIdx": 351
|
||||
},
|
||||
{
|
||||
"icon": {
|
||||
@@ -396,9 +393,9 @@
|
||||
"code": 59660,
|
||||
"name": "exit-full-screen"
|
||||
},
|
||||
"setIdx": 1,
|
||||
"setId": 1,
|
||||
"iconIdx": 13
|
||||
"setIdx": 0,
|
||||
"setId": 2,
|
||||
"iconIdx": 352
|
||||
},
|
||||
{
|
||||
"icon": {
|
||||
@@ -422,9 +419,9 @@
|
||||
"code": 59658,
|
||||
"name": "star-full"
|
||||
},
|
||||
"setIdx": 1,
|
||||
"setId": 1,
|
||||
"iconIdx": 14
|
||||
"setIdx": 0,
|
||||
"setId": 2,
|
||||
"iconIdx": 364
|
||||
},
|
||||
{
|
||||
"icon": {
|
||||
@@ -448,9 +445,9 @@
|
||||
"code": 59661,
|
||||
"name": "security"
|
||||
},
|
||||
"setIdx": 1,
|
||||
"setId": 1,
|
||||
"iconIdx": 15
|
||||
"setIdx": 0,
|
||||
"setId": 2,
|
||||
"iconIdx": 474
|
||||
},
|
||||
{
|
||||
"icon": {
|
||||
@@ -474,9 +471,9 @@
|
||||
"code": 59662,
|
||||
"name": "security-locked"
|
||||
},
|
||||
"setIdx": 1,
|
||||
"setId": 1,
|
||||
"iconIdx": 16
|
||||
"setIdx": 0,
|
||||
"setId": 2,
|
||||
"iconIdx": 475
|
||||
},
|
||||
{
|
||||
"icon": {
|
||||
@@ -500,9 +497,9 @@
|
||||
"code": 59663,
|
||||
"name": "reload"
|
||||
},
|
||||
"setIdx": 1,
|
||||
"setId": 1,
|
||||
"iconIdx": 17
|
||||
"setIdx": 0,
|
||||
"setId": 2,
|
||||
"iconIdx": 483
|
||||
},
|
||||
{
|
||||
"icon": {
|
||||
@@ -526,9 +523,9 @@
|
||||
"code": 59664,
|
||||
"name": "microphone"
|
||||
},
|
||||
"setIdx": 1,
|
||||
"setId": 1,
|
||||
"iconIdx": 18
|
||||
"setIdx": 0,
|
||||
"setId": 2,
|
||||
"iconIdx": 493
|
||||
},
|
||||
{
|
||||
"icon": {
|
||||
@@ -552,9 +549,9 @@
|
||||
"code": 59665,
|
||||
"name": "mic-empty"
|
||||
},
|
||||
"setIdx": 1,
|
||||
"setId": 1,
|
||||
"iconIdx": 19
|
||||
"setIdx": 0,
|
||||
"setId": 2,
|
||||
"iconIdx": 494
|
||||
},
|
||||
{
|
||||
"icon": {
|
||||
@@ -578,9 +575,9 @@
|
||||
"code": 59666,
|
||||
"name": "mic-disabled"
|
||||
},
|
||||
"setIdx": 1,
|
||||
"setId": 1,
|
||||
"iconIdx": 20
|
||||
"setIdx": 0,
|
||||
"setId": 2,
|
||||
"iconIdx": 495
|
||||
},
|
||||
{
|
||||
"icon": {
|
||||
@@ -604,9 +601,9 @@
|
||||
"code": 59678,
|
||||
"name": "raised-hand"
|
||||
},
|
||||
"setIdx": 1,
|
||||
"setId": 1,
|
||||
"iconIdx": 21
|
||||
"setIdx": 0,
|
||||
"setId": 2,
|
||||
"iconIdx": 540
|
||||
},
|
||||
{
|
||||
"icon": {
|
||||
@@ -630,9 +627,9 @@
|
||||
"code": 59675,
|
||||
"name": "contactList"
|
||||
},
|
||||
"setIdx": 1,
|
||||
"setId": 1,
|
||||
"iconIdx": 22
|
||||
"setIdx": 0,
|
||||
"setId": 2,
|
||||
"iconIdx": 550
|
||||
},
|
||||
{
|
||||
"icon": {
|
||||
@@ -656,9 +653,9 @@
|
||||
"code": 59667,
|
||||
"name": "link"
|
||||
},
|
||||
"setIdx": 1,
|
||||
"setId": 1,
|
||||
"iconIdx": 23
|
||||
"setIdx": 0,
|
||||
"setId": 2,
|
||||
"iconIdx": 560
|
||||
},
|
||||
{
|
||||
"icon": {
|
||||
@@ -682,9 +679,9 @@
|
||||
"code": 59668,
|
||||
"name": "shared-video"
|
||||
},
|
||||
"setIdx": 1,
|
||||
"setId": 1,
|
||||
"iconIdx": 24
|
||||
"setIdx": 0,
|
||||
"setId": 2,
|
||||
"iconIdx": 591
|
||||
},
|
||||
{
|
||||
"icon": {
|
||||
@@ -708,9 +705,9 @@
|
||||
"code": 59669,
|
||||
"name": "settings"
|
||||
},
|
||||
"setIdx": 1,
|
||||
"setId": 1,
|
||||
"iconIdx": 25
|
||||
"setIdx": 0,
|
||||
"setId": 2,
|
||||
"iconIdx": 666
|
||||
},
|
||||
{
|
||||
"icon": {
|
||||
@@ -734,35 +731,9 @@
|
||||
"code": 59670,
|
||||
"name": "star"
|
||||
},
|
||||
"setIdx": 1,
|
||||
"setId": 1,
|
||||
"iconIdx": 26
|
||||
},
|
||||
{
|
||||
"icon": {
|
||||
"paths": [
|
||||
"M640 662l150-150-150-150v108h-256v-108l-150 150 150 150v-108h256v108zM854 170c46 0 84 40 84 86v512c0 46-38 86-84 86h-684c-46 0-84-40-84-86v-512c0-46 38-86 84-86h136l78-84h256l78 84h136z"
|
||||
],
|
||||
"isMulticolor": false,
|
||||
"isMulticolor2": false,
|
||||
"tags": [
|
||||
"switch_camera"
|
||||
],
|
||||
"grid": 0,
|
||||
"attrs": []
|
||||
},
|
||||
"attrs": [],
|
||||
"properties": {
|
||||
"id": 741,
|
||||
"order": 108,
|
||||
"ligatures": "switch_camera",
|
||||
"prevSize": 32,
|
||||
"code": 59681,
|
||||
"name": "switch-camera"
|
||||
},
|
||||
"setIdx": 1,
|
||||
"setId": 1,
|
||||
"iconIdx": 27
|
||||
"setIdx": 0,
|
||||
"setId": 2,
|
||||
"iconIdx": 718
|
||||
},
|
||||
{
|
||||
"icon": {
|
||||
@@ -786,9 +757,9 @@
|
||||
"code": 59671,
|
||||
"name": "share-desktop"
|
||||
},
|
||||
"setIdx": 1,
|
||||
"setId": 1,
|
||||
"iconIdx": 28
|
||||
"setIdx": 0,
|
||||
"setId": 2,
|
||||
"iconIdx": 784
|
||||
},
|
||||
{
|
||||
"icon": {
|
||||
@@ -812,9 +783,9 @@
|
||||
"code": 59672,
|
||||
"name": "camera"
|
||||
},
|
||||
"setIdx": 1,
|
||||
"setId": 1,
|
||||
"iconIdx": 29
|
||||
"setIdx": 0,
|
||||
"setId": 2,
|
||||
"iconIdx": 799
|
||||
},
|
||||
{
|
||||
"icon": {
|
||||
@@ -838,9 +809,9 @@
|
||||
"code": 59673,
|
||||
"name": "camera-disabled"
|
||||
},
|
||||
"setIdx": 1,
|
||||
"setId": 1,
|
||||
"iconIdx": 30
|
||||
"setIdx": 0,
|
||||
"setId": 2,
|
||||
"iconIdx": 800
|
||||
},
|
||||
{
|
||||
"icon": {
|
||||
@@ -864,9 +835,9 @@
|
||||
"code": 59674,
|
||||
"name": "volume"
|
||||
},
|
||||
"setIdx": 1,
|
||||
"setId": 1,
|
||||
"iconIdx": 31
|
||||
"setIdx": 0,
|
||||
"setId": 2,
|
||||
"iconIdx": 822
|
||||
},
|
||||
{
|
||||
"icon": {
|
||||
@@ -914,7 +885,7 @@
|
||||
},
|
||||
"setIdx": 1,
|
||||
"setId": 1,
|
||||
"iconIdx": 32
|
||||
"iconIdx": 0
|
||||
},
|
||||
{
|
||||
"icon": {
|
||||
@@ -985,7 +956,7 @@
|
||||
},
|
||||
"setIdx": 1,
|
||||
"setId": 1,
|
||||
"iconIdx": 33
|
||||
"iconIdx": 4
|
||||
},
|
||||
{
|
||||
"icon": {
|
||||
@@ -1012,7 +983,7 @@
|
||||
},
|
||||
"setIdx": 1,
|
||||
"setId": 1,
|
||||
"iconIdx": 34
|
||||
"iconIdx": 12
|
||||
},
|
||||
{
|
||||
"icon": {
|
||||
@@ -1040,7 +1011,7 @@
|
||||
},
|
||||
"setIdx": 1,
|
||||
"setId": 1,
|
||||
"iconIdx": 35
|
||||
"iconIdx": 13
|
||||
},
|
||||
{
|
||||
"icon": {
|
||||
@@ -1068,7 +1039,7 @@
|
||||
},
|
||||
"setIdx": 1,
|
||||
"setId": 1,
|
||||
"iconIdx": 36
|
||||
"iconIdx": 22
|
||||
}
|
||||
],
|
||||
"height": 1024,
|
||||
|
||||
BIN
images/dropdownPointer.png
Normal file
|
After Width: | Height: | Size: 234 B |
BIN
images/leftDropdownPointer.png
Normal file
|
After Width: | Height: | Size: 611 B |
@@ -1,182 +0,0 @@
|
||||
<?xml version="1.0" encoding="UTF-8" standalone="no"?>
|
||||
<!-- Created with Inkscape (http://www.inkscape.org/) -->
|
||||
|
||||
<svg
|
||||
xmlns:dc="http://purl.org/dc/elements/1.1/"
|
||||
xmlns:cc="http://creativecommons.org/ns#"
|
||||
xmlns:rdf="http://www.w3.org/1999/02/22-rdf-syntax-ns#"
|
||||
xmlns:svg="http://www.w3.org/2000/svg"
|
||||
xmlns="http://www.w3.org/2000/svg"
|
||||
xmlns:sodipodi="http://sodipodi.sourceforge.net/DTD/sodipodi-0.dtd"
|
||||
xmlns:inkscape="http://www.inkscape.org/namespaces/inkscape"
|
||||
width="210mm"
|
||||
height="297mm"
|
||||
viewBox="0 0 744.09448819 1052.3622047"
|
||||
id="svg3526"
|
||||
version="1.1"
|
||||
inkscape:version="0.91 r13725"
|
||||
inkscape:export-filename="/Users/ystamcheva/Dropbox/Designs/appLogo.png"
|
||||
inkscape:export-xdpi="90"
|
||||
inkscape:export-ydpi="90"
|
||||
sodipodi:docname="logo-blue.svg">
|
||||
<defs
|
||||
id="defs3528" />
|
||||
<sodipodi:namedview
|
||||
id="base"
|
||||
pagecolor="#ffffff"
|
||||
bordercolor="#666666"
|
||||
borderopacity="1.0"
|
||||
inkscape:pageopacity="0.0"
|
||||
inkscape:pageshadow="2"
|
||||
inkscape:zoom="0.49497475"
|
||||
inkscape:cx="817.30793"
|
||||
inkscape:cy="496.00851"
|
||||
inkscape:document-units="px"
|
||||
inkscape:current-layer="layer1"
|
||||
showgrid="false"
|
||||
inkscape:window-width="1440"
|
||||
inkscape:window-height="851"
|
||||
inkscape:window-x="0"
|
||||
inkscape:window-y="1"
|
||||
inkscape:window-maximized="1" />
|
||||
<metadata
|
||||
id="metadata3531">
|
||||
<rdf:RDF>
|
||||
<cc:Work
|
||||
rdf:about="">
|
||||
<dc:format>image/svg+xml</dc:format>
|
||||
<dc:type
|
||||
rdf:resource="http://purl.org/dc/dcmitype/StillImage" />
|
||||
<dc:title></dc:title>
|
||||
</cc:Work>
|
||||
</rdf:RDF>
|
||||
</metadata>
|
||||
<g
|
||||
inkscape:label="Layer 1"
|
||||
inkscape:groupmode="layer"
|
||||
id="layer1">
|
||||
<g
|
||||
id="g4181">
|
||||
<g
|
||||
style="fill:#17a0db;fill-opacity:1"
|
||||
transform="translate(43.272677,-6.8248629)"
|
||||
id="g33">
|
||||
<path
|
||||
d="m 257.311,591.057 c 27.544,0 85.707,-16.445 124.179,-27.332 5.595,-1.575 10.81,-3.049 15.549,-4.371 0.767,-0.211 1.51,-0.403 2.213,-0.579 -2.161,-2.139 -5.755,-5.387 -11.612,-10.295 -25.628,-17.369 -49.827,-25.456 -76.146,-25.456 -5.741,0 -11.707,0.352 -18.208,1.088 -22.283,2.535 -40.848,7.845 -49.767,10.39 -4.521,1.296 -5.883,1.683 -7.292,1.683 -2.688,0 -4.997,-1.599 -5.9,-4.069 -0.904,-2.483 -0.13,-5.223 1.969,-6.981 l 0.127,-0.102 c 15.379,-12.883 44.032,-36.866 98.39,-47.582 9.428,-1.853 19.514,-2.796 29.968,-2.796 24.334,0 49.53,5.026 74.869,14.925 34.511,13.474 58.094,30.771 77.062,44.67 10.211,7.489 19.03,13.959 26.705,17.516 1.961,0.912 2.979,1.169 3.453,1.236 0.349,-0.452 1.106,-1.7 2.219,-4.974 0.298,-0.867 2.453,-10.019 -13.007,-62.071 -8.985,-30.217 -19.822,-61.077 -25.465,-74.778 -10.916,-26.509 -8.237,-45.296 -4.877,-56.284 -9.248,3.399 -18.701,8.688 -28.646,15.993 l -0.62,0.458 c -4.969,3.684 -10.031,7.853 -15.482,12.725 -32.074,28.718 -56.104,43.69 -71.455,44.504 l -0.423,0.021 -0.421,-0.036 c -13.524,-1.148 -34.019,-20.834 -42.403,-30.801 -1.743,-1.169 -3.729,-1.699 -6.35,-1.699 -2.632,0 -5.583,0.553 -8.438,1.095 -2.077,0.394 -4.218,0.795 -6.341,1.01 -6.767,0.679 -16.252,2.867 -25.406,4.974 -4.413,1.014 -8.967,2.063 -13.13,2.922 -0.079,0.013 -1.866,0.382 -5.06,1.224 -22.624,6.693 -39.673,14.372 -48.012,21.628 -0.091,0.079 -0.36,0.288 -0.789,0.603 -5.64,4.009 -19.199,15.447 -23.29,34.907 l -0.043,0.162 c -8.541,35.837 4.408,80.28 21.615,105.666 8.093,11.932 16.814,19.376 23.944,20.42 1.775,0.252 3.905,0.386 6.321,0.386 z"
|
||||
id="path35"
|
||||
inkscape:connector-curvature="0"
|
||||
style="fill:#17a0db;fill-opacity:1" />
|
||||
</g>
|
||||
<g
|
||||
style="fill:#17a0db;fill-opacity:1"
|
||||
transform="translate(43.272677,-6.8248629)"
|
||||
id="g37">
|
||||
<path
|
||||
d="m 383.729,400.995 c 0.549,0.108 1.191,0.162 1.9,0.162 14.785,0 47.804,-21.408 53.912,-31.205 l 0.486,-0.78 0.694,-0.611 c 2.083,-2.056 8.099,-12.885 11.019,-19.367 -31.312,-9.394 -34.767,-26.347 -37.821,-41.41 -0.355,-1.749 -0.667,-3.324 -0.946,-4.732 -0.357,-1.842 -0.731,-3.713 -1.052,-5.159 -46.646,15.471 -60.905,24.154 -68.687,30.611 -4.027,3.345 -6.398,12.858 5.215,39.189 5.932,13.422 26.386,31.591 35.28,33.302 z"
|
||||
id="path39"
|
||||
inkscape:connector-curvature="0"
|
||||
style="fill:#17a0db;fill-opacity:1" />
|
||||
</g>
|
||||
<path
|
||||
style="fill:#17a0db;fill-opacity:1"
|
||||
inkscape:connector-curvature="0"
|
||||
id="path43"
|
||||
d="m 183.03568,710.19014 c -5.799,-6.834 -8.258,-15.447 -7.293,-25.624 4.105,-49.397 -1.525,-61.33 -4.132,-64.162 -0.629,-0.685 -0.969,-0.685 -1.238,-0.685 -0.101,0 -0.195,0.006 -0.296,0.016 -4.84,1.157 -37.441,23.198 -44.638,89.005 -3.471,31.758 2.611,72.542 7.794,97.348 4.165,-14.646 10.742,-30.779 23.483,-47.384 11.862,-15.444 24.801,-27.623 40.852,-38.298 -4.99,-2.075 -10.346,-5.274 -14.532,-10.216 z" />
|
||||
<g
|
||||
style="fill:#17a0db;fill-opacity:1"
|
||||
transform="translate(43.272677,-6.8248629)"
|
||||
id="g45">
|
||||
<path
|
||||
d="m 485.028,154.141 c -3.896,25.701 -10.239,50.115 -22.077,75.883 12.904,-14.609 20.445,-30.481 22.971,-48.296 1.051,-7.38 2.045,-14.439 -0.894,-27.587 z"
|
||||
id="path47"
|
||||
inkscape:connector-curvature="0"
|
||||
style="fill:#17a0db;fill-opacity:1" />
|
||||
</g>
|
||||
<g
|
||||
style="fill:#17a0db;fill-opacity:1"
|
||||
transform="translate(43.272677,-6.8248629)"
|
||||
id="g49">
|
||||
<path
|
||||
d="m 413.102,273.797 c 23.135,-20.915 37.22,-55.455 43.078,-75.971 -20.149,19.407 -44.636,29.82 -60.351,36.512 -5.412,2.308 -10.08,4.295 -12.878,5.926 -1.178,0.685 -2.367,1.374 -3.571,2.069 -9.533,5.515 -23.924,13.85 -26.022,18.987 l -0.06,0.167 -0.078,0.165 c -6.529,13.72 -10.208,34.352 -11.387,46.184 15.135,-9.242 30.738,-15.41 43.699,-20.529 12.03,-4.753 22.432,-8.863 27.57,-13.51 z"
|
||||
id="path51"
|
||||
inkscape:connector-curvature="0"
|
||||
style="fill:#17a0db;fill-opacity:1" />
|
||||
</g>
|
||||
<g
|
||||
style="fill:#17a0db;fill-opacity:1"
|
||||
transform="translate(43.272677,-6.8248629)"
|
||||
id="g53">
|
||||
<path
|
||||
d="m 436.439,291.877 c -0.141,0.357 -0.292,0.695 -0.455,1.017 -3.833,11.143 1.446,26.3 11.227,32.017 2.602,1.522 5.132,2.452 7.559,2.772 0.334,0.014 0.666,0.027 1.001,0.027 7.601,0 13.801,-5.56 18.4,-16.519 2.896,-8.34 3.308,-18.23 1.125,-27.158 -1.696,-6.936 -6.084,-15.215 -8.88,-19.343 -5.219,3.582 -15.533,11.462 -22.615,17.716 -4.946,4.777 -6.733,7.785 -7.362,9.471 z"
|
||||
id="path55"
|
||||
inkscape:connector-curvature="0"
|
||||
style="fill:#17a0db;fill-opacity:1" />
|
||||
</g>
|
||||
<g
|
||||
style="fill:#17a0db;fill-opacity:1"
|
||||
transform="translate(43.272677,-6.8248629)"
|
||||
id="g57">
|
||||
<path
|
||||
d="m 501.845,575.103 c 8.403,-2.29 15.076,-4.165 19.998,-5.623 -10.137,-7.061 -21.871,-15.846 -37.823,-28.253 -39.096,-30.404 -81.019,-45.826 -124.587,-45.826 -23.861,0 -44.647,4.592 -61.098,10.151 4.101,-0.255 8.271,-0.377 12.554,-0.377 5.088,0 10.42,0.179 15.842,0.541 16.949,1.136 60.616,8.845 100.106,55.931 7.956,9.469 16.507,17.307 40.828,17.307 8.679,0 18.796,-0.967 30.913,-2.959 0.749,-0.209 1.882,-0.518 3.267,-0.892 z"
|
||||
id="path59"
|
||||
inkscape:connector-curvature="0"
|
||||
style="fill:#17a0db;fill-opacity:1" />
|
||||
</g>
|
||||
<g
|
||||
style="fill:#17a0db;fill-opacity:1"
|
||||
transform="translate(43.272677,-6.8248629)"
|
||||
id="g61">
|
||||
<path
|
||||
d="m 557.268,369.949 c -7.755,-12.043 -17.498,-19.524 -25.41,-19.524 -1.464,0 -2.862,0.258 -4.154,0.765 -4.239,1.672 -10.952,21.042 -7.979,35.126 2.023,9.582 13.67,41.96 19.262,57.52 2.142,5.958 3.18,8.869 3.527,9.951 0.275,0.853 0.67,2.077 1.17,3.621 4.517,13.765 16.111,49.145 19.562,77.793 7.175,-30.554 11.239,-67.36 9.647,-111.409 -0.723,-20.199 -6.274,-39.323 -15.625,-53.843 z"
|
||||
id="path63"
|
||||
inkscape:connector-curvature="0"
|
||||
style="fill:#17a0db;fill-opacity:1" />
|
||||
</g>
|
||||
<g
|
||||
style="fill:#17a0db;fill-opacity:1"
|
||||
transform="translate(43.272677,-6.8248629)"
|
||||
id="g65">
|
||||
<path
|
||||
d="m 412.08,575.289 c -0.153,-0.2 -0.3,-0.397 -0.445,-0.585 -0.614,0.1 -1.616,0.319 -3.185,0.776 l -0.657,0.197 c -8.011,2.95 -22.707,7.908 -39.694,13.64 -20.387,6.87 -43.477,14.659 -62.808,21.595 -24.596,9.165 -32.572,12.781 -35.073,14.048 -0.454,1.218 -0.963,2.772 -1.53,4.486 -5.817,17.705 -19.139,58.23 -84.831,86.562 13.568,13.744 43.101,38.415 101.24,38.415 5.035,0 10.258,-0.188 15.494,-0.566 43.896,-3.121 85.158,-22.544 116.206,-54.673 28.233,-29.21 44.259,-65.641 44.507,-100.76 -6.871,-0.571 -18.519,-2.281 -29.301,-7.4 -0.125,-0.061 -12.447,-6.002 -19.923,-15.735 z"
|
||||
id="path67"
|
||||
inkscape:connector-curvature="0"
|
||||
style="fill:#17a0db;fill-opacity:1" />
|
||||
</g>
|
||||
<g
|
||||
style="fill:#17a0db;fill-opacity:1"
|
||||
transform="translate(43.272677,-6.8248629)"
|
||||
id="g69">
|
||||
<path
|
||||
d="m 162.104,639.109 c -0.122,10.334 -1.489,20.245 -2.82,29.907 -0.716,5.216 -1.464,10.615 -2.014,16.041 -0.746,10.914 1.612,14.717 2.659,15.829 0.571,0.629 1.513,1.346 3.536,1.346 1.558,0 3.418,-0.432 5.383,-1.251 19.507,-8.176 38.032,-22.367 46.937,-30.243 -13.668,-6.095 -34.689,-19.26 -53.681,-31.629 z"
|
||||
id="path71"
|
||||
inkscape:connector-curvature="0"
|
||||
style="fill:#17a0db;fill-opacity:1" />
|
||||
</g>
|
||||
<g
|
||||
style="fill:#17a0db;fill-opacity:1"
|
||||
transform="translate(43.272677,-6.8248629)"
|
||||
id="g73">
|
||||
<path
|
||||
d="m 484.26,598.224 c -0.552,7.258 -1.737,20.949 -3.631,31.378 -2.295,12.629 -6.095,23.31 -8.305,28.889 3.945,3.648 7.878,7.228 10.429,9.488 10.265,-6.718 43.961,-32.297 67.208,-90.368 -7.447,5.03 -17.906,9.456 -31.465,13.332 -13.797,3.929 -27.204,6.229 -34.236,7.281 z"
|
||||
id="path75"
|
||||
inkscape:connector-curvature="0"
|
||||
style="fill:#17a0db;fill-opacity:1" />
|
||||
</g>
|
||||
<g
|
||||
transform="translate(43.272677,-6.8248629)"
|
||||
id="g85"
|
||||
style="fill:#17a0db;fill-opacity:1">
|
||||
<path
|
||||
style="fill:#17a0db;fill-opacity:1"
|
||||
inkscape:connector-curvature="0"
|
||||
id="path87"
|
||||
d="M 627.562,350.519 C 613.5,321.124 593.893,306.283 580.351,297.677 568.965,290.444 555.872,285.188 541.339,282 c -1.622,-10.158 -4.397,-20.542 -8.198,-30.646 24.507,-36.531 30.407,-77.605 17.008,-119.213 C 539.858,100.151 531.868,79.524 524.996,67.213 510.15,40.585 489.58,34.997 474.936,34.997 c -15.09,0 -29.538,6.412 -39.667,17.61 -10.37,11.462 -15.213,26.462 -13.634,42.228 1.349,13.446 -2.178,37.872 -4.519,46.594 -0.04,0.117 -4.202,11.776 -35.168,26.784 -0.746,0.268 -2.332,0.811 -4.773,1.629 -17.812,5.965 -50.913,17.062 -72.963,46.219 -16.847,20.407 -20.985,40.629 -25.766,64.036 -2.858,13.955 -5.846,32.187 -5.105,53.745 -55.35,12.291 -95.226,37.338 -118.609,74.54 -24.203,38.52 -28.402,86.272 -12.468,141.993 l 0.14,0.414 c 0.292,1.014 0.6,2.024 0.921,3.03 -2.718,-0.466 -5.465,-0.858 -8.285,-1.169 -2.469,-0.284 -5.015,-0.42 -7.54,-0.42 -27.636,0 -57.043,17.371 -78.666,46.474 -16.427,22.098 -36.156,61.131 -36.852,121.593 -0.523,44.905 4.279,86.306 14.283,123.054 7.461,27.381 15.784,44.202 18.979,50.09 l 67.793,127.079 31.06,-140.731 c 10.6,-47.935 21.066,-68.283 34.571,-81.732 31.425,18.938 68.541,28.901 107.941,28.901 43.919,0 89.715,-12.667 128.934,-35.662 25.477,-14.954 47.193,-33.324 64.629,-54.658 0.236,0 0.469,0 0.704,0 l 1.857,-0.038 c 10.782,-0.365 25.522,-5.697 40.434,-14.63 12.421,-7.433 31.147,-21.108 49.946,-44.064 18.945,-23.155 34.402,-51.324 45.926,-83.731 13.5,-37.939 21.717,-82.115 24.404,-131.272 3.253,-45.723 -2.078,-83.533 -15.881,-112.384 z m -31.124,109.427 c -2.415,44.805 -9.745,84.66 -21.764,118.441 -9.713,27.302 -22.502,50.739 -38.005,69.69 -26.696,32.611 -52.783,41.355 -55.551,41.465 l -0.22,0 c -2.528,0 -4.012,-1.032 -11.095,-5.988 -1.979,-1.379 -4.969,-3.467 -7.436,-5.075 -14.813,28.811 -39.145,53.701 -70.659,72.185 -32.098,18.824 -69.432,29.202 -105.1,29.202 -42.352,0 -79.532,-13.979 -107.842,-40.493 -38.621,24.556 -61.833,45.044 -80.652,130.273 l -3.562,16.157 -7.787,-14.59 C 84.8,867.621 78.058,854.32 71.708,830.982 62.852,798.444 58.598,761.384 59.071,720.842 c 0.944,-80.909 44.373,-121.518 68.427,-121.518 0.792,0 1.578,0.039 2.328,0.128 22.8,2.551 37.699,12.402 64.745,30.291 2.796,1.853 5.74,3.8 8.843,5.838 9.69,6.36 23.387,14.125 26.835,14.791 6.562,-0.381 12.986,-15.079 14.853,-28.713 0.114,-0.829 0.226,-1.598 0.334,-2.315 0.147,-1.612 0.227,-3.03 0.27,-4.194 -1.144,-0.399 -2.333,-0.869 -3.547,-1.403 l -0.27,-0.091 c -17.012,-5.857 -41.868,-34.625 -54.378,-76.385 -12.081,-42.21 -9.691,-77.122 7.099,-103.83 27.221,-43.328 86.307,-53.515 105.849,-56.861 6.109,-1.214 12.498,-2.351 18.999,-3.378 3.035,-0.762 5.11,-1.399 6.449,-1.978 0.58,-0.403 0.835,-0.833 0.439,-2.403 l 0.53,-0.148 -0.513,0.115 c -0.237,-1.065 -0.565,-2.311 -0.941,-3.753 -0.521,-1.997 -1.103,-4.256 -1.705,-6.936 -6.05,-27.141 -2.962,-49.884 0.863,-68.559 4.297,-21.019 6.678,-32.656 16.605,-44.279 13.152,-18.103 36.803,-26.025 50.953,-30.77 3.948,-1.322 7.359,-2.462 9.331,-3.412 43.344,-20.789 57.145,-42.646 61.091,-57.318 3.127,-11.642 8.084,-42.253 5.931,-63.63 -0.239,-2.425 0.326,-4.421 1.695,-5.935 1.215,-1.341 2.942,-2.104 4.748,-2.104 4.061,0 9.623,0 30.377,64.478 10.949,33.996 2.785,65.868 -24.244,94.74 -0.347,0.375 -0.7,0.742 -1.04,1.095 -0.738,0.76 -1.848,1.909 -1.999,2.326 0.006,0 -0.048,1.042 1.755,4.031 11.425,18.864 17.633,42.323 15.832,59.763 -0.429,4.062 -1.206,7.971 -1.879,11.411 -0.4,1.968 -0.879,4.377 -1.126,6.241 0.111,0 0.226,0 0.347,0 3.088,-0.327 7.867,-0.7 13.628,-0.7 13.556,0 32.969,2.077 48.503,11.951 9.382,5.952 21.255,15.137 29.981,33.404 10.281,21.472 14.096,51.453 11.369,89.114 z" />
|
||||
</g>
|
||||
</g>
|
||||
<path
|
||||
style="fill:#ffffff"
|
||||
d=""
|
||||
id="path3618"
|
||||
inkscape:connector-curvature="0" />
|
||||
</g>
|
||||
</svg>
|
||||
|
Before Width: | Height: | Size: 14 KiB |
98
index.html
@@ -1,8 +1,7 @@
|
||||
<html itemscope itemtype="http://schema.org/Product" prefix="og: http://ogp.me/ns#" xmlns="http://www.w3.org/1999/html">
|
||||
<head>
|
||||
<meta charset="utf-8">
|
||||
<meta charset="utf-8" />
|
||||
<meta http-equiv="content-type" content="text/html;charset=utf-8">
|
||||
<meta name="viewport" content="width=device-width, initial-scale=1.0">
|
||||
<!--#include virtual="base.html" -->
|
||||
<script>
|
||||
window.indexLoadedTime = window.performance.now();
|
||||
@@ -29,95 +28,9 @@
|
||||
&& criticalFiles.some(
|
||||
function(file) { return fileRef.indexOf(file) !== -1 })) {
|
||||
window.onload = function() {
|
||||
// The whole complex part below implements page reloads with
|
||||
// "exponential backoff". The retry attempt is passes as
|
||||
// "rCounter" query parameter
|
||||
var href = window.location.href;
|
||||
|
||||
var retryMatch = href.match(/.+(\?|&)rCounter=(\d+)/);
|
||||
var retryCountStr = retryMatch ? retryMatch[2] : "0";
|
||||
var retryCount = Number.parseInt(retryCountStr);
|
||||
|
||||
if (retryMatch == null) {
|
||||
var separator = href.indexOf("?") === -1 ? "?" : "&";
|
||||
var hashIdx = href.indexOf("#");
|
||||
|
||||
if (hashIdx === -1) {
|
||||
href += separator + "rCounter=1";
|
||||
} else {
|
||||
var hashPart = href.substr(hashIdx);
|
||||
|
||||
href = href.substr(0, hashIdx)
|
||||
+ separator + "rCounter=1" + hashPart;
|
||||
}
|
||||
} else {
|
||||
var separator = retryMatch[1];
|
||||
|
||||
href = href.replace(
|
||||
/(\?|&)rCounter=(\d+)/,
|
||||
separator + "rCounter=" + (retryCount + 1));
|
||||
}
|
||||
|
||||
var delay = Math.pow(2, retryCount) * 2000;
|
||||
if (isNaN(delay) || delay < 2000 || delay > 60000)
|
||||
delay = 10000;
|
||||
|
||||
var showMoreText = "show more";
|
||||
var showLessText = "show less";
|
||||
|
||||
document.body.innerHTML
|
||||
= "<div style='"
|
||||
+ "position: absolute;top: 50%;left: 50%;"
|
||||
+ "text-align: center;"
|
||||
+ "font-size: medium;"
|
||||
+ "font-weight: 400;"
|
||||
+ "transform: translate(-50%, -50%)'>"
|
||||
+ "Uh oh! We couldn't fully download everything we needed :(" // jshint ignore:line
|
||||
+ "<br/> "
|
||||
+ "We will try again shortly. In the mean time, check for problems with your Internet connection!" // jshint ignore:line
|
||||
+ "<br/><br/> "
|
||||
+ "<div id='moreInfo' style='"
|
||||
+ "display: none;'>" + "Missing " + fileRef
|
||||
+ "<br/><br/></div>"
|
||||
+ "<a id='showMore' style='"
|
||||
+ "text-decoration: underline;"
|
||||
+ "font-size:small;"
|
||||
+ "cursor: pointer'>" + showMoreText + "</a>"
|
||||
+ " "
|
||||
+ "<a href='" + href + "' style='"
|
||||
+ "text-decoration: underline;"
|
||||
+ "font-size:small;"
|
||||
+ "'>reload now</a>"
|
||||
+ "</div>";
|
||||
|
||||
var showMoreElem = document.getElementById("showMore");
|
||||
showMoreElem.addEventListener('click', function () {
|
||||
var moreInfoElem
|
||||
= document.getElementById("moreInfo");
|
||||
|
||||
if (showMoreElem.innerHTML === showMoreText) {
|
||||
moreInfoElem.setAttribute(
|
||||
"style",
|
||||
"display: block;"
|
||||
+ "color:#FF991F;"
|
||||
+ "font-size:small;"
|
||||
+ "user-select:text;");
|
||||
showMoreElem.innerHTML = showLessText;
|
||||
}
|
||||
else {
|
||||
moreInfoElem.setAttribute(
|
||||
"style", "display: none;");
|
||||
showMoreElem.innerHTML = showMoreText;
|
||||
}
|
||||
});
|
||||
|
||||
window.setTimeout(
|
||||
function () { window.location.replace(href); }, delay);
|
||||
|
||||
// Call extra handler if defined.
|
||||
if (typeof postLoadErrorHandler === "function") {
|
||||
postLoadErrorHandler();
|
||||
}
|
||||
= "The application failed to load, missing file: "
|
||||
+ fileRef;
|
||||
};
|
||||
window.removeEventListener(
|
||||
'error', loadErrHandler, true /* capture phase */);
|
||||
@@ -127,15 +40,14 @@
|
||||
'error', loadErrHandler, true /* capture phase type of listener */);
|
||||
</script>
|
||||
<script><!--#include virtual="/config.js" --></script><!-- adapt to your needs, i.e. set hosts and bosh path -->
|
||||
<script src="static/utils.js?v=1"></script>
|
||||
<script src="utils.js?v=1"></script>
|
||||
<!--#include virtual="connection_optimization/connection_optimization.html" -->
|
||||
<script src="connection_optimization/do_external_connect.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" -->
|
||||
<link rel="stylesheet" href="css/all.css">
|
||||
<link rel="stylesheet" href="css/all.css"/>
|
||||
<!--#include virtual="plugin.head.html" -->
|
||||
</head>
|
||||
<body>
|
||||
|
||||