package zenproject.meditation.android.sketch.painting.ink; import com.juankysoriano.rainbow.core.event.RainbowInputController; import org.junit.Before; import org.junit.Test; import org.junit.runner.RunWith; import org.mockito.Mock; import org.mockito.MockitoAnnotations; import org.robolectric.annotation.Config; import zenproject.meditation.android.BuildConfig; import zenproject.meditation.android.ContextRetriever; import zenproject.meditation.android.R; import zenproject.meditation.android.RobolectricLauncherGradleTestRunner; import zenproject.meditation.android.ZenTestBase; import zenproject.meditation.android.preferences.BrushOptionsPreferences; import static org.fest.assertions.api.Assertions.assertThat; import static org.mockito.Mockito.verify; import static org.mockito.Mockito.when; @RunWith(RobolectricLauncherGradleTestRunner.class) @Config(constants = BuildConfig.class) public class InkDropTest extends ZenTestBase { private static final float INITIAL_RADIUS = ContextRetriever.INSTANCE.getResources().getDimension(R.dimen.ink_drop_min_radius); private static final float INK_VELOCITY_THRESHOLD = ContextRetriever.INSTANCE.getResources().getDimension(R.dimen.ink_velocity_threshold); private static final float RADIUS_STEP = ContextRetriever.INSTANCE.getResources().getDimension(R.dimen.ink_drop_step); private static final float BIG_RADIUS = 10f; @Mock private InkDropSizeLimiter inkDropSizeLimiter; @Mock private BrushOptionsPreferences brushOptionsPreferences; @Mock private RainbowInputController rainbowInputController; private InkDrop inkDrop; @Before public void setUp() { MockitoAnnotations.initMocks(this); when(inkDropSizeLimiter.getMaximumRadius()).thenReturn(BIG_RADIUS); when(inkDropSizeLimiter.getMinimumRadius()).thenReturn(INITIAL_RADIUS); inkDrop = new InkDrop(inkDropSizeLimiter, brushOptionsPreferences, rainbowInputController); } @Test public void testThatInitialRadiusIsTheAbsoluteMinRadius() { assertThat(inkDrop.getRadius()).isEqualTo(INITIAL_RADIUS); } @Test public void testThatGetBrushColorRetrievesFromBrushOptionsPreferences() { inkDrop.getBrushColor(); verify(brushOptionsPreferences).getBrushColor(); } @Test public void testThatGetMaxRadiusRetrievesFromInkDropSizeLimiter() { inkDrop.getMaxRadius(); verify(inkDropSizeLimiter).getMaximumRadius(); } @Test public void testThatUpdateInkRadiusIncreasesRadiusIfTouchingScreenAndFingerMovingSlow() { givenThatRadiusShouldIncrease(); inkDrop.updateInkRadius(); assertThat(inkDrop.getRadius()).isGreaterThan(INITIAL_RADIUS); } @Test public void testThatUpdateInkRadiusDecreasesRadiusIfFingerMovingFast() { givenThatRadiusHasPreviouslyIncreasedTwoSteps(); givenThatFingerIsMovingFast(); givenThatScreenIsTouched(); inkDrop.updateInkRadius(); assertThat(inkDrop.getRadius()).isEqualTo(RADIUS_STEP + INITIAL_RADIUS); } @Test public void testThatUpdateInkRadiusDecreasesRadiusIfNotTouchingScreen() { givenThatRadiusHasPreviouslyIncreasedTwoSteps(); givenThatFingerIsMovingSlow(); givenThatScreenIsNotTouched(); inkDrop.updateInkRadius(); assertThat(inkDrop.getRadius()).isEqualTo(RADIUS_STEP + INITIAL_RADIUS); } @Test public void testThatResetRadiusSetsRadiusToAbsoluteMinimum() { givenThatRadiusHasPreviouslyIncreasedTwoSteps(); inkDrop.resetRadius(); assertThat(inkDrop.getRadius()).isEqualTo(INITIAL_RADIUS); } @Test public void testThatNewInstanceReturnsNotNullInkDrop() { assertThat(InkDrop.newInstance(rainbowInputController)).isNotNull(); } @Test public void testThatNewInstanceReturnsANewInstance() { InkDrop firstInstance = InkDrop.newInstance(rainbowInputController); InkDrop secondInstance = InkDrop.newInstance(rainbowInputController); assertThat(firstInstance).isNotEqualTo(secondInstance); } private void givenThatFingerIsMovingSlow() { when(rainbowInputController.isFingerMoving()).thenReturn(true); when(rainbowInputController.getFingerVelocity()).thenReturn(-1f); } private void givenThatFingerIsMovingFast() { when(rainbowInputController.isFingerMoving()).thenReturn(true); when(rainbowInputController.getFingerVelocity()).thenReturn(INK_VELOCITY_THRESHOLD+1f); } private void givenThatScreenIsTouched() { when(rainbowInputController.isScreenTouched()).thenReturn(true); } private void givenThatScreenIsNotTouched() { when(rainbowInputController.isFingerMoving()).thenReturn(false); when(rainbowInputController.isScreenTouched()).thenReturn(false); } private void givenThatRadiusHasPreviouslyIncreasedTwoSteps() { givenThatRadiusShouldIncrease(); inkDrop.updateInkRadius(); inkDrop.updateInkRadius(); } private void givenThatRadiusShouldIncrease() { givenThatScreenIsTouched(); givenThatFingerIsMovingSlow(); } }