diff --git a/.gitignore b/.gitignore new file mode 100644 index 0000000..aa724b7 --- /dev/null +++ b/.gitignore @@ -0,0 +1,15 @@ +*.iml +.gradle +/local.properties +/.idea/caches +/.idea/libraries +/.idea/modules.xml +/.idea/workspace.xml +/.idea/navEditor.xml +/.idea/assetWizardSettings.xml +.DS_Store +/build +/captures +.externalNativeBuild +.cxx +local.properties diff --git a/.idea/.gitignore b/.idea/.gitignore new file mode 100644 index 0000000..26d3352 --- /dev/null +++ b/.idea/.gitignore @@ -0,0 +1,3 @@ +# Default ignored files +/shelf/ +/workspace.xml diff --git a/.idea/compiler.xml b/.idea/compiler.xml new file mode 100644 index 0000000..fcb19bf --- /dev/null +++ b/.idea/compiler.xml @@ -0,0 +1,6 @@ + + + + + + \ No newline at end of file diff --git a/.idea/gradle.xml b/.idea/gradle.xml new file mode 100644 index 0000000..a9f4e52 --- /dev/null +++ b/.idea/gradle.xml @@ -0,0 +1,18 @@ + + + + + + \ No newline at end of file diff --git a/.idea/misc.xml b/.idea/misc.xml new file mode 100644 index 0000000..2d78bff --- /dev/null +++ b/.idea/misc.xml @@ -0,0 +1,10 @@ + + + + + + + + + \ No newline at end of file diff --git a/app/.gitignore b/app/.gitignore new file mode 100644 index 0000000..42afabf --- /dev/null +++ b/app/.gitignore @@ -0,0 +1 @@ +/build \ No newline at end of file diff --git a/app/build.gradle b/app/build.gradle new file mode 100644 index 0000000..63f59a5 --- /dev/null +++ b/app/build.gradle @@ -0,0 +1,48 @@ +plugins { + id 'com.android.application' +} + +android { + namespace 'com.example.safecampus' + compileSdk 33 + buildToolsVersion "30.0.3" + + defaultConfig { + applicationId "com.example.safecampus" + minSdk 23 + targetSdk 31 + versionCode 1 + versionName "1.0" + + testInstrumentationRunner "androidx.test.runner.AndroidJUnitRunner" + } + + buildTypes { + release { + minifyEnabled false + proguardFiles getDefaultProguardFile('proguard-android-optimize.txt'), 'proguard-rules.pro' + } + } + compileOptions { + sourceCompatibility JavaVersion.VERSION_1_8 + targetCompatibility JavaVersion.VERSION_1_8 + } +} + +dependencies { + + implementation 'androidx.appcompat:appcompat:1.4.1' + implementation 'com.google.android.material:material:1.5.0' + implementation 'androidx.constraintlayout:constraintlayout:2.1.3' + testImplementation 'junit:junit:4.+' + androidTestImplementation 'androidx.test.ext:junit:1.1.3' + androidTestImplementation 'androidx.test.espresso:espresso-core:3.4.0' + + + implementation 'com.google.android.gms:play-services-maps:18.0.2' + implementation 'com.google.android.gms:play-services-location:19.0.1' + implementation 'com.github.tbouron.shakedetector:library:1.0.0@aar' + + implementation 'com.karumi:dexter:6.2.3' + +} \ No newline at end of file diff --git a/app/proguard-rules.pro b/app/proguard-rules.pro new file mode 100644 index 0000000..481bb43 --- /dev/null +++ b/app/proguard-rules.pro @@ -0,0 +1,21 @@ +# Add project specific ProGuard rules here. +# You can control the set of applied configuration files using the +# proguardFiles setting in build.gradle. +# +# For more details, see +# http://developer.android.com/guide/developing/tools/proguard.html + +# If your project uses WebView with JS, uncomment the following +# and specify the fully qualified class name to the JavaScript interface +# class: +#-keepclassmembers class fqcn.of.javascript.interface.for.webview { +# public *; +#} + +# Uncomment this to preserve the line number information for +# debugging stack traces. +#-keepattributes SourceFile,LineNumberTable + +# If you keep the line number information, uncomment this to +# hide the original source file name. +#-renamesourcefileattribute SourceFile \ No newline at end of file diff --git a/app/src/androidTest/java/com/example/safecampus/ExampleInstrumentedTest.java b/app/src/androidTest/java/com/example/safecampus/ExampleInstrumentedTest.java new file mode 100644 index 0000000..a12e88d --- /dev/null +++ b/app/src/androidTest/java/com/example/safecampus/ExampleInstrumentedTest.java @@ -0,0 +1,26 @@ +package com.example.safecampus; + +import android.content.Context; + +import androidx.test.platform.app.InstrumentationRegistry; +import androidx.test.ext.junit.runners.AndroidJUnit4; + +import org.junit.Test; +import org.junit.runner.RunWith; + +import static org.junit.Assert.*; + +/** + * Instrumented test, which will execute on an Android device. + * + * @see Testing documentation + */ +@RunWith(AndroidJUnit4.class) +public class ExampleInstrumentedTest { + @Test + public void useAppContext() { + // Context of the app under test. + Context appContext = InstrumentationRegistry.getInstrumentation().getTargetContext(); + assertEquals("com.example.safecampus", appContext.getPackageName()); + } +} \ No newline at end of file diff --git a/app/src/main/AndroidManifest.xml b/app/src/main/AndroidManifest.xml new file mode 100644 index 0000000..e116e01 --- /dev/null +++ b/app/src/main/AndroidManifest.xml @@ -0,0 +1,50 @@ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + \ No newline at end of file diff --git a/app/src/main/java/com/example/safecampus/ContactActivity.java b/app/src/main/java/com/example/safecampus/ContactActivity.java new file mode 100644 index 0000000..b49612f --- /dev/null +++ b/app/src/main/java/com/example/safecampus/ContactActivity.java @@ -0,0 +1,190 @@ +package com.example.safecampus; + +import androidx.appcompat.app.AppCompatActivity; +import androidx.recyclerview.widget.LinearLayoutManager; +import androidx.recyclerview.widget.RecyclerView; + +import android.app.Dialog; +import android.content.Intent; +import android.content.SharedPreferences; +import android.os.Bundle; +import android.view.View; +import android.view.Window; +import android.widget.Button; +import android.widget.EditText; +import android.widget.ImageView; +import android.widget.TextView; +import android.widget.Toast; + +import java.util.ArrayList; +import java.util.HashMap; +import java.util.LinkedHashSet; +import java.util.Set; + +public class ContactActivity extends AppCompatActivity { + + + EditText contact; + Button addContact; + + RecyclerView recyclerView; + + HashMap contacts; + + ArrayList send; + + ContactsAdapter adapter; + MyOnClickListener onClickListener; + + ImageView edit; + + TextView callerInfo; + + + @Override + public void onBackPressed() { + super.onBackPressed(); + startActivity(new Intent(this,MainActivity.class)); + this.finish(); + } + + @Override + protected void onCreate(Bundle savedInstanceState) { + super.onCreate(savedInstanceState); + setContentView(R.layout.activity_contact); + + + + edit = findViewById(R.id.editCallButton); + + + edit.setOnClickListener(new View.OnClickListener() { + @Override + public void onClick(View view) { + Dialog dialog = new Dialog(ContactActivity.this); + dialog.requestWindowFeature(Window.FEATURE_NO_TITLE); + dialog.setCancelable(false); + dialog.setContentView(R.layout.dialog); + + Button close,save; + close = dialog.findViewById(R.id.dialogCancel); + save = dialog.findViewById(R.id.dialogSave); + EditText number = dialog.findViewById(R.id.dialogEditText); + + save.setOnClickListener(new View.OnClickListener() { + @Override + public void onClick(View view) { + String numberText = number.getText().toString(); + if(numberText.length() == 10){ + SharedPreferences sharedPreferences = getSharedPreferences("MySharedPref",MODE_PRIVATE); + SharedPreferences.Editor editor = sharedPreferences.edit(); + editor.putString("firstNumber",numberText); + editor.apply(); + setCallingInformation(); + dialog.dismiss(); + }else { + Toast.makeText(ContactActivity.this, "Enter valid number!", Toast.LENGTH_SHORT).show(); + } + } + }); + + close.setOnClickListener(new View.OnClickListener() { + @Override + public void onClick(View view) { + dialog.dismiss(); + } + }); + + + dialog.show(); + } + }); + + + + + callerInfo = findViewById(R.id.callText); + + + setCallingInformation(); + + + contacts = new HashMap<>(); + send = new ArrayList<>(); + + adapter = new ContactsAdapter(this, send, new MyOnClickListener() { + @Override + public void onItemClicked(int position) { + deleteItemFromDatabase(position); + } + }); + + recyclerView = findViewById(R.id.contacts); + recyclerView.setAdapter(adapter); + recyclerView.setLayoutManager(new LinearLayoutManager(this)); + + getData(); + + contact = findViewById(R.id.contactGet); + addContact = findViewById(R.id.addContact); + + addContact.setOnClickListener(new View.OnClickListener() { + @Override + public void onClick(View view) { + createContact(contact.getText().toString()); + } + }); + } + + private void createContact(String contactString) { + SharedPreferences sharedPreferences = getSharedPreferences("MySharedPref",MODE_PRIVATE); + SharedPreferences.Editor editor = sharedPreferences.edit(); + Set oldNumbers = sharedPreferences.getStringSet("enumbers", new LinkedHashSet<>()); + oldNumbers.add(contactString); + editor.remove("enumbers"); + editor.putStringSet("enumbers",oldNumbers); + editor.apply(); + + contact.setText(""); + editor.apply(); + getData(); + + } + + + private void setCallingInformation(){ + SharedPreferences sharedPreferences = getSharedPreferences("MySharedPref",MODE_PRIVATE); + String firstNumber = sharedPreferences.getString("firstNumber","null"); + + if (firstNumber.isEmpty()||firstNumber.equalsIgnoreCase("null")){ + callerInfo.setText("Please add number."); + }else { + callerInfo.setText(firstNumber); + } + + } + + + + + private void deleteItemFromDatabase(int position) { + SharedPreferences sharedPreferences = getSharedPreferences("MySharedPref",MODE_PRIVATE); + Set oldNumbers = sharedPreferences.getStringSet("enumbers", new LinkedHashSet<>()); + SharedPreferences.Editor editor = sharedPreferences.edit(); + editor.remove("enumbers"); + oldNumbers.remove(send.get(position)); + editor.putStringSet("enumbers",oldNumbers); + editor.apply(); + getData(); + } + + + + private void getData() { + send.clear(); + SharedPreferences sharedPreferences = getSharedPreferences("MySharedPref",MODE_PRIVATE); + Set oldNumbers = sharedPreferences.getStringSet("enumbers", new LinkedHashSet<>()); + send.addAll(oldNumbers); + adapter.notifyDataSetChanged(); + } +} \ No newline at end of file diff --git a/app/src/main/java/com/example/safecampus/ContactsAdapter.java b/app/src/main/java/com/example/safecampus/ContactsAdapter.java new file mode 100644 index 0000000..087cff9 --- /dev/null +++ b/app/src/main/java/com/example/safecampus/ContactsAdapter.java @@ -0,0 +1,57 @@ +package com.example.safecampus; +import android.content.Context; +import android.view.LayoutInflater; +import android.view.View; +import android.view.ViewGroup; +import android.widget.ImageView; +import android.widget.TextView; + +import androidx.annotation.NonNull; +import androidx.recyclerview.widget.RecyclerView; + +import java.util.ArrayList; +import java.util.HashMap; + +public class ContactsAdapter extends RecyclerView.Adapter { + + HashMap contacts; + Context context; + ArrayList send; + MyOnClickListener myOnClickListener; + + ContactsAdapter(Context context, ArrayList send,MyOnClickListener myOnClickListener){ + this.send = send; + this.context = context; + this.myOnClickListener = myOnClickListener; + } + + @NonNull + @Override + public MyViewHolder onCreateViewHolder(@NonNull ViewGroup parent, int viewType) { + return new MyViewHolder(LayoutInflater.from(context).inflate(R.layout.contact_item,parent,false)); + } + + @Override + public void onBindViewHolder(@NonNull MyViewHolder holder, int position) { + holder.contact.setText(send.get(position)); + holder.delete.setOnClickListener(view -> myOnClickListener.onItemClicked(position)); + } + + @Override + public int getItemCount() { + return send.size(); + } + + class MyViewHolder extends RecyclerView.ViewHolder{ + + TextView name,contact; + ImageView delete; + + public MyViewHolder(@NonNull View itemView) { + super(itemView); + contact = itemView.findViewById(R.id.contactItem); + delete = itemView.findViewById(R.id.deleteIcon); + } + } + +} diff --git a/app/src/main/java/com/example/safecampus/LawDisplayerActivity.java b/app/src/main/java/com/example/safecampus/LawDisplayerActivity.java new file mode 100644 index 0000000..c2cb625 --- /dev/null +++ b/app/src/main/java/com/example/safecampus/LawDisplayerActivity.java @@ -0,0 +1,74 @@ +package com.example.safecampus; + +import androidx.appcompat.app.AppCompatActivity; + +import android.os.Bundle; +import android.view.View; +import android.widget.Button; +import android.widget.TextView; + +public class LawDisplayerActivity extends AppCompatActivity implements View.OnClickListener { + + TextView big,oneLine; + String[] laws, lawsContent; + int counter; + Button back, next; + View closeBtn; + @Override + protected void onCreate(Bundle savedInstanceState) { + super.onCreate(savedInstanceState); + setContentView(R.layout.activity_law_displayer); + + big = findViewById(R.id.bigLaws); + oneLine = findViewById(R.id.lawString); + counter = getIntent().getIntExtra("position",0); + laws = new String[]{ + "Tools for Self-Defense", + "Create Boundaries", + "Have a Plan Before going anywhere", + "Ping Your Location", + "Power Up", + "Use technology", + "Don’t take eve teasing lightly", + "Avoid late night travel ", + "In a sticky situation don’t be afraid to Attack", + "Feel regularly followed"}; + lawsContent = this.getResources().getStringArray(R.array.lawsBig); + + closeBtn = findViewById(R.id.closeBtn); + closeBtn.setOnClickListener(view -> { + onBackPressed(); + LawDisplayerActivity.this.finish(); + }); + + back = findViewById(R.id.backBtn); + next = findViewById(R.id.nextBtn); + next.setOnClickListener(this); + back.setOnClickListener(this); + setData(); + } + + public void setData(){ + oneLine.setText(laws[counter]); + big.setText(lawsContent[counter]); + } + + @Override + public void onClick(View view) { + if(view.getId() == R.id.nextBtn){ + if(counter<9){ + counter++; + }else { + counter = 0; + } + } else if (view.getId() == R.id.backBtn) { + if(counter == 0){ + counter = (laws.length-1); + }else { + counter--; + } + } + + setData(); + } +} \ No newline at end of file diff --git a/app/src/main/java/com/example/safecampus/LawModel.java b/app/src/main/java/com/example/safecampus/LawModel.java new file mode 100644 index 0000000..e3e6abe --- /dev/null +++ b/app/src/main/java/com/example/safecampus/LawModel.java @@ -0,0 +1,29 @@ +package com.example.safecampus; + +public class LawModel { + String lawString, lawDescription; + + public LawModel(String lawString, String lawDescription) { + this.lawString = lawString; + this.lawDescription = lawDescription; + } + + public LawModel() { + } + + public String getLawString() { + return lawString; + } + + public void setLawString(String lawString) { + this.lawString = lawString; + } + + public String getLawDescription() { + return lawDescription; + } + + public void setLawDescription(String lawDescription) { + this.lawDescription = lawDescription; + } +} diff --git a/app/src/main/java/com/example/safecampus/LawsActivity.java b/app/src/main/java/com/example/safecampus/LawsActivity.java new file mode 100644 index 0000000..46cab95 --- /dev/null +++ b/app/src/main/java/com/example/safecampus/LawsActivity.java @@ -0,0 +1,45 @@ +package com.example.safecampus; + +import androidx.appcompat.app.AppCompatActivity; +import androidx.recyclerview.widget.LinearLayoutManager; +import androidx.recyclerview.widget.RecyclerView; + +import android.content.Intent; +import android.os.Bundle; + +public class LawsActivity extends AppCompatActivity { + + @Override + public void onBackPressed() { + super.onBackPressed(); + startActivity(new Intent(LawsActivity.this,MainActivity.class)); + LawsActivity.this.finish(); + } + + @Override + protected void onCreate(Bundle savedInstanceState) { + super.onCreate(savedInstanceState); + setContentView(R.layout.activity_laws); + RecyclerView recyclerView = findViewById(R.id.recycleLaws); + String[] laws = new String[]{"Tools for Self-Defense","Create Boundaries", + "Have a Plan Before going anywhere","Ping Your Location","Power Up","Use technology", + "Don’t take eve teasing lightly","Avoid late night travel ", + "In a sticky situation don’t be afraid to Attack"," Feel regularly followed"}; + + MyAdapter adapter = new MyAdapter(this, laws, position -> { + Intent intent = new Intent(LawsActivity.this,LawDisplayerActivity.class); + intent.putExtra("position",position); + startActivity(intent); + }); + + recyclerView.setAdapter(adapter); + recyclerView.setLayoutManager(new LinearLayoutManager(this)); + + + + findViewById(R.id.backBtn).setOnClickListener(view -> { + startActivity(new Intent(LawsActivity.this,MainActivity.class)); + LawsActivity.this.finish(); + }); + } +} \ No newline at end of file diff --git a/app/src/main/java/com/example/safecampus/MainActivity.java b/app/src/main/java/com/example/safecampus/MainActivity.java new file mode 100644 index 0000000..1860be9 --- /dev/null +++ b/app/src/main/java/com/example/safecampus/MainActivity.java @@ -0,0 +1,93 @@ +package com.example.safecampus; + +import androidx.appcompat.app.AppCompatActivity; +import androidx.core.app.ActivityCompat; + +import android.Manifest; +import android.content.Intent; +import android.content.SharedPreferences; +import android.content.pm.PackageManager; +import android.net.Uri; +import android.os.Bundle; +import android.telephony.SmsManager; +import android.view.View; +import com.google.android.gms.location.FusedLocationProviderClient; +import com.google.android.gms.location.LocationServices; + +import java.util.HashSet; +import java.util.Set; + +public class MainActivity extends AppCompatActivity implements View.OnClickListener { + + FusedLocationProviderClient fusedLocationClient; + String myLocation = "", numberCall; + SmsManager manager = SmsManager.getDefault(); + + @Override + protected void onCreate(Bundle savedInstanceState) { + super.onCreate(savedInstanceState); + setContentView(R.layout.activity_main); + + fusedLocationClient = LocationServices.getFusedLocationProviderClient(this); + findViewById(R.id.panicBtn).setOnClickListener(this); + findViewById(R.id.fourth).setOnClickListener(this); + findViewById(R.id.first).setOnClickListener(this); + findViewById(R.id.second).setOnClickListener(this); + findViewById(R.id.fifth).setOnClickListener(this); + findViewById(R.id.mapBtn).setOnClickListener(this); + } + + @Override + public void onClick(View view) { + int id = view.getId(); + if (id == R.id.fourth) { + startActivity(new Intent(MainActivity.this, LawsActivity.class)); + MainActivity.this.finish(); + }else if(id == R.id.first) { + startActivity(new Intent(MainActivity.this, ContactActivity.class)); + MainActivity.this.finish(); + }else if(id == R.id.mapBtn){ + startActivity(new Intent(MainActivity.this, MapsActivity.class)); + MainActivity.this.finish(); + }else if(id == R.id.fifth){ + startActivity(new Intent(MainActivity.this, SelfDefenseActivity.class)); + } else if(id == R.id.second){ + startActivity(new Intent(MainActivity.this, SmsActivity.class)); + MainActivity.this.finish(); + } else if (id == R.id.panicBtn) { + + if (ActivityCompat.checkSelfPermission(this, Manifest.permission.ACCESS_FINE_LOCATION) != PackageManager.PERMISSION_GRANTED && ActivityCompat.checkSelfPermission(this, Manifest.permission.ACCESS_COARSE_LOCATION) != PackageManager.PERMISSION_GRANTED) { + return; + } + fusedLocationClient.getLastLocation() + .addOnSuccessListener(location -> { + if (location != null) { + location.getAltitude(); + location.getLongitude(); + myLocation = "http://maps.google.com/maps?q=loc:"+location.getLatitude()+","+location.getLongitude(); + }else { + myLocation = "Unable to Find Location :("; + } + sendMsg(); + }); + SharedPreferences sharedPreferences = getSharedPreferences("MySharedPref",MODE_PRIVATE); + numberCall = sharedPreferences.getString("firstNumber","None"); + if(!numberCall.equalsIgnoreCase("None")){ + Intent intent = new Intent(Intent.ACTION_CALL); + intent.setData(Uri.parse("tel:"+numberCall)); + startActivity(intent); + } + + } + + + } + void sendMsg(){ + SharedPreferences sharedPreferences = getSharedPreferences("MySharedPref",MODE_PRIVATE); + Set oldNumbers = sharedPreferences.getStringSet("enumbers", new HashSet<>()); + if(!oldNumbers.isEmpty()){ + for(String ENUM : oldNumbers) + manager.sendTextMessage(ENUM,null,"Im in Trouble!\nSending My Location :\n"+myLocation,null,null); + } + } +} \ No newline at end of file diff --git a/app/src/main/java/com/example/safecampus/MapsActivity.java b/app/src/main/java/com/example/safecampus/MapsActivity.java new file mode 100644 index 0000000..bcbaf71 --- /dev/null +++ b/app/src/main/java/com/example/safecampus/MapsActivity.java @@ -0,0 +1,23 @@ +package com.example.safecampus; + +import android.content.Intent; +import android.net.Uri; +import android.os.Bundle; +import android.view.View; + +import androidx.appcompat.app.AppCompatActivity; + +public class MapsActivity extends AppCompatActivity implements View.OnClickListener{ + + @Override + protected void onCreate(Bundle savedInstanceState) { + super.onCreate(savedInstanceState); + setContentView(R.layout.activity_maps); + + } + + @Override + public void onClick(View v) { + + } +} diff --git a/app/src/main/java/com/example/safecampus/MyAdapter.java b/app/src/main/java/com/example/safecampus/MyAdapter.java new file mode 100644 index 0000000..b91a023 --- /dev/null +++ b/app/src/main/java/com/example/safecampus/MyAdapter.java @@ -0,0 +1,55 @@ +package com.example.safecampus; + +import android.content.Context; +import android.view.LayoutInflater; +import android.view.View; +import android.view.ViewGroup; +import android.widget.TextView; + +import androidx.annotation.NonNull; +import androidx.recyclerview.widget.RecyclerView; + +public class MyAdapter extends RecyclerView.Adapter{ + + + String[] laws; + Context context; + MyOnClickListener myOnClickListener; + + public MyAdapter(Context context, String[] laws,MyOnClickListener onClickListener){ + this.laws = laws; + this.context = context; + this.myOnClickListener = onClickListener; + } + + @NonNull + @Override + public MyViewHolder onCreateViewHolder(@NonNull ViewGroup parent, int viewType) { + return new MyViewHolder(LayoutInflater.from(context).inflate(R.layout.law_item,parent,false)); + } + + @Override + public void onBindViewHolder(@NonNull MyViewHolder holder, int position) { + int newPosition = position + 1; + String displayString = newPosition + " " + laws[position]; + holder.law.setText(displayString); + holder.law.setOnClickListener(view -> myOnClickListener.onItemClicked(position)); + } + + @Override + public int getItemCount() { + return laws.length; + } + + static class MyViewHolder extends RecyclerView.ViewHolder{ + + TextView law; + + public MyViewHolder(@NonNull View itemView) { + super(itemView); + law = itemView.findViewById(R.id.lawItem); + + } + } + +} diff --git a/app/src/main/java/com/example/safecampus/MyOnClickListener.java b/app/src/main/java/com/example/safecampus/MyOnClickListener.java new file mode 100644 index 0000000..5e6baa2 --- /dev/null +++ b/app/src/main/java/com/example/safecampus/MyOnClickListener.java @@ -0,0 +1,5 @@ +package com.example.safecampus; + +public interface MyOnClickListener { + void onItemClicked(int position); +} diff --git a/app/src/main/java/com/example/safecampus/SelfDefenseActivity.java b/app/src/main/java/com/example/safecampus/SelfDefenseActivity.java new file mode 100644 index 0000000..62a32ba --- /dev/null +++ b/app/src/main/java/com/example/safecampus/SelfDefenseActivity.java @@ -0,0 +1,26 @@ +package com.example.safecampus; +import android.os.Bundle; +import android.webkit.WebChromeClient; +import android.webkit.WebView; +import android.webkit.WebViewClient; + +import androidx.appcompat.app.AppCompatActivity; + +public class SelfDefenseActivity extends AppCompatActivity { + + WebView webView; + + @Override + protected void onCreate(Bundle savedInstanceState) { + super.onCreate(savedInstanceState); + setContentView(R.layout.activity_self_defense); + + webView = findViewById(R.id.webView); + + webView.setWebChromeClient(new WebChromeClient()); + webView.getSettings().setLoadsImagesAutomatically(true); + webView.getSettings().setJavaScriptEnabled(true); + webView.loadUrl("https://www.youtube.com/embed/T7aNSRoDCmg"); + + } +} \ No newline at end of file diff --git a/app/src/main/java/com/example/safecampus/ServiceMine.java b/app/src/main/java/com/example/safecampus/ServiceMine.java new file mode 100644 index 0000000..5fe5cc7 --- /dev/null +++ b/app/src/main/java/com/example/safecampus/ServiceMine.java @@ -0,0 +1,187 @@ + +package com.example.safecampus; + +import android.Manifest; +import android.annotation.SuppressLint; +import android.app.Notification; +import android.app.NotificationChannel; +import android.app.NotificationManager; +import android.app.PendingIntent; +import android.app.Service; +import android.content.Context; +import android.content.Intent; +import android.content.SharedPreferences; +import android.content.pm.PackageManager; +import android.location.Location; +import android.media.MediaPlayer; +import android.os.Build; +import android.os.IBinder; +import android.telephony.SmsManager; +import android.view.View; + +import androidx.annotation.Nullable; +import androidx.core.app.ActivityCompat; + +import com.github.tbouron.shakedetector.library.ShakeDetector; +import com.google.android.gms.location.FusedLocationProviderClient; +import com.google.android.gms.location.LocationServices; +import com.google.android.gms.tasks.OnSuccessListener; + +import java.util.HashSet; +import java.util.Set; + +public class ServiceMine extends Service { + + static boolean isRunning = false; + + static MediaPlayer mediaPlayer; + + FusedLocationProviderClient fusedLocationClient; + + @Nullable + @Override + public IBinder onBind(Intent intent) { + return null; + } + + SmsManager manager = SmsManager.getDefault(); +// WindowManager windowManager; + String myLocation; + View view; + @SuppressLint("SuspiciousIndentation") + @Override + public void onCreate() { + + super.onCreate(); + + mediaPlayer = MediaPlayer.create(getBaseContext(),R.raw.siren); + mediaPlayer.setLooping(true); + + + + fusedLocationClient = LocationServices.getFusedLocationProviderClient(this); + if (ActivityCompat.checkSelfPermission(this, Manifest.permission.ACCESS_FINE_LOCATION) != PackageManager.PERMISSION_GRANTED && ActivityCompat.checkSelfPermission(this, Manifest.permission.ACCESS_COARSE_LOCATION) != PackageManager.PERMISSION_GRANTED) { + return; + } + fusedLocationClient.getLastLocation() + .addOnSuccessListener(new OnSuccessListener() { + @Override + public void onSuccess(Location location) { + if (location != null) { + // Logic to handle location object + location.getAltitude(); + location.getLongitude(); + myLocation = "http://maps.google.com/maps?q=loc:"+location.getLatitude()+","+location.getLongitude(); + }else { + myLocation = "Unable to Find Location :("; + } + } + }); + + + +// windowManager= (WindowManager) getSystemService(WINDOW_SERVICE); +// +// WindowManager.LayoutParams params= null; +// if (android.os.Build.VERSION.SDK_INT >= android.os.Build.VERSION_CODES.O) { +// params = new WindowManager.LayoutParams( +// WindowManager.LayoutParams.WRAP_CONTENT, +// WindowManager.LayoutParams.WRAP_CONTENT, +// WindowManager.LayoutParams.TYPE_APPLICATION_OVERLAY, +// WindowManager.LayoutParams.FLAG_NOT_FOCUSABLE, +// PixelFormat.TRANSLUCENT); +// } +// +// params.gravity = Gravity.START; +// params.x = 0; +// params.y = 100; +// +// LayoutInflater inflater = (LayoutInflater) getSystemService(Context.LAYOUT_INFLATER_SERVICE); +// view = inflater.inflate(R.layout.floating_menu, null); +// Button panic = view.findViewById(R.id.panicService); +// panic.setOnClickListener(new View.OnClickListener() { +// @Override +// public void onClick(View view) { +// mediaPlayer.start(); +// +// +// SharedPreferences sharedPreferences = getSharedPreferences("MySharedPref",MODE_PRIVATE); +// Set oldNumbers = sharedPreferences.getStringSet("enumbers", new HashSet<>()); +// if(!oldNumbers.isEmpty()){ +// for(String ENUM : oldNumbers) +// manager.sendTextMessage(ENUM,null,"Im in Trouble!\nSending My Location :\n"+myLocation,null,null); +// } +// +// } +// }); +// +// windowManager.addView(view,params); + + + + ShakeDetector.create(this, () -> { + + mediaPlayer.start(); + + + SharedPreferences sharedPreferences = getSharedPreferences("MySharedPref",MODE_PRIVATE); + Set oldNumbers = sharedPreferences.getStringSet("enumbers", new HashSet<>()); + if(!oldNumbers.isEmpty()){ + for(String ENUM : oldNumbers) + manager.sendTextMessage(ENUM,null,"Im in Trouble!\nSending My Location :\n"+myLocation,null,null); + } + + }); + + } + + + + @Override + public int onStartCommand(Intent intent, int flags, int startId) { + + if (intent.getAction().equalsIgnoreCase("STOP")) { + if(isRunning){ + mediaPlayer.stop(); + this.stopForeground(true); + this.stopSelf(); +// windowManager.removeView(view); + isRunning = false; + } + } else { + Intent notificationIntent = new Intent(this, SmsActivity.class); + PendingIntent pendingIntent = PendingIntent.getActivity(this, 0, notificationIntent, PendingIntent.FLAG_MUTABLE); + + if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.O) { + NotificationChannel channel = new NotificationChannel("MYID", "CHANNELFOREGROUND", NotificationManager.IMPORTANCE_DEFAULT); + + NotificationManager m = (NotificationManager) getSystemService(Context.NOTIFICATION_SERVICE); + m.createNotificationChannel(channel); + + Notification notification = new Notification.Builder(this, "MYID") + .setContentTitle("Women Safety") + .setContentText("Shake Device to Send SOS") + .setSmallIcon(R.drawable.tips) + .setContentIntent(pendingIntent) + .build(); + this.startForeground(115, notification); + isRunning = true; + return START_NOT_STICKY; + } + if (intent.getAction().equalsIgnoreCase("PLAY")) { + mediaPlayer.start(); + } + } + + return super.onStartCommand(intent,flags,startId); + + + } + + @Override + public void onDestroy() { + mediaPlayer.stop(); + mediaPlayer.release(); + super.onDestroy(); + } +} diff --git a/app/src/main/java/com/example/safecampus/SmsActivity.java b/app/src/main/java/com/example/safecampus/SmsActivity.java new file mode 100644 index 0000000..763402b --- /dev/null +++ b/app/src/main/java/com/example/safecampus/SmsActivity.java @@ -0,0 +1,87 @@ +package com.example.safecampus; + +import androidx.appcompat.app.AppCompatActivity; +import androidx.core.content.ContextCompat; + +import android.Manifest; +import android.content.Intent; +import android.content.pm.PackageManager; +import android.net.Uri; +import android.os.Build; +import android.os.Bundle; +import android.provider.Settings; +import android.view.View; +import android.widget.Button; + +import com.google.android.material.snackbar.Snackbar; + +public class SmsActivity extends AppCompatActivity { + + + + Button start,stop; + + + @Override + public void onBackPressed() { + super.onBackPressed(); + startActivity(new Intent(SmsActivity.this,MainActivity.class)); + } + + @Override + protected void onCreate(Bundle savedInstanceState) { + super.onCreate(savedInstanceState); + setContentView(R.layout.activity_sms); + stop = findViewById(R.id.stopService); + start = findViewById(R.id.startService); + + start.setOnClickListener(this::startServiceV); + + stop.setOnClickListener(this::stopService); + + } + + + public void stopService(View view) { + + Intent notificationIntent = new Intent(this,ServiceMine.class); + notificationIntent.setAction("stop"); + if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.O) { + if(ServiceMine.isRunning){ + getApplicationContext().startForegroundService(notificationIntent); + Snackbar.make(findViewById(android.R.id.content),"Service Stopped!", Snackbar.LENGTH_LONG).show(); + } + }else { + if(ServiceMine.isRunning){ +// getApplicationContext().startService(notificationIntent); + getApplicationContext().startService(notificationIntent); + Snackbar.make(findViewById(android.R.id.content),"Service Stopped!", Snackbar.LENGTH_LONG).show(); + } + } + } + + public void startServiceV(View view) { + + if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.O) { + if (!Settings.canDrawOverlays(this)) { + Intent intent = new Intent(Settings.ACTION_MANAGE_OVERLAY_PERMISSION, + Uri.parse("package:" + getPackageName())); + startActivity(intent); + } + } + + if (ContextCompat.checkSelfPermission(this, Manifest.permission.SEND_SMS) == PackageManager.PERMISSION_GRANTED && ContextCompat.checkSelfPermission(this, Manifest.permission.ACCESS_COARSE_LOCATION) == PackageManager.PERMISSION_GRANTED && ContextCompat.checkSelfPermission(this, Manifest.permission.ACCESS_FINE_LOCATION) == PackageManager.PERMISSION_GRANTED ) { + Intent notificationIntent = new Intent(this,ServiceMine.class); + notificationIntent.setAction("Start"); + if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.O) { + getApplicationContext().startForegroundService(notificationIntent); + Snackbar.make(findViewById(android.R.id.content),"Service Started!", Snackbar.LENGTH_LONG).show(); + }else { + getApplicationContext().startService(notificationIntent); + Snackbar.make(findViewById(android.R.id.content),"Service Started!", Snackbar.LENGTH_LONG).show(); + } + } + + } + +} \ No newline at end of file diff --git a/app/src/main/java/com/example/safecampus/SplashActivity.java b/app/src/main/java/com/example/safecampus/SplashActivity.java new file mode 100644 index 0000000..63eda02 --- /dev/null +++ b/app/src/main/java/com/example/safecampus/SplashActivity.java @@ -0,0 +1,96 @@ +package com.example.safecampus; + +import androidx.appcompat.app.AppCompatActivity; +import androidx.core.app.ActivityCompat; + +import android.Manifest; +import android.content.Intent; +import android.content.pm.PackageManager; +import android.location.Location; +import android.os.Bundle; +import android.widget.Toast; + +import com.google.android.gms.location.LocationCallback; +import com.google.android.gms.location.LocationRequest; +import com.google.android.gms.location.LocationResult; +import com.google.android.gms.location.LocationServices; +import com.karumi.dexter.Dexter; +import com.karumi.dexter.MultiplePermissionsReport; +import com.karumi.dexter.PermissionToken; +import com.karumi.dexter.listener.PermissionRequest; +import com.karumi.dexter.listener.multi.MultiplePermissionsListener; + +import java.util.List; + +public class SplashActivity extends AppCompatActivity { + + boolean isAllPermissionsGranted = false; + + + @Override + protected void onCreate(Bundle savedInstanceState) { + super.onCreate(savedInstanceState); + setContentView(R.layout.activity_splash); + requestPermission(); + findViewById(R.id.btnGetStarted).setOnClickListener(view -> { + if(isAllPermissionsGranted){ + startActivity(new Intent(SplashActivity.this,MainActivity.class)); + SplashActivity.this.finish(); + }else { + Toast.makeText(this, "Please grant required permissions!", Toast.LENGTH_SHORT).show(); + requestPermission(); + } + }); + } + + + + + private void requestPermission() { + Dexter.withContext(this) + .withPermissions( + Manifest.permission.ACCESS_FINE_LOCATION, + Manifest.permission.ACCESS_COARSE_LOCATION, + Manifest.permission.CALL_PHONE, + Manifest.permission.SEND_SMS + ).withListener(new MultiplePermissionsListener() { + @Override public void onPermissionsChecked(MultiplePermissionsReport report) { + if(report.areAllPermissionsGranted()){ + isAllPermissionsGranted = true; + requestLocation(); + } + } + @Override public void onPermissionRationaleShouldBeShown(List permissions, PermissionToken token) { + token.continuePermissionRequest(); + } + }).check(); + } + + + + + void requestLocation(){ + LocationRequest mLocationRequest = com.google.android.gms.location.LocationRequest.create(); + mLocationRequest.setInterval(60000); + mLocationRequest.setFastestInterval(5000); + mLocationRequest.setPriority(com.google.android.gms.location.LocationRequest.PRIORITY_HIGH_ACCURACY); + LocationCallback mLocationCallback = new LocationCallback() { + @Override + public void onLocationResult(LocationResult locationResult) { + if (locationResult == null) { + return; + } + for (Location location : locationResult.getLocations()) { + if (location != null) { + //TODO: UI updates. + } + } + } + }; + if (ActivityCompat.checkSelfPermission(this, Manifest.permission.ACCESS_FINE_LOCATION) != PackageManager.PERMISSION_GRANTED && ActivityCompat.checkSelfPermission(this, Manifest.permission.ACCESS_COARSE_LOCATION) != PackageManager.PERMISSION_GRANTED) { + return; + } + LocationServices.getFusedLocationProviderClient(SplashActivity.this).requestLocationUpdates(mLocationRequest, mLocationCallback, null); + } + +} \ No newline at end of file diff --git a/app/src/main/res/drawable-v24/ic_launcher_foreground.xml b/app/src/main/res/drawable-v24/ic_launcher_foreground.xml new file mode 100644 index 0000000..f9dc2a5 --- /dev/null +++ b/app/src/main/res/drawable-v24/ic_launcher_foreground.xml @@ -0,0 +1,6 @@ + + + + diff --git a/app/src/main/res/drawable/baseline_privacy_tip_24.xml b/app/src/main/res/drawable/baseline_privacy_tip_24.xml new file mode 100644 index 0000000..2c3aa8b --- /dev/null +++ b/app/src/main/res/drawable/baseline_privacy_tip_24.xml @@ -0,0 +1,5 @@ + + + diff --git a/app/src/main/res/drawable/baseline_safety_check_24.xml b/app/src/main/res/drawable/baseline_safety_check_24.xml new file mode 100644 index 0000000..e7933f2 --- /dev/null +++ b/app/src/main/res/drawable/baseline_safety_check_24.xml @@ -0,0 +1,6 @@ + + + + diff --git a/app/src/main/res/drawable/contact.xml b/app/src/main/res/drawable/contact.xml new file mode 100644 index 0000000..9f67531 --- /dev/null +++ b/app/src/main/res/drawable/contact.xml @@ -0,0 +1,6 @@ + + + diff --git a/app/src/main/res/drawable/girl.jpg b/app/src/main/res/drawable/girl.jpg new file mode 100644 index 0000000..10957c6 Binary files /dev/null and b/app/src/main/res/drawable/girl.jpg differ diff --git a/app/src/main/res/drawable/ic_baseline_account_circle_24.xml b/app/src/main/res/drawable/ic_baseline_account_circle_24.xml new file mode 100644 index 0000000..8e207d9 --- /dev/null +++ b/app/src/main/res/drawable/ic_baseline_account_circle_24.xml @@ -0,0 +1,5 @@ + + + diff --git a/app/src/main/res/drawable/ic_baseline_close_24.xml b/app/src/main/res/drawable/ic_baseline_close_24.xml new file mode 100644 index 0000000..e1b6896 --- /dev/null +++ b/app/src/main/res/drawable/ic_baseline_close_24.xml @@ -0,0 +1,5 @@ + + + diff --git a/app/src/main/res/drawable/ic_baseline_delete_24.xml b/app/src/main/res/drawable/ic_baseline_delete_24.xml new file mode 100644 index 0000000..5f57505 --- /dev/null +++ b/app/src/main/res/drawable/ic_baseline_delete_24.xml @@ -0,0 +1,5 @@ + + + diff --git a/app/src/main/res/drawable/ic_baseline_edit_24.xml b/app/src/main/res/drawable/ic_baseline_edit_24.xml new file mode 100644 index 0000000..66aa48f --- /dev/null +++ b/app/src/main/res/drawable/ic_baseline_edit_24.xml @@ -0,0 +1,5 @@ + + + diff --git a/app/src/main/res/drawable/ic_baseline_logout_24.xml b/app/src/main/res/drawable/ic_baseline_logout_24.xml new file mode 100644 index 0000000..adab46a --- /dev/null +++ b/app/src/main/res/drawable/ic_baseline_logout_24.xml @@ -0,0 +1,5 @@ + + + diff --git a/app/src/main/res/drawable/ic_baseline_message_24.xml b/app/src/main/res/drawable/ic_baseline_message_24.xml new file mode 100644 index 0000000..7693fe5 --- /dev/null +++ b/app/src/main/res/drawable/ic_baseline_message_24.xml @@ -0,0 +1,5 @@ + + + diff --git a/app/src/main/res/drawable/ic_launcher_background.xml b/app/src/main/res/drawable/ic_launcher_background.xml new file mode 100644 index 0000000..6811c7d --- /dev/null +++ b/app/src/main/res/drawable/ic_launcher_background.xml @@ -0,0 +1,170 @@ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + diff --git a/app/src/main/res/drawable/img.png b/app/src/main/res/drawable/img.png new file mode 100644 index 0000000..1b7bc33 Binary files /dev/null and b/app/src/main/res/drawable/img.png differ diff --git a/app/src/main/res/drawable/logo.png b/app/src/main/res/drawable/logo.png new file mode 100644 index 0000000..e02c15f Binary files /dev/null and b/app/src/main/res/drawable/logo.png differ diff --git a/app/src/main/res/drawable/maps.jpg b/app/src/main/res/drawable/maps.jpg new file mode 100644 index 0000000..519e7d7 Binary files /dev/null and b/app/src/main/res/drawable/maps.jpg differ diff --git a/app/src/main/res/drawable/oval_purple_full.xml b/app/src/main/res/drawable/oval_purple_full.xml new file mode 100644 index 0000000..9242e79 --- /dev/null +++ b/app/src/main/res/drawable/oval_purple_full.xml @@ -0,0 +1,6 @@ + + + + + + \ No newline at end of file diff --git a/app/src/main/res/drawable/purple_background.xml b/app/src/main/res/drawable/purple_background.xml new file mode 100644 index 0000000..dcf4a3a --- /dev/null +++ b/app/src/main/res/drawable/purple_background.xml @@ -0,0 +1,7 @@ + + + + + + + \ No newline at end of file diff --git a/app/src/main/res/drawable/rectangle_border.xml b/app/src/main/res/drawable/rectangle_border.xml new file mode 100644 index 0000000..9057a66 --- /dev/null +++ b/app/src/main/res/drawable/rectangle_border.xml @@ -0,0 +1,7 @@ + + + + + + + \ No newline at end of file diff --git a/app/src/main/res/drawable/safe.jpg b/app/src/main/res/drawable/safe.jpg new file mode 100644 index 0000000..c02f31b Binary files /dev/null and b/app/src/main/res/drawable/safe.jpg differ diff --git a/app/src/main/res/drawable/self_defence.xml b/app/src/main/res/drawable/self_defence.xml new file mode 100644 index 0000000..89a28f0 --- /dev/null +++ b/app/src/main/res/drawable/self_defence.xml @@ -0,0 +1,8 @@ + + + + + + diff --git a/app/src/main/res/drawable/settings.xml b/app/src/main/res/drawable/settings.xml new file mode 100644 index 0000000..235a472 --- /dev/null +++ b/app/src/main/res/drawable/settings.xml @@ -0,0 +1,5 @@ + + + diff --git a/app/src/main/res/drawable/sitting_girl.png b/app/src/main/res/drawable/sitting_girl.png new file mode 100644 index 0000000..dac74ce Binary files /dev/null and b/app/src/main/res/drawable/sitting_girl.png differ diff --git a/app/src/main/res/drawable/tips.png b/app/src/main/res/drawable/tips.png new file mode 100644 index 0000000..f1a7b78 Binary files /dev/null and b/app/src/main/res/drawable/tips.png differ diff --git a/app/src/main/res/drawable/top_left_corner_oval.xml b/app/src/main/res/drawable/top_left_corner_oval.xml new file mode 100644 index 0000000..4546a7e --- /dev/null +++ b/app/src/main/res/drawable/top_left_corner_oval.xml @@ -0,0 +1,11 @@ + + + + + + + + + + \ No newline at end of file diff --git a/app/src/main/res/layout/activity_contact.xml b/app/src/main/res/layout/activity_contact.xml new file mode 100644 index 0000000..535aa34 --- /dev/null +++ b/app/src/main/res/layout/activity_contact.xml @@ -0,0 +1,149 @@ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +