2011-04-30 13:44:17 +02:00
|
|
|
package jrummikub.model;
|
|
|
|
|
2011-04-30 18:21:22 +02:00
|
|
|
import java.util.ArrayList;
|
|
|
|
import java.util.Collections;
|
2011-05-01 01:05:56 +02:00
|
|
|
import java.util.HashSet;
|
2011-04-30 18:21:22 +02:00
|
|
|
import java.util.Iterator;
|
2011-04-30 17:20:14 +02:00
|
|
|
import java.util.List;
|
2011-05-01 01:05:56 +02:00
|
|
|
import java.util.Set;
|
2011-04-30 17:20:14 +02:00
|
|
|
|
2011-04-30 18:21:22 +02:00
|
|
|
import sun.reflect.generics.reflectiveObjects.NotImplementedException;
|
|
|
|
|
2011-04-30 15:45:11 +02:00
|
|
|
import jrummikub.util.Pair;
|
|
|
|
|
2011-04-30 14:47:42 +02:00
|
|
|
/** Class managing {@link Stone}s joined together to form sets */
|
2011-05-01 01:32:19 +02:00
|
|
|
public class StoneSet implements Iterable<Stone>, Sizeable {
|
|
|
|
float border = 0.125f;
|
2011-04-30 15:45:11 +02:00
|
|
|
private List<Stone> stones;
|
2011-04-30 13:44:17 +02:00
|
|
|
|
2011-04-30 17:20:14 +02:00
|
|
|
public StoneSet(Stone stone) {
|
2011-05-01 01:05:56 +02:00
|
|
|
stones = Collections.singletonList(stone);
|
2011-04-30 17:20:14 +02:00
|
|
|
}
|
|
|
|
|
|
|
|
public StoneSet(List<Stone> stones) {
|
2011-05-01 01:05:56 +02:00
|
|
|
this.stones = new ArrayList<Stone>(stones);
|
2011-04-30 17:20:14 +02:00
|
|
|
}
|
|
|
|
|
2011-04-30 14:47:42 +02:00
|
|
|
/** Test for rule conflict within the StoneSet */
|
2011-04-30 13:44:17 +02:00
|
|
|
public boolean isValid() {
|
2011-05-01 01:05:56 +02:00
|
|
|
if (stones.size() < 3) {
|
|
|
|
return false;
|
|
|
|
}
|
|
|
|
int nonJoker1 = -1, nonJoker2 = -1;
|
|
|
|
for (int i = 0; i < stones.size(); i++) {
|
|
|
|
if (stones.get(i).isJoker()) {
|
|
|
|
continue;
|
|
|
|
}
|
|
|
|
nonJoker2 = nonJoker1;
|
|
|
|
nonJoker1 = i;
|
|
|
|
}
|
|
|
|
if (nonJoker2 == -1) {
|
|
|
|
return true;
|
|
|
|
}
|
|
|
|
// is run
|
|
|
|
if (stones.get(nonJoker1).getColor() == stones.get(nonJoker2)
|
|
|
|
.getColor()) {
|
|
|
|
StoneColor runColor = stones.get(nonJoker1).getColor();
|
|
|
|
int startValue = stones.get(nonJoker1).getValue() - nonJoker1;
|
|
|
|
int endValue = startValue + stones.size() - 1;
|
|
|
|
if (startValue < 1 || endValue > 13) {
|
|
|
|
return false;
|
|
|
|
}
|
|
|
|
for (int i = 0; i < stones.size(); i++) {
|
|
|
|
if (stones.get(i).isJoker()) {
|
|
|
|
continue;
|
|
|
|
}
|
|
|
|
if (stones.get(i).getColor() != runColor) {
|
|
|
|
// warum macht er das nicht?
|
|
|
|
return false;
|
|
|
|
}
|
|
|
|
if (stones.get(i).getValue() != i + startValue) {
|
|
|
|
return false;
|
|
|
|
}
|
|
|
|
}
|
|
|
|
return true;
|
2011-04-30 13:44:17 +02:00
|
|
|
|
2011-05-01 01:05:56 +02:00
|
|
|
}
|
|
|
|
// is group
|
|
|
|
else {
|
|
|
|
if (stones.size() > 4) {
|
|
|
|
return false;
|
|
|
|
}
|
|
|
|
Set<StoneColor> seenColors = new HashSet<StoneColor>();
|
|
|
|
for (Stone i : stones) {
|
|
|
|
if (i.isJoker()) {
|
|
|
|
continue;
|
|
|
|
}
|
|
|
|
if (seenColors.contains(i.getColor())) {
|
|
|
|
return false;
|
|
|
|
} else {
|
|
|
|
seenColors.add(i.getColor());
|
|
|
|
}
|
|
|
|
}
|
|
|
|
return true;
|
|
|
|
}
|
2011-04-30 13:44:17 +02:00
|
|
|
}
|
|
|
|
|
2011-04-30 14:47:42 +02:00
|
|
|
/**
|
|
|
|
* Splits the StoneSet at a specified {@link Position} and returns two new
|
|
|
|
* Stone Sets
|
|
|
|
*
|
|
|
|
* @param position
|
|
|
|
* Splitting {@link Position}
|
|
|
|
*/
|
2011-04-30 15:45:11 +02:00
|
|
|
public Pair<StoneSet, StoneSet> splitAt(int position) {
|
2011-05-01 01:23:15 +02:00
|
|
|
// Exception in case of wrong index
|
2011-05-01 01:05:56 +02:00
|
|
|
if (position == 0 || position == stones.size()) {
|
2011-05-01 01:23:15 +02:00
|
|
|
throw new IndexOutOfBoundsException();
|
2011-04-30 17:20:14 +02:00
|
|
|
}
|
2011-05-01 01:23:15 +02:00
|
|
|
StoneSet firstSet = new StoneSet(stones.subList(0, position));
|
|
|
|
StoneSet secondSet = new StoneSet(stones.subList(position,
|
|
|
|
stones.size()));
|
|
|
|
return new Pair<StoneSet, StoneSet>(firstSet, secondSet);
|
2011-04-30 13:44:17 +02:00
|
|
|
}
|
|
|
|
|
2011-04-30 14:47:42 +02:00
|
|
|
/**
|
|
|
|
* Joins StoneSet to another StoneSet and returns the resulting new StoneSet
|
|
|
|
*
|
|
|
|
* @param other
|
|
|
|
* StoneSet to be joined to active StoneSet
|
|
|
|
*/
|
2011-04-30 13:44:17 +02:00
|
|
|
public StoneSet join(StoneSet other) {
|
2011-05-01 01:23:15 +02:00
|
|
|
List<Stone> joinedList = new ArrayList<Stone>();
|
|
|
|
joinedList.addAll(stones);
|
|
|
|
joinedList.addAll(other.stones);
|
|
|
|
return new StoneSet(joinedList);
|
2011-04-30 17:20:14 +02:00
|
|
|
}
|
|
|
|
|
|
|
|
public int size() {
|
|
|
|
return stones.size();
|
|
|
|
}
|
2011-04-30 13:44:17 +02:00
|
|
|
|
2011-04-30 17:20:14 +02:00
|
|
|
public Stone get(int i) {
|
|
|
|
return stones.get(i);
|
2011-04-30 13:44:17 +02:00
|
|
|
}
|
|
|
|
|
2011-05-01 01:05:56 +02:00
|
|
|
@Override
|
|
|
|
public Iterator<Stone> iterator() {
|
|
|
|
final Iterator<Stone> it = stones.iterator();
|
|
|
|
|
|
|
|
return new Iterator<Stone>() {
|
|
|
|
|
|
|
|
@Override
|
|
|
|
public boolean hasNext() {
|
|
|
|
return it.hasNext();
|
|
|
|
}
|
|
|
|
|
|
|
|
@Override
|
|
|
|
public Stone next() {
|
|
|
|
return it.next();
|
|
|
|
}
|
|
|
|
|
|
|
|
@Override
|
|
|
|
public void remove() {
|
|
|
|
// removing stones is impossible
|
|
|
|
|
|
|
|
throw new NotImplementedException();
|
|
|
|
}
|
|
|
|
};
|
|
|
|
}
|
2011-04-30 18:21:22 +02:00
|
|
|
|
2011-05-01 01:32:19 +02:00
|
|
|
@Override
|
|
|
|
public float getWidth() {
|
|
|
|
return stones.size() + 2 * border;
|
|
|
|
}
|
|
|
|
|
|
|
|
@Override
|
|
|
|
public float getHeight() {
|
|
|
|
return 1;
|
|
|
|
}
|
|
|
|
|
2011-04-30 13:44:17 +02:00
|
|
|
}
|