package com.gianlu.pretendyourexyzzy.dialogs; import android.content.Context; import android.os.Bundle; import android.util.TypedValue; import android.view.LayoutInflater; import android.view.View; import android.view.ViewGroup; import android.widget.ArrayAdapter; import android.widget.AutoCompleteTextView; import android.widget.Button; import android.widget.CheckBox; import android.widget.LinearLayout; import android.widget.TextView; import androidx.annotation.NonNull; import androidx.annotation.Nullable; import androidx.fragment.app.DialogFragment; import com.gianlu.commonutils.CommonUtils; import com.gianlu.commonutils.dialogs.DialogUtils; import com.gianlu.commonutils.ui.Toaster; import com.gianlu.pretendyourexyzzy.R; import com.gianlu.pretendyourexyzzy.Utils; import com.gianlu.pretendyourexyzzy.api.LevelMismatchException; import com.gianlu.pretendyourexyzzy.api.RegisteredPyx; import com.gianlu.pretendyourexyzzy.api.models.Deck; import com.gianlu.pretendyourexyzzy.api.models.Game; import com.google.android.material.checkbox.MaterialCheckBox; import com.google.android.material.textfield.TextInputLayout; public class EditGameOptionsDialog extends DialogFragment { private TextInputLayout scoreLimit; private TextInputLayout playerLimit; private TextInputLayout spectatorLimit; private TextInputLayout timerMultiplier; private TextInputLayout blankCards; private TextInputLayout password; private LinearLayout decks; private LinearLayout layout; private int gid; private ApplyOptions listener; private TextView decksTitle; private RegisteredPyx pyx; @NonNull public static EditGameOptionsDialog get(int gid, Game.Options options) { EditGameOptionsDialog dialog = new EditGameOptionsDialog(); Bundle args = new Bundle(); args.putInt("gid", gid); args.putSerializable("options", options); dialog.setArguments(args); return dialog; } @Override public void onAttach(@NonNull Context context) { super.onAttach(context); if (context instanceof ApplyOptions) listener = (ApplyOptions) context; } private void done() { scoreLimit.setErrorEnabled(false); playerLimit.setErrorEnabled(false); spectatorLimit.setErrorEnabled(false); timerMultiplier.setErrorEnabled(false); blankCards.setErrorEnabled(false); password.setErrorEnabled(false); Game.Options newOptions; try { newOptions = Game.Options.validateAndCreate(pyx.config(), pyx.server.params(), CommonUtils.getText(timerMultiplier).trim(), CommonUtils.getText(spectatorLimit), CommonUtils.getText(playerLimit), CommonUtils.getText(scoreLimit), CommonUtils.getText(blankCards), decks, CommonUtils.getText(password)); } catch (Game.Options.InvalidFieldException ex) { View view = layout.findViewById(ex.fieldId); if (view instanceof TextInputLayout) { if (ex.throwMessage == R.string.outOfRange) ((TextInputLayout) view).setError(getString(R.string.outOfRange, ex.min, ex.max)); else ((TextInputLayout) view).setError(getString(ex.throwMessage)); } return; } dismissAllowingStateLoss(); if (listener != null) listener.changeGameOptions(gid, newOptions); } @Nullable @Override public View onCreateView(@NonNull LayoutInflater inflater, @Nullable ViewGroup container, @Nullable Bundle savedInstanceState) { layout = (LinearLayout) inflater.inflate(R.layout.dialog_edit_game_options, container, false); Bundle args = getArguments(); Game.Options options; if (args == null || (options = (Game.Options) args.getSerializable("options")) == null || (gid = args.getInt("gid", -1)) == -1 || getContext() == null) { dismissAllowingStateLoss(); return layout; } try { pyx = RegisteredPyx.get(); } catch (LevelMismatchException ex) { DialogUtils.showToast(getContext(), Toaster.build().message(R.string.failedLoading)); dismissAllowingStateLoss(); return layout; } scoreLimit = layout.findViewById(R.id.editGameOptions_scoreLimit); CommonUtils.setText(scoreLimit, String.valueOf(options.scoreLimit)); playerLimit = layout.findViewById(R.id.editGameOptions_playerLimit); CommonUtils.setText(playerLimit, String.valueOf(options.playersLimit)); spectatorLimit = layout.findViewById(R.id.editGameOptions_spectatorLimit); CommonUtils.setText(spectatorLimit, String.valueOf(options.spectatorsLimit)); timerMultiplier = layout.findViewById(R.id.editGameOptions_timerMultiplier); AutoCompleteTextView timerMultiplierEditText = (AutoCompleteTextView) CommonUtils.getEditText(timerMultiplier); timerMultiplierEditText.setAdapter(new ArrayAdapter<>(getContext(), android.R.layout.simple_spinner_dropdown_item, Game.Options.VALID_TIMER_MULTIPLIERS)); timerMultiplierEditText.setText(options.timerMultiplier, false); timerMultiplierEditText.setValidator(new AutoCompleteTextView.Validator() { @Override public boolean isValid(CharSequence text) { return Game.Options.timerMultiplierIndex(String.valueOf(text)) != -1; } @Override public CharSequence fixText(CharSequence invalidText) { return null; } }); blankCards = layout.findViewById(R.id.editGameOptions_blankCards); CommonUtils.setText(blankCards, String.valueOf(options.blanksLimit)); if (pyx.config().blankCardsEnabled()) blankCards.setVisibility(View.VISIBLE); else blankCards.setVisibility(View.GONE); password = layout.findViewById(R.id.editGameOptions_password); CommonUtils.setText(password, options.password); decksTitle = layout.findViewById(R.id.editGameOptions_decksTitle); decks = layout.findViewById(R.id.editGameOptions_decks); decks.removeAllViews(); for (Deck set : pyx.firstLoad().decks) { MaterialCheckBox item = new MaterialCheckBox(getContext()); item.setTag(set); item.setText(set.name); item.setChecked(options.cardSets.contains(set.id)); item.setOnCheckedChangeListener((buttonView, isChecked) -> updateDecksCount()); LinearLayout.LayoutParams lp = new LinearLayout.LayoutParams(ViewGroup.LayoutParams.MATCH_PARENT, ViewGroup.LayoutParams.WRAP_CONTENT); lp.topMargin = lp.bottomMargin = (int) -TypedValue.applyDimension(TypedValue.COMPLEX_UNIT_DIP, 8, getResources().getDisplayMetrics()); decks.addView(item, lp); } updateDecksCount(); Button cancel = layout.findViewById(R.id.editGameOptions_cancel); cancel.setOnClickListener(v -> dismissAllowingStateLoss()); Button apply = layout.findViewById(R.id.editGameOptions_apply); apply.setOnClickListener(v -> done()); return layout; } private void updateDecksCount() { int count = 0; int black = 0; int white = 0; for (int i = 0; i < decks.getChildCount(); i++) { CheckBox view = (CheckBox) decks.getChildAt(i); if (view.isChecked()) { Deck deck = (Deck) view.getTag(); count++; black += deck.blackCards; white += deck.whiteCards; } } decksTitle.setText(String.format("%s (%s)", getString(R.string.cardSetsLabel), Utils.buildDeckCountString(count, black, white))); } public interface ApplyOptions { void changeGameOptions(int gid, @NonNull Game.Options options); } }