package com.wildplot.android.rendering;
import android.graphics.Color;
import com.wildplot.android.rendering.graphics.wrapper.ColorWrap;
import com.wildplot.android.rendering.graphics.wrapper.FontMetricsWrap;
import com.wildplot.android.rendering.graphics.wrapper.GraphicsWrap;
import com.wildplot.android.rendering.graphics.wrapper.RectangleWrap;
import org.junit.Before;
import org.junit.Test;
import org.junit.runner.RunWith;
import org.junit.runners.Parameterized;
import org.junit.runners.Parameterized.Parameter;
import org.mockito.InOrder;
import org.mockito.Mock;
import org.powermock.core.classloader.annotations.PrepareForTest;
import org.powermock.modules.junit4.PowerMockRunner;
import org.powermock.modules.junit4.PowerMockRunnerDelegate;
import java.util.ArrayList;
import java.util.Arrays;
import java.util.Collection;
import static com.wildplot.android.rendering.PieChartTest.createRectangleMock;
import static java.util.Arrays.asList;
import static org.mockito.Matchers.any;
import static org.mockito.Matchers.anyFloat;
import static org.mockito.Matchers.anyInt;
import static org.mockito.Matchers.floatThat;
import static org.mockito.Mockito.inOrder;
import static org.powermock.api.mockito.PowerMockito.mock;
import static org.powermock.api.mockito.PowerMockito.mockStatic;
import static org.powermock.api.mockito.PowerMockito.when;
@RunWith(PowerMockRunner.class)
@PowerMockRunnerDelegate(value = Parameterized.class)
@PrepareForTest({RectangleWrap.class, GraphicsWrap.class, ColorWrap.class,
android.graphics.Color.class})
@SuppressWarnings("WeakerAccess")
public class PieChartParameterizedTest {
private static final double PRECISION = 2 * 1E-3F;
@Parameter(0)
public double[] values;
@Parameter(1)
public double[] startAngles;
@Parameter(2)
public double[] arcLengths;
@Parameter(3)
public ColorWrap[] colors;
@Mock
GraphicsWrap graphics;
@Mock
PlotSheet plot;
PieChart pieChart;
@Before
public void setUp() throws Exception {
mockStatic(android.graphics.Color.class);
when(Color.argb(anyInt(), anyInt(), anyInt(), anyInt())).thenReturn(0);
when(plot.getFrameThickness()).thenReturn(new float[]{0, 0, 0, 0});
FontMetricsWrap fm = mock(FontMetricsWrap.class);
when(fm.getHeight()).thenReturn(10f);
when(fm.stringWidth(any(String.class))).thenReturn(30f);
when(graphics.getFontMetrics()).thenReturn(fm);
RectangleWrap r = createRectangleMock(100, 100);
when(graphics.getClipBounds()).thenReturn(r);
pieChart = new PieChart(plot, values, colors);
}
@Test
public void testPaintDrawsAllArcs() throws Exception {
pieChart.paint(graphics);
// ordered verification is used to prevent failures when there are tiny adjacent sectors
InOrder inOrder = inOrder(graphics);
for (int i = 0; i < values.length; i++) {
if (arcLengths[i] == 0) continue;
inOrder.verify(graphics).setColor(colors[i]);
inOrder.verify(graphics).fillArc(anyFloat(), anyFloat(), anyFloat(), anyFloat(),
floatThat(closeTo(startAngles[i])),
floatThat(closeTo(arcLengths[i])));
}
}
private static FloatMatcher closeTo(double v) {
return FloatMatcher.closeTo(v, PRECISION);
}
@Parameterized.Parameters
public static Collection<Object[]> data() {
return createParametersCollection(asList(
values(1),
values(0, 1),
values(1, 0),
values(1, 0, 1),
// arrays of equal values of various sizes
equalValues(2),
equalValues(3),
equalValues(4),
equalValues(17),
// tiny only
values(1E-100),
values(1E-100, 1E-100, 1E-100),
// huge only
values(1E100),
values(1E100, 1E100, 1E100),
// huge and tiny
values(1E-100, 1E100),
values(1E100, 1E-100),
values(1E100, 1E-100, 1E100),
values(1E-100, 1E100, 1E-100),
values(1E100, 1E-100, 1E-100, 1E100)
));
}
private static Collection<Object[]> createParametersCollection(Collection<double[]> values) {
Collection<Object[]> parameters = new ArrayList<>(values.size());
for (double[] v : values) {
parameters.add(createParameters(v));
}
return parameters;
}
private static Object[] createParameters(double[] values) {
PieChartTestParametersBuilder builder = new PieChartTestParametersBuilder(values,
PieChart.FIRST_SECTOR_OFFSET);
return new Object[] {
values,
builder.getStartAngles(),
builder.getArcLengths(),
builder.getColors()
};
}
private static double[] values(double... d) {
return d;
}
private static double[] equalValues(int numberOfValues) {
double[] v = new double[numberOfValues];
Arrays.fill(v, 1);
return v;
}
}