From 7217515b38cfad4d1f09ff0882c24642b4608863 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?=D0=94=D0=B0=D0=BD=D0=B8=D0=BB?= <119668441+Jiga228@users.noreply.github.com> Date: Tue, 27 May 2025 20:11:29 +0700 Subject: [PATCH] Add change password --- app/src/main/AndroidManifest.xml | 6 + .../tasktracker/Activities/LoginActivity.java | 11 +- .../tasktracker/Activities/MainMenu.java | 37 ++++--- .../Activities/SettingsActivity.java | 103 ++++++++++++++++++ .../{LoginAnswer.java => StatusAnswer.java} | 2 +- .../example/tasktracker/Api/ApiService.java | 9 +- app/src/main/res/drawable/setting.png | Bin 0 -> 12862 bytes .../main/res/layout/activity_main_menu.xml | 12 +- app/src/main/res/layout/activity_settings.xml | 69 ++++++++++++ app/src/main/res/values-en/strings.xml | 7 ++ app/src/main/res/values-ru/strings.xml | 7 ++ app/src/main/res/values/strings.xml | 7 ++ 12 files changed, 246 insertions(+), 24 deletions(-) create mode 100644 app/src/main/java/com/example/tasktracker/Activities/SettingsActivity.java rename app/src/main/java/com/example/tasktracker/Answers/{LoginAnswer.java => StatusAnswer.java} (82%) create mode 100644 app/src/main/res/drawable/setting.png create mode 100644 app/src/main/res/layout/activity_settings.xml diff --git a/app/src/main/AndroidManifest.xml b/app/src/main/AndroidManifest.xml index a15ba51..62c087e 100644 --- a/app/src/main/AndroidManifest.xml +++ b/app/src/main/AndroidManifest.xml @@ -17,6 +17,12 @@ android:theme="@style/Theme.TaskTracker" android:usesCleartextTraffic="true" tools:targetApi="31"> + + diff --git a/app/src/main/java/com/example/tasktracker/Activities/LoginActivity.java b/app/src/main/java/com/example/tasktracker/Activities/LoginActivity.java index cef1e11..0b49400 100644 --- a/app/src/main/java/com/example/tasktracker/Activities/LoginActivity.java +++ b/app/src/main/java/com/example/tasktracker/Activities/LoginActivity.java @@ -2,14 +2,13 @@ package com.example.tasktracker.Activities; import android.annotation.SuppressLint; import android.content.Intent; -import android.content.SharedPreferences; import android.os.Bundle; import android.util.Log; import androidx.activity.EdgeToEdge; import androidx.appcompat.app.AppCompatActivity; -import com.example.tasktracker.Answers.LoginAnswer; +import com.example.tasktracker.Answers.StatusAnswer; import com.example.tasktracker.Api.ApiFactory; import com.example.tasktracker.PublicKeyNames; import com.example.tasktracker.R; @@ -84,9 +83,9 @@ public class LoginActivity extends AppCompatActivity { private void SingIn() { Disposable disposable = ApiFactory.getApiService().singin(login, password) - .subscribeOn(Schedulers.io()).subscribe(new Consumer() { + .subscribeOn(Schedulers.io()).subscribe(new Consumer() { @Override - public void accept(LoginAnswer loginAnswer) throws Throwable { + public void accept(StatusAnswer loginAnswer) throws Throwable { if(loginAnswer.getStatus().equals("big")) { Snackbar.make(binding.getRoot(), R.string.snackbar_InvalidLogin, Snackbar.LENGTH_SHORT).show(); return; @@ -116,9 +115,9 @@ public class LoginActivity extends AppCompatActivity { } private void SingUp() { Disposable disposable = ApiFactory.getApiService().singup(login, password) - .subscribeOn(Schedulers.io()).subscribe(new Consumer() { + .subscribeOn(Schedulers.io()).subscribe(new Consumer() { @Override - public void accept(LoginAnswer loginAnswer) throws Throwable { + public void accept(StatusAnswer loginAnswer) throws Throwable { if(loginAnswer.getStatus().equals("big")) { Snackbar.make(binding.getRoot(), R.string.snackbar_BigLoginPassword, Snackbar.LENGTH_SHORT).show(); return; diff --git a/app/src/main/java/com/example/tasktracker/Activities/MainMenu.java b/app/src/main/java/com/example/tasktracker/Activities/MainMenu.java index 83bb7d7..a5acb34 100644 --- a/app/src/main/java/com/example/tasktracker/Activities/MainMenu.java +++ b/app/src/main/java/com/example/tasktracker/Activities/MainMenu.java @@ -1,5 +1,8 @@ package com.example.tasktracker.Activities; +import static android.view.View.INVISIBLE; +import static android.view.View.VISIBLE; + import android.annotation.SuppressLint; import android.content.Context; import android.content.Intent; @@ -115,19 +118,6 @@ public class MainMenu extends AppCompatActivity { } }); - binding.buttonSingOut.setOnClickListener(v -> { - getSharedPreferences(PublicKeyNames.TOKEN_LIST, MODE_PRIVATE). - edit(). - remove(PublicKeyNames.LOGIN_KEY). - remove(PublicKeyNames.PASSWORD_KEY). - apply(); - - @SuppressLint("UnsafeIntentLaunch") - Intent intent = new Intent(this, LoginActivity.class); - startActivity(intent); - finish(); - }); - viewModel.getOnLoad().observe(this, new Observer>() { @Override public void onChanged(List tasks) { @@ -148,6 +138,22 @@ public class MainMenu extends AppCompatActivity { } public void Offline() { + binding.buttonSettings.setVisibility(INVISIBLE); + binding.buttonLogOut.setVisibility(VISIBLE); + + binding.buttonLogOut.setOnClickListener(v -> { + getSharedPreferences(PublicKeyNames.TOKEN_LIST, MODE_PRIVATE). + edit(). + remove(PublicKeyNames.LOGIN_KEY). + remove(PublicKeyNames.PASSWORD_KEY). + apply(); + + @SuppressLint("UnsafeIntentLaunch") + Intent intent = new Intent(this, LoginActivity.class); + startActivity(intent); + finish(); + }); + ItemTouchHelper helper = new ItemTouchHelper(new ItemTouchHelper.SimpleCallback(0, ItemTouchHelper.LEFT | ItemTouchHelper.RIGHT) { @Override @@ -181,6 +187,11 @@ public class MainMenu extends AppCompatActivity { } private void Online() { + binding.buttonSettings.setOnClickListener(v->{ + Intent intent = SettingsActivity.getIntent(this, login); + startActivity(intent); + }); + viewModel.onFail().observe(this, new Observer() { @Override public void onChanged(String s) { diff --git a/app/src/main/java/com/example/tasktracker/Activities/SettingsActivity.java b/app/src/main/java/com/example/tasktracker/Activities/SettingsActivity.java new file mode 100644 index 0000000..d8f9f52 --- /dev/null +++ b/app/src/main/java/com/example/tasktracker/Activities/SettingsActivity.java @@ -0,0 +1,103 @@ +package com.example.tasktracker.Activities; + +import android.content.Context; +import android.content.Intent; +import android.content.SharedPreferences; +import android.os.Bundle; + +import androidx.appcompat.app.AppCompatActivity; + +import com.example.tasktracker.Answers.StatusAnswer; +import com.example.tasktracker.Api.ApiFactory; +import com.example.tasktracker.PublicKeyNames; +import com.example.tasktracker.R; +import com.example.tasktracker.databinding.ActivitySettingsBinding; +import com.google.android.material.snackbar.Snackbar; + +import io.reactivex.rxjava3.disposables.CompositeDisposable; +import io.reactivex.rxjava3.disposables.Disposable; +import io.reactivex.rxjava3.functions.Consumer; +import io.reactivex.rxjava3.schedulers.Schedulers; + +public class SettingsActivity extends AppCompatActivity { + private ActivitySettingsBinding binding; + private CompositeDisposable compositeDisposable; + + private String login; + + public static Intent getIntent(Context context, String login) { + Intent intent = new Intent(context, SettingsActivity.class); + intent.putExtra(PublicKeyNames.LOGIN_KEY, login); + return intent; + } + + @Override + protected void onCreate(Bundle savedInstanceState) { + binding = ActivitySettingsBinding.inflate(getLayoutInflater()); + super.onCreate(savedInstanceState); + setContentView(binding.getRoot()); + + login = getIntent().getStringExtra(PublicKeyNames.LOGIN_KEY); + + binding.login.setText(login); + + binding.buttonBack.setOnClickListener(v->{ + finish(); + }); + binding.buttonLogOut.setOnClickListener(v->{ + getSharedPreferences(PublicKeyNames.TOKEN_LIST, MODE_PRIVATE) + .edit() + .remove(PublicKeyNames.LOGIN_KEY) + .remove(PublicKeyNames.PASSWORD_KEY) + .apply(); + Intent intent = new Intent(SettingsActivity.this, LoginActivity.class); + startActivity(intent); + finish(); + }); + compositeDisposable = new CompositeDisposable(); + + binding.buttonChangePassword.setOnClickListener(v->{ + String oldPassword = binding.fieldOldPassword.getText().toString(); + String newPassword = binding.fieldNewPassword.getText().toString(); + String retryPassword = binding.fieldRetreyPassword.getText().toString(); + + if(!retryPassword.equals(newPassword)) { + Snackbar.make(binding.getRoot(), R.string.snackbar_PasswordsNotEquals, Snackbar.LENGTH_LONG).show(); + return; + } + + Disposable disposable = ApiFactory.getApiService().changePassword(oldPassword, login, newPassword) + .subscribeOn(Schedulers.io()) + .subscribe(new Consumer() { + @Override + public void accept(StatusAnswer statusAnswer) throws Throwable { + if (statusAnswer.getStatus().equals("ok")) { + getSharedPreferences(PublicKeyNames.TOKEN_LIST, MODE_PRIVATE) + .edit() + .remove(PublicKeyNames.LOGIN_KEY) + .remove(PublicKeyNames.PASSWORD_KEY) + .apply(); + Intent intent = new Intent(SettingsActivity.this, LoginActivity.class); + startActivity(intent); + finish(); + } + else { + Snackbar.make(binding.getRoot(), R.string.snackbar_InvalidPassword, Snackbar.LENGTH_SHORT).show(); + } + } + }, new Consumer() { + @Override + public void accept(Throwable throwable) throws Throwable { + Snackbar.make(binding.getRoot(), R.string.snackbar_InternetError, Snackbar.LENGTH_SHORT).show(); + } + }); + compositeDisposable.add(disposable); + }); + } + + @Override + protected void onDestroy() { + super.onDestroy(); + compositeDisposable.dispose(); + } +} \ No newline at end of file diff --git a/app/src/main/java/com/example/tasktracker/Answers/LoginAnswer.java b/app/src/main/java/com/example/tasktracker/Answers/StatusAnswer.java similarity index 82% rename from app/src/main/java/com/example/tasktracker/Answers/LoginAnswer.java rename to app/src/main/java/com/example/tasktracker/Answers/StatusAnswer.java index 934c2f8..0ff85ae 100644 --- a/app/src/main/java/com/example/tasktracker/Answers/LoginAnswer.java +++ b/app/src/main/java/com/example/tasktracker/Answers/StatusAnswer.java @@ -4,7 +4,7 @@ import com.google.gson.annotations.SerializedName; import java.io.Serializable; -public class LoginAnswer implements Serializable { +public class StatusAnswer implements Serializable { @SerializedName("status") private String status; diff --git a/app/src/main/java/com/example/tasktracker/Api/ApiService.java b/app/src/main/java/com/example/tasktracker/Api/ApiService.java index 4de7b0a..44d06cc 100644 --- a/app/src/main/java/com/example/tasktracker/Api/ApiService.java +++ b/app/src/main/java/com/example/tasktracker/Api/ApiService.java @@ -1,6 +1,6 @@ package com.example.tasktracker.Api; -import com.example.tasktracker.Answers.LoginAnswer; +import com.example.tasktracker.Answers.StatusAnswer; import com.example.tasktracker.Answers.Task; import java.util.ArrayList; @@ -14,10 +14,10 @@ import retrofit2.http.Query; public interface ApiService { @GET("singin") - Single singin(@Query("login") String login, @Query("password") String password); + Single singin(@Query("login") String login, @Query("password") String password); @POST("singup") - Single singup(@Query("login") String login, @Query("password") String password); + Single singup(@Query("login") String login, @Query("password") String password); @GET("user/task") Single getTask(@Query("login") String login, @Query("password") String password, @Query("id") long id); @@ -33,4 +33,7 @@ public interface ApiService { @POST("user/task/remove") Call removeTask(@Query("login") String login, @Query("password") String password, @Query("id") long ID); + + @POST("user/ChangePassword") + Single changePassword(@Query("oldPassword") String oldPassword, @Query("login") String login, @Query("newPassword") String newPassword); } diff --git a/app/src/main/res/drawable/setting.png b/app/src/main/res/drawable/setting.png new file mode 100644 index 0000000000000000000000000000000000000000..bfbf3264460b3c879a96fd0a9985789e3f24880e GIT binary patch literal 12862 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�C5pnSvt}2I_X2~43~R?FZw3?=`v$E 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 VIwOAB5B%>3L@>2BDL+cQ`ajT>LWTeU literal 0 HcmV?d00001 diff --git a/app/src/main/res/layout/activity_main_menu.xml b/app/src/main/res/layout/activity_main_menu.xml index 5b47b68..2edc006 100644 --- a/app/src/main/res/layout/activity_main_menu.xml +++ b/app/src/main/res/layout/activity_main_menu.xml @@ -29,12 +29,22 @@ app:layout_constraintTop_toBottomOf="@id/findLine"/> + + + + + + + + + + + + + + +