Skip to content
Snippets Groups Projects
Commit 7fa7a56a authored by Leonard Kupper's avatar Leonard Kupper
Browse files

Make ready for automatic merge. (Merge master)

parent 41a7aaf6
No related branches found
No related tags found
1 merge request!8Feat/rasterizer 10
Showing
with 656 additions and 0 deletions
package de.tudresden.inf.mci.brailleplot.printabledata;
import de.tudresden.inf.mci.brailleplot.configparser.Printer;
import de.tudresden.inf.mci.brailleplot.configparser.Format;
/**
* Abstract parent class for all {@link PrintableData} implementations.
* @author Georg Graßnick
* @version 2019.06.26
*/
abstract class AbstractPrintableData implements PrintableData {
private final Printer mPrinter;
private final Format mFormat;
AbstractPrintableData(final Printer printer, final Format format) {
if (printer == null || format == null) {
throw new NullPointerException();
}
mPrinter = printer;
mFormat = format;
}
@Override
public Printer getPrinterConfig() {
return mPrinter;
}
@Override
public Format getFormatConfig() {
return mFormat;
}
}
package de.tudresden.inf.mci.brailleplot.printabledata;
/**
* Simple container class encapsulating 6 dots to form a representation of a Braille cell.
* The ordering of the positions follows the following convention:
* Top to bottom, then left to right; indices start at 0:
*
* 0 3
* 1 4
* 2 5
*
* @param <T> The type used for representing the intensity. Could be set to {@link Boolean} for basic Braille support,
* but could also by set to {@link Short} if different embossing strengths are required.
* @author Georg Graßnick
* @version 2019.06.28
*/
public final class BrailleCell6<T> {
static final int DOT_COUNT = 6;
static final int ROW_COUNT = 3;
static final int COLUMN_COUNT = 2;
private T[] mDots;
/**
* Constructor.
* The values are not checked for null!
* @param first Value of the first dot.
* @param second Value of the second dot.
* @param third Value of the third dot.
* @param fourth Value of the fourth dot.
* @param fifth Value of the fifth dot.
* @param sixth Value of the sixth dot.
*/
@SuppressWarnings({"unchecked", "checkstyle:MagicNumber"})
public BrailleCell6(final T first, final T second, final T third, final T fourth, final T fifth, final T sixth) {
mDots = (T[]) new Object[DOT_COUNT];
mDots[0] = first;
mDots[1] = second;
mDots[2] = third;
mDots[3] = fourth;
mDots[4] = fifth;
mDots[5] = sixth;
}
/**
* Constructor.
* The values are not checked for null!
* @param vals An array of values to obtain the values from.
* @throws IllegalArgumentException If the length is not equal to 6.
*/
BrailleCell6(final T[] vals) {
if (vals.length != DOT_COUNT) {
throw new IllegalArgumentException("Input Array must be of length " + DOT_COUNT);
}
mDots = vals.clone();
}
/**
* Get the value at the specified position.
* @param index The index of the position,
* @return The according value.
* @throws ArrayIndexOutOfBoundsException If the index is out of bounds (not in 0-5).
*/
public T get(final int index) {
if (index < 0 || index >= DOT_COUNT) {
throw new ArrayIndexOutOfBoundsException("Index not valid");
}
return mDots[index];
}
/**
* Set the value at the specified position.
* @param index The index of the position.
* @param value The value to set.
* @throws ArrayIndexOutOfBoundsException If the index is out of bounds (not in 0-5).
*/
public void set(final int index, final T value) {
if (index < 0 || index >= DOT_COUNT) {
throw new ArrayIndexOutOfBoundsException("Index not valid");
}
mDots[index] = value;
}
/**
* Get the internal data array.
* @return The internal data array of length 6.
*/
public T[] data() {
return mDots;
}
public String toString() {
StringBuilder sb = new StringBuilder();
for (int i = 0; i < ROW_COUNT; i++) {
for (int j = 0; j < COLUMN_COUNT; j++) {
sb.append(mDots[i * COLUMN_COUNT + j]);
sb.append(" ");
}
sb.append("\n");
}
return sb.toString();
}
}
package de.tudresden.inf.mci.brailleplot.printabledata;
import java.util.Iterator;
/**
* This data is used to describe the data for the "Floating Dot Area" print mode.
* For each dot to emboss, there is one {@link Point2D} object which encapsulates both the position in width and height,
* as well as the intensity of the point.
* @param <T> The type used for representing the intensity. Could be set to {@link Boolean} for basic Braille support,
* but could also by set to {@link Short} if different embossing strengths are required.
* @author Georg Graßnick
* @version 2019.06.26
*/
public interface FloatingPointData<T> extends PrintableData {
/**
* Returns an iterator over all {@link Point2DValued}.
* @return An iterator over all points.
*/
Iterator<Point2DValued<T>> getIterator();
/**
* Add a point to the data structure.
* @param point The point to be inserted.
*/
void addPoint(Point2DValued<T> point);
}
package de.tudresden.inf.mci.brailleplot.printabledata;
import java.util.Iterator;
/**
* This data is used to describe the data for the "Braille" and "Graphics" print modes.
* The data is organized in a matrix structure, which can be queried for its values on integer x (row) and y (column) indices.
* @param <T> The type used for representing the intensity. Could be set to {@link Boolean} for basic Braille support,
* but could also by set to {@link Short} if different embossing strengths are required.
* @author Georg Graßnick
* @version 2019.06.26
*/
public interface MatrixData<T> extends PrintableData {
/**
* Get the value for a specific position in the matrix.
* Indices start at 0.
* @param row The row index of the position.
* @param column The column index of the position.
* @return The value at the requested position.
*/
T getValue(int row, int column);
/**
* Get an iterator which iterates all dots of the matrix.
* Depending on the width and height parameters, the iterator will iterate the dots of Braille cells of the
* specified size from top to bottom and then from left to right
* Example: width = 2, height = 3; matrix size is 4x6:
*
* 01 04 07 10
* 02 05 08 11
* 03 06 09 12
* 13 16 19 22
* 14 17 20 23
* 15 18 21 24
*
* @param width The width of a Braille cell
* @param height The height of a Braille cell
* @return The according iterator.
*/
Iterator<T> getDotIterator(int width, int height);
/**
* Get an iterator which iterates over Braille cells of the matrix.
* The cells have a width of 2 columns and a height of 3 rows to mach a standard 6 dot Braille cell.
* The matrix is traversed from left to right and then top to bottom.
* Example: matrix size is 4x6 - The ids specify the associated Braille cell.
*
* 01 01 02 02
* 01 01 02 02
* 01 01 02 02
* 03 03 04 04
* 03 03 04 04
* 03 03 04 04
*
* @return The according iterator.
*/
Iterator<BrailleCell6<T>> getBrailleCell6Iterator();
/**
* Set the value at a specific position.
* Indices start at 0.
* @param row The row index of the position.
* @param column The column index of the position.
* @param value The value to set.
*/
void setValue(int row, int column, T value);
/**
* Getter.
* @return The number of rows.
*/
int getRowCount();
/**
* Getter.
* @return The number of columns.
*/
int getColumnCount();
}
package de.tudresden.inf.mci.brailleplot.printabledata;
import javax.measure.Quantity;
import javax.measure.quantity.Length;
import java.util.Objects;
/**
* Representation of a 2 dimensional point.
* Encapsulates a position on x and y axis.
* @author Georg Graßnick
* @version 2019.06.26
*/
public class Point2D {
private final Quantity<Length> mX;
private final Quantity<Length> mY;
/**
* Constructor.
* @param x Position on the x axis.
* @param y Position on the y axis.
*/
public Point2D(final Quantity<Length> x, final Quantity<Length> y) {
if (x == null || y == null) {
throw new NullPointerException();
}
mX = x;
mY = y;
}
/**
* Getter.
* @return The position on the x axis.
*/
public final Quantity<Length> getX() {
return mX;
}
/**
* Getter.
* @return The position on the y axis.
*/
public final Quantity<Length> getY() {
return mY;
}
/**
* Check for Object equality.
* @param other The other to compare to.
* @return true, if X and Y positions of both points are equal; else false
*/
@Override
public boolean equals(final Object other) {
if (this == other) {
return true;
}
if (!(other instanceof Point2D)) {
return false;
}
Point2D point = (Point2D) other;
return mX.equals(point.mX) && mY.equals(point.mY);
}
@Override
public int hashCode() {
return Objects.hash(mX, mY);
}
/**
* Create a human readable String to represent the point.
* @return A human readable String.
*/
@Override
public String toString() {
return "(" + mX + ", " + mY + ")";
}
}
package de.tudresden.inf.mci.brailleplot.printabledata;
import javax.measure.Quantity;
import javax.measure.quantity.Length;
import java.util.Objects;
/**
* Representation of a 2 dimensional point with an associated value.
* Encapsulates both the position on x and y axis, as well as a value (think of embossing intensity).
* @param <T> The type used for representing the intensity. Could be set to {@link Boolean} for basic Braille support,
* but could also by set to {@link Short} if different embossing strengths are required.
* @author Georg Graßnick
* @version 2019.06.26
*/
public class Point2DValued<T> extends Point2D {
private final T mVal;
/**
* Constructor.
* @param x Position on the x axis.
* @param y Position on the y axis.
* @param val The value of the dot
*/
public Point2DValued(final Quantity<Length> x, final Quantity<Length> y, final T val) {
super(x, y);
if (val == null) {
throw new NullPointerException();
}
mVal = val;
}
/**
* Getter.
* @return The value that is associated with this point.
*/
public final T getVal() {
return mVal;
}
/**
* Check for Object equality.
* @param other The other to compare to.
* @return true, if X and Y positions and the values of both points are equal; else false
*/
@Override
public boolean equals(final Object other) {
if (this == other) {
return true;
}
if (!(other instanceof Point2DValued)) {
return false;
}
Point2D point = (Point2DValued) other;
return super.equals(other) && mVal.equals(((Point2DValued) other).mVal);
}
@Override
public int hashCode() {
return Objects.hash(mVal, super.hashCode());
}
/**
* Create a human readable String to represent the point.
* @return A human readable String.
*/
@Override
public String toString() {
return "(" + super.getX() + ", " + super.getY() + ": " + mVal + ")";
}
}
package de.tudresden.inf.mci.brailleplot.printabledata;
import de.tudresden.inf.mci.brailleplot.configparser.Printer;
import de.tudresden.inf.mci.brailleplot.configparser.Format;
/**
* Top interface for all data types that describe data ready for printing.
* These data containers are generated by the rasterizer and later on processed by the printer backend.
* @author Georg Graßnick
* @version 2019.06.26
*/
public interface PrintableData {
/**
* Getter for the Printer Configuration, that was used to generate this data representation in the rasterizer.
* @return The associated Printer Configuration
*/
Printer getPrinterConfig();
/**
* Getter for the Format Configuration, that was used to generate this data representation in the rasterizer.
* @return The associated Format Configuration
*/
Format getFormatConfig();
}
package de.tudresden.inf.mci.brailleplot.printabledata;
import java.util.Iterator;
import java.util.LinkedList;
import de.tudresden.inf.mci.brailleplot.configparser.Printer;
import de.tudresden.inf.mci.brailleplot.configparser.Format;
/**
* A low effort implementation of the {@link FloatingPointData} interface.
* The underlying data is organized in a {@link LinkedList}, which makes insertions fast, but slows down random access.
* @param <T> The type used for representing the intensity. Could be set to {@link Boolean} for basic Braille support,
* but could also by set to {@link Short} if different embossing strengths are required.
* @author Georg Graßnick
* @version 2019.06.26
*/
public class SimpleFloatingPointDataImpl<T> extends AbstractPrintableData implements FloatingPointData<T> {
private LinkedList<Point2DValued<T>> mPoints;
public SimpleFloatingPointDataImpl(final Printer printer, final Format format) {
super(printer, format);
mPoints = new LinkedList<>();
}
@Override
public Iterator<Point2DValued<T>> getIterator() {
return mPoints.iterator();
}
@Override
public void addPoint(final Point2DValued<T> point) {
if (point == null) {
throw new NullPointerException();
}
mPoints.addLast(point);
}
}
package de.tudresden.inf.mci.brailleplot.printabledata;
import java.util.Iterator;
import java.util.Vector;
import de.tudresden.inf.mci.brailleplot.configparser.Printer;
import de.tudresden.inf.mci.brailleplot.configparser.Format;
/**
* A low effort implementation of the {@link MatrixData} interface.
* The underlying data is represented by a {@link Vector} which makes the lookup and insertion fast, but uses lots of memory.
* @param <T> The type used for representing the intensity. Could be set to {@link Boolean} for basic Braille support,
* * but could also by set to {@link Short} if different embossing strengths are required.
* @author Georg Graßnick
* @version 2019.06.26
*/
public class SimpleMatrixDataImpl<T> extends AbstractPrintableData implements MatrixData<T> {
private final int mRows;
private final int mColumns;
private final Vector<T> mData;
/**
* Constructor.
* @param printer The according {@link Printer} object.
* @param format The according {@link Format} object.
* @param rowCount The height of the matrix.
* @param columnCount The width of the matrix.
* @param defaultValue The default value each element will be assigned.
* @throws IllegalArgumentException if rowCount {@literal <} 0 or columnCount {@literal <} 0
*/
public SimpleMatrixDataImpl(final Printer printer, final Format format, final int rowCount, final int columnCount, final T defaultValue) {
super(printer, format);
if (rowCount <= 0 || columnCount <= 0) {
throw new IllegalArgumentException("rowCount and columnCount must be a non zero positive integer");
}
mRows = rowCount;
mColumns = columnCount;
mData = new Vector<>(rowCount * columnCount);
mData.setSize(rowCount * columnCount);
for (int i = 0; i < mData.size(); i++) {
mData.setElementAt(defaultValue, i);
}
}
/**
* Calculate the index for the underlying {@link java.util.ArrayList}.
* @param row The row index of the requested index.
* @param column The column index of the requested index.
* @return The according index in the underlying {@link java.util.ArrayList}
* @throws IndexOutOfBoundsException If row or column are negative or larger than the size of the matrix.
*/
private int calcIndex(final int row, final int column) {
if (row >= mRows || column > mColumns || row < 0 || column < 0) {
throw new IndexOutOfBoundsException("Index (" + row + "," + column + ") out of bounds");
}
return row * mColumns + column;
}
@Override
public T getValue(final int row, final int column) {
return mData.get(calcIndex(row, column));
}
@Override
public void setValue(final int row, final int column, final T value) {
if (value == null) {
throw new NullPointerException();
}
mData.set(calcIndex(row, column), value);
}
@Override
public Iterator<T> getDotIterator(final int width, final int height) {
return new ElementIter(width, height, this);
}
@Override
public Iterator<BrailleCell6<T>> getBrailleCell6Iterator() {
return new BrailleCell6Iterator(this);
}
@Override
public int getColumnCount() {
return mColumns;
}
@Override
public int getRowCount() {
return mRows;
}
public final String toString() {
StringBuilder sb = new StringBuilder();
for (int i = 0; i < getRowCount(); i++) {
for (int j = 0; j < getColumnCount(); j++) {
sb.append(getValue(i, j));
sb.append(" ");
}
sb.append("\n");
}
return sb.toString();
}
/**
* Iterator that iterates all elements of the matrix in a pattern that iterates Braille cells of specified height
* and width from left to right and top to bottom.
* See {@link MatrixData#getDotIterator(int, int)} for details.
*/
class ElementIter implements Iterator<T> {
private final SimpleMatrixDataImpl<T> mMatrix;
private final int mCellWidth;
private final int mCellHeight;
// We use indices starting at 1, so that we do not have to check for the x-index to be 0 in the next() method call
private int mCurrentX = 1;
private int mCurrentY = 1;
private boolean mIsFirstElem = true;
ElementIter(final int cellWidth, final int cellHeight, final SimpleMatrixDataImpl<T> matrix) {
if (matrix.getColumnCount() % cellWidth != 0) {
throw new IllegalArgumentException("Cannot create requested iterator: matrix column count (" + matrix.getColumnCount() + ") is not a multiple of cell height (" + cellHeight + ")");
}
if (matrix.getRowCount() % cellHeight != 0) {
throw new IllegalArgumentException("Cannot create requested iterator: matrix row count (" + matrix.getRowCount() + ") is not a multiple of cell width (" + cellWidth + ")");
}
mMatrix = matrix;
mCellWidth = cellWidth;
mCellHeight = cellHeight;
}
@Override
public boolean hasNext() {
return !(mCurrentY == mMatrix.getRowCount() && mCurrentX == mMatrix.getColumnCount());
}
@Override
public T next() {
if (mIsFirstElem) {
mIsFirstElem = false;
} else if (mCurrentY % mCellHeight != 0) {
// Staying in the current cell, move down
mCurrentY++;
} else if (mCurrentX % mCellWidth != 0) {
// Staying in current cell, move right, set y to the top most index of the current cell
mCurrentX++;
mCurrentY = (((mCurrentY / mCellHeight) - 1) * mCellHeight) + 1;
} else if (mCurrentX < mMatrix.getColumnCount()) { // Moving on to the next cell
// Right is possible
mCurrentX += 1;
mCurrentY = (((mCurrentY / mCellHeight) - 1) * mCellHeight) + 1;
} else {
// We need to go downwards
mCurrentY += 1;
mCurrentX = 1;
}
// Correct index to match the specifications of the MatrixData interface
return mMatrix.getValue(mCurrentY - 1, mCurrentX - 1);
}
}
/**
* Iterator that returns {@link BrailleCell6} objects rather than the dots themselves.
* See {@link MatrixData#getBrailleCell6Iterator()} for details.
*/
class BrailleCell6Iterator implements Iterator<BrailleCell6<T>> {
private final Iterator<T> mElemIter;
BrailleCell6Iterator(final SimpleMatrixDataImpl<T> matrix) {
mElemIter = matrix.getDotIterator(BrailleCell6.COLUMN_COUNT, BrailleCell6.ROW_COUNT);
}
@Override
public boolean hasNext() {
return mElemIter.hasNext();
}
@Override
@SuppressWarnings("unchecked")
public BrailleCell6<T> next() {
T[] vals = (T[]) new Object[BrailleCell6.DOT_COUNT];
for (int i = 0; i < BrailleCell6.DOT_COUNT; i++) {
vals[i] = mElemIter.next();
}
return new BrailleCell6<>(vals);
}
}
}
/**
* This package contains all the requiered classes and interfaces for data exchange between the rasterizer and
* the printer backend.
* @author Georg Graßnick
* @version 2019.06.26
*/
package de.tudresden.inf.mci.brailleplot.printabledata;
0% Loading or .
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment