Merge branch 'master' into 'development'
Master See merge request Cloud_Solution/diplomatic-quarter!230merge-requests/232/merge
@ -0,0 +1,13 @@
|
|||||||
|
{
|
||||||
|
// Use IntelliSense to learn about possible attributes.
|
||||||
|
// Hover to view descriptions of existing attributes.
|
||||||
|
// For more information, visit: https://go.microsoft.com/fwlink/?linkid=830387
|
||||||
|
"version": "0.2.0",
|
||||||
|
"configurations": [
|
||||||
|
{
|
||||||
|
"name": "Flutter",
|
||||||
|
"request": "launch",
|
||||||
|
"type": "dart"
|
||||||
|
}
|
||||||
|
]
|
||||||
|
}
|
||||||
@ -0,0 +1,16 @@
|
|||||||
|
-----BEGIN CERTIFICATE REQUEST-----
|
||||||
|
MIICkDCCAXgCAQAwSzEjMCEGCSqGSIb3DQEJARYUaGFyb29uNjEzOEBnbWFpbC5j
|
||||||
|
b20xFzAVBgNVBAMMDk1vaGFtZWQgTWVrYXd5MQswCQYDVQQGEwJBRTCCASIwDQYJ
|
||||||
|
KoZIhvcNAQEBBQADggEPADCCAQoCggEBALcPrk09MmhQhRNe8LYdaeN4mYtoKJg3
|
||||||
|
SndMLgpxnaRqP7a6f4sp118wCFZsTXnwhPVP4DzmXWc2AzZtsusmhdw1tzNFtme0
|
||||||
|
PtEjDXIPI2lHU3Zhi2zukZdAVxF+uNi3pcp0axina60ZQciIfb/7Fx6hNbqpk90E
|
||||||
|
O8a2Ob17Wq/ZTYIP4H7ZGydUe2ra9QyDtjmGj9vpEv+xXYWX685sgEylTG14DSOP
|
||||||
|
ozGsQmaf+QCMbCT3osq7idWc1IQ+3Oed0kUTx1jmRtZwPzQkJJ1Bx3vYSXN/EOlb
|
||||||
|
u+ei1Nqtc14aVCYvmcuvGDtMyRtw6w+syCw2CpJCPGNkxNz+EH9h+EUCAwEAAaAA
|
||||||
|
MA0GCSqGSIb3DQEBCwUAA4IBAQBYdu2AaZY6kReuT1Xp8ktlyPfjBRKhPPChuaeR
|
||||||
|
tFnYMsJtG0aIA/xOu4/RYDgmL92seimULXd9DIPvkJ2DuaB+bdfGTw0qXUlihkm8
|
||||||
|
ui5O0L2F9OZbQxJogvTmrMsKnkoR27O5vyfCn9VMOLk3x1nyEzAXIj/5GHWw9T6t
|
||||||
|
r65jPUOfm6ikiZtICBzSaTPBtyfZB8mrbwG2dpOvVNSa1dj3xip4L8CL6TxH+qM3
|
||||||
|
+N90QFYjvjphJkpn2Kt0ow9IyIyeqJbIYJmsWoV9pXddOHCjKdTWUjq7D2Jn3eUA
|
||||||
|
DAKjKgVqF4/dU10k7EtSfrw01aHLXjj5FxsD5YhVrgTA5xSq
|
||||||
|
-----END CERTIFICATE REQUEST-----
|
||||||
@ -0,0 +1,16 @@
|
|||||||
|
-----BEGIN CERTIFICATE REQUEST-----
|
||||||
|
MIICkDCCAXgCAQAwSzEjMCEGCSqGSIb3DQEJARYUaGFyb29uNjEzOEBnbWFpbC5j
|
||||||
|
b20xFzAVBgNVBAMMDk1vaGFtZWQgTWVrYXd5MQswCQYDVQQGEwJBRTCCASIwDQYJ
|
||||||
|
KoZIhvcNAQEBBQADggEPADCCAQoCggEBAJnHqsyE7WfiVcE1Lpa4t4OVO6qlll2q
|
||||||
|
1djs0XG06R/dlDtIqv4940/XLj+hU93mzAcVvFW4DSIEdD3InM3+T6oMTjPu6meU
|
||||||
|
69h9ryaVkluQRrT/tdGI1EKO4MWGMe4MDIt7DqMhMfAcxTwekwdxdKaCEhaw3qnA
|
||||||
|
l/64AelY6URW1pHHJMA0VV7j+pE3jVNai+muMXPrhQ1VrOrV8FftpY3bEeRJR2Cl
|
||||||
|
T0tv0LhEMu4SfLnVWCzGQQC82hilDw3rH3ZDs8DFxF9agNVdwKlYamarh1dQXwRq
|
||||||
|
Yx2+sjY1/51r9L4VS+GAh9ECxz0e+43NpzfZ/N+mTeDYKDepaBwPQ6kCAwEAAaAA
|
||||||
|
MA0GCSqGSIb3DQEBCwUAA4IBAQB89OyLfywKT7ftmpEqCmgsmaJexb580q9w8wOk
|
||||||
|
1JhJkNV5ec+p1dnge2NZeJ4LGII/5wmPj1vANNW0GZdmJDgnC+2gg9toq1QLCAsF
|
||||||
|
rW7/LMpgAoEH+P5bhrHV9RRv6BQi0ZmN0apBHjp/pqZfm2Cl5jQPEWjUEf2tIF4l
|
||||||
|
LSKdok6IPO9n4Fgyk0XdUNSEhgVhsLtZkGiXnkI1YovKDnupTFYPXMLp103bc9zP
|
||||||
|
xDxwscvOysNDijlzZAkJPg2z8NrJIRDrKvLRHzxQwZ/1LHVB/51bp/1iyks3vOjh
|
||||||
|
qw5XVsrtGAjCjU9md7q3XkPSyKzhK9UqPdOxdvl1OY0KKIIY
|
||||||
|
-----END CERTIFICATE REQUEST-----
|
||||||
@ -0,0 +1,16 @@
|
|||||||
|
-----BEGIN CERTIFICATE REQUEST-----
|
||||||
|
MIICkDCCAXgCAQAwSzEjMCEGCSqGSIb3DQEJARYUaGFyb29uNjEzOEBnbWFpbC5j
|
||||||
|
b20xFzAVBgNVBAMMDk1vaGFtZWQgTWVrYXd5MQswCQYDVQQGEwJBRTCCASIwDQYJ
|
||||||
|
KoZIhvcNAQEBBQADggEPADCCAQoCggEBAJnHqsyE7WfiVcE1Lpa4t4OVO6qlll2q
|
||||||
|
1djs0XG06R/dlDtIqv4940/XLj+hU93mzAcVvFW4DSIEdD3InM3+T6oMTjPu6meU
|
||||||
|
69h9ryaVkluQRrT/tdGI1EKO4MWGMe4MDIt7DqMhMfAcxTwekwdxdKaCEhaw3qnA
|
||||||
|
l/64AelY6URW1pHHJMA0VV7j+pE3jVNai+muMXPrhQ1VrOrV8FftpY3bEeRJR2Cl
|
||||||
|
T0tv0LhEMu4SfLnVWCzGQQC82hilDw3rH3ZDs8DFxF9agNVdwKlYamarh1dQXwRq
|
||||||
|
Yx2+sjY1/51r9L4VS+GAh9ECxz0e+43NpzfZ/N+mTeDYKDepaBwPQ6kCAwEAAaAA
|
||||||
|
MA0GCSqGSIb3DQEBCwUAA4IBAQB89OyLfywKT7ftmpEqCmgsmaJexb580q9w8wOk
|
||||||
|
1JhJkNV5ec+p1dnge2NZeJ4LGII/5wmPj1vANNW0GZdmJDgnC+2gg9toq1QLCAsF
|
||||||
|
rW7/LMpgAoEH+P5bhrHV9RRv6BQi0ZmN0apBHjp/pqZfm2Cl5jQPEWjUEf2tIF4l
|
||||||
|
LSKdok6IPO9n4Fgyk0XdUNSEhgVhsLtZkGiXnkI1YovKDnupTFYPXMLp103bc9zP
|
||||||
|
xDxwscvOysNDijlzZAkJPg2z8NrJIRDrKvLRHzxQwZ/1LHVB/51bp/1iyks3vOjh
|
||||||
|
qw5XVsrtGAjCjU9md7q3XkPSyKzhK9UqPdOxdvl1OY0KKIIY
|
||||||
|
-----END CERTIFICATE REQUEST-----
|
||||||
@ -0,0 +1,8 @@
|
|||||||
|
{\rtf1\ansi\ansicpg1252\cocoartf2513
|
||||||
|
\cocoatextscaling0\cocoaplatform0{\fonttbl\f0\fswiss\fcharset0 Helvetica;}
|
||||||
|
{\colortbl;\red255\green255\blue255;}
|
||||||
|
{\*\expandedcolortbl;;}
|
||||||
|
\paperw11900\paperh16840\margl1440\margr1440\vieww10800\viewh8400\viewkind0
|
||||||
|
\pard\tx566\tx1133\tx1700\tx2267\tx2834\tx3401\tx3968\tx4535\tx5102\tx5669\tx6236\tx6803\pardirnatural\partightenfactor0
|
||||||
|
|
||||||
|
\f0\fs24 \cf0 Hmg54321}
|
||||||
@ -0,0 +1,17 @@
|
|||||||
|
package io.flutter.plugins.firebasemessaging;
|
||||||
|
|
||||||
|
import android.content.Intent;
|
||||||
|
|
||||||
|
import com.google.firebase.messaging.RemoteMessage;
|
||||||
|
|
||||||
|
public class CustomFlutterFirebaseMessagingService extends FlutterFirebaseMessagingService {
|
||||||
|
@Override
|
||||||
|
public void onMessageReceived(RemoteMessage remoteMessage) {
|
||||||
|
if (remoteMessage.getData().containsKey("is_call")) {
|
||||||
|
Intent intent = getPackageManager().getLaunchIntentForPackage(getPackageName());
|
||||||
|
startActivity(intent);
|
||||||
|
super.onMessageReceived(remoteMessage);
|
||||||
|
} else
|
||||||
|
super.onMessageReceived(remoteMessage);
|
||||||
|
}
|
||||||
|
}
|
||||||
@ -0,0 +1,36 @@
|
|||||||
|
<?xml version="1.0" encoding="UTF-8"?>
|
||||||
|
<!DOCTYPE plist PUBLIC "-//Apple//DTD PLIST 1.0//EN" "http://www.apple.com/DTDs/PropertyList-1.0.dtd">
|
||||||
|
<plist version="1.0">
|
||||||
|
<dict>
|
||||||
|
<key>CLIENT_ID</key>
|
||||||
|
<string>864393916058-ekeb4s8tgfo58dutv0l54399t7ivr06r.apps.googleusercontent.com</string>
|
||||||
|
<key>REVERSED_CLIENT_ID</key>
|
||||||
|
<string>com.googleusercontent.apps.864393916058-ekeb4s8tgfo58dutv0l54399t7ivr06r</string>
|
||||||
|
<key>API_KEY</key>
|
||||||
|
<string>AIzaSyA_6ayGCk4fly7o7eTVBrj9kuHBYHMAOfs</string>
|
||||||
|
<key>GCM_SENDER_ID</key>
|
||||||
|
<string>864393916058</string>
|
||||||
|
<key>PLIST_VERSION</key>
|
||||||
|
<string>1</string>
|
||||||
|
<key>BUNDLE_ID</key>
|
||||||
|
<string>com.cloud.diplomaticquarterapp</string>
|
||||||
|
<key>PROJECT_ID</key>
|
||||||
|
<string>diplomaticquarter-d2385</string>
|
||||||
|
<key>STORAGE_BUCKET</key>
|
||||||
|
<string>diplomaticquarter-d2385.appspot.com</string>
|
||||||
|
<key>IS_ADS_ENABLED</key>
|
||||||
|
<false></false>
|
||||||
|
<key>IS_ANALYTICS_ENABLED</key>
|
||||||
|
<false></false>
|
||||||
|
<key>IS_APPINVITE_ENABLED</key>
|
||||||
|
<true></true>
|
||||||
|
<key>IS_GCM_ENABLED</key>
|
||||||
|
<true></true>
|
||||||
|
<key>IS_SIGNIN_ENABLED</key>
|
||||||
|
<true></true>
|
||||||
|
<key>GOOGLE_APP_ID</key>
|
||||||
|
<string>1:864393916058:ios:13f787bbfe6051f8b97923</string>
|
||||||
|
<key>DATABASE_URL</key>
|
||||||
|
<string>https://diplomaticquarter-d2385.firebaseio.com</string>
|
||||||
|
</dict>
|
||||||
|
</plist>
|
||||||
@ -0,0 +1,17 @@
|
|||||||
|
package io.flutter.plugins.firebasemessaging;
|
||||||
|
|
||||||
|
import android.content.Intent;
|
||||||
|
|
||||||
|
import com.google.firebase.messaging.RemoteMessage;
|
||||||
|
|
||||||
|
public class CustomFlutterFirebaseMessagingService extends FlutterFirebaseMessagingService {
|
||||||
|
@Override
|
||||||
|
public void onMessageReceived(RemoteMessage remoteMessage) {
|
||||||
|
if (remoteMessage.getData().containsKey("is_call")) {
|
||||||
|
Intent intent = getPackageManager().getLaunchIntentForPackage(getPackageName());
|
||||||
|
startActivity(intent);
|
||||||
|
super.onMessageReceived(remoteMessage);
|
||||||
|
} else
|
||||||
|
super.onMessageReceived(remoteMessage);
|
||||||
|
}
|
||||||
|
}
|
||||||
@ -0,0 +1,42 @@
|
|||||||
|
{
|
||||||
|
"project_info": {
|
||||||
|
"project_number": "815750722565",
|
||||||
|
"firebase_url": "https://api-project-815750722565.firebaseio.com",
|
||||||
|
"project_id": "api-project-815750722565",
|
||||||
|
"storage_bucket": "api-project-815750722565.appspot.com"
|
||||||
|
},
|
||||||
|
"client": [
|
||||||
|
{
|
||||||
|
"client_info": {
|
||||||
|
"mobilesdk_app_id": "1:815750722565:android:62281cd3e5df4063",
|
||||||
|
"android_client_info": {
|
||||||
|
"package_name": "com.cloud.diplomaticquarterapp"
|
||||||
|
}
|
||||||
|
},
|
||||||
|
"oauth_client": [
|
||||||
|
{
|
||||||
|
"client_id": "815750722565-3a0gc7neins0eoahdrimrfksk0sqice8.apps.googleusercontent.com",
|
||||||
|
"client_type": 3
|
||||||
|
}
|
||||||
|
],
|
||||||
|
"api_key": [
|
||||||
|
{
|
||||||
|
"current_key": "AIzaSyDUfg6AKM1-00WyzpvLImUBC46wFrq9-qw"
|
||||||
|
}
|
||||||
|
],
|
||||||
|
"services": {
|
||||||
|
"analytics_service": {
|
||||||
|
"status": 1
|
||||||
|
},
|
||||||
|
"appinvite_service": {
|
||||||
|
"status": 1,
|
||||||
|
"other_platform_oauth_client": []
|
||||||
|
},
|
||||||
|
"ads_service": {
|
||||||
|
"status": 2
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
],
|
||||||
|
"configuration_version": "1"
|
||||||
|
}
|
||||||
@ -0,0 +1,6 @@
|
|||||||
|
#Sun Sep 20 09:53:06 EEST 2020
|
||||||
|
distributionBase=GRADLE_USER_HOME
|
||||||
|
distributionPath=wrapper/dists
|
||||||
|
zipStoreBase=GRADLE_USER_HOME
|
||||||
|
zipStorePath=wrapper/dists
|
||||||
|
distributionUrl=https\://services.gradle.org/distributions/gradle-6.1.1-all.zip
|
||||||
@ -0,0 +1,172 @@
|
|||||||
|
#!/usr/bin/env sh
|
||||||
|
|
||||||
|
##############################################################################
|
||||||
|
##
|
||||||
|
## Gradle start up script for UN*X
|
||||||
|
##
|
||||||
|
##############################################################################
|
||||||
|
|
||||||
|
# Attempt to set APP_HOME
|
||||||
|
# Resolve links: $0 may be a link
|
||||||
|
PRG="$0"
|
||||||
|
# Need this for relative symlinks.
|
||||||
|
while [ -h "$PRG" ] ; do
|
||||||
|
ls=`ls -ld "$PRG"`
|
||||||
|
link=`expr "$ls" : '.*-> \(.*\)$'`
|
||||||
|
if expr "$link" : '/.*' > /dev/null; then
|
||||||
|
PRG="$link"
|
||||||
|
else
|
||||||
|
PRG=`dirname "$PRG"`"/$link"
|
||||||
|
fi
|
||||||
|
done
|
||||||
|
SAVED="`pwd`"
|
||||||
|
cd "`dirname \"$PRG\"`/" >/dev/null
|
||||||
|
APP_HOME="`pwd -P`"
|
||||||
|
cd "$SAVED" >/dev/null
|
||||||
|
|
||||||
|
APP_NAME="Gradle"
|
||||||
|
APP_BASE_NAME=`basename "$0"`
|
||||||
|
|
||||||
|
# Add default JVM options here. You can also use JAVA_OPTS and GRADLE_OPTS to pass JVM options to this script.
|
||||||
|
DEFAULT_JVM_OPTS=""
|
||||||
|
|
||||||
|
# Use the maximum available, or set MAX_FD != -1 to use that value.
|
||||||
|
MAX_FD="maximum"
|
||||||
|
|
||||||
|
warn () {
|
||||||
|
echo "$*"
|
||||||
|
}
|
||||||
|
|
||||||
|
die () {
|
||||||
|
echo
|
||||||
|
echo "$*"
|
||||||
|
echo
|
||||||
|
exit 1
|
||||||
|
}
|
||||||
|
|
||||||
|
# OS specific support (must be 'true' or 'false').
|
||||||
|
cygwin=false
|
||||||
|
msys=false
|
||||||
|
darwin=false
|
||||||
|
nonstop=false
|
||||||
|
case "`uname`" in
|
||||||
|
CYGWIN* )
|
||||||
|
cygwin=true
|
||||||
|
;;
|
||||||
|
Darwin* )
|
||||||
|
darwin=true
|
||||||
|
;;
|
||||||
|
MINGW* )
|
||||||
|
msys=true
|
||||||
|
;;
|
||||||
|
NONSTOP* )
|
||||||
|
nonstop=true
|
||||||
|
;;
|
||||||
|
esac
|
||||||
|
|
||||||
|
CLASSPATH=$APP_HOME/gradle/wrapper/gradle-wrapper.jar
|
||||||
|
|
||||||
|
# Determine the Java command to use to start the JVM.
|
||||||
|
if [ -n "$JAVA_HOME" ] ; then
|
||||||
|
if [ -x "$JAVA_HOME/jre/sh/java" ] ; then
|
||||||
|
# IBM's JDK on AIX uses strange locations for the executables
|
||||||
|
JAVACMD="$JAVA_HOME/jre/sh/java"
|
||||||
|
else
|
||||||
|
JAVACMD="$JAVA_HOME/bin/java"
|
||||||
|
fi
|
||||||
|
if [ ! -x "$JAVACMD" ] ; then
|
||||||
|
die "ERROR: JAVA_HOME is set to an invalid directory: $JAVA_HOME
|
||||||
|
|
||||||
|
Please set the JAVA_HOME variable in your environment to match the
|
||||||
|
location of your Java installation."
|
||||||
|
fi
|
||||||
|
else
|
||||||
|
JAVACMD="java"
|
||||||
|
which java >/dev/null 2>&1 || die "ERROR: JAVA_HOME is not set and no 'java' command could be found in your PATH.
|
||||||
|
|
||||||
|
Please set the JAVA_HOME variable in your environment to match the
|
||||||
|
location of your Java installation."
|
||||||
|
fi
|
||||||
|
|
||||||
|
# Increase the maximum file descriptors if we can.
|
||||||
|
if [ "$cygwin" = "false" -a "$darwin" = "false" -a "$nonstop" = "false" ] ; then
|
||||||
|
MAX_FD_LIMIT=`ulimit -H -n`
|
||||||
|
if [ $? -eq 0 ] ; then
|
||||||
|
if [ "$MAX_FD" = "maximum" -o "$MAX_FD" = "max" ] ; then
|
||||||
|
MAX_FD="$MAX_FD_LIMIT"
|
||||||
|
fi
|
||||||
|
ulimit -n $MAX_FD
|
||||||
|
if [ $? -ne 0 ] ; then
|
||||||
|
warn "Could not set maximum file descriptor limit: $MAX_FD"
|
||||||
|
fi
|
||||||
|
else
|
||||||
|
warn "Could not query maximum file descriptor limit: $MAX_FD_LIMIT"
|
||||||
|
fi
|
||||||
|
fi
|
||||||
|
|
||||||
|
# For Darwin, add options to specify how the application appears in the dock
|
||||||
|
if $darwin; then
|
||||||
|
GRADLE_OPTS="$GRADLE_OPTS \"-Xdock:name=$APP_NAME\" \"-Xdock:icon=$APP_HOME/media/gradle.icns\""
|
||||||
|
fi
|
||||||
|
|
||||||
|
# For Cygwin, switch paths to Windows format before running java
|
||||||
|
if $cygwin ; then
|
||||||
|
APP_HOME=`cygpath --path --mixed "$APP_HOME"`
|
||||||
|
CLASSPATH=`cygpath --path --mixed "$CLASSPATH"`
|
||||||
|
JAVACMD=`cygpath --unix "$JAVACMD"`
|
||||||
|
|
||||||
|
# We build the pattern for arguments to be converted via cygpath
|
||||||
|
ROOTDIRSRAW=`find -L / -maxdepth 1 -mindepth 1 -type d 2>/dev/null`
|
||||||
|
SEP=""
|
||||||
|
for dir in $ROOTDIRSRAW ; do
|
||||||
|
ROOTDIRS="$ROOTDIRS$SEP$dir"
|
||||||
|
SEP="|"
|
||||||
|
done
|
||||||
|
OURCYGPATTERN="(^($ROOTDIRS))"
|
||||||
|
# Add a user-defined pattern to the cygpath arguments
|
||||||
|
if [ "$GRADLE_CYGPATTERN" != "" ] ; then
|
||||||
|
OURCYGPATTERN="$OURCYGPATTERN|($GRADLE_CYGPATTERN)"
|
||||||
|
fi
|
||||||
|
# Now convert the arguments - kludge to limit ourselves to /bin/sh
|
||||||
|
i=0
|
||||||
|
for arg in "$@" ; do
|
||||||
|
CHECK=`echo "$arg"|egrep -c "$OURCYGPATTERN" -`
|
||||||
|
CHECK2=`echo "$arg"|egrep -c "^-"` ### Determine if an option
|
||||||
|
|
||||||
|
if [ $CHECK -ne 0 ] && [ $CHECK2 -eq 0 ] ; then ### Added a condition
|
||||||
|
eval `echo args$i`=`cygpath --path --ignore --mixed "$arg"`
|
||||||
|
else
|
||||||
|
eval `echo args$i`="\"$arg\""
|
||||||
|
fi
|
||||||
|
i=$((i+1))
|
||||||
|
done
|
||||||
|
case $i in
|
||||||
|
(0) set -- ;;
|
||||||
|
(1) set -- "$args0" ;;
|
||||||
|
(2) set -- "$args0" "$args1" ;;
|
||||||
|
(3) set -- "$args0" "$args1" "$args2" ;;
|
||||||
|
(4) set -- "$args0" "$args1" "$args2" "$args3" ;;
|
||||||
|
(5) set -- "$args0" "$args1" "$args2" "$args3" "$args4" ;;
|
||||||
|
(6) set -- "$args0" "$args1" "$args2" "$args3" "$args4" "$args5" ;;
|
||||||
|
(7) set -- "$args0" "$args1" "$args2" "$args3" "$args4" "$args5" "$args6" ;;
|
||||||
|
(8) set -- "$args0" "$args1" "$args2" "$args3" "$args4" "$args5" "$args6" "$args7" ;;
|
||||||
|
(9) set -- "$args0" "$args1" "$args2" "$args3" "$args4" "$args5" "$args6" "$args7" "$args8" ;;
|
||||||
|
esac
|
||||||
|
fi
|
||||||
|
|
||||||
|
# Escape application args
|
||||||
|
save () {
|
||||||
|
for i do printf %s\\n "$i" | sed "s/'/'\\\\''/g;1s/^/'/;\$s/\$/' \\\\/" ; done
|
||||||
|
echo " "
|
||||||
|
}
|
||||||
|
APP_ARGS=$(save "$@")
|
||||||
|
|
||||||
|
# Collect all arguments for the java command, following the shell quoting and substitution rules
|
||||||
|
eval set -- $DEFAULT_JVM_OPTS $JAVA_OPTS $GRADLE_OPTS "\"-Dorg.gradle.appname=$APP_BASE_NAME\"" -classpath "\"$CLASSPATH\"" org.gradle.wrapper.GradleWrapperMain "$APP_ARGS"
|
||||||
|
|
||||||
|
# by default we should be in the correct project dir, but when run from Finder on Mac, the cwd is wrong
|
||||||
|
if [ "$(uname)" = "Darwin" ] && [ "$HOME" = "$PWD" ]; then
|
||||||
|
cd "$(dirname "$0")"
|
||||||
|
fi
|
||||||
|
|
||||||
|
exec "$JAVACMD" "$@"
|
||||||
@ -0,0 +1,84 @@
|
|||||||
|
@if "%DEBUG%" == "" @echo off
|
||||||
|
@rem ##########################################################################
|
||||||
|
@rem
|
||||||
|
@rem Gradle startup script for Windows
|
||||||
|
@rem
|
||||||
|
@rem ##########################################################################
|
||||||
|
|
||||||
|
@rem Set local scope for the variables with windows NT shell
|
||||||
|
if "%OS%"=="Windows_NT" setlocal
|
||||||
|
|
||||||
|
set DIRNAME=%~dp0
|
||||||
|
if "%DIRNAME%" == "" set DIRNAME=.
|
||||||
|
set APP_BASE_NAME=%~n0
|
||||||
|
set APP_HOME=%DIRNAME%
|
||||||
|
|
||||||
|
@rem Add default JVM options here. You can also use JAVA_OPTS and GRADLE_OPTS to pass JVM options to this script.
|
||||||
|
set DEFAULT_JVM_OPTS=
|
||||||
|
|
||||||
|
@rem Find java.exe
|
||||||
|
if defined JAVA_HOME goto findJavaFromJavaHome
|
||||||
|
|
||||||
|
set JAVA_EXE=java.exe
|
||||||
|
%JAVA_EXE% -version >NUL 2>&1
|
||||||
|
if "%ERRORLEVEL%" == "0" goto init
|
||||||
|
|
||||||
|
echo.
|
||||||
|
echo ERROR: JAVA_HOME is not set and no 'java' command could be found in your PATH.
|
||||||
|
echo.
|
||||||
|
echo Please set the JAVA_HOME variable in your environment to match the
|
||||||
|
echo location of your Java installation.
|
||||||
|
|
||||||
|
goto fail
|
||||||
|
|
||||||
|
:findJavaFromJavaHome
|
||||||
|
set JAVA_HOME=%JAVA_HOME:"=%
|
||||||
|
set JAVA_EXE=%JAVA_HOME%/bin/java.exe
|
||||||
|
|
||||||
|
if exist "%JAVA_EXE%" goto init
|
||||||
|
|
||||||
|
echo.
|
||||||
|
echo ERROR: JAVA_HOME is set to an invalid directory: %JAVA_HOME%
|
||||||
|
echo.
|
||||||
|
echo Please set the JAVA_HOME variable in your environment to match the
|
||||||
|
echo location of your Java installation.
|
||||||
|
|
||||||
|
goto fail
|
||||||
|
|
||||||
|
:init
|
||||||
|
@rem Get command-line arguments, handling Windows variants
|
||||||
|
|
||||||
|
if not "%OS%" == "Windows_NT" goto win9xME_args
|
||||||
|
|
||||||
|
:win9xME_args
|
||||||
|
@rem Slurp the command line arguments.
|
||||||
|
set CMD_LINE_ARGS=
|
||||||
|
set _SKIP=2
|
||||||
|
|
||||||
|
:win9xME_args_slurp
|
||||||
|
if "x%~1" == "x" goto execute
|
||||||
|
|
||||||
|
set CMD_LINE_ARGS=%*
|
||||||
|
|
||||||
|
:execute
|
||||||
|
@rem Setup the command line
|
||||||
|
|
||||||
|
set CLASSPATH=%APP_HOME%\gradle\wrapper\gradle-wrapper.jar
|
||||||
|
|
||||||
|
@rem Execute Gradle
|
||||||
|
"%JAVA_EXE%" %DEFAULT_JVM_OPTS% %JAVA_OPTS% %GRADLE_OPTS% "-Dorg.gradle.appname=%APP_BASE_NAME%" -classpath "%CLASSPATH%" org.gradle.wrapper.GradleWrapperMain %CMD_LINE_ARGS%
|
||||||
|
|
||||||
|
:end
|
||||||
|
@rem End local scope for the variables with windows NT shell
|
||||||
|
if "%ERRORLEVEL%"=="0" goto mainEnd
|
||||||
|
|
||||||
|
:fail
|
||||||
|
rem Set variable GRADLE_EXIT_CONSOLE if you need the _script_ return code instead of
|
||||||
|
rem the _cmd.exe /c_ return code!
|
||||||
|
if not "" == "%GRADLE_EXIT_CONSOLE%" exit 1
|
||||||
|
exit /b 1
|
||||||
|
|
||||||
|
:mainEnd
|
||||||
|
if "%OS%"=="Windows_NT" endlocal
|
||||||
|
|
||||||
|
:omega
|
||||||
@ -0,0 +1,8 @@
|
|||||||
|
## This file must *NOT* be checked into Version Control Systems,
|
||||||
|
# as it contains information specific to your local configuration.
|
||||||
|
#
|
||||||
|
# Location of the SDK. This is only used by Gradle.
|
||||||
|
# For customization when using a Version Control System, please read the
|
||||||
|
# header note.
|
||||||
|
#Sun Sep 20 09:53:03 EEST 2020
|
||||||
|
sdk.dir=/Users/erababah/Library/Android/sdk
|
||||||
@ -1,6 +1,23 @@
|
|||||||
package com.cloud.diplomaticquarterapp
|
package com.cloud.diplomaticquarterapp
|
||||||
|
import android.os.Bundle
|
||||||
|
import android.util.Log
|
||||||
|
import androidx.annotation.NonNull;
|
||||||
|
import com.cloud.diplomaticquarterapp.utils.FlutterText
|
||||||
|
import com.cloud.diplomaticquarterapp.utils.PlatformBridge
|
||||||
|
import io.flutter.embedding.android.FlutterFragmentActivity
|
||||||
|
import io.flutter.embedding.engine.FlutterEngine
|
||||||
|
import io.flutter.plugin.common.MethodChannel
|
||||||
|
import io.flutter.plugins.GeneratedPluginRegistrant
|
||||||
|
|
||||||
import io.flutter.embedding.android.FlutterActivity
|
class MainActivity: FlutterFragmentActivity() {
|
||||||
|
override fun configureFlutterEngine(@NonNull flutterEngine: FlutterEngine) {
|
||||||
|
GeneratedPluginRegistrant.registerWith(flutterEngine);
|
||||||
|
// Create Flutter Platform Bridge
|
||||||
|
PlatformBridge(flutterEngine.dartExecutor.binaryMessenger, this).create()
|
||||||
|
|
||||||
class MainActivity: FlutterActivity() {
|
}
|
||||||
|
|
||||||
|
override fun onResume() {
|
||||||
|
super.onResume()
|
||||||
|
}
|
||||||
}
|
}
|
||||||
@ -0,0 +1,56 @@
|
|||||||
|
package com.cloud.diplomaticquarterapp.geofence
|
||||||
|
|
||||||
|
import com.google.android.gms.location.Geofence
|
||||||
|
import com.google.gson.Gson
|
||||||
|
import com.google.gson.reflect.TypeToken
|
||||||
|
|
||||||
|
class GeoZoneModel {
|
||||||
|
var GEOF_ID:Int = 0
|
||||||
|
var Radius:Int = 0
|
||||||
|
var Type:Int = 0
|
||||||
|
var ProjectID:Int = 0
|
||||||
|
|
||||||
|
var Description:String? = null
|
||||||
|
var DescriptionN:String? = null
|
||||||
|
var Latitude:String? = null
|
||||||
|
var Longitude:String? = null
|
||||||
|
var ImageURL:String? = null
|
||||||
|
var IsCity:String? = null
|
||||||
|
|
||||||
|
fun identifier():String{
|
||||||
|
return "$GEOF_ID" + "_hmg"
|
||||||
|
}
|
||||||
|
|
||||||
|
fun message():String{
|
||||||
|
return Description ?: "nil"
|
||||||
|
}
|
||||||
|
|
||||||
|
fun listFrom(jsonString: String) : List<GeoZoneModel>{
|
||||||
|
val type = object : TypeToken<List<GeoZoneModel?>?>() {}.getType()
|
||||||
|
return Gson().fromJson(jsonString, type)
|
||||||
|
}
|
||||||
|
|
||||||
|
fun toGeofence() : Geofence?{
|
||||||
|
if (!Latitude.isNullOrEmpty() && !Longitude.isNullOrEmpty() && Radius > 50) {
|
||||||
|
val lat = Latitude!!.trim().toDoubleOrNull()
|
||||||
|
val long = Longitude!!.trim().toDoubleOrNull()
|
||||||
|
val rad = Radius.toFloat()
|
||||||
|
if(lat != null && long != null){
|
||||||
|
|
||||||
|
return Geofence.Builder()
|
||||||
|
.setRequestId(identifier())
|
||||||
|
.setCircularRegion(
|
||||||
|
lat,
|
||||||
|
long,
|
||||||
|
rad
|
||||||
|
)
|
||||||
|
.setTransitionTypes(GeofenceTransition.ENTER_EXIT.value)
|
||||||
|
// .setNotificationResponsiveness(0)
|
||||||
|
.setExpirationDuration(Geofence.NEVER_EXPIRE)
|
||||||
|
.build()
|
||||||
|
}
|
||||||
|
}
|
||||||
|
return null
|
||||||
|
}
|
||||||
|
|
||||||
|
}
|
||||||
@ -0,0 +1,13 @@
|
|||||||
|
|
||||||
|
|
||||||
|
package com.cloud.diplomaticquarterapp.geofence
|
||||||
|
|
||||||
|
import android.content.BroadcastReceiver
|
||||||
|
import android.content.Context
|
||||||
|
import android.content.Intent
|
||||||
|
|
||||||
|
class GeofenceBroadcastReceiver : BroadcastReceiver() {
|
||||||
|
override fun onReceive(context: Context, intent: Intent) {
|
||||||
|
GeofenceTransitionsJobIntentService.enqueueWork(context, intent)
|
||||||
|
}
|
||||||
|
}
|
||||||
@ -0,0 +1,34 @@
|
|||||||
|
|
||||||
|
|
||||||
|
package com.cloud.diplomaticquarterapp.geofence
|
||||||
|
|
||||||
|
import android.content.Context
|
||||||
|
import com.cloud.diplomaticquarterapp.R
|
||||||
|
import com.google.android.gms.common.api.ApiException
|
||||||
|
import com.google.android.gms.location.GeofenceStatusCodes
|
||||||
|
|
||||||
|
object GeofenceErrorMessages {
|
||||||
|
fun getErrorString(context: Context, e: Exception): String {
|
||||||
|
return if (e is ApiException) {
|
||||||
|
getErrorString(context, e.statusCode)
|
||||||
|
} else {
|
||||||
|
context.resources.getString(R.string.geofence_unknown_error)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
fun getErrorString(context: Context, errorCode: Int): String {
|
||||||
|
val resources = context.resources
|
||||||
|
return when (errorCode) {
|
||||||
|
GeofenceStatusCodes.GEOFENCE_NOT_AVAILABLE ->
|
||||||
|
resources.getString(R.string.geofence_not_available)
|
||||||
|
|
||||||
|
GeofenceStatusCodes.GEOFENCE_TOO_MANY_GEOFENCES ->
|
||||||
|
resources.getString(R.string.geofence_too_many_geofences)
|
||||||
|
|
||||||
|
GeofenceStatusCodes.GEOFENCE_TOO_MANY_PENDING_INTENTS ->
|
||||||
|
resources.getString(R.string.geofence_too_many_pending_intents)
|
||||||
|
|
||||||
|
else -> resources.getString(R.string.geofence_unknown_error)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
@ -0,0 +1,106 @@
|
|||||||
|
/*
|
||||||
|
* Copyright (c) 2018 Razeware LLC
|
||||||
|
*
|
||||||
|
* Permission is hereby granted, free of charge, to any person obtaining a copy
|
||||||
|
* of this software and associated documentation files (the "Software"), to deal
|
||||||
|
* in the Software without restriction, including without limitation the rights
|
||||||
|
* to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
|
||||||
|
* copies of the Software, and to permit persons to whom the Software is
|
||||||
|
* furnished to do so, subject to the following conditions:
|
||||||
|
*
|
||||||
|
* The above copyright notice and this permission notice shall be included in
|
||||||
|
* all copies or substantial portions of the Software.
|
||||||
|
*
|
||||||
|
* Notwithstanding the foregoing, you may not use, copy, modify, merge, publish,
|
||||||
|
* distribute, sublicense, create a derivative work, and/or sell copies of the
|
||||||
|
* Software in any work that is designed, intended, or marketed for pedagogical or
|
||||||
|
* instructional purposes related to programming, coding, application development,
|
||||||
|
* or information technology. Permission for such use, copying, modification,
|
||||||
|
* merger, publication, distribution, sublicensing, creation of derivative works,
|
||||||
|
* or sale is expressly withheld.
|
||||||
|
*
|
||||||
|
* THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
||||||
|
* IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
||||||
|
* FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
|
||||||
|
* AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
|
||||||
|
* LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
|
||||||
|
* OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
|
||||||
|
* THE SOFTWARE.
|
||||||
|
*/
|
||||||
|
|
||||||
|
|
||||||
|
package com.cloud.diplomaticquarterapp.geofence
|
||||||
|
|
||||||
|
import android.content.Context
|
||||||
|
import android.content.Intent
|
||||||
|
import android.location.Location
|
||||||
|
import android.util.Log
|
||||||
|
import androidx.core.app.JobIntentService
|
||||||
|
import com.cloud.diplomaticquarterapp.utils.API
|
||||||
|
import com.cloud.diplomaticquarterapp.utils.httpPost
|
||||||
|
import com.cloud.diplomaticquarterapp.utils.sendNotification
|
||||||
|
import com.github.kittinunf.fuel.core.extensions.jsonBody
|
||||||
|
import com.github.kittinunf.fuel.core.isSuccessful
|
||||||
|
import com.github.kittinunf.fuel.httpPost
|
||||||
|
import com.google.android.gms.location.Geofence
|
||||||
|
import com.google.android.gms.location.GeofencingEvent
|
||||||
|
import com.google.gson.Gson
|
||||||
|
|
||||||
|
class GeofenceTransitionsJobIntentService : JobIntentService() {
|
||||||
|
|
||||||
|
companion object {
|
||||||
|
private const val LOG_TAG = "GeoTrIntentService"
|
||||||
|
|
||||||
|
private const val JOB_ID = 573
|
||||||
|
|
||||||
|
fun enqueueWork(context: Context, intent: Intent) {
|
||||||
|
enqueueWork(
|
||||||
|
context,
|
||||||
|
GeofenceTransitionsJobIntentService::class.java, JOB_ID,
|
||||||
|
intent)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
override fun onHandleWork(intent: Intent) {
|
||||||
|
val geofencingEvent = GeofencingEvent.fromIntent(intent)
|
||||||
|
if (geofencingEvent.hasError()) {
|
||||||
|
val errorMessage = GeofenceErrorMessages.getErrorString(this, geofencingEvent.errorCode)
|
||||||
|
Log.e(LOG_TAG, errorMessage)
|
||||||
|
return
|
||||||
|
}
|
||||||
|
|
||||||
|
if (geofencingEvent.geofenceTransition == Geofence.GEOFENCE_TRANSITION_ENTER || geofencingEvent.geofenceTransition == Geofence.GEOFENCE_TRANSITION_EXIT) {
|
||||||
|
handleEvent(geofencingEvent.triggeringGeofences,geofencingEvent.triggeringLocation, GeofenceTransition.fromInt(geofencingEvent.geofenceTransition));
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
private fun handleEvent(triggerGeofences: List<Geofence>, location:Location, transition:GeofenceTransition) {
|
||||||
|
val hmg = HMG_Geofence.shared(this)
|
||||||
|
hmg.getPatientID()?.let { patientId ->
|
||||||
|
|
||||||
|
hmg.getActiveGeofences({ activeGeofences ->
|
||||||
|
|
||||||
|
triggerGeofences.forEach { geofence ->
|
||||||
|
// Extract PointID from 'geofence.requestId' and find from active geofences
|
||||||
|
val pointID = activeGeofences.firstOrNull {it == geofence.requestId}?.split('_')?.first()
|
||||||
|
if(!pointID.isNullOrEmpty() && pointID.toIntOrNull() != null){
|
||||||
|
|
||||||
|
val body = mapOf(
|
||||||
|
"PointsID" to pointID.toIntOrNull(),
|
||||||
|
"GeoType" to transition.value,
|
||||||
|
"PatientID" to patientId
|
||||||
|
)
|
||||||
|
|
||||||
|
httpPost<Map<String,Any>>(API.LOG_GEOFENCE, body, { response ->
|
||||||
|
sendNotification(this, transition.named(), geofence.requestId, "Notified to server.😎")
|
||||||
|
},{ exception ->
|
||||||
|
sendNotification(this, transition.named(), geofence.requestId, "Failed to notify server.😔")
|
||||||
|
})
|
||||||
|
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
},null)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
@ -0,0 +1,27 @@
|
|||||||
|
|
||||||
|
|
||||||
|
package com.cloud.diplomaticquarterapp.geofence
|
||||||
|
|
||||||
|
import android.content.BroadcastReceiver
|
||||||
|
import android.content.Context
|
||||||
|
import android.content.Intent
|
||||||
|
import android.os.Handler
|
||||||
|
import android.os.Message
|
||||||
|
import com.cloud.diplomaticquarterapp.geofence.HMG_Geofence
|
||||||
|
import com.cloud.diplomaticquarterapp.utils.HMGUtils
|
||||||
|
|
||||||
|
class GeofencingRebootBroadcastReceiver : BroadcastReceiver(){
|
||||||
|
override fun onReceive(context: Context, intent: Intent) {
|
||||||
|
|
||||||
|
if (Intent.ACTION_BOOT_COMPLETED.equals(intent.action)) {
|
||||||
|
val pref = context.getSharedPreferences(PREFS_STORAGE, Context.MODE_PRIVATE)
|
||||||
|
pref.edit().putString("REBOOT_DETECTED","YES").apply()
|
||||||
|
|
||||||
|
HMG_Geofence.shared(context).unRegisterAll { status, exception ->
|
||||||
|
val geoZones = HMGUtils.getGeoZonesFromPreference(context)
|
||||||
|
HMG_Geofence.shared(context).register(geoZones)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
}
|
||||||
@ -0,0 +1,165 @@
|
|||||||
|
package com.cloud.diplomaticquarterapp.geofence
|
||||||
|
|
||||||
|
import android.Manifest
|
||||||
|
import android.app.PendingIntent
|
||||||
|
import android.content.Context
|
||||||
|
import android.content.Intent
|
||||||
|
import android.content.SharedPreferences
|
||||||
|
import android.content.pm.PackageManager
|
||||||
|
import androidx.core.content.ContextCompat
|
||||||
|
import com.google.android.gms.location.Geofence
|
||||||
|
import com.google.android.gms.location.GeofencingClient
|
||||||
|
import com.google.android.gms.location.GeofencingRequest
|
||||||
|
import com.google.android.gms.location.LocationServices
|
||||||
|
import com.google.gson.Gson
|
||||||
|
import com.google.gson.reflect.TypeToken
|
||||||
|
|
||||||
|
enum class GeofenceTransition(val value: Int) {
|
||||||
|
ENTER(1),
|
||||||
|
EXIT(2),
|
||||||
|
ENTER_EXIT((ENTER.value or EXIT.value)),
|
||||||
|
DWELL(4);
|
||||||
|
|
||||||
|
companion object {
|
||||||
|
fun fromInt(value: Int) = GeofenceTransition.values().first { it.value == value }
|
||||||
|
}
|
||||||
|
|
||||||
|
fun named():String{
|
||||||
|
if (value == 1)return "Enter"
|
||||||
|
if (value == 2)return "Exit"
|
||||||
|
if (value == (ENTER.value or EXIT.value))return "Enter or Exit"
|
||||||
|
if (value == 4)return "dWell"
|
||||||
|
return "unknown"
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
const val PREFS_STORAGE = "FlutterSharedPreferences"
|
||||||
|
const val PREF_KEY_SUCCESS = "HMG_GEOFENCE_SUCCESS"
|
||||||
|
const val PREF_KEY_FAILED = "HMG_GEOFENCE_FAILED"
|
||||||
|
const val PREF_KEY_HMG_ZONES = "flutter.hmg-geo-fences"
|
||||||
|
|
||||||
|
class HMG_Geofence {
|
||||||
|
// https://developer.android.com/training/location/geofencing#java
|
||||||
|
|
||||||
|
private lateinit var context: Context
|
||||||
|
private lateinit var preferences:SharedPreferences
|
||||||
|
private val gson = Gson()
|
||||||
|
|
||||||
|
private lateinit var geofencingClient:GeofencingClient
|
||||||
|
private val geofencePendingIntent: PendingIntent by lazy {
|
||||||
|
val intent = Intent(context, GeofenceBroadcastReceiver::class.java)
|
||||||
|
PendingIntent.getBroadcast(
|
||||||
|
context,
|
||||||
|
0,
|
||||||
|
intent,
|
||||||
|
PendingIntent.FLAG_UPDATE_CURRENT)
|
||||||
|
}
|
||||||
|
|
||||||
|
companion object{
|
||||||
|
|
||||||
|
var instance: HMG_Geofence? = null
|
||||||
|
fun shared(context: Context) : HMG_Geofence {
|
||||||
|
if (instance == null) {
|
||||||
|
instance = HMG_Geofence()
|
||||||
|
instance?.context = context
|
||||||
|
instance?.geofencingClient = LocationServices.getGeofencingClient(context)
|
||||||
|
instance?.preferences = context.getSharedPreferences(PREFS_STORAGE, Context.MODE_PRIVATE)
|
||||||
|
}
|
||||||
|
return instance!!
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
fun register(geoZones: List<GeoZoneModel>){
|
||||||
|
if (geoZones.isEmpty())
|
||||||
|
return
|
||||||
|
|
||||||
|
fun buildGeofencingRequest(geofences: List<Geofence>): GeofencingRequest {
|
||||||
|
return GeofencingRequest.Builder()
|
||||||
|
.setInitialTrigger(0)
|
||||||
|
.addGeofences(geofences)
|
||||||
|
.build()
|
||||||
|
}
|
||||||
|
|
||||||
|
getActiveGeofences({ active ->
|
||||||
|
|
||||||
|
val geofences = mutableListOf<Geofence>()
|
||||||
|
geoZones.forEach {
|
||||||
|
it.toGeofence()?.let { geof ->
|
||||||
|
if(!active.contains(geof.requestId)){ // if not already registered then register
|
||||||
|
geofences.add(geof)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
if (checkPermission() && geofences.isNotEmpty()) {
|
||||||
|
geofencingClient
|
||||||
|
.addGeofences(buildGeofencingRequest(geofences), geofencePendingIntent)
|
||||||
|
.addOnSuccessListener {
|
||||||
|
saveActiveGeofence(geofences.map { it.requestId }, listOf())
|
||||||
|
}
|
||||||
|
.addOnFailureListener {
|
||||||
|
print(it.localizedMessage)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
},null)
|
||||||
|
}
|
||||||
|
|
||||||
|
fun unRegisterAll(completion: (status: Boolean, exception:Exception?) -> Unit){
|
||||||
|
getActiveGeofences({ success ->
|
||||||
|
val mList = success.toMutableList()
|
||||||
|
mList.add("12345")
|
||||||
|
geofencingClient
|
||||||
|
.removeGeofences(success)
|
||||||
|
.addOnSuccessListener {
|
||||||
|
completion(true, null)
|
||||||
|
}
|
||||||
|
.addOnFailureListener {
|
||||||
|
completion(false, it)
|
||||||
|
}
|
||||||
|
removeActiveGeofences()
|
||||||
|
}, { failed ->
|
||||||
|
// Nothing to do with failed geofences.
|
||||||
|
})
|
||||||
|
}
|
||||||
|
|
||||||
|
fun saveActiveGeofence(success: List<String>, failed: List<String>){
|
||||||
|
val jsonSuccess = gson.toJson(success)
|
||||||
|
val jsonFailure = gson.toJson(failed)
|
||||||
|
preferences.edit().putString(PREF_KEY_SUCCESS, jsonSuccess).apply()
|
||||||
|
preferences.edit().putString(PREF_KEY_FAILED, jsonFailure).apply()
|
||||||
|
}
|
||||||
|
|
||||||
|
fun removeActiveGeofences(){
|
||||||
|
preferences.edit().putString(PREF_KEY_SUCCESS,"[]").apply()
|
||||||
|
preferences.edit().putString(PREF_KEY_FAILED,"[]").apply()
|
||||||
|
}
|
||||||
|
|
||||||
|
fun getActiveGeofences(success: (success: List<String>) -> Unit, failure: ((failed: List<String>) -> Unit)?){
|
||||||
|
val type = object : TypeToken<List<String?>?>() {}.type
|
||||||
|
|
||||||
|
val jsonSuccess = preferences.getString(PREF_KEY_SUCCESS, "[]")
|
||||||
|
val success = gson.fromJson<List<String>>(jsonSuccess, type)
|
||||||
|
success(success)
|
||||||
|
|
||||||
|
if(failure != null){
|
||||||
|
val jsonFailure = preferences.getString(PREF_KEY_FAILED, "[]")
|
||||||
|
val failed = gson.fromJson<List<String>>(jsonFailure, type)
|
||||||
|
failure(failed)
|
||||||
|
}
|
||||||
|
|
||||||
|
}
|
||||||
|
|
||||||
|
private fun checkPermission() : Boolean{
|
||||||
|
return ContextCompat.checkSelfPermission(context, Manifest.permission.ACCESS_FINE_LOCATION) == PackageManager.PERMISSION_GRANTED
|
||||||
|
}
|
||||||
|
|
||||||
|
fun getPatientID():Int?{
|
||||||
|
val profileJson = preferences.getString("flutter.imei-user-data", "{}")
|
||||||
|
val type = object : TypeToken<Map<String?, Any?>?>() {}.type
|
||||||
|
return gson.fromJson<Map<String?, Any?>?>(profileJson,type)
|
||||||
|
?.get("PatientID")
|
||||||
|
.toString()
|
||||||
|
.toDoubleOrNull()
|
||||||
|
?.toInt()
|
||||||
|
}
|
||||||
|
}
|
||||||
@ -0,0 +1,172 @@
|
|||||||
|
package com.cloud.diplomaticquarterapp.hmgwifi
|
||||||
|
|
||||||
|
import android.content.Context
|
||||||
|
import android.net.ConnectivityManager
|
||||||
|
import android.net.wifi.WifiConfiguration
|
||||||
|
import android.net.wifi.WifiInfo
|
||||||
|
import android.net.wifi.WifiManager
|
||||||
|
import android.os.Build
|
||||||
|
import android.util.Log
|
||||||
|
import android.widget.Toast
|
||||||
|
import com.cloud.diplomaticquarterapp.MainActivity
|
||||||
|
import com.cloud.diplomaticquarterapp.utils.FlutterText
|
||||||
|
import com.cloud.diplomaticquarterapp.utils.HMGUtils
|
||||||
|
|
||||||
|
|
||||||
|
class HMG_Guest(context: MainActivity) {
|
||||||
|
private var wifiManager: WifiManager? = context.applicationContext.getSystemService(Context.WIFI_SERVICE) as WifiManager?
|
||||||
|
private var connectivityManager: ConnectivityManager? = context.applicationContext.getSystemService(Context.CONNECTIVITY_SERVICE) as ConnectivityManager?
|
||||||
|
private var context = context
|
||||||
|
|
||||||
|
private val TAG = "HMG_Guest"
|
||||||
|
private val TEST = false
|
||||||
|
private var SSID = """"HMG-MobileApp""""
|
||||||
|
|
||||||
|
private lateinit var completionListener: ((status: Boolean, message: String) -> Unit)
|
||||||
|
|
||||||
|
fun completionOnUiThread(status: Boolean, message: String){
|
||||||
|
completionListener(status, message)
|
||||||
|
}
|
||||||
|
|
||||||
|
/*
|
||||||
|
* Helpful:
|
||||||
|
* http://stackoverflow.com/questions/8818290/how-to-connect-to-a-specific-wifi-network-in-android-programmatically
|
||||||
|
*/
|
||||||
|
fun connectToHMGGuestNetwork(completion: (status: Boolean, message: String) -> Unit) {
|
||||||
|
wifiManager?.let { wm ->
|
||||||
|
completionListener = completion
|
||||||
|
|
||||||
|
if (!wm.isWifiEnabled){
|
||||||
|
wm.isWifiEnabled = true
|
||||||
|
HMGUtils.popFlutterText(context,"enablingWifi");
|
||||||
|
HMGUtils.timer(2000,false){
|
||||||
|
connect()
|
||||||
|
}
|
||||||
|
}else{
|
||||||
|
connect()
|
||||||
|
}
|
||||||
|
|
||||||
|
}
|
||||||
|
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
private fun connect(){
|
||||||
|
val security = "OPEN"
|
||||||
|
val networkPass = ""
|
||||||
|
Log.d(TAG, "Connecting to SSID \"$SSID\" with password \"$networkPass\" and with security \"$security\" ...")
|
||||||
|
|
||||||
|
// You need to create WifiConfiguration instance like this:
|
||||||
|
val conf = WifiConfiguration()
|
||||||
|
conf.SSID = SSID
|
||||||
|
conf.allowedKeyManagement.set(WifiConfiguration.KeyMgmt.NONE)
|
||||||
|
conf.networkId = ssidToNetworkId(SSID)
|
||||||
|
|
||||||
|
val wm = wifiManager!!
|
||||||
|
|
||||||
|
if (conf.networkId == -1) {
|
||||||
|
wm.addNetwork(conf)
|
||||||
|
} else {
|
||||||
|
Log.v(TAG, "WiFi found - updating it.\n")
|
||||||
|
wm.updateNetwork(conf)
|
||||||
|
}
|
||||||
|
|
||||||
|
conf.networkId = ssidToNetworkId(SSID)
|
||||||
|
Log.d(TAG, "Network ID: ${conf.networkId}")
|
||||||
|
|
||||||
|
val networkIdToConnect = conf.networkId
|
||||||
|
if (networkIdToConnect >= 0) {
|
||||||
|
Log.v(TAG, "Start connecting to $SSID Wifi...")
|
||||||
|
|
||||||
|
// We disable the network before connecting, because if this was the last connection before
|
||||||
|
// a disconnect(), this will not reconnect.
|
||||||
|
wm.disableNetwork(networkIdToConnect)
|
||||||
|
val result = wm.enableNetwork(networkIdToConnect, true)
|
||||||
|
if(result){
|
||||||
|
HMGUtils.timer(8000,false){
|
||||||
|
if(wm.getConnectionInfo().getSSID() == SSID){
|
||||||
|
completionOnUiThread(true, "successConnectingHmgNetwork")
|
||||||
|
|
||||||
|
}else{
|
||||||
|
errorConnecting()
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
}else{
|
||||||
|
errorConnecting()
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
}else{
|
||||||
|
Log.v(TAG, "Cannot connect to $SSID network")
|
||||||
|
errorConnecting()
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
private fun errorConnecting(){
|
||||||
|
completionOnUiThread(false, "errorConnectingHmgNetwork")
|
||||||
|
}
|
||||||
|
|
||||||
|
// If CompileSDK is greater and equals to APILevel 29
|
||||||
|
private fun connectNewer(wm:WifiManager){
|
||||||
|
|
||||||
|
// Log.e(TAG, "connection wifi Q")
|
||||||
|
//
|
||||||
|
// val wifiNetworkSpecifier: WifiNetworkSpecifier = WifiNetworkSpecifier.Builder()
|
||||||
|
// .setSsid(ssid)
|
||||||
|
// .setWpa2Passphrase(password)
|
||||||
|
// .build()
|
||||||
|
//
|
||||||
|
// val networkRequest: NetworkRequest = NetworkRequest.Builder()
|
||||||
|
// .addTransportType(NetworkCapabilities.TRANSPORT_WIFI)
|
||||||
|
// .setNetworkSpecifier(wifiNetworkSpecifier)
|
||||||
|
// .build()
|
||||||
|
//
|
||||||
|
// var connectivityManager = context.getSystemService(Context.CONNECTIVITY_SERVICE) as ConnectivityManager
|
||||||
|
// var networkCallback = object : ConnectivityManager.NetworkCallback() {
|
||||||
|
// override fun onAvailable(network: Network) {
|
||||||
|
// super.onAvailable(network)
|
||||||
|
// connectivityManager.bindProcessToNetwork(network)
|
||||||
|
// Log.e(TAG, "onAvailable")
|
||||||
|
// }
|
||||||
|
//
|
||||||
|
// override fun onLosing(network: Network, maxMsToLive: Int) {
|
||||||
|
// super.onLosing(network, maxMsToLive)
|
||||||
|
// Log.e(TAG, "onLosing")
|
||||||
|
// }
|
||||||
|
//
|
||||||
|
// override fun onLost(network: Network) {
|
||||||
|
// super.onLost(network)
|
||||||
|
// Log.e(TAG, "onLosing")
|
||||||
|
// Log.e(TAG, "losing active connection")
|
||||||
|
// }
|
||||||
|
//
|
||||||
|
// override fun onUnavailable() {
|
||||||
|
// super.onUnavailable()
|
||||||
|
// Log.e(TAG, "onUnavailable")
|
||||||
|
// }
|
||||||
|
// }
|
||||||
|
// connectivityManager.requestNetwork(networkRequest, networkCallback)
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
/**
|
||||||
|
* This method takes a given String, searches the current list of configured WiFi
|
||||||
|
* networks, and returns the networkId for the network if the SSID matches. If not,
|
||||||
|
* it returns -1.
|
||||||
|
*/
|
||||||
|
private fun ssidToNetworkId(ssid: String): Int {
|
||||||
|
val currentNetworks = wifiManager!!.configuredNetworks
|
||||||
|
var networkId = -1
|
||||||
|
|
||||||
|
// For each network in the list, compare the SSID with the given one
|
||||||
|
for (test in currentNetworks) {
|
||||||
|
if (test.SSID == ssid) {
|
||||||
|
networkId = test.networkId
|
||||||
|
break
|
||||||
|
}
|
||||||
|
}
|
||||||
|
return networkId
|
||||||
|
}
|
||||||
|
}
|
||||||
@ -0,0 +1,110 @@
|
|||||||
|
package com.cloud.diplomaticquarterapp.hmgwifi
|
||||||
|
|
||||||
|
import android.annotation.SuppressLint
|
||||||
|
import com.cloud.diplomaticquarterapp.utils.API
|
||||||
|
import com.cloud.diplomaticquarterapp.MainActivity
|
||||||
|
import com.cloud.diplomaticquarterapp.utils.FlutterText
|
||||||
|
import com.github.kittinunf.fuel.core.extensions.jsonBody
|
||||||
|
import com.github.kittinunf.fuel.httpGet
|
||||||
|
import com.github.kittinunf.fuel.httpPost
|
||||||
|
import org.json.JSONObject
|
||||||
|
import java.util.*
|
||||||
|
|
||||||
|
|
||||||
|
@SuppressLint("MissingPermission")
|
||||||
|
class HMG_Internet(flutterMainActivity: MainActivity) {
|
||||||
|
private val TAG = "HMG_Wifi"
|
||||||
|
private val TEST = false
|
||||||
|
|
||||||
|
private var context = flutterMainActivity;
|
||||||
|
|
||||||
|
private lateinit var completionListener: ((status: Boolean, message: String) -> Unit)
|
||||||
|
|
||||||
|
private var SSID = "GUEST-POC"
|
||||||
|
private var USER_NAME = ""
|
||||||
|
private var PASSWORD = ""
|
||||||
|
|
||||||
|
fun completionOnUiThread(status: Boolean, message: String){
|
||||||
|
completionListener(status, message)
|
||||||
|
// context.runOnUiThread {
|
||||||
|
//
|
||||||
|
// FlutterText.with(message){localized ->
|
||||||
|
// completionListener(status, localized)
|
||||||
|
// }
|
||||||
|
// }
|
||||||
|
}
|
||||||
|
|
||||||
|
/*
|
||||||
|
* Helpful:
|
||||||
|
* http://stackoverflow.com/questions/8818290/how-to-connect-to-a-specific-wifi-network-in-android-programmatically
|
||||||
|
*/
|
||||||
|
fun connectToHMGGuestNetwork(patientId: String, completion: (status: Boolean, message: String) -> Unit): HMG_Internet {
|
||||||
|
completionListener = completion
|
||||||
|
getWifiCredentials(patientId) {
|
||||||
|
WPA(context,SSID).connect(USER_NAME,PASSWORD) { status, message ->
|
||||||
|
completionOnUiThread(status,message)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
return this
|
||||||
|
}
|
||||||
|
|
||||||
|
private fun haveInternet(completion: ((status: Boolean) -> Unit)){
|
||||||
|
if (TEST)
|
||||||
|
completion(true)
|
||||||
|
|
||||||
|
"https://captive.apple.com".httpGet().response { request, response, result ->
|
||||||
|
result.fold(success = {
|
||||||
|
val html = String(it).toLowerCase(Locale.ENGLISH)
|
||||||
|
.replace(" ", "", true)
|
||||||
|
.replace("\n","",true)
|
||||||
|
val have = html.contains("<title>success</title>", true)
|
||||||
|
completion(have)
|
||||||
|
|
||||||
|
},failure = {
|
||||||
|
completion(false)
|
||||||
|
})
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
private fun getWifiCredentials(patientId:String, success: (() -> Unit)){
|
||||||
|
if (TEST){
|
||||||
|
SSID = "GUEST-POC"
|
||||||
|
USER_NAME = "0696"
|
||||||
|
PASSWORD = "0000"
|
||||||
|
success()
|
||||||
|
return
|
||||||
|
}
|
||||||
|
|
||||||
|
val jsonBody = """{"PatientID":$patientId}"""
|
||||||
|
API.WIFI_CREDENTIALS.
|
||||||
|
httpPost()
|
||||||
|
.jsonBody(jsonBody, Charsets.UTF_8)
|
||||||
|
.response { request, response, result ->
|
||||||
|
|
||||||
|
result.fold(success = { data ->
|
||||||
|
val jsonString = String(data)
|
||||||
|
val jsonObject = JSONObject(jsonString)
|
||||||
|
if(!jsonObject.getString("ErrorMessage").equals("null")){
|
||||||
|
val errorMsg = jsonObject.getString("ErrorMessage")
|
||||||
|
completionOnUiThread(false, errorMsg)
|
||||||
|
|
||||||
|
}else{
|
||||||
|
jsonObject.getJSONArray("Hmg_SMS_Get_By_ProjectID_And_PatientIDList").let { array ->
|
||||||
|
array.getJSONObject(0).let { object_ ->
|
||||||
|
if (object_.has("UserName") && object_.has("UserName")){
|
||||||
|
USER_NAME = object_.getString("UserName")
|
||||||
|
PASSWORD = object_.getString("Password")
|
||||||
|
success()
|
||||||
|
}else{
|
||||||
|
completionOnUiThread(false, "somethingWentWrong")
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
},failure = { error ->
|
||||||
|
completionOnUiThread(false, "somethingWentWrong" )
|
||||||
|
})
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
@ -0,0 +1,105 @@
|
|||||||
|
package com.cloud.diplomaticquarterapp.hmgwifi
|
||||||
|
|
||||||
|
import android.annotation.SuppressLint
|
||||||
|
import android.content.Context
|
||||||
|
import android.net.ConnectivityManager
|
||||||
|
import android.net.wifi.*
|
||||||
|
import android.net.wifi.SupplicantState.ASSOCIATED
|
||||||
|
import android.net.wifi.SupplicantState.COMPLETED
|
||||||
|
import android.util.Log
|
||||||
|
import com.cloud.diplomaticquarterapp.MainActivity
|
||||||
|
import com.cloud.diplomaticquarterapp.utils.HMGUtils
|
||||||
|
|
||||||
|
class WPA(mainActivity: MainActivity, SSID:String) {
|
||||||
|
private var TAG = "WPA"
|
||||||
|
private var SSID = "GUEST-POC"
|
||||||
|
private var wifiManager_: WifiManager? = null
|
||||||
|
private var connectivityManager_: ConnectivityManager? = null
|
||||||
|
|
||||||
|
init {
|
||||||
|
wifiManager_ = mainActivity.applicationContext.getSystemService(Context.WIFI_SERVICE) as WifiManager?
|
||||||
|
connectivityManager_ = mainActivity.applicationContext.getSystemService(Context.CONNECTIVITY_SERVICE) as ConnectivityManager?
|
||||||
|
}
|
||||||
|
|
||||||
|
fun connect(identity:String, password:String, completion: (status: Boolean, message: String) -> Unit) {
|
||||||
|
if(wifiManager_ == null || connectivityManager_ == null){
|
||||||
|
completion(false,"errorConnectingHmgNetwork")
|
||||||
|
return
|
||||||
|
}
|
||||||
|
|
||||||
|
val wifiManager = wifiManager_!!
|
||||||
|
val connectivityManager = connectivityManager_!!
|
||||||
|
|
||||||
|
// Initialize the WifiConfiguration object
|
||||||
|
val enterpriseConfig = WifiEnterpriseConfig()
|
||||||
|
val wifi = WifiConfiguration()
|
||||||
|
wifi.SSID = """"$SSID""""
|
||||||
|
wifi.allowedKeyManagement.set(WifiConfiguration.KeyMgmt.WPA_EAP)
|
||||||
|
wifi.allowedKeyManagement.set(WifiConfiguration.KeyMgmt.IEEE8021X)
|
||||||
|
enterpriseConfig.eapMethod = WifiEnterpriseConfig.Eap.PEAP
|
||||||
|
enterpriseConfig.identity = identity
|
||||||
|
enterpriseConfig.password = password
|
||||||
|
wifi.enterpriseConfig = enterpriseConfig
|
||||||
|
wifi.networkId = ssidToNetworkId(wifi.SSID)
|
||||||
|
if (wifi.networkId == -1) {
|
||||||
|
wifiManager.addNetwork(wifi)
|
||||||
|
} else {
|
||||||
|
Log.v(TAG, "WiFi found - updating it.\n")
|
||||||
|
wifiManager.updateNetwork(wifi)
|
||||||
|
}
|
||||||
|
Log.v(TAG, "saving config.\n")
|
||||||
|
wifiManager.saveConfiguration()
|
||||||
|
wifi.networkId = ssidToNetworkId(wifi.SSID)
|
||||||
|
|
||||||
|
Log.v(TAG, "wifi ID in device = " + wifi.networkId)
|
||||||
|
|
||||||
|
var supState: SupplicantState
|
||||||
|
val networkIdToConnect = wifi.networkId
|
||||||
|
if (networkIdToConnect >= 0) {
|
||||||
|
Log.v(TAG, "Start connecting...\n")
|
||||||
|
|
||||||
|
// We disable the network before connecting, because if this was the last connection before
|
||||||
|
// a disconnect(), this will not reconnect.
|
||||||
|
wifiManager.disableNetwork(networkIdToConnect)
|
||||||
|
wifiManager.enableNetwork(networkIdToConnect, true)
|
||||||
|
|
||||||
|
val wifiInfo: WifiInfo = wifiManager.connectionInfo
|
||||||
|
|
||||||
|
HMGUtils.timer(5000,false){
|
||||||
|
supState = wifiInfo.supplicantState
|
||||||
|
Log.i(TAG, "WifiWizard: Done connect to network : status = $supState")
|
||||||
|
val successStates = listOf(COMPLETED, ASSOCIATED)
|
||||||
|
if (successStates.contains(COMPLETED /*supState*/))
|
||||||
|
|
||||||
|
completion(true,"Connected to internet Wifi")
|
||||||
|
|
||||||
|
else
|
||||||
|
completion(false,"errorConnectingHmgNetwork")
|
||||||
|
}
|
||||||
|
|
||||||
|
} else {
|
||||||
|
Log.v(TAG, "WifiWizard: cannot connect to network")
|
||||||
|
completion(false,"errorConnectingHmgNetwork")
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* This method takes a given String, searches the current list of configured WiFi
|
||||||
|
* networks, and returns the networkId for the network if the SSID matches. If not,
|
||||||
|
* it returns -1.
|
||||||
|
*/
|
||||||
|
@SuppressLint("MissingPermission")
|
||||||
|
private fun ssidToNetworkId(ssid: String): Int {
|
||||||
|
val currentNetworks = wifiManager_!!.configuredNetworks
|
||||||
|
var networkId = -1
|
||||||
|
|
||||||
|
// For each network in the list, compare the SSID with the given one
|
||||||
|
for (test in currentNetworks) {
|
||||||
|
if (test.SSID == ssid) {
|
||||||
|
networkId = test.networkId
|
||||||
|
break
|
||||||
|
}
|
||||||
|
}
|
||||||
|
return networkId
|
||||||
|
}
|
||||||
|
}
|
||||||
@ -0,0 +1,11 @@
|
|||||||
|
package com.cloud.diplomaticquarterapp.utils
|
||||||
|
|
||||||
|
class API {
|
||||||
|
companion object{
|
||||||
|
private val BASE = "https://uat.hmgwebservices.com"
|
||||||
|
private val SERVICE = "Services/Patients.svc/REST"
|
||||||
|
|
||||||
|
val WIFI_CREDENTIALS = "$BASE/$SERVICE/Hmg_SMS_Get_By_ProjectID_And_PatientID"
|
||||||
|
val LOG_GEOFENCE = "$BASE/$SERVICE/GeoF_InsertPatientFileInfo"
|
||||||
|
}
|
||||||
|
}
|
||||||
@ -0,0 +1,36 @@
|
|||||||
|
package com.cloud.diplomaticquarterapp.utils
|
||||||
|
|
||||||
|
import io.flutter.plugin.common.MethodChannel
|
||||||
|
import io.flutter.plugin.common.MethodChannel.Result
|
||||||
|
|
||||||
|
class FlutterText{
|
||||||
|
|
||||||
|
companion object{
|
||||||
|
fun with(key:String, completion:(String)->Unit){
|
||||||
|
HMGUtils.getPlatformChannel().invokeMethod("localizedValue",key, object:MethodChannel.Result{
|
||||||
|
override fun success(result: Any?) {
|
||||||
|
val localized = result as String?
|
||||||
|
if (localized != null){
|
||||||
|
completion(localized)
|
||||||
|
}else{
|
||||||
|
completion(key)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
override fun error(errorCode: String?, errorMessage: String?, errorDetails: Any?) {
|
||||||
|
completion(key)
|
||||||
|
require(false){
|
||||||
|
"'localizedValue' $errorMessage"
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
override fun notImplemented() {
|
||||||
|
require(false){
|
||||||
|
"'localizedValue' method not implemented at flutter"
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
})
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
@ -0,0 +1,160 @@
|
|||||||
|
package com.cloud.diplomaticquarterapp.utils
|
||||||
|
|
||||||
|
import android.app.NotificationChannel
|
||||||
|
import android.app.NotificationManager
|
||||||
|
import android.app.PendingIntent
|
||||||
|
import android.content.Context
|
||||||
|
import android.content.Intent
|
||||||
|
import android.os.Build
|
||||||
|
import android.widget.Toast
|
||||||
|
import androidx.annotation.Nullable
|
||||||
|
import androidx.core.app.NotificationCompat
|
||||||
|
import androidx.core.app.TaskStackBuilder
|
||||||
|
import com.cloud.diplomaticquarterapp.BuildConfig
|
||||||
|
import com.cloud.diplomaticquarterapp.MainActivity
|
||||||
|
import com.cloud.diplomaticquarterapp.R
|
||||||
|
import com.cloud.diplomaticquarterapp.geofence.GeoZoneModel
|
||||||
|
import com.cloud.diplomaticquarterapp.geofence.PREFS_STORAGE
|
||||||
|
import com.cloud.diplomaticquarterapp.geofence.PREF_KEY_HMG_ZONES
|
||||||
|
import com.github.kittinunf.fuel.core.extensions.jsonBody
|
||||||
|
import com.github.kittinunf.fuel.httpPost
|
||||||
|
import com.google.android.gms.location.Geofence
|
||||||
|
import com.google.gson.Gson
|
||||||
|
import com.google.gson.reflect.TypeToken
|
||||||
|
import io.flutter.plugin.common.MethodChannel
|
||||||
|
import org.json.JSONArray
|
||||||
|
import org.json.JSONException
|
||||||
|
import org.json.JSONObject
|
||||||
|
import java.util.*
|
||||||
|
import kotlin.concurrent.timerTask
|
||||||
|
|
||||||
|
|
||||||
|
class HMGUtils {
|
||||||
|
|
||||||
|
companion object{
|
||||||
|
private lateinit var platformChannel: MethodChannel
|
||||||
|
fun getPlatformChannel():MethodChannel{
|
||||||
|
return platformChannel
|
||||||
|
}
|
||||||
|
fun setPlatformChannel(channel: MethodChannel){
|
||||||
|
platformChannel = channel
|
||||||
|
}
|
||||||
|
|
||||||
|
fun timer(delay: Long, repeat: Boolean, tick: (Timer) -> Unit) : Timer{
|
||||||
|
val timer = Timer()
|
||||||
|
if(repeat)
|
||||||
|
timer.schedule(timerTask {
|
||||||
|
tick(timer)
|
||||||
|
}, delay, delay)
|
||||||
|
else
|
||||||
|
timer.schedule(timerTask {
|
||||||
|
tick(timer)
|
||||||
|
}, delay)
|
||||||
|
|
||||||
|
return timer
|
||||||
|
}
|
||||||
|
|
||||||
|
fun popMessage(context: MainActivity, message: String){
|
||||||
|
context.runOnUiThread {
|
||||||
|
Toast.makeText(context, message, Toast.LENGTH_LONG).show()
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
fun popFlutterText(context: MainActivity, key: String){
|
||||||
|
context.runOnUiThread {
|
||||||
|
FlutterText.with(key){
|
||||||
|
Toast.makeText(context, it, Toast.LENGTH_LONG).show()
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
fun getGeoZonesFromPreference(context: Context):List<GeoZoneModel>{
|
||||||
|
val pref = context.getSharedPreferences(PREFS_STORAGE, Context.MODE_PRIVATE)
|
||||||
|
val json = pref.getString(PREF_KEY_HMG_ZONES,"[]")
|
||||||
|
|
||||||
|
val geoZones = GeoZoneModel().listFrom(json)
|
||||||
|
return geoZones
|
||||||
|
}
|
||||||
|
|
||||||
|
}
|
||||||
|
|
||||||
|
}
|
||||||
|
|
||||||
|
private fun Timer.schedule(timerTask: TimerTask) {
|
||||||
|
|
||||||
|
}
|
||||||
|
private const val NOTIFICATION_CHANNEL_ID = BuildConfig.APPLICATION_ID + ".channel"
|
||||||
|
|
||||||
|
fun sendNotification(context: Context, title:String, @Nullable subtitle:String?, message:String?) {
|
||||||
|
val notificationManager = context.getSystemService(Context.NOTIFICATION_SERVICE) as NotificationManager
|
||||||
|
|
||||||
|
if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.O
|
||||||
|
&& notificationManager.getNotificationChannel(NOTIFICATION_CHANNEL_ID) == null) {
|
||||||
|
val name = context.getString(R.string.app_name)
|
||||||
|
val channel = NotificationChannel(NOTIFICATION_CHANNEL_ID,
|
||||||
|
name,
|
||||||
|
NotificationManager.IMPORTANCE_DEFAULT)
|
||||||
|
|
||||||
|
notificationManager.createNotificationChannel(channel)
|
||||||
|
}
|
||||||
|
|
||||||
|
val intent = Intent(context, MainActivity::class.java)
|
||||||
|
|
||||||
|
val stackBuilder = TaskStackBuilder.create(context)
|
||||||
|
.addParentStack(MainActivity::class.java)
|
||||||
|
.addNextIntent(intent)
|
||||||
|
val notificationPendingIntent = stackBuilder.getPendingIntent(getUniqueId(), PendingIntent.FLAG_UPDATE_CURRENT)
|
||||||
|
|
||||||
|
val notification = NotificationCompat.Builder(context, NOTIFICATION_CHANNEL_ID)
|
||||||
|
.setSmallIcon(R.mipmap.ic_launcher)
|
||||||
|
.setContentIntent(notificationPendingIntent)
|
||||||
|
.setAutoCancel(true)
|
||||||
|
.setContentTitle(title)
|
||||||
|
|
||||||
|
subtitle.let { notification.setContentText(it) }
|
||||||
|
message.let { notification.setSubText(it) }
|
||||||
|
|
||||||
|
notificationManager.notify(getUniqueId(), notification.build())
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
private fun getUniqueId() = ((System.currentTimeMillis() % 10000).toInt())
|
||||||
|
|
||||||
|
fun isJSONValid(jsonString: String?): Boolean {
|
||||||
|
try { JSONObject(jsonString) } catch (ex: JSONException) {
|
||||||
|
try { JSONArray(jsonString) } catch (ex1: JSONException) {
|
||||||
|
return false
|
||||||
|
}
|
||||||
|
}
|
||||||
|
return true
|
||||||
|
}
|
||||||
|
|
||||||
|
class HTTPResponse<T>(data: T){
|
||||||
|
final var data:T = data
|
||||||
|
}
|
||||||
|
fun <T>httpPost(url: String, body: Map<String, Any?>, onSuccess: (response: HTTPResponse<T>) -> Unit, onError: (error: Exception) -> Unit){
|
||||||
|
|
||||||
|
val gson = Gson()
|
||||||
|
val type = object : TypeToken<T>() {}.type
|
||||||
|
val jsonBody = gson.toJson(body)
|
||||||
|
url.httpPost()
|
||||||
|
.jsonBody(jsonBody, Charsets.UTF_8)
|
||||||
|
.timeout(10000)
|
||||||
|
.header("Content-Type","application/json")
|
||||||
|
.header("Allow","*/*")
|
||||||
|
.response { request, response, result ->
|
||||||
|
result.fold({ data ->
|
||||||
|
val dataString = String(data)
|
||||||
|
if(isJSONValid(dataString)){
|
||||||
|
val responseData = gson.fromJson<T>(dataString,type)
|
||||||
|
onSuccess(HTTPResponse(responseData))
|
||||||
|
}else{
|
||||||
|
onError(Exception("Invalid response from server (Not a valid JSON)"))
|
||||||
|
}
|
||||||
|
}, {
|
||||||
|
onError(it)
|
||||||
|
it.localizedMessage
|
||||||
|
})
|
||||||
|
|
||||||
|
}
|
||||||
|
}
|
||||||
@ -0,0 +1,351 @@
|
|||||||
|
//package com.cloud.diplomaticquarterapp.utils
|
||||||
|
//
|
||||||
|
//import android.annotation.SuppressLint
|
||||||
|
//import android.content.Context
|
||||||
|
//import android.net.ConnectivityManager
|
||||||
|
//import android.net.Network
|
||||||
|
//import android.net.NetworkCapabilities
|
||||||
|
//import android.net.NetworkRequest
|
||||||
|
//import android.net.wifi.ScanResult
|
||||||
|
//import android.net.wifi.WifiConfiguration
|
||||||
|
//import android.net.wifi.WifiManager
|
||||||
|
//import android.util.Log
|
||||||
|
//import com.cloud.diplomaticquarterapp.utils.API
|
||||||
|
//import com.cloud.diplomaticquarterapp.FlutterMainActivity
|
||||||
|
//import com.github.kittinunf.fuel.core.extensions.jsonBody
|
||||||
|
//import com.github.kittinunf.fuel.httpGet
|
||||||
|
//import com.github.kittinunf.fuel.httpPost
|
||||||
|
//import org.json.JSONObject
|
||||||
|
//import java.util.*
|
||||||
|
//
|
||||||
|
//
|
||||||
|
//@SuppressLint("MissingPermission")
|
||||||
|
//class HMG_Wifi_(flutterMainActivity: FlutterMainActivity) {
|
||||||
|
// val TAG = "WIFI"
|
||||||
|
// val TEST = true
|
||||||
|
//
|
||||||
|
// var context = flutterMainActivity;
|
||||||
|
// var completionListener: ((status: Boolean, message: String) -> Unit)? = null
|
||||||
|
//
|
||||||
|
//
|
||||||
|
// private var SSID = "HMG-GUEST"
|
||||||
|
// private var USER_NAME = ""
|
||||||
|
// private var PASSWORD = ""
|
||||||
|
// var NETWORK_ID = -1 // HMG-GUEST Assigned Network ID by Android
|
||||||
|
// private lateinit var PATIENT_ID:String
|
||||||
|
// /*
|
||||||
|
// * Helpful:
|
||||||
|
// * http://stackoverflow.com/questions/5452940/how-can-i-get-android-wifi-scan-results-into-a-list
|
||||||
|
// */
|
||||||
|
// fun triggerWifiScan(context: Context) {
|
||||||
|
// val wifi = context.getSystemService(Context.WIFI_SERVICE) as WifiManager
|
||||||
|
// wifi.startScan()
|
||||||
|
// }
|
||||||
|
//
|
||||||
|
// /*
|
||||||
|
// * Helpful:
|
||||||
|
// * http://stackoverflow.com/questions/8818290/how-to-connect-to-a-specific-wifi-network-in-android-programmatically
|
||||||
|
// */
|
||||||
|
// fun connectToWifiNetworkWith(patientId: String): HMG_Wifi_ {
|
||||||
|
//
|
||||||
|
// val connectivityManager = context.applicationContext.getSystemService(Context.CONNECTIVITY_SERVICE) as ConnectivityManager
|
||||||
|
//
|
||||||
|
// PATIENT_ID = patientId
|
||||||
|
//
|
||||||
|
// val security = "OPEN"
|
||||||
|
// val networkPass = ""
|
||||||
|
// Log.d(TAG, "Connecting to SSID \"$SSID\" with password \"$networkPass\" and with security \"$security\" ...")
|
||||||
|
//
|
||||||
|
// // You need to create WifiConfiguration instance like this:
|
||||||
|
// val conf = WifiConfiguration()
|
||||||
|
// conf.SSID = "\"" + SSID + "\""
|
||||||
|
//
|
||||||
|
// if (security == "OPEN") {
|
||||||
|
// conf.allowedKeyManagement.set(WifiConfiguration.KeyMgmt.NONE)
|
||||||
|
// } else if (security == "WEP") {
|
||||||
|
// conf.wepKeys[0] = "\"" + networkPass + "\""
|
||||||
|
// conf.wepTxKeyIndex = 0
|
||||||
|
// conf.allowedKeyManagement.set(WifiConfiguration.KeyMgmt.NONE)
|
||||||
|
// conf.allowedGroupCiphers.set(WifiConfiguration.GroupCipher.WEP40)
|
||||||
|
// } else {
|
||||||
|
// conf.preSharedKey = "\"" + networkPass + "\""
|
||||||
|
// }
|
||||||
|
//
|
||||||
|
// // Then, you need to add it to Android wifi manager settings:
|
||||||
|
// val wifiManager = context.applicationContext.getSystemService(Context.WIFI_SERVICE) as WifiManager
|
||||||
|
//
|
||||||
|
// NETWORK_ID = wifiManager.addNetwork(conf)
|
||||||
|
// Log.d(TAG, "Network ID: $NETWORK_ID")
|
||||||
|
//
|
||||||
|
// //wifiManager.disconnect();
|
||||||
|
// val result = wifiManager.enableNetwork(NETWORK_ID, true)
|
||||||
|
// //wifiManager.reconnect();
|
||||||
|
// wifiManager.saveConfiguration()
|
||||||
|
//
|
||||||
|
// if(result == true){
|
||||||
|
// authNetworkConnection(NETWORK_ID);
|
||||||
|
// }else{
|
||||||
|
// completionListener?.let { it(false, "Error connecting to HMG network") }
|
||||||
|
// }
|
||||||
|
// return this
|
||||||
|
// }
|
||||||
|
//
|
||||||
|
// private var authTimer:Timer? = null
|
||||||
|
// fun authNetworkConnection(networkId: Int){
|
||||||
|
// authTimer = Timer()
|
||||||
|
// authTimer?.scheduleAtFixedRate(object : TimerTask() {
|
||||||
|
// override fun run() {
|
||||||
|
// if (connectedNetworkId() == networkId && connectedNetworkIPAddress() > 0) {
|
||||||
|
// authServerCall()
|
||||||
|
// authTimer?.cancel()
|
||||||
|
// }
|
||||||
|
// }
|
||||||
|
//
|
||||||
|
// }, 2000, 1000)
|
||||||
|
//
|
||||||
|
// // If wifi not connected in 5 sec terminate with fail status
|
||||||
|
// Timer().schedule(object : TimerTask() {
|
||||||
|
// override fun run() {
|
||||||
|
// if (null != authTimer) {
|
||||||
|
// authTimer?.cancel()
|
||||||
|
// completionListener?.let { it(false, "Error connecting to HMG network") }
|
||||||
|
// }
|
||||||
|
// }
|
||||||
|
// }, 5000)
|
||||||
|
//
|
||||||
|
// }
|
||||||
|
//
|
||||||
|
// fun authServerCall(){
|
||||||
|
//
|
||||||
|
// fun call(){
|
||||||
|
//
|
||||||
|
// forceNetworkCallOverWifi()
|
||||||
|
//
|
||||||
|
// val params = listOf("cmd" to "authenticate", "password" to PASSWORD, "user" to USER_NAME)
|
||||||
|
// val serverUrl = "https://captiveportal-login.hmg.com/cgi-bin/login"
|
||||||
|
//// val serverUrl = "http://192.168.102.223/cgi-bin/login"
|
||||||
|
// serverUrl
|
||||||
|
// .httpPost(params)
|
||||||
|
// .timeout(10000)
|
||||||
|
// .response { request, response, result ->
|
||||||
|
// Log.v(TAG, response.statusCode.toString())
|
||||||
|
//
|
||||||
|
// haveInternet { have ->
|
||||||
|
// if(have){
|
||||||
|
// Log.v(TAG, "Connected to internet via $SSID network at HMG")
|
||||||
|
// completionListener?.let { it(true, "Successfully connected to the internet") }
|
||||||
|
// }else{
|
||||||
|
// Log.e(TAG, "failed to connect to internet via $SSID network at HMG")
|
||||||
|
// completionListener?.let { it(false, "Authentication failed or you are already using your credentials on another device") }
|
||||||
|
// }
|
||||||
|
// }
|
||||||
|
// }
|
||||||
|
// }
|
||||||
|
//
|
||||||
|
// haveInternet { has ->
|
||||||
|
// if (has){
|
||||||
|
// getAuthCredentials {
|
||||||
|
// call()
|
||||||
|
// }
|
||||||
|
// }else{
|
||||||
|
// completionListener?.let { it(false, "You must have active internet connection to connect with HMG Network") }
|
||||||
|
// }
|
||||||
|
// }
|
||||||
|
// }
|
||||||
|
//
|
||||||
|
// fun haveInternet(completion: ((status: Boolean) -> Unit)){
|
||||||
|
// if (TEST)
|
||||||
|
// completion(true)
|
||||||
|
//
|
||||||
|
// "https://captive.apple.com".httpGet().response { request, response, result ->
|
||||||
|
// val have = response.statusCode == 200 && String(response.data).contains("<TITLE>Success</TITLE>", true)
|
||||||
|
// completion(have)
|
||||||
|
// }
|
||||||
|
// }
|
||||||
|
//
|
||||||
|
// fun getAuthCredentials(completion: (() -> Unit)){
|
||||||
|
// if (TEST){
|
||||||
|
// USER_NAME = "2300"
|
||||||
|
// PASSWORD = "1820"
|
||||||
|
// completion()
|
||||||
|
// return
|
||||||
|
// }
|
||||||
|
//
|
||||||
|
// val jsonBody = """{"PatientID":$PATIENT_ID}"""
|
||||||
|
// API.WIFI_CREDENTIALS
|
||||||
|
// .httpPost()
|
||||||
|
// .jsonBody(jsonBody, Charsets.UTF_8)
|
||||||
|
// .response { request, response, result ->
|
||||||
|
// val jsonString = String(response.data)
|
||||||
|
// Log.d(TAG, "JSON $jsonString")
|
||||||
|
//
|
||||||
|
// if (response.statusCode == 200){
|
||||||
|
//
|
||||||
|
// val jsonObject = JSONObject(jsonString)
|
||||||
|
// if(!jsonObject.getString("ErrorMessage").equals("null")){
|
||||||
|
// val errorMsg = jsonObject.getString("ErrorMessage")
|
||||||
|
// completionListener?.let { it(false, errorMsg) }
|
||||||
|
//
|
||||||
|
// }else{
|
||||||
|
// jsonObject.getJSONArray("Hmg_SMS_Get_By_ProjectID_And_PatientIDList").let { array ->
|
||||||
|
// array.getJSONObject(0).let { object_ ->
|
||||||
|
// if (object_.has("UserName") && object_.has("UserName")){
|
||||||
|
// USER_NAME = object_.getString("UserName")
|
||||||
|
// PASSWORD = object_.getString("Password")
|
||||||
|
// completion()
|
||||||
|
// }else{
|
||||||
|
// completionListener?.let { it(false, "Failed to get your internet credentials") }
|
||||||
|
// }
|
||||||
|
// }
|
||||||
|
// }
|
||||||
|
// }
|
||||||
|
//
|
||||||
|
// }else{
|
||||||
|
// completionListener?.let { it(false, "Failed to get your internet credentials") }
|
||||||
|
// }
|
||||||
|
// }
|
||||||
|
// }
|
||||||
|
//
|
||||||
|
// fun forceNetworkCallOverWifi(){
|
||||||
|
// val connectivityManager = context.applicationContext.getSystemService(Context.CONNECTIVITY_SERVICE) as ConnectivityManager
|
||||||
|
//// val network = Network
|
||||||
|
//// connectivityManager.activeNetwork
|
||||||
|
// // Exit app if Network disappears.
|
||||||
|
// // Exit app if Network disappears.
|
||||||
|
//// val networkCapabilities: NetworkCapabilities = ConnectivityManager.from(context).getNetworkCapabilities(network)
|
||||||
|
//// val networkCapabilities: NetworkCapabilities = connectivityManager.getNetworkCapabilities(network)
|
||||||
|
//
|
||||||
|
//// if (networkCapabilities == null) {
|
||||||
|
//// return
|
||||||
|
//// }
|
||||||
|
//
|
||||||
|
// val mNetworkCallback = object : ConnectivityManager.NetworkCallback() {
|
||||||
|
// override fun onLost(lostNetwork: Network?) {
|
||||||
|
//// if (network.equals(lostNetwork)){
|
||||||
|
//// //GlyphLayout.done(false)
|
||||||
|
//// }
|
||||||
|
// }
|
||||||
|
// }
|
||||||
|
// val builder: NetworkRequest.Builder = NetworkRequest.Builder()
|
||||||
|
//// for (transportType in networkCapabilities.getTransportTypes()) {
|
||||||
|
//// builder.addTransportType(transportType)
|
||||||
|
//// }
|
||||||
|
// connectivityManager.registerNetworkCallback(builder.build(), mNetworkCallback)
|
||||||
|
// }
|
||||||
|
//
|
||||||
|
// /*
|
||||||
|
// * Helpful:
|
||||||
|
// * http://stackoverflow.com/questions/6517314/android-wifi-connection-programmatically
|
||||||
|
// */
|
||||||
|
// fun getScanResultSecurity(result: ScanResult): String? {
|
||||||
|
// val capabilities: String = result.capabilities
|
||||||
|
// val securityModes = arrayOf("WEP", "PSK", "EAP")
|
||||||
|
// for (securityMode in securityModes) {
|
||||||
|
// if (capabilities.contains(securityMode)) {
|
||||||
|
// return securityMode
|
||||||
|
// }
|
||||||
|
// }
|
||||||
|
// return "OPEN"
|
||||||
|
// }
|
||||||
|
//
|
||||||
|
// //connects to the given ssid
|
||||||
|
// fun connectToWPAWiFi(ssid: String, password: String){
|
||||||
|
//
|
||||||
|
// WifiUtils.withContext(context)
|
||||||
|
// .connectWith(ssid, "")
|
||||||
|
// .setTimeout(40000)
|
||||||
|
// .onConnectionResult(object : ConnectionSuccessListener {
|
||||||
|
// override fun success() {
|
||||||
|
// Log.v(TAG,"Success")
|
||||||
|
// }
|
||||||
|
//
|
||||||
|
// override fun failed(@NonNull errorCode: ConnectionErrorCode) {
|
||||||
|
// Log.v(TAG,"Failed")
|
||||||
|
// }
|
||||||
|
// })
|
||||||
|
// .start()
|
||||||
|
// if(isConnectedTo(ssid)){ //see if we are already connected to the given ssid
|
||||||
|
// return
|
||||||
|
// }
|
||||||
|
//
|
||||||
|
// if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.Q) {
|
||||||
|
// Log.e(TAG, "connection wifi Q")
|
||||||
|
//
|
||||||
|
// val wifiNetworkSpecifier: WifiNetworkSpecifier = WifiNetworkSpecifier.Builder()
|
||||||
|
// .setSsid(ssid)
|
||||||
|
// .setWpa2Passphrase(password)
|
||||||
|
// .build()
|
||||||
|
//
|
||||||
|
// val networkRequest: NetworkRequest = NetworkRequest.Builder()
|
||||||
|
// .addTransportType(NetworkCapabilities.TRANSPORT_WIFI)
|
||||||
|
// .setNetworkSpecifier(wifiNetworkSpecifier)
|
||||||
|
// .build()
|
||||||
|
//
|
||||||
|
// var connectivityManager = context.getSystemService(Context.CONNECTIVITY_SERVICE) as ConnectivityManager
|
||||||
|
// var networkCallback = object : ConnectivityManager.NetworkCallback() {
|
||||||
|
// override fun onAvailable(network: Network) {
|
||||||
|
// super.onAvailable(network)
|
||||||
|
// connectivityManager.bindProcessToNetwork(network)
|
||||||
|
// Log.e(TAG, "onAvailable")
|
||||||
|
// }
|
||||||
|
//
|
||||||
|
// override fun onLosing(network: Network, maxMsToLive: Int) {
|
||||||
|
// super.onLosing(network, maxMsToLive)
|
||||||
|
// Log.e(TAG, "onLosing")
|
||||||
|
// }
|
||||||
|
//
|
||||||
|
// override fun onLost(network: Network) {
|
||||||
|
// super.onLost(network)
|
||||||
|
// Log.e(TAG, "onLosing")
|
||||||
|
// Log.e(TAG, "losing active connection")
|
||||||
|
// }
|
||||||
|
//
|
||||||
|
// override fun onUnavailable() {
|
||||||
|
// super.onUnavailable()
|
||||||
|
// Log.e(TAG, "onUnavailable")
|
||||||
|
// }
|
||||||
|
// }
|
||||||
|
// connectivityManager.requestNetwork(networkRequest, networkCallback)
|
||||||
|
//
|
||||||
|
// }else{
|
||||||
|
//
|
||||||
|
// try {
|
||||||
|
// val wm:WifiManager= context.applicationContext.getSystemService(Context.WIFI_SERVICE) as WifiManager
|
||||||
|
//
|
||||||
|
// Log.e(TAG, "connection wifi pre Q")
|
||||||
|
//
|
||||||
|
// var netId: Int = wm.addNetwork(getWifiConfig(ssid))
|
||||||
|
// if (netId == -1) netId = getExistingNetworkId(ssid);
|
||||||
|
// wm.saveConfiguration()
|
||||||
|
// if(wm.enableNetwork(netId, true)){
|
||||||
|
// Log.v(TAG,"HMG-GUEST Connected")
|
||||||
|
// }else{
|
||||||
|
// Log.v(TAG,"HMG-GUEST failed to connect")
|
||||||
|
// }
|
||||||
|
// } catch (e: Exception) {
|
||||||
|
// e.printStackTrace()
|
||||||
|
// Log.v(TAG,"HMG-GUEST failed to connect")
|
||||||
|
// }
|
||||||
|
// }
|
||||||
|
//
|
||||||
|
// }
|
||||||
|
//
|
||||||
|
// fun connectedNetworkId():Int{
|
||||||
|
// val wm:WifiManager= context.applicationContext.getSystemService(Context.WIFI_SERVICE) as WifiManager
|
||||||
|
// return wm.connectionInfo.networkId
|
||||||
|
// }
|
||||||
|
//
|
||||||
|
// fun connectedNetworkIPAddress():Int{
|
||||||
|
// val wm:WifiManager= context.applicationContext.getSystemService(Context.WIFI_SERVICE) as WifiManager
|
||||||
|
// return wm.connectionInfo.ipAddress
|
||||||
|
// }
|
||||||
|
//
|
||||||
|
// fun isConnectedTo(bssid: String):Boolean{
|
||||||
|
// val wm:WifiManager= context.applicationContext.getSystemService(Context.WIFI_SERVICE) as WifiManager
|
||||||
|
// if(wm.connectionInfo.bssid == bssid){
|
||||||
|
// return true
|
||||||
|
// }
|
||||||
|
// return false
|
||||||
|
// }
|
||||||
|
//
|
||||||
|
//}
|
||||||
@ -0,0 +1,127 @@
|
|||||||
|
package com.cloud.diplomaticquarterapp.utils
|
||||||
|
|
||||||
|
import android.content.Context
|
||||||
|
import android.net.wifi.WifiManager
|
||||||
|
import android.util.Log
|
||||||
|
import com.cloud.diplomaticquarterapp.MainActivity
|
||||||
|
import com.cloud.diplomaticquarterapp.hmgwifi.HMG_Guest
|
||||||
|
import com.cloud.diplomaticquarterapp.hmgwifi.HMG_Internet
|
||||||
|
import com.cloud.diplomaticquarterapp.geofence.GeoZoneModel
|
||||||
|
import com.cloud.diplomaticquarterapp.geofence.HMG_Geofence
|
||||||
|
import io.flutter.plugin.common.BinaryMessenger
|
||||||
|
import io.flutter.plugin.common.MethodCall
|
||||||
|
import io.flutter.plugin.common.MethodChannel
|
||||||
|
|
||||||
|
class PlatformBridge(binaryMessenger: BinaryMessenger, flutterMainActivity: MainActivity) {
|
||||||
|
private var binaryMessenger = binaryMessenger
|
||||||
|
private var mainActivity = flutterMainActivity
|
||||||
|
|
||||||
|
private lateinit var channel: MethodChannel
|
||||||
|
|
||||||
|
companion object {
|
||||||
|
private const val CHANNEL = "HMG-Platform-Bridge"
|
||||||
|
private const val HMG_INTERNET_WIFI_CONNECT_METHOD = "connectHMGInternetWifi"
|
||||||
|
private const val HMG_GUEST_WIFI_CONNECT_METHOD = "connectHMGGuestWifi"
|
||||||
|
private const val ENABLE_WIFI_IF_NOT = "enableWifiIfNot"
|
||||||
|
private const val REGISTER_HMG_GEOFENCES = "registerHmgGeofences"
|
||||||
|
private const val UN_REGISTER_HMG_GEOFENCES = "unRegisterHmgGeofences"
|
||||||
|
}
|
||||||
|
|
||||||
|
fun create(){
|
||||||
|
channel = MethodChannel(binaryMessenger, CHANNEL)
|
||||||
|
HMGUtils.setPlatformChannel(channel)
|
||||||
|
channel.setMethodCallHandler { methodCall: MethodCall, result: MethodChannel.Result ->
|
||||||
|
|
||||||
|
if (methodCall.method == HMG_INTERNET_WIFI_CONNECT_METHOD) {
|
||||||
|
connectHMGInternetWifi(methodCall,result)
|
||||||
|
|
||||||
|
}else if (methodCall.method == HMG_GUEST_WIFI_CONNECT_METHOD) {
|
||||||
|
connectHMGGuestWifi(methodCall,result)
|
||||||
|
|
||||||
|
}else if (methodCall.method == ENABLE_WIFI_IF_NOT) {
|
||||||
|
enableWifiIfNot(methodCall,result)
|
||||||
|
}else if (methodCall.method == REGISTER_HMG_GEOFENCES) {
|
||||||
|
registerHmgGeofences(methodCall,result)
|
||||||
|
}else if (methodCall.method == UN_REGISTER_HMG_GEOFENCES) {
|
||||||
|
unRegisterHmgGeofences(methodCall,result)
|
||||||
|
}else{
|
||||||
|
|
||||||
|
result.notImplemented()
|
||||||
|
}
|
||||||
|
|
||||||
|
}
|
||||||
|
|
||||||
|
val res = channel.invokeMethod("localizedValue","errorConnectingHmgNetwork")
|
||||||
|
print(res)
|
||||||
|
}
|
||||||
|
|
||||||
|
private fun connectHMGInternetWifi(methodCall: MethodCall, result: MethodChannel.Result){
|
||||||
|
(methodCall.arguments as ArrayList<*>).let {
|
||||||
|
require(it.size > 0 && (it[0] is String),lazyMessage = {
|
||||||
|
"Missing or invalid arguments (Must have one argument 'String at 0'"
|
||||||
|
})
|
||||||
|
|
||||||
|
val patientId = it[0].toString()
|
||||||
|
HMG_Internet(mainActivity)
|
||||||
|
.connectToHMGGuestNetwork(patientId){ status, message ->
|
||||||
|
|
||||||
|
mainActivity.runOnUiThread {
|
||||||
|
result.success(if(status) 1 else 0)
|
||||||
|
|
||||||
|
HMGUtils.popFlutterText(mainActivity, message)
|
||||||
|
Log.v(this.javaClass.simpleName, "$status | $message")
|
||||||
|
}
|
||||||
|
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
private fun connectHMGGuestWifi(methodCall: MethodCall, result: MethodChannel.Result){
|
||||||
|
HMG_Guest(mainActivity).connectToHMGGuestNetwork { status, message ->
|
||||||
|
mainActivity.runOnUiThread {
|
||||||
|
result.success(if(status) 1 else 0)
|
||||||
|
|
||||||
|
HMGUtils.popFlutterText(mainActivity, message)
|
||||||
|
Log.v(this.javaClass.simpleName, "$status | $message")
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
private fun enableWifiIfNot(methodCall: MethodCall, result: MethodChannel.Result) {
|
||||||
|
val wm = mainActivity.applicationContext.getSystemService(Context.WIFI_SERVICE) as WifiManager?
|
||||||
|
if (wm != null){
|
||||||
|
if (!wm.isWifiEnabled)
|
||||||
|
wm.isWifiEnabled = true
|
||||||
|
result.success(true)
|
||||||
|
}else
|
||||||
|
result.error("101","Error while opening wifi, Please try to open wifi yourself and try again","'WifiManager' service failed");
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
private fun registerHmgGeofences(methodCall: MethodCall, result: MethodChannel.Result) {
|
||||||
|
|
||||||
|
channel.invokeMethod("getGeoZones",null, object : MethodChannel.Result{
|
||||||
|
override fun success(result: Any?) {
|
||||||
|
if(result is String) {
|
||||||
|
val geoZones = GeoZoneModel().listFrom(result)
|
||||||
|
HMG_Geofence.shared(mainActivity).register(geoZones)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
override fun error(errorCode: String?, errorMessage: String?, errorDetails: Any?) { print(result) }
|
||||||
|
override fun notImplemented() { print(result) }
|
||||||
|
})
|
||||||
|
|
||||||
|
}
|
||||||
|
|
||||||
|
private fun unRegisterHmgGeofences(methodCall: MethodCall, result: MethodChannel.Result) {
|
||||||
|
HMG_Geofence.shared(mainActivity).unRegisterAll { status, exception ->
|
||||||
|
if(status)
|
||||||
|
result.success(true)
|
||||||
|
else
|
||||||
|
result.error("101", exception?.localizedMessage, exception);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
}
|
||||||
|
After Width: | Height: | Size: 1.9 KiB |
|
After Width: | Height: | Size: 1.7 KiB |
|
After Width: | Height: | Size: 1021 B |
|
After Width: | Height: | Size: 180 B |
|
After Width: | Height: | Size: 1.0 KiB |
@ -0,0 +1,3 @@
|
|||||||
|
<?xml version="1.0" encoding="utf-8"?>
|
||||||
|
<resources xmlns:tools="http://schemas.android.com/tools"
|
||||||
|
tools:keep="@drawable/*,@raw/slow_spring_board" />
|
||||||
@ -0,0 +1,16 @@
|
|||||||
|
<resources>
|
||||||
|
<string name="app_name">HMG Patient App</string>
|
||||||
|
|
||||||
|
<string name="geofence_unknown_error">
|
||||||
|
Unknown error: the Geofence service is not available now.
|
||||||
|
</string>
|
||||||
|
<string name="geofence_not_available">
|
||||||
|
Geofence service is not available now. Go to Settings>Location>Mode and choose High accuracy.
|
||||||
|
</string>
|
||||||
|
<string name="geofence_too_many_geofences">
|
||||||
|
Your app has registered too many geofences.
|
||||||
|
</string>
|
||||||
|
<string name="geofence_too_many_pending_intents">
|
||||||
|
You have provided too many PendingIntents to the addGeofences() call.
|
||||||
|
</string>
|
||||||
|
</resources>
|
||||||
@ -0,0 +1,40 @@
|
|||||||
|
{
|
||||||
|
"project_info": {
|
||||||
|
"project_number": "864393916058",
|
||||||
|
"firebase_url": "https://diplomaticquarter-d2385.firebaseio.com",
|
||||||
|
"project_id": "diplomaticquarter-d2385",
|
||||||
|
"storage_bucket": "diplomaticquarter-d2385.appspot.com"
|
||||||
|
},
|
||||||
|
"client": [
|
||||||
|
{
|
||||||
|
"client_info": {
|
||||||
|
"mobilesdk_app_id": "1:864393916058:android:5b5a65cd6d8c18b4b97923",
|
||||||
|
"android_client_info": {
|
||||||
|
"package_name": "com.cloud.diplomaticquarterapp"
|
||||||
|
}
|
||||||
|
},
|
||||||
|
"oauth_client": [
|
||||||
|
{
|
||||||
|
"client_id": "864393916058-tphjrn8j39ntevt32ekcvmll8aue7qql.apps.googleusercontent.com",
|
||||||
|
"client_type": 3
|
||||||
|
}
|
||||||
|
],
|
||||||
|
"api_key": [
|
||||||
|
{
|
||||||
|
"current_key": "AIzaSyBdV3mos1BPhUzNKCj2KANJtiO3o2zh9IM"
|
||||||
|
}
|
||||||
|
],
|
||||||
|
"services": {
|
||||||
|
"appinvite_service": {
|
||||||
|
"other_platform_oauth_client": [
|
||||||
|
{
|
||||||
|
"client_id": "864393916058-tphjrn8j39ntevt32ekcvmll8aue7qql.apps.googleusercontent.com",
|
||||||
|
"client_type": 3
|
||||||
|
}
|
||||||
|
]
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
],
|
||||||
|
"configuration_version": "1"
|
||||||
|
}
|
||||||
@ -1,4 +1,5 @@
|
|||||||
org.gradle.jvmargs=-Xmx1536M
|
|
||||||
android.enableR8=true
|
android.enableR8=true
|
||||||
android.useAndroidX=true
|
android.useAndroidX=true
|
||||||
android.enableJetifier=true
|
android.enableJetifier=true
|
||||||
|
org.gradle.jvmargs=-Xmx4608m
|
||||||
|
|||||||
@ -1,6 +1,6 @@
|
|||||||
#Fri Jun 23 08:50:38 CEST 2017
|
#Thu Sep 03 16:26:30 EEST 2020
|
||||||
distributionBase=GRADLE_USER_HOME
|
distributionBase=GRADLE_USER_HOME
|
||||||
distributionPath=wrapper/dists
|
distributionPath=wrapper/dists
|
||||||
zipStoreBase=GRADLE_USER_HOME
|
zipStoreBase=GRADLE_USER_HOME
|
||||||
zipStorePath=wrapper/dists
|
zipStorePath=wrapper/dists
|
||||||
distributionUrl=https\://services.gradle.org/distributions/gradle-5.6.2-all.zip
|
distributionUrl=https\://services.gradle.org/distributions/gradle-6.1.1-all.zip
|
||||||
|
|||||||
@ -0,0 +1 @@
|
|||||||
|
include ':app'
|
||||||
@ -0,0 +1,93 @@
|
|||||||
|
Copyright (c) 2014-2015 Wei Huang (wweeiihhuuaanngg@gmail.com)
|
||||||
|
|
||||||
|
This Font Software is licensed under the SIL Open Font License, Version 1.1.
|
||||||
|
This license is copied below, and is also available with a FAQ at:
|
||||||
|
http://scripts.sil.org/OFL
|
||||||
|
|
||||||
|
|
||||||
|
-----------------------------------------------------------
|
||||||
|
SIL OPEN FONT LICENSE Version 1.1 - 26 February 2007
|
||||||
|
-----------------------------------------------------------
|
||||||
|
|
||||||
|
PREAMBLE
|
||||||
|
The goals of the Open Font License (OFL) are to stimulate worldwide
|
||||||
|
development of collaborative font projects, to support the font creation
|
||||||
|
efforts of academic and linguistic communities, and to provide a free and
|
||||||
|
open framework in which fonts may be shared and improved in partnership
|
||||||
|
with others.
|
||||||
|
|
||||||
|
The OFL allows the licensed fonts to be used, studied, modified and
|
||||||
|
redistributed freely as long as they are not sold by themselves. The
|
||||||
|
fonts, including any derivative works, can be bundled, embedded,
|
||||||
|
redistributed and/or sold with any software provided that any reserved
|
||||||
|
names are not used by derivative works. The fonts and derivatives,
|
||||||
|
however, cannot be released under any other type of license. The
|
||||||
|
requirement for fonts to remain under this license does not apply
|
||||||
|
to any document created using the fonts or their derivatives.
|
||||||
|
|
||||||
|
DEFINITIONS
|
||||||
|
"Font Software" refers to the set of files released by the Copyright
|
||||||
|
Holder(s) under this license and clearly marked as such. This may
|
||||||
|
include source files, build scripts and documentation.
|
||||||
|
|
||||||
|
"Reserved Font Name" refers to any names specified as such after the
|
||||||
|
copyright statement(s).
|
||||||
|
|
||||||
|
"Original Version" refers to the collection of Font Software components as
|
||||||
|
distributed by the Copyright Holder(s).
|
||||||
|
|
||||||
|
"Modified Version" refers to any derivative made by adding to, deleting,
|
||||||
|
or substituting -- in part or in whole -- any of the components of the
|
||||||
|
Original Version, by changing formats or by porting the Font Software to a
|
||||||
|
new environment.
|
||||||
|
|
||||||
|
"Author" refers to any designer, engineer, programmer, technical
|
||||||
|
writer or other person who contributed to the Font Software.
|
||||||
|
|
||||||
|
PERMISSION & CONDITIONS
|
||||||
|
Permission is hereby granted, free of charge, to any person obtaining
|
||||||
|
a copy of the Font Software, to use, study, copy, merge, embed, modify,
|
||||||
|
redistribute, and sell modified and unmodified copies of the Font
|
||||||
|
Software, subject to the following conditions:
|
||||||
|
|
||||||
|
1) Neither the Font Software nor any of its individual components,
|
||||||
|
in Original or Modified Versions, may be sold by itself.
|
||||||
|
|
||||||
|
2) Original or Modified Versions of the Font Software may be bundled,
|
||||||
|
redistributed and/or sold with any software, provided that each copy
|
||||||
|
contains the above copyright notice and this license. These can be
|
||||||
|
included either as stand-alone text files, human-readable headers or
|
||||||
|
in the appropriate machine-readable metadata fields within text or
|
||||||
|
binary files as long as those fields can be easily viewed by the user.
|
||||||
|
|
||||||
|
3) No Modified Version of the Font Software may use the Reserved Font
|
||||||
|
Name(s) unless explicit written permission is granted by the corresponding
|
||||||
|
Copyright Holder. This restriction only applies to the primary font name as
|
||||||
|
presented to the users.
|
||||||
|
|
||||||
|
4) The name(s) of the Copyright Holder(s) or the Author(s) of the Font
|
||||||
|
Software shall not be used to promote, endorse or advertise any
|
||||||
|
Modified Version, except to acknowledge the contribution(s) of the
|
||||||
|
Copyright Holder(s) and the Author(s) or with their explicit written
|
||||||
|
permission.
|
||||||
|
|
||||||
|
5) The Font Software, modified or unmodified, in part or in whole,
|
||||||
|
must be distributed entirely under this license, and must not be
|
||||||
|
distributed under any other license. The requirement for fonts to
|
||||||
|
remain under this license does not apply to any document created
|
||||||
|
using the Font Software.
|
||||||
|
|
||||||
|
TERMINATION
|
||||||
|
This license becomes null and void if any of the above conditions are
|
||||||
|
not met.
|
||||||
|
|
||||||
|
DISCLAIMER
|
||||||
|
THE FONT SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
|
||||||
|
EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO ANY WARRANTIES OF
|
||||||
|
MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT
|
||||||
|
OF COPYRIGHT, PATENT, TRADEMARK, OR OTHER RIGHT. IN NO EVENT SHALL THE
|
||||||
|
COPYRIGHT HOLDER BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY,
|
||||||
|
INCLUDING ANY GENERAL, SPECIAL, INDIRECT, INCIDENTAL, OR CONSEQUENTIAL
|
||||||
|
DAMAGES, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
|
||||||
|
FROM, OUT OF THE USE OR INABILITY TO USE THE FONT SOFTWARE OR FROM
|
||||||
|
OTHER DEALINGS IN THE FONT SOFTWARE.
|
||||||
|
After Width: | Height: | Size: 18 KiB |
|
After Width: | Height: | Size: 41 KiB |
|
After Width: | Height: | Size: 1.3 KiB |
|
After Width: | Height: | Size: 24 KiB |
|
After Width: | Height: | Size: 44 KiB |
|
After Width: | Height: | Size: 1.6 KiB |
|
After Width: | Height: | Size: 408 B |
|
After Width: | Height: | Size: 130 KiB |
|
After Width: | Height: | Size: 24 KiB |
|
After Width: | Height: | Size: 19 KiB |
|
After Width: | Height: | Size: 52 KiB |
|
After Width: | Height: | Size: 60 KiB |
|
After Width: | Height: | Size: 30 KiB |
|
After Width: | Height: | Size: 34 KiB |
|
After Width: | Height: | Size: 3.4 KiB |
|
After Width: | Height: | Size: 62 KiB |
|
After Width: | Height: | Size: 76 KiB |
|
After Width: | Height: | Size: 30 KiB |
|
After Width: | Height: | Size: 12 KiB |