Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Testing, Map and Information - final layouts #1

Open
wants to merge 16 commits into
base: master
Choose a base branch
from
1 change: 1 addition & 0 deletions app/.idea/gradle.xml

Some generated files are not rendered by default. Learn more about how customized files appear on GitHub.

28 changes: 11 additions & 17 deletions app/app/build.gradle
Original file line number Diff line number Diff line change
@@ -1,19 +1,3 @@
/*
* Copyright 2020 The Android Open Source Project
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* https://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/

apply plugin: 'com.android.application'
apply plugin: 'kotlin-android'
apply plugin: 'kotlin-kapt'
Expand Down Expand Up @@ -66,10 +50,17 @@ dependencies {
implementation 'androidx.appcompat:appcompat:1.1.0'
implementation 'androidx.lifecycle:lifecycle-runtime-ktx:2.2.0'
implementation 'androidx.constraintlayout:constraintlayout:1.1.3'
implementation 'androidx.legacy:legacy-support-v4:1.0.0'
implementation 'androidx.preference:preference:1.1.0-rc01'
implementation 'de.hdodenhof:circleimageview:3.1.0'
implementation 'com.google.code.gson:gson:2.8.6'
testImplementation 'junit:junit:4.12'

implementation 'com.google.firebase:firebase-ml-vision:24.0.2'
// If you want to detect face contours (landmark detection and classification
// don't require this additional model):
implementation 'com.google.firebase:firebase-ml-vision-face-model:20.0.0'

// Navigation library
def nav_version = "2.2.1"
implementation "androidx.navigation:navigation-fragment-ktx:$nav_version"
Expand Down Expand Up @@ -107,5 +98,8 @@ dependencies {
androidTestImplementation 'androidx.test:rules:1.2.0'
androidTestImplementation 'androidx.test:runner:1.2.0'
androidTestImplementation 'androidx.test.espresso:espresso-core:3.2.0'
implementation 'com.google.android.material:material:1.0.0'
implementation 'androidx.cardview:cardview:1.0.0'
implementation 'com.google.android.gms:play-services-maps:17.0.0'
implementation 'com.google.android.gms:play-services-location:17.0.0'
}

69 changes: 42 additions & 27 deletions app/app/src/main/AndroidManifest.xml
Original file line number Diff line number Diff line change
@@ -1,19 +1,4 @@
<?xml version="1.0" encoding="utf-8"?>
<!--
~ Copyright 2020 The Android Open Source Project
~
~ Licensed under the Apache License, Version 2.0 (the "License");
~ you may not use this file except in compliance with the License.
~ You may obtain a copy of the License at
~
~ https://www.apache.org/licenses/LICENSE-2.0
~
~ Unless required by applicable law or agreed to in writing, software
~ distributed under the License is distributed on an "AS IS" BASIS,
~ WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
~ See the License for the specific language governing permissions and
~ limitations under the License.
-->
<manifest
xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:dist="http://schemas.android.com/apk/distribution"
Expand All @@ -25,32 +10,47 @@

<!-- Declare features -->
<uses-feature android:name="android.hardware.camera" />
<uses-feature
android:name="android.location.Location"
android:required="true" />

<!-- Declare permissions -->
<uses-permission android:name="android.permission.INTERNET" />
<uses-permission android:name="android.permission.ACCESS_FINE_LOCATION" />
<uses-permission android:name="android.permission.ACCESS_COARSE_LOCATION" />
<uses-permission android:name="android.permission.ACCESS_NETWORK_STATE" />
<uses-permission android:name="android.permission.WRITE_EXTERNAL_STORAGE" />
<uses-permission android:name="com.google.android.providers.gsf.permission.READ_GSERVICES" />
<uses-permission android:name="com.dev.cromer.jason.coverme.permission.MAPS_RECEIVE" />
<uses-permission android:name="android.permission.CAMERA" />
<uses-permission android:name="android.permission.SEND_SMS" />

<application
android:allowBackup="true"
android:icon="@mipmap/ic_launcher"
android:roundIcon="@mipmap/ic_launcher_round"
android:label="@string/app_name"
android:allowBackup="true"
android:roundIcon="@mipmap/ic_launcher_round"
android:supportsRtl="true"
android:theme="@style/AppTheme"
tools:ignore="AllowBackup">

<!-- Main Activity -->
<activity android:name=".MainActivity">
<intent-filter>
<action android:name="android.intent.action.MAIN" />

<category android:name="android.intent.category.LAUNCHER" />
</intent-filter>
</activity>

<!-- Self Testing Activity -->
<activity
android:name=".MainActivity"
android:name=".SelfTesting"
android:clearTaskOnLaunch="true"
android:theme="@style/AppTheme"
android:icon="@mipmap/ic_launcher"
android:screenOrientation="fullUser"
android:rotationAnimation="seamless"
tools:targetApi="O">

<!-- Main app intent filter -->
<intent-filter>
<action android:name="android.intent.action.MAIN" />
<category android:name="android.intent.category.LAUNCHER" />
</intent-filter>

<!-- Register as a system camera app -->
<intent-filter>
<action android:name="android.media.action.IMAGE_CAPTURE" />
Expand All @@ -75,6 +75,22 @@

</activity>

<!-- Other Testing Activity -->
<activity android:name=".OtherTesting" />

<!-- Settings Activity -->
<activity
android:name=".settings.SettingsActivity"
android:label="@string/title_activity_settings" />

<!-- Declare Google Maps API Keys -->
<meta-data
android:name="com.google.android.geo.API_KEY"
android:value="AIzaSyBNm-E7ZO5XA7WYNaiW0RA1KUZAEG-XIEE" />
<meta-data
android:name="com.google.android.geo.API_KEY"
android:value="AIzaSyBNm-E7ZO5XA7WYNaiW0RA1KUZAEG-XIEE" />

<!-- FileProvider used to share photos with other apps -->
<provider
android:name="androidx.core.content.FileProvider"
Expand All @@ -85,7 +101,6 @@
android:name="android.support.FILE_PROVIDER_PATHS"
android:resource="@xml/file_paths"/>
</provider>

</application>

</manifest>
2 changes: 2 additions & 0 deletions app/app/src/main/assets/arms_information.txt
Original file line number Diff line number Diff line change
@@ -0,0 +1,2 @@
The person may not be able to lift both arms and keep them there because of weakness or numbness in one arm.
Is one arm weak or numb? Ask the person to raise both arms. Does one arm drift downward?
2 changes: 2 additions & 0 deletions app/app/src/main/assets/face_information.txt
Original file line number Diff line number Diff line change
@@ -0,0 +1,2 @@
The face may have dropped on one side, the person may not be able to smile, or their mouth or eye may have drooped.
Does one side of the face droop or is it numb? Ask the person to smile. Is the person's smile uneven or lopsided?
1 change: 1 addition & 0 deletions app/app/src/main/assets/speech_information.txt
Original file line number Diff line number Diff line change
@@ -0,0 +1 @@
Their speech may be slurred or garbled, or the person may not be able to talk at all despite appearing to be awake. They may also have problems understanding what you're saying to them.
19 changes: 19 additions & 0 deletions app/app/src/main/assets/stroke_symptoms.txt
Original file line number Diff line number Diff line change
@@ -0,0 +1,19 @@
If you suspect you or someone else is having a stroke, phone 112 immediately and ask for an ambulance.
Even if the symptoms disappear while you're waiting for the ambulance, it's still important to go to hospital for an assessment.
After an initial assessment, you will be referred to a specialist for further tests to help determine the cause of the stroke. You should be referred to see a specialist within 24 hours of the start of your symptoms. Treatment can also begin if necessary.
Symptoms of a stroke that disappear quickly and in less than 24 hours may mean you had a transient ischaemic attack (TIA).
These symptoms should also be treated as a medical emergency to reduce the chances of having another stroke.

The signs and symptoms of a stroke vary from person to person, but usually begin suddenly.
As different parts of your brain control different parts of your body, your symptoms will depend on the part of your brain affected and the extent of the damage.
The main stroke symptoms can be remembered with the word FAST.

The symptoms of a transient ischaemic attack (TIA), also known as a mini-stroke, are the same as a stroke, but tend to only last between a few minutes and a few hours before disappearing completely.
Although the symptoms do improve, a TIA should never be ignored as it's a serious warning sign of a problem with the blood supply to your brain.
It means you're at an increased risk of having a stroke in the near future.

It's important to phone 112 immediately and ask for an ambulance if you or someone else have TIA or stroke symptoms.
If a TIA is suspected, you will be offered aspirin to take straightaway. This helps to prevent a stroke.
Even if the symptoms disappear while you're waiting for the ambulance to arrive, an assessment in a hospital should still be done. You should be referred to see a specialist within 24 hours of the start of your symptoms.
If you think you have had a TIA before, but the symptoms have since passed and you did not seek medical advice at the time, make an urgent appointment with a GP.
They can refer you for a hospital assessment, if appropriate.
1 change: 1 addition & 0 deletions app/app/src/main/assets/time_information.txt
Original file line number Diff line number Diff line change
@@ -0,0 +1 @@
If the person shows any of these symptoms, even if the symptoms go away, call 112 and get them to the hospital immediately.
Binary file added app/app/src/main/ic_launcher-playstore.png
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
113 changes: 57 additions & 56 deletions app/app/src/main/java/com/example/avcapp/MainActivity.kt
Original file line number Diff line number Diff line change
@@ -1,80 +1,81 @@
/*
* Copyright 2020 The Android Open Source Project
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* https://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/

package com.example.avcapp

import android.content.Context
import android.content.Intent
import android.os.Bundle
import android.view.KeyEvent
import android.view.View
import android.widget.TextView
import androidx.appcompat.app.AppCompatActivity
import java.io.File
import androidx.localbroadcastmanager.content.LocalBroadcastManager
import android.content.Intent
import android.widget.FrameLayout
import com.android.example.cameraxbasic.utils.FLAGS_FULLSCREEN
import com.google.firebase.FirebaseApp

const val KEY_EVENT_ACTION = "key_event_action"
const val KEY_EVENT_EXTRA = "key_event_extra"
private const val IMMERSIVE_FLAG_TIMEOUT = 500L
import androidx.viewpager.widget.ViewPager
import com.example.avcapp.settings.SettingsActivity
import com.example.avcapp.utils.makeStatusBarTransparent
import com.google.android.material.tabs.TabLayout

/**
* Main entry point into our app. This app follows the single-activity pattern, and all
* functionality is implemented in the form of fragments.
*/
class MainActivity : AppCompatActivity() {
private lateinit var container: FrameLayout

var tabLayout: TabLayout? = null
var viewPager: ViewPager? = null

override fun onCreate(savedInstanceState: Bundle?) {
super.onCreate(savedInstanceState)
setContentView(R.layout.activity_main)
container = findViewById(R.id.fragment_container)
FirebaseApp.initializeApp(applicationContext)
}

override fun onResume() {
super.onResume()
// Before setting full screen flags, we must wait a bit to let UI settle; otherwise, we may
// be trying to set app to immersive mode before it's ready and the flags do not stick
container.postDelayed({
container.systemUiVisibility = FLAGS_FULLSCREEN
}, IMMERSIVE_FLAG_TIMEOUT)
}
makeStatusBarTransparent()

tabLayout = findViewById<TabLayout>(R.id.tabLayout)
viewPager = findViewById<ViewPager>(R.id.viewPager)

tabLayout!!.addTab(tabLayout!!.newTab().setText(R.string.testing_fragment))
tabLayout!!.addTab(tabLayout!!.newTab().setText(R.string.map_fragment))
tabLayout!!.addTab(tabLayout!!.newTab().setText(R.string.information_fragment))
tabLayout!!.tabGravity = TabLayout.GRAVITY_FILL

val adapter = MyAdapter(this, supportFragmentManager, tabLayout!!.tabCount)
viewPager!!.adapter = adapter

viewPager!!.addOnPageChangeListener(TabLayout.TabLayoutOnPageChangeListener(tabLayout))

tabLayout!!.addOnTabSelectedListener(object : TabLayout.OnTabSelectedListener {
override fun onTabSelected(tab: TabLayout.Tab) {
viewPager!!.currentItem = tab.position
}
override fun onTabUnselected(tab: TabLayout.Tab) {

/** When key down event is triggered, relay it via local broadcast so fragments can handle it */
override fun onKeyDown(keyCode: Int, event: KeyEvent): Boolean {
return when (keyCode) {
KeyEvent.KEYCODE_VOLUME_DOWN -> {
val intent = Intent(KEY_EVENT_ACTION).apply { putExtra(KEY_EVENT_EXTRA, keyCode) }
LocalBroadcastManager.getInstance(this).sendBroadcast(intent)
true
}
else -> super.onKeyDown(keyCode, event)
override fun onTabReselected(tab: TabLayout.Tab) {

}
})

val sharedPref = this.getSharedPreferences(getString(R.string.app_name), Context.MODE_PRIVATE) ?: return
with (sharedPref.edit()) {
putString(getString(R.string.user_name), "John Doe")
putString(getString(R.string.country), "Iasi, Romania")
putString(getString(R.string.contact_name), "Robert Jr.")
putString(getString(R.string.contact_number), "+40751753645")
commit()
}

(this.findViewById<View>(R.id.welcomeMessage) as TextView).text = getString(R.string.welcome_message,
sharedPref.getString(getString(R.string.user_name), ""))
}

companion object {
fun goToSettings(view: View) {
val intent = Intent(this, SettingsActivity::class.java)
startActivity(intent)
}

/** Use external media if it is available, our app's file directory otherwise */
fun getOutputDirectory(context: Context): File {
val appContext = context.applicationContext
val mediaDir = context.externalMediaDirs.firstOrNull()?.let {
File(it, appContext.resources.getString(R.string.app_name)).apply { mkdirs() } }
return if (mediaDir != null && mediaDir.exists())
mediaDir else appContext.filesDir
}
fun goToOtherTest(view: View?) {
val intent = Intent(this, OtherTesting::class.java)
startActivity(intent)
}

fun goToSelfTest(view: View) {
val intent = Intent(this, SelfTesting::class.java)
startActivity(intent)
}
}
31 changes: 31 additions & 0 deletions app/app/src/main/java/com/example/avcapp/MyAdapter.kt
Original file line number Diff line number Diff line change
@@ -0,0 +1,31 @@
package com.example.avcapp

import android.content.Context
import androidx.fragment.app.Fragment
import androidx.fragment.app.FragmentManager
import androidx.fragment.app.FragmentPagerAdapter
import com.example.avcapp.fragments.InformationFragment
import com.example.avcapp.fragments.MapFragment
import com.example.avcapp.fragments.TestingFragment

class MyAdapter(private val myContext: Context, fm: FragmentManager, private var totalTabs: Int) : FragmentPagerAdapter(fm) {

override fun getItem(position: Int): Fragment {
return when (position) {
0 -> {
TestingFragment()
}
1 -> {
MapFragment()
}
2 -> {
InformationFragment()
}
else -> throw IllegalStateException("position $position is invalid for this viewpager")
}
}

override fun getCount(): Int {
return totalTabs
}
}
Loading