Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
3 changes: 3 additions & 0 deletions app/build.gradle
Original file line number Diff line number Diff line change
Expand Up @@ -152,6 +152,9 @@ dependencies {
implementation 'androidx.swiperefreshlayout:swiperefreshlayout:1.1.0'
implementation 'androidx.work:work-runtime:2.10.5'
implementation 'com.google.android.material:material:1.13.0'

// Vanitech
implementation 'com.vanniktech:emoji-google:0.21.0'

// Database
implementation "androidx.room:room-runtime:${roomVersion}"
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -14,21 +14,34 @@
import android.graphics.drawable.LayerDrawable;
import android.net.Uri;
import android.os.Bundle;
import android.view.View;

import androidx.annotation.NonNull;
import androidx.fragment.app.DialogFragment;

import com.google.android.material.dialog.MaterialAlertDialogBuilder;
import com.owncloud.android.lib.resources.users.Status;
import com.owncloud.android.lib.resources.users.StatusType;

import java.util.concurrent.ExecutorService;
import java.util.concurrent.Executors;

import it.niedermann.owncloud.notes.NotesApplication;
import it.niedermann.owncloud.notes.R;
import it.niedermann.owncloud.notes.accountswitcher.adapter.accountSwitcher.AccountSwitcherAdapter;
import it.niedermann.owncloud.notes.accountswitcher.bottomSheet.AccountSwitcherBottomSheetTag;
import it.niedermann.owncloud.notes.accountswitcher.repository.UserStatusRepository;
import it.niedermann.owncloud.notes.branding.BrandedDialogFragment;
import it.niedermann.owncloud.notes.branding.BrandingUtil;
import it.niedermann.owncloud.notes.databinding.DialogAccountSwitcherBinding;
import it.niedermann.owncloud.notes.manageaccounts.ManageAccountsActivity;
import it.niedermann.owncloud.notes.persistence.NotesRepository;
import it.niedermann.owncloud.notes.persistence.entity.Account;
import it.niedermann.owncloud.notes.share.helper.AvatarLoader;
import it.niedermann.owncloud.notes.shared.util.DisplayUtils;
import it.niedermann.owncloud.notes.util.ActivityExtensionsKt;
import it.niedermann.owncloud.notes.util.StatusTypeExtensionsKt;
import kotlin.Unit;

/**
* Displays all available {@link Account} entries and provides basic operations for them, like adding or switching
Expand All @@ -41,6 +54,9 @@ public class AccountSwitcherDialog extends BrandedDialogFragment {
private DialogAccountSwitcherBinding binding;
private AccountSwitcherListener accountSwitcherListener;
private long currentAccountId;
private UserStatusRepository repository;
private Status currentStatus;
private final ExecutorService executor = Executors.newSingleThreadExecutor();

@Override
public void onAttach(@NonNull Context context) {
Expand All @@ -60,6 +76,38 @@ public void onAttach(@NonNull Context context) {
}

repo = NotesRepository.getInstance(requireContext());
initRepositoryAndFetchCurrentStatus();
}

private void initRepositoryAndFetchCurrentStatus() {
ActivityExtensionsKt.ssoAccount(requireActivity(), account -> {
if (account != null) {
repository = new UserStatusRepository(requireContext(), account);
} else {
DisplayUtils.showSnackMessage(requireView(), R.string.account_switch_dialog_status_fetching_error_message);
}
executor.execute(() -> {
currentStatus = repository.fetchUserStatus();
requireActivity().runOnUiThread(() -> {
final var message = currentStatus.getMessage();
if (message != null) {
binding.accountStatus.setVisibility(View.VISIBLE);
binding.accountStatus.setText(message);
}

final var emoji = currentStatus.getIcon();
if (emoji != null) {
binding.accountStatusEmoji.setVisibility(View.VISIBLE);
binding.accountStatusEmoji.setText(emoji);
} else {
final var status = currentStatus.getStatus();
binding.accountStatusIcon.setVisibility(View.VISIBLE);
binding.accountStatusIcon.setImageResource(StatusTypeExtensionsKt.getImageResource(status));
}
});
});
return Unit.INSTANCE;
});
}

@NonNull
Expand All @@ -76,6 +124,14 @@ public Dialog onCreateDialog(Bundle savedInstanceState) {
AvatarLoader.INSTANCE.load(requireContext(), binding.currentAccountItemAvatar, currentLocalAccount);
binding.accountLayout.setOnClickListener((v) -> dismiss());

binding.onlineStatus.setOnClickListener(v -> {
showBottomSheetDialog(AccountSwitcherBottomSheetTag.ONLINE_STATUS);
});

binding.statusMessage.setOnClickListener(v -> {
showBottomSheetDialog(AccountSwitcherBottomSheetTag.MESSAGE_STATUS);
});

final var adapter = new AccountSwitcherAdapter((localAccount -> {
accountSwitcherListener.onAccountChosen(localAccount);
dismiss();
Expand Down Expand Up @@ -112,6 +168,17 @@ public Dialog onCreateDialog(Bundle savedInstanceState) {
return builder.create();
}

private void showBottomSheetDialog(@NonNull AccountSwitcherBottomSheetTag tag) {
if (repository == null || currentStatus == null) {
DisplayUtils.showSnackMessage(requireView(), R.string.account_switch_dialog_status_fetching_error_message);
return;
}

final var fragment = tag.fragment(repository, currentStatus);
fragment.show(requireActivity().getSupportFragmentManager(), tag.name());
dismiss();
}

public static DialogFragment newInstance(long currentAccountId) {
final var dialog = new AccountSwitcherDialog();

Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -5,7 +5,7 @@
* SPDX-FileCopyrightText: 2020 Stefan Niedermann <info@niedermann.it>
* SPDX-License-Identifier: GPL-3.0-or-later
*/
package it.niedermann.owncloud.notes.accountswitcher;
package it.niedermann.owncloud.notes.accountswitcher.adapter.accountSwitcher;

import android.view.LayoutInflater;
import android.view.ViewGroup;
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -5,7 +5,7 @@
* SPDX-FileCopyrightText: 2020-2021 Stefan Niedermann <info@niedermann.it>
* SPDX-License-Identifier: GPL-3.0-or-later
*/
package it.niedermann.owncloud.notes.accountswitcher;
package it.niedermann.owncloud.notes.accountswitcher.adapter.accountSwitcher;

import android.net.Uri;
import android.view.View;
Expand Down
Original file line number Diff line number Diff line change
@@ -0,0 +1,13 @@
/*
* Nextcloud Notes - Android Client
*
* SPDX-FileCopyrightText: 2022 Tim Krüger <t@timkrueger.me
* SPDX-License-Identifier: GPL-3.0-or-later
*/
package it.niedermann.owncloud.notes.accountswitcher.adapter.predefinedStatus

import com.owncloud.android.lib.resources.users.PredefinedStatus

interface PredefinedStatusClickListener {
fun onClick(predefinedStatus: PredefinedStatus)
}
Original file line number Diff line number Diff line change
@@ -0,0 +1,31 @@
/*
* Nextcloud Notes - Android Client
*
* SPDX-FileCopyrightText: 2020 Tobias Kaminsky <tobias@kaminsky.me>
* SPDX-FileCopyrightText: 2020 Nextcloud GmbH
* SPDX-License-Identifier: GPL-3.0-or-later
*/
package it.niedermann.owncloud.notes.accountswitcher.adapter.predefinedStatus

import android.content.Context
import android.view.LayoutInflater
import android.view.ViewGroup
import androidx.recyclerview.widget.RecyclerView
import com.owncloud.android.lib.resources.users.PredefinedStatus
import it.niedermann.owncloud.notes.databinding.PredefinedStatusBinding

class PredefinedStatusListAdapter(private val clickListener: PredefinedStatusClickListener, val context: Context) :
RecyclerView.Adapter<PredefinedStatusViewHolder>() {
internal var list: List<PredefinedStatus> = emptyList()

override fun onCreateViewHolder(parent: ViewGroup, viewType: Int): PredefinedStatusViewHolder {
val itemBinding = PredefinedStatusBinding.inflate(LayoutInflater.from(parent.context), parent, false)
return PredefinedStatusViewHolder(itemBinding)
}

override fun onBindViewHolder(holder: PredefinedStatusViewHolder, position: Int) {
holder.bind(list[position], clickListener, context)
}

override fun getItemCount(): Int = list.size
}
Original file line number Diff line number Diff line change
@@ -0,0 +1,44 @@
/*
* Nextcloud Notes - Android Client
*
* SPDX-FileCopyrightText: 2020 Tobias Kaminsky <tobias@kaminsky.me>
* SPDX-FileCopyrightText: 2020 Nextcloud GmbH
* SPDX-License-Identifier: GPL-3.0-or-later
*/
package it.niedermann.owncloud.notes.accountswitcher.adapter.predefinedStatus

import android.content.Context
import androidx.recyclerview.widget.RecyclerView
import com.owncloud.android.lib.resources.users.PredefinedStatus
import it.niedermann.owncloud.notes.R
import it.niedermann.owncloud.notes.databinding.PredefinedStatusBinding
import it.niedermann.owncloud.notes.shared.util.DisplayUtils

private const val ONE_SECOND_IN_MILLIS = 1000

class PredefinedStatusViewHolder(private val binding: PredefinedStatusBinding) : RecyclerView.ViewHolder(binding.root) {

fun bind(status: PredefinedStatus, clickListener: PredefinedStatusClickListener, context: Context) {
binding.root.setOnClickListener { clickListener.onClick(status) }
binding.icon.text = status.icon
binding.name.text = status.message

if (status.clearAt == null) {
binding.clearAt.text = context.getString(R.string.dontClear)
} else {
val clearAt = status.clearAt
if (clearAt?.type == "period") {
binding.clearAt.text = DisplayUtils.getRelativeTimestamp(
context,
System.currentTimeMillis() + clearAt.time.toInt() * ONE_SECOND_IN_MILLIS,
true
)
} else {
// end-of
if (clearAt?.time == "day") {
binding.clearAt.text = context.getString(R.string.today)
}
}
}
}
}
Original file line number Diff line number Diff line change
@@ -0,0 +1,31 @@
/*
* Nextcloud Notes - Android Client
*
* SPDX-FileCopyrightText: 2015-2025 Nextcloud GmbH and Nextcloud contributors
* SPDX-License-Identifier: GPL-3.0-or-later
*/
package it.niedermann.owncloud.notes.accountswitcher.bottomSheet

import com.owncloud.android.lib.resources.users.Status
import it.niedermann.owncloud.notes.accountswitcher.repository.UserStatusRepository
import it.niedermann.owncloud.notes.branding.BrandedBottomSheetDialogFragment

enum class AccountSwitcherBottomSheetTag(tag: String) {
ONLINE_STATUS("fragment_set_status"),
MESSAGE_STATUS("fragment_set_status_message");

fun fragment(
repository: UserStatusRepository,
currentStatus: Status
): BrandedBottomSheetDialogFragment {
return when (this) {
ONLINE_STATUS -> {
SetOnlineStatusBottomSheet(repository, currentStatus)
}

MESSAGE_STATUS -> {
SetStatusMessageBottomSheet(repository, currentStatus)
}
}
}
}
Loading
Loading