Simplify ListHabitsActivity

pull/309/head
Alinson S. Xavier 8 years ago
parent 50a6c6d9dd
commit f8a9da59dd

@ -57,7 +57,6 @@ public class CheckmarkPanelViewTest extends BaseViewTest
Checkmark.CHECKED_IMPLICITLY, Checkmark.CHECKED_EXPLICITLY}; Checkmark.CHECKED_IMPLICITLY, Checkmark.CHECKED_EXPLICITLY};
view = new CheckmarkPanelView(targetContext); view = new CheckmarkPanelView(targetContext);
view.setHabit(habit);
view.setValues(checkmarks); view.setValues(checkmarks);
view.setButtonCount(4); view.setButtonCount(4);
view.setColor(PaletteUtils.getAndroidTestColor(7)); view.setColor(PaletteUtils.getAndroidTestColor(7));

@ -28,8 +28,6 @@ import org.isoron.uhabits.core.utils.*;
import org.junit.*; import org.junit.*;
import org.junit.runner.*; import org.junit.runner.*;
import static org.mockito.Mockito.mock;
@RunWith(AndroidJUnit4.class) @RunWith(AndroidJUnit4.class)
@MediumTest @MediumTest
public class HabitCardViewTest extends BaseViewTest public class HabitCardViewTest extends BaseViewTest
@ -38,8 +36,6 @@ public class HabitCardViewTest extends BaseViewTest
public static final String PATH = "habits/list/HabitCardView/"; public static final String PATH = "habits/list/HabitCardView/";
private HabitCardView.Controller controller;
private Habit habit; private Habit habit;
@Override @Override
@ -55,14 +51,11 @@ public class HabitCardViewTest extends BaseViewTest
long day = DateUtils.millisecondsInOneDay; long day = DateUtils.millisecondsInOneDay;
int[] values = checkmarks.getValues(today - 5 * day, today); int[] values = checkmarks.getValues(today - 5 * day, today);
controller = mock(HabitCardView.Controller.class);
view = new HabitCardView(targetContext); view = new HabitCardView(targetContext);
view.setHabit(habit); view.setHabit(habit);
view.setValues(values); view.setValues(values);
view.setSelected(false); view.setSelected(false);
view.setScore(habit.getScores().getTodayValue()); view.setScore(habit.getScores().getTodayValue());
view.setController(controller);
view.setButtonCount(6); view.setButtonCount(6);
measureView(view, dpToPixels(400), dpToPixels(50)); measureView(view, dpToPixels(400), dpToPixels(50));
} }

@ -23,14 +23,12 @@ import android.support.test.filters.*;
import android.support.test.runner.*; import android.support.test.runner.*;
import org.isoron.uhabits.*; import org.isoron.uhabits.*;
import org.isoron.uhabits.activities.habits.list.controllers.*;
import org.isoron.uhabits.utils.*; import org.isoron.uhabits.utils.*;
import org.junit.*; import org.junit.*;
import org.junit.runner.*; import org.junit.runner.*;
import static org.hamcrest.MatcherAssert.*;
import static org.hamcrest.CoreMatchers.*; import static org.hamcrest.CoreMatchers.*;
import static org.mockito.Mockito.*; import static org.hamcrest.MatcherAssert.*;
@RunWith(AndroidJUnit4.class) @RunWith(AndroidJUnit4.class)
@MediumTest @MediumTest
@ -40,7 +38,6 @@ public class NumberButtonViewTest extends BaseViewTest
private NumberButtonView view; private NumberButtonView view;
private NumberButtonController controller;
@Override @Override
@Before @Before
@ -54,9 +51,6 @@ public class NumberButtonViewTest extends BaseViewTest
view.setColor(PaletteUtils.getAndroidTestColor(8)); view.setColor(PaletteUtils.getAndroidTestColor(8));
measureView(view, dpToPixels(48), dpToPixels(48)); measureView(view, dpToPixels(48), dpToPixels(48));
controller = mock(NumberButtonController.class);
view.setController(controller);
} }
@Test @Test
@ -98,14 +92,4 @@ public class NumberButtonViewTest extends BaseViewTest
view.setValue(0); view.setValue(0);
assertRenders(view, PATH + "render_zero.png"); assertRenders(view, PATH + "render_zero.png");
} }
@Test
public void test_click()
{
view.performClick();
verify(controller).onClick();
view.performLongClick();
verify(controller).onLongClick();
}
} }

@ -24,10 +24,10 @@ import org.isoron.uhabits.*;
import org.isoron.uhabits.activities.about.*; import org.isoron.uhabits.activities.about.*;
import org.isoron.uhabits.activities.common.dialogs.*; import org.isoron.uhabits.activities.common.dialogs.*;
import org.isoron.uhabits.activities.habits.list.*; import org.isoron.uhabits.activities.habits.list.*;
import org.isoron.uhabits.activities.habits.list.controllers.*; import org.isoron.uhabits.activities.habits.list.views.*;
import org.isoron.uhabits.activities.habits.list.model.*;
import org.isoron.uhabits.activities.habits.show.*; import org.isoron.uhabits.activities.habits.show.*;
import org.isoron.uhabits.core.ui.*; import org.isoron.uhabits.core.ui.*;
import org.isoron.uhabits.core.ui.screens.habits.list.*;
import dagger.*; import dagger.*;
@ -46,14 +46,12 @@ public interface HabitsActivityComponent
AboutScreen getAboutScreen(); AboutScreen getAboutScreen();
BaseActivity getActivity();
CheckmarkButtonControllerFactory getCheckmarkButtonControllerFactory();
ColorPickerDialogFactory getColorPickerDialogFactory(); ColorPickerDialogFactory getColorPickerDialogFactory();
HabitCardListAdapter getHabitCardListAdapter(); HabitCardListAdapter getHabitCardListAdapter();
ListHabitsBehavior getListHabitsBehavior();
ListHabitsController getListHabitsController(); ListHabitsController getListHabitsController();
ListHabitsMenu getListHabitsMenu(); ListHabitsMenu getListHabitsMenu();
@ -64,8 +62,6 @@ public interface HabitsActivityComponent
ListHabitsSelectionMenu getListHabitsSelectionMenu(); ListHabitsSelectionMenu getListHabitsSelectionMenu();
NumberButtonControllerFactory getNumberButtonControllerFactory();
ShowHabitScreen getShowHabitScreen(); ShowHabitScreen getShowHabitScreen();
ThemeSwitcher getThemeSwitcher(); ThemeSwitcher getThemeSwitcher();

@ -22,7 +22,7 @@ package org.isoron.uhabits.activities.habits.list;
import android.os.*; import android.os.*;
import org.isoron.uhabits.activities.*; import org.isoron.uhabits.activities.*;
import org.isoron.uhabits.activities.habits.list.model.*; import org.isoron.uhabits.activities.habits.list.views.*;
import org.isoron.uhabits.core.preferences.*; import org.isoron.uhabits.core.preferences.*;
import org.isoron.uhabits.core.ui.*; import org.isoron.uhabits.core.ui.*;
import org.isoron.uhabits.core.utils.*; import org.isoron.uhabits.core.utils.*;

@ -23,8 +23,7 @@ import android.support.annotation.*;
import org.isoron.androidbase.activities.*; import org.isoron.androidbase.activities.*;
import org.isoron.uhabits.R; import org.isoron.uhabits.R;
import org.isoron.uhabits.activities.habits.list.controllers.*; import org.isoron.uhabits.activities.habits.list.views.*;
import org.isoron.uhabits.activities.habits.list.model.*;
import org.isoron.uhabits.core.models.*; import org.isoron.uhabits.core.models.*;
import org.isoron.uhabits.core.tasks.*; import org.isoron.uhabits.core.tasks.*;
import org.isoron.uhabits.core.ui.screens.habits.list.*; import org.isoron.uhabits.core.ui.screens.habits.list.*;
@ -70,7 +69,6 @@ public class ListHabitsController
this.exportDBFactory = exportDBFactory; this.exportDBFactory = exportDBFactory;
} }
@Override
public void onEdit(@NonNull Habit habit, long timestamp) public void onEdit(@NonNull Habit habit, long timestamp)
{ {
behavior.onEdit(habit, timestamp); behavior.onEdit(habit, timestamp);
@ -127,7 +125,6 @@ public class ListHabitsController
})); }));
} }
@Override
public void onInvalidEdit() public void onInvalidEdit()
{ {
screen.showMessage(R.string.long_press_to_edit); screen.showMessage(R.string.long_press_to_edit);

@ -24,7 +24,7 @@ import android.support.annotation.*;
import org.isoron.androidbase.*; import org.isoron.androidbase.*;
import org.isoron.uhabits.activities.*; import org.isoron.uhabits.activities.*;
import org.isoron.uhabits.activities.habits.list.model.*; import org.isoron.uhabits.activities.habits.list.views.*;
import org.isoron.uhabits.core.ui.screens.habits.list.*; import org.isoron.uhabits.core.ui.screens.habits.list.*;
import javax.inject.*; import javax.inject.*;

@ -29,8 +29,6 @@ import org.isoron.androidbase.activities.*;
import org.isoron.androidbase.utils.*; import org.isoron.androidbase.utils.*;
import org.isoron.uhabits.R; import org.isoron.uhabits.R;
import org.isoron.uhabits.activities.common.views.*; import org.isoron.uhabits.activities.common.views.*;
import org.isoron.uhabits.activities.habits.list.controllers.*;
import org.isoron.uhabits.activities.habits.list.model.*;
import org.isoron.uhabits.activities.habits.list.views.*; import org.isoron.uhabits.activities.habits.list.views.*;
import org.isoron.uhabits.core.models.*; import org.isoron.uhabits.core.models.*;
import org.isoron.uhabits.core.tasks.*; import org.isoron.uhabits.core.tasks.*;

@ -24,8 +24,7 @@ import android.view.*;
import org.isoron.androidbase.activities.*; import org.isoron.androidbase.activities.*;
import org.isoron.uhabits.R; import org.isoron.uhabits.R;
import org.isoron.uhabits.activities.habits.list.controllers.*; import org.isoron.uhabits.activities.habits.list.views.*;
import org.isoron.uhabits.activities.habits.list.model.*;
import org.isoron.uhabits.core.commands.*; import org.isoron.uhabits.core.commands.*;
import org.isoron.uhabits.core.ui.screens.habits.list.*; import org.isoron.uhabits.core.ui.screens.habits.list.*;

@ -1,99 +0,0 @@
/*
* Copyright (C) 2016 Álinson Santos Xavier <isoron@gmail.com>
*
* This file is part of Loop Habit Tracker.
*
* Loop Habit Tracker is free software: you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by the
* Free Software Foundation, either version 3 of the License, or (at your
* option) any later version.
*
* Loop Habit Tracker is distributed in the hope that it will be useful, but
* WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY
* or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for
* more details.
*
* You should have received a copy of the GNU General Public License along
* with this program. If not, see <http://www.gnu.org/licenses/>.
*/
package org.isoron.uhabits.activities.habits.list.controllers;
import android.support.annotation.*;
import com.google.auto.factory.*;
import org.isoron.uhabits.activities.habits.list.views.*;
import org.isoron.uhabits.core.models.*;
import org.isoron.uhabits.core.preferences.*;
@AutoFactory
public class CheckmarkButtonController
{
@Nullable
private CheckmarkButtonView view;
@Nullable
private Listener listener;
@NonNull
private final Preferences prefs;
@NonNull
private Habit habit;
private long timestamp;
public CheckmarkButtonController(@Provided @NonNull Preferences prefs,
@NonNull Habit habit,
long timestamp)
{
this.habit = habit;
this.timestamp = timestamp;
this.prefs = prefs;
}
public void onClick()
{
if (prefs.isShortToggleEnabled()) performToggle();
else performInvalidToggle();
}
public boolean onLongClick()
{
performToggle();
return true;
}
public void performInvalidToggle()
{
if (listener != null) listener.onInvalidToggle();
}
public void performToggle()
{
if (view != null) view.toggle();
if (listener != null) listener.onToggle(habit, timestamp);
}
public void setListener(@Nullable Listener listener)
{
this.listener = listener;
}
public void setView(@Nullable CheckmarkButtonView view)
{
this.view = view;
}
public interface Listener
{
/**
* Called when the user's attempt to perform a toggle is rejected.
*/
void onInvalidToggle();
void onToggle(@NonNull Habit habit, long timestamp);
}
}

@ -1,75 +0,0 @@
/*
* Copyright (C) 2016 Álinson Santos Xavier <isoron@gmail.com>
*
* This file is part of Loop Habit Tracker.
*
* Loop Habit Tracker is free software: you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by the
* Free Software Foundation, either version 3 of the License, or (at your
* option) any later version.
*
* Loop Habit Tracker is distributed in the hope that it will be useful, but
* WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY
* or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for
* more details.
*
* You should have received a copy of the GNU General Public License along
* with this program. If not, see <http://www.gnu.org/licenses/>.
*/
package org.isoron.uhabits.activities.habits.list.controllers;
import android.support.annotation.*;
import org.isoron.uhabits.activities.habits.list.views.*;
import org.isoron.uhabits.core.models.*;
public class HabitCardController implements HabitCardView.Controller
{
@Nullable
private HabitCardView view;
@Nullable
private Listener listener;
@Override
public void onEdit(@NonNull Habit habit, long timestamp)
{
if(listener != null) listener.onEdit(habit, timestamp);
}
@Override
public void onInvalidEdit()
{
if(listener != null) listener.onInvalidEdit();
}
@Override
public void onInvalidToggle()
{
if (listener != null) listener.onInvalidToggle();
}
@Override
public void onToggle(@NonNull Habit habit, long timestamp)
{
if (view != null) view.triggerRipple(timestamp);
if (listener != null) listener.onToggle(habit, timestamp);
}
public void setListener(@Nullable Listener listener)
{
this.listener = listener;
}
public void setView(@Nullable HabitCardView view)
{
this.view = view;
}
public interface Listener extends CheckmarkButtonController.Listener,
NumberButtonController.Listener
{
}
}

@ -1,93 +0,0 @@
/*
* Copyright (C) 2016 Álinson Santos Xavier <isoron@gmail.com>
*
* This file is part of Loop Habit Tracker.
*
* Loop Habit Tracker is free software: you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by the
* Free Software Foundation, either version 3 of the License, or (at your
* option) any later version.
*
* Loop Habit Tracker is distributed in the hope that it will be useful, but
* WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY
* or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for
* more details.
*
* You should have received a copy of the GNU General Public License along
* with this program. If not, see <http://www.gnu.org/licenses/>.
*/
package org.isoron.uhabits.activities.habits.list.controllers;
import android.support.annotation.*;
import com.google.auto.factory.*;
import org.isoron.uhabits.core.models.*;
import org.isoron.uhabits.core.preferences.*;
@AutoFactory
public class NumberButtonController
{
@Nullable
private Listener listener;
@NonNull
private final Preferences prefs;
@NonNull
private Habit habit;
private long timestamp;
public NumberButtonController(@Provided @NonNull Preferences prefs,
@NonNull Habit habit,
long timestamp)
{
this.habit = habit;
this.timestamp = timestamp;
this.prefs = prefs;
}
public void onClick()
{
if (prefs.isShortToggleEnabled()) performEdit();
else performInvalidToggle();
}
public boolean onLongClick()
{
performEdit();
return true;
}
public void performInvalidToggle()
{
if (listener != null) listener.onInvalidEdit();
}
public void performEdit()
{
if (listener != null) listener.onEdit(habit, timestamp);
}
public void setListener(@Nullable Listener listener)
{
this.listener = listener;
}
public interface Listener
{
/**
* Called when the user's attempt to edit the value is rejected.
*/
void onInvalidEdit();
/**
* Called when a the user's attempt to edit the value has been accepted.
* @param habit the habit being edited
* @param timestamp the timestamp being edited
*/
void onEdit(@NonNull Habit habit, long timestamp);
}
}

@ -1,23 +0,0 @@
/*
* Copyright (C) 2016 Álinson Santos Xavier <isoron@gmail.com>
*
* This file is part of Loop Habit Tracker.
*
* Loop Habit Tracker is free software: you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by the
* Free Software Foundation, either version 3 of the License, or (at your
* option) any later version.
*
* Loop Habit Tracker is distributed in the hope that it will be useful, but
* WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY
* or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for
* more details.
*
* You should have received a copy of the GNU General Public License along
* with this program. If not, see <http://www.gnu.org/licenses/>.
*/
/**
* Provides controllers that are specific for {@link org.isoron.uhabits.activities.habits.list.ListHabitsActivity}.
*/
package org.isoron.uhabits.activities.habits.list.controllers;

@ -29,14 +29,17 @@ import android.view.*;
import org.isoron.androidbase.utils.*; import org.isoron.androidbase.utils.*;
import org.isoron.uhabits.*; import org.isoron.uhabits.*;
import org.isoron.uhabits.activities.habits.list.controllers.*; import org.isoron.uhabits.activities.*;
import org.isoron.uhabits.core.preferences.*;
import org.isoron.uhabits.utils.*; import org.isoron.uhabits.utils.*;
import static android.view.View.MeasureSpec.*; import static android.view.View.MeasureSpec.EXACTLY;
import static org.isoron.uhabits.core.models.Checkmark.*; import static android.view.View.MeasureSpec.makeMeasureSpec;
import static org.isoron.uhabits.utils.AttributeSetUtils.*;
import static org.isoron.androidbase.utils.InterfaceUtils.getDimension; import static org.isoron.androidbase.utils.InterfaceUtils.getDimension;
import static org.isoron.androidbase.utils.InterfaceUtils.getFontAwesome; import static org.isoron.androidbase.utils.InterfaceUtils.getFontAwesome;
import static org.isoron.uhabits.core.models.Checkmark.CHECKED_EXPLICITLY;
import static org.isoron.uhabits.core.models.Checkmark.UNCHECKED;
import static org.isoron.uhabits.utils.AttributeSetUtils.getIntAttribute;
public class CheckmarkButtonView extends View public class CheckmarkButtonView extends View
{ {
@ -52,6 +55,15 @@ public class CheckmarkButtonView extends View
private RectF rect; private RectF rect;
@Nullable
private Preferences prefs;
@NonNull
private OnToggleListener onToggleListener;
@NonNull
private OnInvalidToggleListener onInvalidToggleListener;
public CheckmarkButtonView(@Nullable Context context) public CheckmarkButtonView(@Nullable Context context)
{ {
super(context); super(context);
@ -68,7 +80,6 @@ public class CheckmarkButtonView extends View
int paletteColor = getIntAttribute(ctx, attrs, "color", 0); int paletteColor = getIntAttribute(ctx, attrs, "color", 0);
setColor(PaletteUtils.getAndroidTestColor(paletteColor)); setColor(PaletteUtils.getAndroidTestColor(paletteColor));
int value = getIntAttribute(ctx, attrs, "value", 0); int value = getIntAttribute(ctx, attrs, "value", 0);
setValue(value); setValue(value);
} }
@ -79,20 +90,15 @@ public class CheckmarkButtonView extends View
postInvalidate(); postInvalidate();
} }
public void setController(final CheckmarkButtonController controller)
{
setOnClickListener(v -> controller.onClick());
setOnLongClickListener(v -> controller.onLongClick());
}
public void setValue(int value) public void setValue(int value)
{ {
this.value = value; this.value = value;
postInvalidate(); postInvalidate();
} }
public void toggle() public void performToggle()
{ {
onToggleListener.onToggle();
value = (value == CHECKED_EXPLICITLY ? UNCHECKED : CHECKED_EXPLICITLY); value = (value == CHECKED_EXPLICITLY ? UNCHECKED : CHECKED_EXPLICITLY);
performHapticFeedback(HapticFeedbackConstants.LONG_PRESS); performHapticFeedback(HapticFeedbackConstants.LONG_PRESS);
postInvalidate(); postInvalidate();
@ -142,5 +148,47 @@ public class CheckmarkButtonView extends View
rect = new RectF(); rect = new RectF();
color = Color.BLACK; color = Color.BLACK;
lowContrastColor = styledRes.getColor(R.attr.lowContrastTextColor); lowContrastColor = styledRes.getColor(R.attr.lowContrastTextColor);
onToggleListener = () -> {};
onInvalidToggleListener = () -> {};
if (getContext() instanceof HabitsActivity)
{
HabitsApplicationComponent component =
((HabitsActivity) getContext()).getAppComponent();
prefs = component.getPreferences();
}
setOnClickListener((v) -> {
if (prefs == null) return;
if (prefs.isShortToggleEnabled()) performToggle();
else onInvalidToggleListener.onInvalidToggle();
});
setOnLongClickListener(v -> {
performToggle();
return true;
});
}
public void setOnInvalidToggleListener(
@NonNull OnInvalidToggleListener onInvalidToggleListener)
{
this.onInvalidToggleListener = onInvalidToggleListener;
}
public void setOnToggleListener(@NonNull OnToggleListener onToggleListener)
{
this.onToggleListener = onToggleListener;
}
public interface OnInvalidToggleListener
{
void onInvalidToggle();
}
public interface OnToggleListener
{
void onToggle();
} }
} }

@ -25,9 +25,6 @@ import android.util.*;
import android.widget.*; import android.widget.*;
import org.isoron.uhabits.*; import org.isoron.uhabits.*;
import org.isoron.uhabits.activities.*;
import org.isoron.uhabits.activities.habits.list.controllers.*;
import org.isoron.uhabits.core.models.*;
import org.isoron.uhabits.core.preferences.*; import org.isoron.uhabits.core.preferences.*;
import org.isoron.uhabits.core.utils.*; import org.isoron.uhabits.core.utils.*;
@ -35,9 +32,9 @@ import java.util.*;
import static android.view.View.MeasureSpec.EXACTLY; import static android.view.View.MeasureSpec.EXACTLY;
import static android.view.View.MeasureSpec.makeMeasureSpec; import static android.view.View.MeasureSpec.makeMeasureSpec;
import static org.isoron.androidbase.utils.InterfaceUtils.getDimension;
import static org.isoron.uhabits.utils.AttributeSetUtils.getIntAttribute; import static org.isoron.uhabits.utils.AttributeSetUtils.getIntAttribute;
import static org.isoron.uhabits.utils.PaletteUtils.getAndroidTestColor; import static org.isoron.uhabits.utils.PaletteUtils.getAndroidTestColor;
import static org.isoron.androidbase.utils.InterfaceUtils.getDimension;
public class CheckmarkPanelView extends LinearLayout public class CheckmarkPanelView extends LinearLayout
implements Preferences.Listener implements Preferences.Listener
@ -55,12 +52,13 @@ public class CheckmarkPanelView extends LinearLayout
private int color; private int color;
private Controller controller; private int dataOffset;
@NonNull @NonNull
private Habit habit; private OnInvalidToggleListener onInvalidToggleListener;
private int dataOffset; @NonNull
private OnToggleListener onToggleLister;
public CheckmarkPanelView(Context context) public CheckmarkPanelView(Context context)
{ {
@ -115,22 +113,21 @@ public class CheckmarkPanelView extends LinearLayout
setupButtons(); setupButtons();
} }
public void setController(Controller controller) public void setDataOffset(int dataOffset)
{ {
this.controller = controller; this.dataOffset = dataOffset;
setupButtons(); setupButtons();
} }
public void setDataOffset(int dataOffset) public void setOnInvalidToggleListener(
@NonNull OnInvalidToggleListener onInvalidToggleListener)
{ {
this.dataOffset = dataOffset; this.onInvalidToggleListener = onInvalidToggleListener;
setupButtons();
} }
public void setHabit(@NonNull Habit habit) public void setOnToggleLister(@NonNull OnToggleListener onToggleLister)
{ {
this.habit = habit; this.onToggleLister = onToggleLister;
setupButtons();
} }
public void setValues(int[] values) public void setValues(int[] values)
@ -157,7 +154,8 @@ public class CheckmarkPanelView extends LinearLayout
protected void onMeasure(int widthSpec, int heightSpec) protected void onMeasure(int widthSpec, int heightSpec)
{ {
float buttonWidth = getDimension(getContext(), R.dimen.checkmarkWidth); float buttonWidth = getDimension(getContext(), R.dimen.checkmarkWidth);
float buttonHeight = getDimension(getContext(), R.dimen.checkmarkHeight); float buttonHeight =
getDimension(getContext(), R.dimen.checkmarkHeight);
float width = buttonWidth * nButtons; float width = buttonWidth * nButtons;
@ -190,6 +188,9 @@ public class CheckmarkPanelView extends LinearLayout
prefs = app.getComponent().getPreferences(); prefs = app.getComponent().getPreferences();
} }
onInvalidToggleListener = () -> {};
onToggleLister = (t) -> {};
setWillNotDraw(false); setWillNotDraw(false);
values = new int[0]; values = new int[0];
} }
@ -207,19 +208,10 @@ public class CheckmarkPanelView extends LinearLayout
private void setupButtonControllers(long timestamp, private void setupButtonControllers(long timestamp,
CheckmarkButtonView buttonView) CheckmarkButtonView buttonView)
{ {
if (controller == null) return; buttonView.setOnInvalidToggleListener(
if (!(getContext() instanceof HabitsActivity)) return; () -> onInvalidToggleListener.onInvalidToggle());
buttonView.setOnToggleListener(
HabitsActivity activity = (HabitsActivity) getContext(); () -> onToggleLister.onToggle(timestamp));
CheckmarkButtonControllerFactory buttonControllerFactory = activity
.getActivityComponent()
.getCheckmarkButtonControllerFactory();
CheckmarkButtonController buttonController =
buttonControllerFactory.create(habit, timestamp);
buttonController.setListener(controller);
buttonController.setView(buttonView);
buttonView.setController(buttonController);
} }
private void setupButtons() private void setupButtons()
@ -239,8 +231,13 @@ public class CheckmarkPanelView extends LinearLayout
} }
} }
public interface Controller extends CheckmarkButtonController.Listener public interface OnInvalidToggleListener
{ {
void onInvalidToggle();
}
public interface OnToggleListener
{
void onToggle(long timestamp);
} }
} }

@ -17,7 +17,7 @@
* with this program. If not, see <http://www.gnu.org/licenses/>. * with this program. If not, see <http://www.gnu.org/licenses/>.
*/ */
package org.isoron.uhabits.activities.habits.list.model; package org.isoron.uhabits.activities.habits.list.views;
import android.support.annotation.*; import android.support.annotation.*;
import android.support.v7.widget.*; import android.support.v7.widget.*;
@ -25,7 +25,6 @@ import android.view.*;
import org.isoron.androidbase.activities.*; import org.isoron.androidbase.activities.*;
import org.isoron.uhabits.activities.habits.list.*; import org.isoron.uhabits.activities.habits.list.*;
import org.isoron.uhabits.activities.habits.list.views.*;
import org.isoron.uhabits.core.models.*; import org.isoron.uhabits.core.models.*;
import org.isoron.uhabits.core.preferences.*; import org.isoron.uhabits.core.preferences.*;
import org.isoron.uhabits.core.ui.screens.habits.list.*; import org.isoron.uhabits.core.ui.screens.habits.list.*;

@ -17,13 +17,11 @@
* with this program. If not, see <http://www.gnu.org/licenses/>. * with this program. If not, see <http://www.gnu.org/licenses/>.
*/ */
package org.isoron.uhabits.activities.habits.list.controllers; package org.isoron.uhabits.activities.habits.list.views;
import android.support.annotation.*; import android.support.annotation.*;
import org.isoron.androidbase.activities.*; import org.isoron.androidbase.activities.*;
import org.isoron.uhabits.activities.habits.list.model.*;
import org.isoron.uhabits.activities.habits.list.views.*;
import org.isoron.uhabits.core.models.*; import org.isoron.uhabits.core.models.*;
import javax.inject.*; import javax.inject.*;
@ -200,9 +198,10 @@ public class HabitCardListController implements HabitCardListView.Controller,
if (selectionListener != null) selectionListener.onSelectionFinish(); if (selectionListener != null) selectionListener.onSelectionFinish();
} }
public interface HabitListener extends CheckmarkButtonController.Listener, public interface HabitListener
NumberButtonController.Listener
{ {
void onEdit(Habit habit, long timestamp);
/** /**
* Called when the user clicks a habit. * Called when the user clicks a habit.
* *
@ -218,6 +217,12 @@ public class HabitCardListController implements HabitCardListView.Controller,
* @param to habit that currently occupies the desired position * @param to habit that currently occupies the desired position
*/ */
void onHabitReorder(@NonNull Habit from, @NonNull Habit to); void onHabitReorder(@NonNull Habit from, @NonNull Habit to);
void onInvalidEdit();
void onInvalidToggle();
void onToggle(Habit habit, long timestamp);
} }
/** /**

@ -28,8 +28,6 @@ import android.util.*;
import android.view.*; import android.view.*;
import org.isoron.uhabits.activities.common.views.*; import org.isoron.uhabits.activities.common.views.*;
import org.isoron.uhabits.activities.habits.list.controllers.*;
import org.isoron.uhabits.activities.habits.list.model.*;
import org.isoron.uhabits.core.models.*; import org.isoron.uhabits.core.models.*;
import java.util.*; import java.util.*;
@ -39,7 +37,7 @@ public class HabitCardListView extends RecyclerView
@Nullable @Nullable
private HabitCardListAdapter adapter; private HabitCardListAdapter adapter;
@Nullable @NonNull
private Controller controller; private Controller controller;
private final ItemTouchHelper touchHelper; private final ItemTouchHelper touchHelper;
@ -62,6 +60,7 @@ public class HabitCardListView extends RecyclerView
touchHelper.attachToRecyclerView(this); touchHelper.attachToRecyclerView(this);
attachedHolders = new LinkedList<>(); attachedHolders = new LinkedList<>();
controller = new Controller() {};
} }
public void attachCardView(HabitCardViewHolder holder) public void attachCardView(HabitCardViewHolder holder)
@ -97,7 +96,7 @@ public class HabitCardListView extends RecyclerView
cardView.setScore(score); cardView.setScore(score);
cardView.setUnit(habit.getUnit()); cardView.setUnit(habit.getUnit());
cardView.setThreshold(habit.getTargetValue()); cardView.setThreshold(habit.getTargetValue());
if (controller != null) setupCardViewController(holder); setupCardViewListeners(holder);
return cardView; return cardView;
} }
@ -123,7 +122,7 @@ public class HabitCardListView extends RecyclerView
this.checkmarkCount = checkmarkCount; this.checkmarkCount = checkmarkCount;
} }
public void setController(@Nullable Controller controller) public void setController(@NonNull Controller controller)
{ {
this.controller = controller; this.controller = controller;
} }
@ -175,13 +174,15 @@ public class HabitCardListView extends RecyclerView
return new BundleSavedState(superState, bundle); return new BundleSavedState(superState, bundle);
} }
protected void setupCardViewController(@NonNull HabitCardViewHolder holder) protected void setupCardViewListeners(@NonNull HabitCardViewHolder holder)
{ {
HabitCardView cardView = (HabitCardView) holder.itemView; HabitCardView cardView = (HabitCardView) holder.itemView;
HabitCardController cardController = new HabitCardController(); cardView.setOnInvalidEditListener(() -> controller.onInvalidEdit());
cardController.setListener(controller); cardView.setOnInvalidToggleListener(() -> controller.onInvalidToggle());
cardView.setController(cardController); cardView.setOnToggleListener(
cardController.setView(cardView); (habit, timestamp) -> controller.onToggle(habit, timestamp));
cardView.setOnEditListener(
(habit, timestamp) -> controller.onEdit(habit, timestamp));
GestureDetector detector = new GestureDetector(getContext(), GestureDetector detector = new GestureDetector(getContext(),
new CardViewGestureDetector(holder)); new CardViewGestureDetector(holder));
@ -193,15 +194,22 @@ public class HabitCardListView extends RecyclerView
} }
public interface Controller public interface Controller
extends CheckmarkButtonController.Listener, HabitCardController.Listener
{ {
void drop(int from, int to); default void drop(int from, int to) {}
default void onItemClick(int pos) {}
default void onItemLongClick(int pos) {}
default void startDrag(int position) {}
default void onInvalidToggle() {}
void onItemClick(int pos); default void onInvalidEdit() {}
void onItemLongClick(int pos); default void onToggle(@NonNull Habit habit, long timestamp) {}
void startDrag(int position); default void onEdit(@NonNull Habit habit, long timestamp) {}
} }
private class CardViewGestureDetector private class CardViewGestureDetector

@ -38,15 +38,16 @@ import org.isoron.uhabits.utils.*;
import java.util.*; import java.util.*;
import static android.os.Build.VERSION.*; import static android.os.Build.VERSION.SDK_INT;
import static android.os.Build.VERSION_CODES.*; import static android.os.Build.VERSION_CODES.LOLLIPOP;
import static android.view.ViewGroup.LayoutParams.*; import static android.os.Build.VERSION_CODES.M;
import static org.isoron.androidbase.utils.InterfaceUtils.*; import static android.view.ViewGroup.LayoutParams.MATCH_PARENT;
import static android.view.ViewGroup.LayoutParams.WRAP_CONTENT;
import static org.isoron.androidbase.utils.InterfaceUtils.dpToPixels;
public class HabitCardView extends FrameLayout public class HabitCardView extends FrameLayout
implements ModelObservable.Listener implements ModelObservable.Listener
{ {
private static final String EDIT_MODE_HABITS[] = { private static final String EDIT_MODE_HABITS[] = {
"Wake up early", "Wake up early",
"Wash dishes", "Wash dishes",
@ -76,6 +77,18 @@ public class HabitCardView extends FrameLayout
private int dataOffset; private int dataOffset;
@NonNull
OnInvalidEditListener onInvalidEditListener;
@NonNull
OnEditListener onEditListener;
@NonNull
private OnToggleListener onToggleListener;
@NonNull
private OnInvalidToggleListener onInvalidToggleListener;
public HabitCardView(Context context) public HabitCardView(Context context)
{ {
super(context); super(context);
@ -100,15 +113,6 @@ public class HabitCardView extends FrameLayout
numberPanel.setButtonCount(buttonCount); numberPanel.setButtonCount(buttonCount);
} }
public void setController(Controller controller)
{
checkmarkPanel.setController(null);
numberPanel.setController(null);
if (controller == null) return;
checkmarkPanel.setController(controller);
numberPanel.setController(controller);
}
public void setDataOffset(int dataOffset) public void setDataOffset(int dataOffset)
{ {
this.dataOffset = dataOffset; this.dataOffset = dataOffset;
@ -119,11 +123,7 @@ public class HabitCardView extends FrameLayout
public void setHabit(@NonNull Habit habit) public void setHabit(@NonNull Habit habit)
{ {
if (isAttachedToWindow()) stopListening(); if (isAttachedToWindow()) stopListening();
this.habit = habit; this.habit = habit;
checkmarkPanel.setHabit(habit);
numberPanel.setHabit(habit);
refresh(); refresh();
if (isAttachedToWindow()) startListening(); if (isAttachedToWindow()) startListening();
postInvalidate(); postInvalidate();
@ -214,9 +214,25 @@ public class HabitCardView extends FrameLayout
initScoreRing(); initScoreRing();
initLabel(); initLabel();
onInvalidEditListener = () -> {};
onInvalidToggleListener = () -> {};
onEditListener = ((h, t) -> {});
onToggleListener = ((h,t) -> {});
checkmarkPanel = new CheckmarkPanelView(context); checkmarkPanel = new CheckmarkPanelView(context);
checkmarkPanel.setOnToggleLister(
(t) -> onToggleListener.onToggle(habit, t));
checkmarkPanel.setOnInvalidToggleListener(
() -> onInvalidToggleListener.onInvalidToggle());
numberPanel = new NumberPanelView(context); numberPanel = new NumberPanelView(context);
numberPanel.setVisibility(GONE); numberPanel.setVisibility(GONE);
numberPanel.setOnInvalidEditListener(() ->
onInvalidEditListener.onInvalidEdit());
numberPanel.setOnEditListener(((t) -> {
triggerRipple(t);
onEditListener.onEdit(habit, t);
}));
innerFrame.addView(scoreRing); innerFrame.addView(scoreRing);
innerFrame.addView(label); innerFrame.addView(label);
@ -346,9 +362,45 @@ public class HabitCardView extends FrameLayout
} }
} }
public interface Controller public void setOnEditListener(@NonNull OnEditListener onEditListener)
extends CheckmarkPanelView.Controller, NumberPanelView.Controller {
this.onEditListener = onEditListener;
}
public void setOnInvalidEditListener(
@NonNull OnInvalidEditListener onInvalidEditListener)
{
this.onInvalidEditListener = onInvalidEditListener;
}
public void setOnToggleListener(@NonNull OnToggleListener onToggleListener)
{
this.onToggleListener = onToggleListener;
}
public void setOnInvalidToggleListener(
@NonNull OnInvalidToggleListener onInvalidToggleListener)
{
this.onInvalidToggleListener = onInvalidToggleListener;
}
public interface OnEditListener
{ {
void onEdit(@NonNull Habit habit, long timestamp);
}
public interface OnInvalidEditListener
{
void onInvalidEdit();
}
public interface OnInvalidToggleListener
{
void onInvalidToggle();
}
public interface OnToggleListener
{
void onToggle(@NonNull Habit habit, long timestamp);
} }
} }

@ -17,7 +17,7 @@
* with this program. If not, see <http://www.gnu.org/licenses/>. * with this program. If not, see <http://www.gnu.org/licenses/>.
*/ */
package org.isoron.uhabits.activities.habits.list.model; package org.isoron.uhabits.activities.habits.list.views;
import android.support.v7.widget.*; import android.support.v7.widget.*;
import android.view.*; import android.view.*;

@ -28,15 +28,18 @@ import android.view.*;
import org.isoron.androidbase.utils.*; import org.isoron.androidbase.utils.*;
import org.isoron.uhabits.*; import org.isoron.uhabits.*;
import org.isoron.uhabits.activities.habits.list.controllers.*; import org.isoron.uhabits.activities.*;
import org.isoron.uhabits.core.preferences.*;
import org.isoron.uhabits.utils.*; import org.isoron.uhabits.utils.*;
import java.text.*; import java.text.*;
import static org.isoron.uhabits.utils.AttributeSetUtils.*; import static org.isoron.androidbase.utils.InterfaceUtils.getDimension;
import static org.isoron.androidbase.utils.InterfaceUtils.*; import static org.isoron.uhabits.utils.AttributeSetUtils.getAttribute;
import static org.isoron.uhabits.utils.AttributeSetUtils.getIntAttribute;
public class NumberButtonView extends View public class NumberButtonView extends View implements View.OnClickListener,
View.OnLongClickListener
{ {
private static Typeface BOLD_TYPEFACE = private static Typeface BOLD_TYPEFACE =
Typeface.create("sans-serif-condensed", Typeface.BOLD); Typeface.create("sans-serif-condensed", Typeface.BOLD);
@ -64,6 +67,15 @@ public class NumberButtonView extends View
private int darkGrey; private int darkGrey;
@NonNull
private OnEditListener onEditListener;
@NonNull
private OnInvalidEditListener onInvalidEditListener;
@Nullable
private Preferences prefs;
public NumberButtonView(@Nullable Context context) public NumberButtonView(@Nullable Context context)
{ {
super(context); super(context);
@ -88,10 +100,6 @@ public class NumberButtonView extends View
} }
} }
/**
* @param v
* @return
*/
public static String formatValue(double v) public static String formatValue(double v)
{ {
if (v >= 1e9) return String.format("%.1fG", v / 1e9); if (v >= 1e9) return String.format("%.1fG", v / 1e9);
@ -106,20 +114,25 @@ public class NumberButtonView extends View
return new DecimalFormat("#.##").format(v); return new DecimalFormat("#.##").format(v);
} }
public void setColor(int color) @Override
public void onClick(View v)
{ {
this.color = color; if(prefs == null) return;
postInvalidate(); if (prefs.isShortToggleEnabled()) onEditListener.onEdit();
else onInvalidEditListener.onInvalidEdit();
}
@Override
public boolean onLongClick(View v)
{
onEditListener.onEdit();
return true;
} }
public void setController(@NonNull NumberButtonController controller) public void setColor(int color)
{ {
setOnClickListener(v -> controller.onClick()); this.color = color;
setOnLongClickListener(v -> postInvalidate();
{
controller.onLongClick();
return true;
});
} }
public void setThreshold(double threshold) public void setThreshold(double threshold)
@ -140,6 +153,17 @@ public class NumberButtonView extends View
postInvalidate(); postInvalidate();
} }
public void setOnEditListener(@NonNull OnEditListener onEditListener)
{
this.onEditListener = onEditListener;
}
public void setOnInvalidEditListener(
@NonNull OnInvalidEditListener onInvalidEditListener)
{
this.onInvalidEditListener = onInvalidEditListener;
}
@Override @Override
protected void onDraw(Canvas canvas) protected void onDraw(Canvas canvas)
{ {
@ -188,5 +212,28 @@ public class NumberButtonView extends View
em = pBold.measureText("m"); em = pBold.measureText("m");
lightGrey = sr.getColor(R.attr.lowContrastTextColor); lightGrey = sr.getColor(R.attr.lowContrastTextColor);
darkGrey = sr.getColor(R.attr.mediumContrastTextColor); darkGrey = sr.getColor(R.attr.mediumContrastTextColor);
onEditListener = () -> {};
onInvalidEditListener = () -> {};
setOnClickListener(this);
setOnLongClickListener(this);
if(getContext() instanceof HabitsActivity)
{
HabitsApplicationComponent component =
((HabitsActivity) getContext()).getAppComponent();
prefs = component.getPreferences();
}
}
public interface OnEditListener
{
void onEdit();
}
public interface OnInvalidEditListener
{
void onInvalidEdit();
} }
} }

@ -25,9 +25,6 @@ import android.util.*;
import android.widget.*; import android.widget.*;
import org.isoron.uhabits.*; import org.isoron.uhabits.*;
import org.isoron.uhabits.activities.*;
import org.isoron.uhabits.activities.habits.list.controllers.*;
import org.isoron.uhabits.core.models.*;
import org.isoron.uhabits.core.preferences.*; import org.isoron.uhabits.core.preferences.*;
import org.isoron.uhabits.core.utils.*; import org.isoron.uhabits.core.utils.*;
@ -35,10 +32,10 @@ import java.util.*;
import static android.view.View.MeasureSpec.EXACTLY; import static android.view.View.MeasureSpec.EXACTLY;
import static android.view.View.MeasureSpec.makeMeasureSpec; import static android.view.View.MeasureSpec.makeMeasureSpec;
import static org.isoron.androidbase.utils.InterfaceUtils.getDimension;
import static org.isoron.uhabits.utils.AttributeSetUtils.getAttribute; import static org.isoron.uhabits.utils.AttributeSetUtils.getAttribute;
import static org.isoron.uhabits.utils.AttributeSetUtils.getIntAttribute; import static org.isoron.uhabits.utils.AttributeSetUtils.getIntAttribute;
import static org.isoron.uhabits.utils.PaletteUtils.getAndroidTestColor; import static org.isoron.uhabits.utils.PaletteUtils.getAndroidTestColor;
import static org.isoron.androidbase.utils.InterfaceUtils.getDimension;
public class NumberPanelView extends LinearLayout public class NumberPanelView extends LinearLayout
implements Preferences.Listener implements Preferences.Listener
@ -58,14 +55,14 @@ public class NumberPanelView extends LinearLayout
private int color; private int color;
private Controller controller;
private String unit; private String unit;
private int dataOffset;
@NonNull @NonNull
private Habit habit; private OnInvalidEditListener onInvalidEditListener;
private int dataOffset; private OnEditListener onEditListener;
public NumberPanelView(Context context) public NumberPanelView(Context context)
{ {
@ -87,30 +84,24 @@ public class NumberPanelView extends LinearLayout
setUnit(getAttribute(ctx, attrs, "unit", "min")); setUnit(getAttribute(ctx, attrs, "unit", "min"));
} }
if(isInEditMode()) initEditMode(); if (isInEditMode()) initEditMode();
} }
public void setUnit(String unit) public NumberButtonView indexToButton(int i)
{ {
this.unit = unit; int position = i;
setupButtons(); if (getCheckmarkOrder() == RIGHT_TO_LEFT) position = nButtons - i - 1;
return (NumberButtonView) getChildAt(position);
} }
public void initEditMode() public void initEditMode()
{ {
double values[] = new double[nButtons]; double values[] = new double[nButtons];
for(int i = 0; i < nButtons; i++) for (int i = 0; i < nButtons; i++)
values[i] = new Random().nextDouble() * (threshold * 3); values[i] = new Random().nextDouble() * (threshold * 3);
setValues(values); setValues(values);
} }
public NumberButtonView indexToButton(int i)
{
int position = i;
if (getCheckmarkOrder() == RIGHT_TO_LEFT) position = nButtons - i - 1;
return (NumberButtonView) getChildAt(position);
}
@Override @Override
public void onCheckmarkOrderChanged() public void onCheckmarkOrderChanged()
{ {
@ -134,22 +125,21 @@ public class NumberPanelView extends LinearLayout
setupButtons(); setupButtons();
} }
public void setController(Controller controller) public void setDataOffset(int dataOffset)
{ {
this.controller = controller; this.dataOffset = dataOffset;
setupButtons(); setupButtons();
} }
public void setDataOffset(int dataOffset) public void setOnInvalidEditListener(
@NonNull OnInvalidEditListener onInvalidEditListener)
{ {
this.dataOffset = dataOffset; this.onInvalidEditListener = onInvalidEditListener;
setupButtons();
} }
public void setHabit(@NonNull Habit habit) public void setOnEditListener(OnEditListener onEditListener)
{ {
this.habit = habit; this.onEditListener = onEditListener;
setupButtons();
} }
public void setThreshold(double threshold) public void setThreshold(double threshold)
@ -158,6 +148,12 @@ public class NumberPanelView extends LinearLayout
setupButtons(); setupButtons();
} }
public void setUnit(String unit)
{
this.unit = unit;
setupButtons();
}
public void setValues(double[] values) public void setValues(double[] values)
{ {
this.values = values; this.values = values;
@ -196,7 +192,6 @@ public class NumberPanelView extends LinearLayout
private void addButtons() private void addButtons()
{ {
removeAllViews(); removeAllViews();
for (int i = 0; i < nButtons; i++) for (int i = 0; i < nButtons; i++)
addView(new NumberButtonView(getContext())); addView(new NumberButtonView(getContext()));
} }
@ -218,23 +213,19 @@ public class NumberPanelView extends LinearLayout
setWillNotDraw(false); setWillNotDraw(false);
values = new double[0]; values = new double[0];
onInvalidEditListener = () -> {};
onEditListener = (t) -> {};
} }
private void setupButtonControllers(long timestamp, private void setupButtonControllers(long timestamp,
NumberButtonView buttonView) NumberButtonView buttonView)
{ {
if (controller == null) return; buttonView.setOnEditListener(
if (!(getContext() instanceof HabitsActivity)) return; () -> onEditListener.onEdit(timestamp));
HabitsActivity activity = (HabitsActivity) getContext(); buttonView.setOnInvalidEditListener(
NumberButtonControllerFactory buttonControllerFactory = activity () -> onInvalidEditListener.onInvalidEdit());
.getActivityComponent()
.getNumberButtonControllerFactory();
NumberButtonController buttonController =
buttonControllerFactory.create(habit, timestamp);
buttonController.setListener(controller);
buttonView.setController(buttonController);
} }
private void setupButtons() private void setupButtons()
@ -256,7 +247,13 @@ public class NumberPanelView extends LinearLayout
} }
} }
public interface Controller extends NumberButtonController.Listener public interface OnInvalidEditListener
{
void onInvalidEdit();
}
public interface OnEditListener
{ {
void onEdit(long timestamp);
} }
} }

@ -1,96 +0,0 @@
/*
* Copyright (C) 2017 Álinson Santos Xavier <isoron@gmail.com>
*
* This file is part of Loop Habit Tracker.
*
* Loop Habit Tracker is free software: you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by the
* Free Software Foundation, either version 3 of the License, or (at your
* option) any later version.
*
* Loop Habit Tracker is distributed in the hope that it will be useful, but
* WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY
* or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for
* more details.
*
* You should have received a copy of the GNU General Public License along
* with this program. If not, see <http://www.gnu.org/licenses/>.
*/
package org.isoron.uhabits.activities.habits.list.controllers;
import org.isoron.uhabits.*;
import org.isoron.uhabits.activities.habits.list.views.*;
import org.isoron.uhabits.core.models.*;
import org.isoron.uhabits.core.preferences.*;
import org.junit.*;
import static org.mockito.Mockito.*;
public class CheckmarkButtonControllerTest extends BaseAndroidUnitTest
{
private CheckmarkButtonController controller;
private CheckmarkButtonView view;
private CheckmarkButtonController.Listener listener;
private Habit habit;
private int timestamp;
private Preferences prefs;
@Override
@Before
public void setUp()
{
super.setUp();
timestamp = 0;
habit = mock(Habit.class);
prefs = mock(Preferences.class);
this.view = mock(CheckmarkButtonView.class);
this.listener = mock(CheckmarkButtonController.Listener.class);
this.controller =
new CheckmarkButtonController(prefs, habit, timestamp);
controller.setView(view);
controller.setListener(listener);
}
@Test
public void testOnClick_withShortToggle() throws Exception
{
doReturn(true).when(prefs).isShortToggleEnabled();
controller.onClick();
verifyToggle();
}
@Test
public void testOnClick_withoutShortToggle() throws Exception
{
doReturn(false).when(prefs).isShortToggleEnabled();
controller.onClick();
verifyInvalidToggle();
}
@Test
public void testOnLongClick() throws Exception
{
controller.onLongClick();
verifyToggle();
}
protected void verifyInvalidToggle()
{
verifyZeroInteractions(view);
verify(listener).onInvalidToggle();
}
protected void verifyToggle()
{
verify(view).toggle();
verify(listener).onToggle(habit, timestamp);
}
}

@ -1,72 +0,0 @@
/*
* Copyright (C) 2017 Álinson Santos Xavier <isoron@gmail.com>
*
* This file is part of Loop Habit Tracker.
*
* Loop Habit Tracker is free software: you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by the
* Free Software Foundation, either version 3 of the License, or (at your
* option) any later version.
*
* Loop Habit Tracker is distributed in the hope that it will be useful, but
* WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY
* or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for
* more details.
*
* You should have received a copy of the GNU General Public License along
* with this program. If not, see <http://www.gnu.org/licenses/>.
*/
package org.isoron.uhabits.activities.habits.list.controllers;
import org.isoron.uhabits.*;
import org.isoron.uhabits.core.models.*;
import org.isoron.uhabits.activities.habits.list.views.*;
import org.isoron.uhabits.core.utils.*;
import org.junit.*;
import static org.mockito.Mockito.*;
public class HabitCardControllerTest extends BaseAndroidUnitTest
{
private Habit habit;
private HabitCardController controller;
private HabitCardController.Listener listener;
private HabitCardView view;
@Override
@Before
public void setUp()
{
super.setUp();
this.habit = mock(Habit.class);
this.listener = mock(HabitCardController.Listener.class);
this.view = mock(HabitCardView.class);
this.controller = new HabitCardController();
controller.setListener(listener);
controller.setView(view);
view.setController(controller);
}
@Test
public void testOnInvalidToggle()
{
controller.onInvalidToggle();
verify(listener).onInvalidToggle();
}
@Test
public void testOnToggle()
{
long timestamp = DateUtils.getStartOfToday();
controller.onToggle(habit, timestamp);
verify(view).triggerRipple(timestamp);
verify(listener).onToggle(habit, timestamp);
}
}

@ -20,7 +20,6 @@
package org.isoron.uhabits.activities.habits.list.controllers; package org.isoron.uhabits.activities.habits.list.controllers;
import org.isoron.uhabits.*; import org.isoron.uhabits.*;
import org.isoron.uhabits.activities.habits.list.model.*;
import org.isoron.uhabits.core.models.*; import org.isoron.uhabits.core.models.*;
import org.isoron.uhabits.activities.habits.list.views.*; import org.isoron.uhabits.activities.habits.list.views.*;
import org.junit.*; import org.junit.*;

Loading…
Cancel
Save