Match is being initialized with lobbyPlayer (to possibly match several players controlled)

This commit is contained in:
Maxmtg
2013-05-23 18:47:17 +00:00
parent c9a0e4ff3e
commit a4deb25e43
16 changed files with 314 additions and 297 deletions

1
.gitattributes vendored
View File

@@ -14364,6 +14364,7 @@ src/main/java/forge/gui/framework/IDocIdList.java -text
src/main/java/forge/gui/framework/ILocalRepaint.java -text
src/main/java/forge/gui/framework/IVDoc.java -text
src/main/java/forge/gui/framework/IVTopLevelUI.java -text
src/main/java/forge/gui/framework/RectangleOfDouble.java -text
src/main/java/forge/gui/framework/SDisplayUtil.java -text
src/main/java/forge/gui/framework/SLayoutConstants.java -text
src/main/java/forge/gui/framework/SLayoutIO.java -text

View File

@@ -178,11 +178,11 @@ public class MatchController {
public static void attachUiToMatch(MatchController match, LobbyPlayer humanLobbyPlayer) {
FControl.SINGLETON_INSTANCE.setMatch(match);
GameState currentGame = match.getCurrentGame();
currentGame.getEvents().register(Singletons.getControl().getSoundSystem());
GameState game = match.getCurrentGame();
game.getEvents().register(Singletons.getControl().getSoundSystem());
Player localHuman = null;
for(Player p : currentGame.getPlayers()) {
for(Player p : game.getPlayers()) {
if ( p.getLobbyPlayer() != humanLobbyPlayer)
continue;
localHuman = p;
@@ -192,11 +192,11 @@ public class MatchController {
FControl.SINGLETON_INSTANCE.setPlayer(localHuman);
// The UI controls should use these game data as models
CMatchUI.SINGLETON_INSTANCE.initMatch(currentGame.getRegisteredPlayers(), localHuman);
CDock.SINGLETON_INSTANCE.setModel(currentGame, localHuman);
CStack.SINGLETON_INSTANCE.setModel(currentGame.getStack(), localHuman);
CLog.SINGLETON_INSTANCE.setModel(currentGame.getGameLog());
CCombat.SINGLETON_INSTANCE.setModel(currentGame);
CMatchUI.SINGLETON_INSTANCE.initMatch(game.getRegisteredPlayers(), humanLobbyPlayer);
CDock.SINGLETON_INSTANCE.setModel(game, localHuman);
CStack.SINGLETON_INSTANCE.setModel(game.getStack(), localHuman);
CLog.SINGLETON_INSTANCE.setModel(game.getGameLog());
CCombat.SINGLETON_INSTANCE.setModel(game);
CMessage.SINGLETON_INSTANCE.setModel(match);
@@ -204,18 +204,18 @@ public class MatchController {
Singletons.getControl().changeState(FControl.Screens.MATCH_SCREEN);
SDisplayUtil.showTab(EDocID.REPORT_LOG.getDoc());
CMessage.SINGLETON_INSTANCE.getInputControl().setGame(currentGame);
CMessage.SINGLETON_INSTANCE.getInputControl().setGame(game);
// models shall notify controllers of changes
currentGame.getStack().addObserver(CStack.SINGLETON_INSTANCE);
currentGame.getGameLog().addObserver(CLog.SINGLETON_INSTANCE);
game.getStack().addObserver(CStack.SINGLETON_INSTANCE);
game.getGameLog().addObserver(CLog.SINGLETON_INSTANCE);
// some observers were set in CMatchUI.initMatch
// black magic still
VAntes.SINGLETON_INSTANCE.setModel(currentGame.getRegisteredPlayers());
VAntes.SINGLETON_INSTANCE.setModel(game.getRegisteredPlayers());
for (final VField field : VMatchUI.SINGLETON_INSTANCE.getFieldViews()) {
field.getLblLibrary().setHoverable(Preferences.DEV_MODE);

View File

@@ -31,10 +31,7 @@ import forge.view.FView;
@SuppressWarnings("serial")
public final class DragCell extends JPanel implements ILocalRepaint {
// Layout creation worker vars
private double roughX = 0;
private double roughY = 0;
private double roughW = 0;
private double roughH = 0;
private RectangleOfDouble roughSize;
private int smoothX = 0;
private int smoothY = 0;
private int smoothW = 0;
@@ -196,12 +193,13 @@ public final class DragCell extends JPanel implements ILocalRepaint {
/**
* Automatically calculates rough bounds of this cell.
* @param rectangleOfDouble
*/
public void setRoughBounds() {
public void updateRoughBounds() {
final double contentW = FView.SINGLETON_INSTANCE.getPnlContent().getWidth();
final double contentH = FView.SINGLETON_INSTANCE.getPnlContent().getHeight();
setRoughBounds(this.getX() / contentW, this.getY() / contentH,
this.roughSize = new RectangleOfDouble(this.getX() / contentW, this.getY() / contentH,
this.getW() / contentW, this.getH() / contentH);
}
@@ -212,36 +210,16 @@ public final class DragCell extends JPanel implements ILocalRepaint {
* @param w0   double
* @param h0   double
*/
public void setRoughBounds(final double x0, final double y0, final double w0, final double h0) {
if (x0 > 1) { throw new IllegalArgumentException("X value greater than 100%!"); }
if (y0 > 1) { throw new IllegalArgumentException("Y value greater than 100%!"); }
if (w0 > 1) { throw new IllegalArgumentException("W value greater than 100%!"); }
if (h0 > 1) { throw new IllegalArgumentException("H value greater than 100%!"); }
this.roughX = x0;
this.roughY = y0;
this.roughW = w0;
this.roughH = h0;
public void setRoughBounds(RectangleOfDouble rectangleOfDouble) {
this.roughSize = rectangleOfDouble;
}
/** @return double */
public double getRoughX() {
return this.roughX;
}
/** @return double */
public double getRoughY() {
return this.roughY;
}
/** @return double */
public double getRoughW() {
return this.roughW;
}
/** @return double */
public double getRoughH() {
return this.roughH;
/**
* TODO: Write javadoc for this method.
* @return
*/
public RectangleOfDouble getRoughBounds() {
return roughSize;
}
/** Sets bounds in superclass using smoothed values from this class. */

View File

@@ -101,6 +101,10 @@ public enum EDocID { /** */
HAND_1 (null), /** */
HAND_2 (null), /** */
HAND_3 (null), /** */
HAND_4 (null), /** */
HAND_5 (null), /** */
HAND_6 (null), /** */
HAND_7 (null), /** */
COMMAND_0 (null), /** */
COMMAND_1 (null), /** */
@@ -111,6 +115,10 @@ public enum EDocID { /** */
COMMAND_6 (null), /** */
COMMAND_7 (null); /** */
public final static EDocID[] Commands = new EDocID[] {COMMAND_0, COMMAND_1, COMMAND_2, COMMAND_3, COMMAND_4, COMMAND_5, COMMAND_6, COMMAND_7};
public final static EDocID[] Fields = new EDocID[] {FIELD_0, FIELD_1, FIELD_2, FIELD_3, FIELD_4, FIELD_5, FIELD_6, FIELD_7};
public final static EDocID[] Hands = new EDocID[] {HAND_0, HAND_1, HAND_2, HAND_3, HAND_4, HAND_5, HAND_6, HAND_7};
// End enum declarations, start enum methods.
private IVDoc<? extends ICDoc> vDoc;

View File

@@ -0,0 +1,90 @@
package forge.gui.framework;
/**
* Dimensions for a cell, stored as % of available space
*
*/
public class RectangleOfDouble {
private final double x;
private final double y;
private final double w;
private final double h;
public RectangleOfDouble(final double x0, final double y0, final double w0, final double h0) {
if (x0 > 1) { throw new IllegalArgumentException("X value greater than 100%!"); }
x = x0;
if (y0 > 1) { throw new IllegalArgumentException("Y value greater than 100%!"); }
y = y0;
if (w0 > 1) { throw new IllegalArgumentException("W value greater than 100%!"); }
w = w0;
if (h0 > 1) { throw new IllegalArgumentException("H value greater than 100%!"); }
h = h0;
}
@Override
public int hashCode() {
final int prime = 31;
int result = 1;
long temp;
temp = Double.doubleToLongBits(h);
result = prime * result + (int) (temp ^ (temp >>> 32));
temp = Double.doubleToLongBits(w);
result = prime * result + (int) (temp ^ (temp >>> 32));
temp = Double.doubleToLongBits(x);
result = prime * result + (int) (temp ^ (temp >>> 32));
temp = Double.doubleToLongBits(y);
result = prime * result + (int) (temp ^ (temp >>> 32));
return result;
}
@Override
public boolean equals(Object obj) {
if (this == obj)
return true;
if (obj == null)
return false;
if (getClass() != obj.getClass())
return false;
RectangleOfDouble other = (RectangleOfDouble) obj;
if (Double.doubleToLongBits(h) != Double.doubleToLongBits(other.h))
return false;
if (Double.doubleToLongBits(w) != Double.doubleToLongBits(other.w))
return false;
if (Double.doubleToLongBits(x) != Double.doubleToLongBits(other.x))
return false;
if (Double.doubleToLongBits(y) != Double.doubleToLongBits(other.y))
return false;
return true;
}
public final double getX() {
return x;
}
public final double getY() {
return y;
}
public final double getW() {
return w;
}
public final double getH() {
return h;
}
/* (non-Javadoc)
* @see java.lang.Object#toString()
*/
@Override
public String toString() {
return String.format("Rectangle @(%f, %f) sz=(%f, %f)", x,y, w,h);
}
}

View File

@@ -4,10 +4,11 @@ import java.awt.BorderLayout;
import java.io.File;
import java.io.FileInputStream;
import java.io.FileOutputStream;
import java.util.Collection;
import java.util.Iterator;
import java.util.List;
import java.util.Map.Entry;
import javax.swing.JPanel;
import javax.swing.SwingUtilities;
import javax.swing.border.EmptyBorder;
import javax.xml.stream.XMLEventFactory;
@@ -21,8 +22,12 @@ import javax.xml.stream.events.StartElement;
import javax.xml.stream.events.XMLEvent;
import forge.control.FControl;
import forge.control.FControl.Screens;
import forge.properties.FileLocation;
import forge.properties.NewConstants;
import forge.util.maps.CollectionSuppliers;
import forge.util.maps.HashMapOfLists;
import forge.util.maps.MapOfLists;
import forge.view.FView;
@@ -33,15 +38,14 @@ import forge.view.FView;
*/
public final class SLayoutIO {
/** Each cell must save these elements of its display. */
private enum Property {
x,
y,
w,
h,
doc
private static class Property {
public final static String x = "x";
public final static String y = "y";
public final static String w = "w";
public final static String h = "h";
public final static String doc = "doc";
}
private static FileLocation file = null;
private static final XMLEventFactory EF = XMLEventFactory.newInstance();
private static final XMLEvent NEWLINE = EF.createDTD("\n");
private static final XMLEvent TAB = EF.createDTD("\t");
@@ -51,7 +55,7 @@ public final class SLayoutIO {
* @return {@link java.lang.String}
*/
public static String getFilePreferred() {
return null == file ? null : file.userPrefLoc;
return SLayoutIO.getFileForState(FControl.SINGLETON_INSTANCE.getState()).userPrefLoc;
}
/** Publicly-accessible save method, to neatly handle exception handling.
@@ -69,18 +73,9 @@ public final class SLayoutIO {
}
/**
* Publicly-accessible load method, to neatly handle exception handling.
* @param f0 &emsp; {@link java.io.File}
*/
public static void loadLayout(final File f0) {
try { load(f0); }
catch (final Exception e) { e.printStackTrace(); }
}
private synchronized static void save(final File f0) throws Exception {
final String fWriteTo;
SLayoutIO.setFilesForState();
FileLocation file = SLayoutIO.getFileForState(FControl.SINGLETON_INSTANCE.getState());
if (f0 == null) {
if (null == file) {
@@ -95,8 +90,6 @@ public final class SLayoutIO {
final XMLOutputFactory out = XMLOutputFactory.newInstance();
final XMLEventWriter writer = out.createXMLEventWriter(new FileOutputStream(fWriteTo));
final List<DragCell> cells = FView.SINGLETON_INSTANCE.getDragCells();
final JPanel pnl = FView.SINGLETON_INSTANCE.getPnlContent();
double x0, y0, w0, h0;
writer.add(EF.createStartDocument());
writer.add(NEWLINE);
@@ -104,19 +97,15 @@ public final class SLayoutIO {
writer.add(NEWLINE);
for (final DragCell cell : cells) {
x0 = ((double) Math.round(((double) cell.getX() / (double) pnl.getWidth()) * 100000)) / 100000;
y0 = ((double) Math.round(((double) cell.getY() / (double) pnl.getHeight()) * 100000)) / 100000;
w0 = ((double) Math.round(((double) cell.getW() / (double) pnl.getWidth()) * 100000)) / 100000;
h0 = ((double) Math.round(((double) cell.getH() / (double) pnl.getHeight()) * 100000)) / 100000;
//cell.setRoughBounds(x, y, w, h);
cell.updateRoughBounds();
RectangleOfDouble bounds = cell.getRoughBounds();
writer.add(TAB);
writer.add(EF.createStartElement("", "", "cell"));
writer.add(EF.createAttribute(Property.x.toString(), String.valueOf(x0)));
writer.add(EF.createAttribute(Property.y.toString(), String.valueOf(y0)));
writer.add(EF.createAttribute(Property.w.toString(), String.valueOf(w0)));
writer.add(EF.createAttribute(Property.h.toString(), String.valueOf(h0)));
writer.add(EF.createAttribute(Property.x.toString(), String.valueOf(Math.rint(bounds.getX() * 100000) / 100000)));
writer.add(EF.createAttribute(Property.y.toString(), String.valueOf(Math.rint(bounds.getY() * 100000) / 100000)));
writer.add(EF.createAttribute(Property.w.toString(), String.valueOf(Math.rint(bounds.getW() * 100000) / 100000)));
writer.add(EF.createAttribute(Property.h.toString(), String.valueOf(Math.rint(bounds.getH() * 100000) / 100000)));
writer.add(NEWLINE);
for (final IVDoc<? extends ICDoc> vDoc : cell.getDocs()) {
@@ -133,36 +122,65 @@ public final class SLayoutIO {
writer.close();
}
private static void load(final File f) throws Exception {
public static void loadLayout(final File f) {
final FView view = FView.SINGLETON_INSTANCE;
final XMLInputFactory inputFactory = XMLInputFactory.newInstance();
SLayoutIO.setFilesForState();
FileLocation file = SLayoutIO.getFileForState(FControl.SINGLETON_INSTANCE.getState());
view.getPnlInsets().removeAll();
view.getPnlInsets().setLayout(new BorderLayout());
view.getPnlInsets().add(view.getPnlContent(), BorderLayout.CENTER);
view.getPnlInsets().setBorder(new EmptyBorder(
SLayoutConstants.BORDER_T, SLayoutConstants.BORDER_T, 0, 0));
final XMLEventReader reader;
if (f != null && f.exists()) {
reader = inputFactory.createXMLEventReader(new FileInputStream(f));
} else if (null == file) {
reader = null;
} else if (new File(file.userPrefLoc).exists()) {
reader = inputFactory.createXMLEventReader(new FileInputStream(file.userPrefLoc));
} else {
reader = inputFactory.createXMLEventReader(new FileInputStream(file.defaultLoc));
}
view.getPnlInsets().setBorder(new EmptyBorder(SLayoutConstants.BORDER_T, SLayoutConstants.BORDER_T, 0, 0));
view.removeAllDragCells();
// Read a model for new layout
MapOfLists<RectangleOfDouble, EDocID> model = null;
try {
FileInputStream fis = null;
if (f != null && f.exists())
fis = new FileInputStream(f);
else {
File userSetting = new File(file.userPrefLoc);
fis = userSetting.exists() ? new FileInputStream(userSetting) : new FileInputStream(file.defaultLoc);
}
model = readLayout(inputFactory.createXMLEventReader(fis));
} catch (final Exception e) { e.printStackTrace(); }
// Apply new layout
DragCell cell = null;
for(Entry<RectangleOfDouble, Collection<EDocID>> kv : model.entrySet()) {
cell = new DragCell();
cell.setRoughBounds(kv.getKey());
FView.SINGLETON_INSTANCE.addDragCell(cell);
for(EDocID edoc : kv.getValue()) {
try {
// System.out.println(String.format("adding doc %s -> %s", edoc, edoc.getDoc()));
cell.addDoc(edoc.getDoc());
} catch (IllegalArgumentException e) {
System.err.println("Failed to get doc for " + edoc);
}
}
}
// Rough bounds are all in place; resize the window.
SResizingUtil.resizeWindow();
}
private static MapOfLists<RectangleOfDouble, EDocID> readLayout(final XMLEventReader reader)
throws XMLStreamException {
XMLEvent event;
StartElement element;
Iterator<?> attributes;
Attribute attribute;
DragCell cell = null;
double x0 = 0, y0 = 0, w0 = 0, h0 = 0;
MapOfLists<RectangleOfDouble, EDocID> model = new HashMapOfLists<RectangleOfDouble, EDocID>(CollectionSuppliers.<EDocID>arrayLists());
RectangleOfDouble currentKey = null;
while (null != reader && reader.hasNext()) {
event = reader.nextEvent();
@@ -173,72 +191,59 @@ public final class SLayoutIO {
attributes = element.getAttributes();
while (attributes.hasNext()) {
attribute = (Attribute) attributes.next();
if (attribute.getName().toString().equals(Property.x.toString())) {
x0 = Double.valueOf(attribute.getValue());
}
else if (attribute.getName().toString().equals(Property.y.toString())) {
y0 = Double.valueOf(attribute.getValue());
}
else if (attribute.getName().toString().equals(Property.w.toString())) {
w0 = Double.valueOf(attribute.getValue());
}
else if (attribute.getName().toString().equals(Property.h.toString())) {
h0 = Double.valueOf(attribute.getValue());
}
}
double val = Double.parseDouble(attribute.getValue());
String atrName = attribute.getName().toString();
cell = new DragCell();
cell.setRoughBounds(x0, y0, w0, h0);
FView.SINGLETON_INSTANCE.addDragCell(cell);
if (atrName.equals(Property.x)) x0 = val;
else if (atrName.equals(Property.y)) y0 = val;
else if (atrName.equals(Property.w)) w0 = val;
else if (atrName.equals(Property.h)) h0 = val;
}
currentKey = new RectangleOfDouble(x0, y0, w0, h0);
}
else if (element.getName().getLocalPart().equals("doc")) {
else if (element.getName().getLocalPart().equals(Property.doc)) {
event = reader.nextEvent();
try {
cell.addDoc(EDocID.valueOf(event.asCharacters().getData()).getDoc());
} catch (IllegalArgumentException e) { /* ignore; just don't add invalid element */ }
model.add(currentKey, EDocID.valueOf(event.asCharacters().getData()));
}
}
}
// Rough bounds are all in place; resize the window.
SResizingUtil.resizeWindow();
return model;
}
private static void createNode(final XMLEventWriter writer0, final Property name0,
final String val0) throws XMLStreamException {
private static void createNode(final XMLEventWriter writer0, final String propertyName, final String value) throws XMLStreamException {
writer0.add(TAB);
writer0.add(TAB);
writer0.add(EF.createStartElement("", "", name0.toString()));
writer0.add(EF.createCharacters(val0));
writer0.add(EF.createEndElement("", "", name0.toString()));
writer0.add(EF.createStartElement("", "", propertyName));
writer0.add(EF.createCharacters(value));
writer0.add(EF.createEndElement("", "", propertyName));
writer0.add(NEWLINE);
}
/**
* Updates preferred / default layout addresses particular to each UI state.
* Always called before a load or a save, to ensure file addresses are correct.
* @return
*/
private static void setFilesForState() {
switch(FControl.SINGLETON_INSTANCE.getState()) {
private static FileLocation getFileForState(Screens state) {
switch(state) {
case HOME_SCREEN:
file = NewConstants.HOME_LAYOUT_FILE;
break;
return NewConstants.HOME_LAYOUT_FILE;
case MATCH_SCREEN:
file = NewConstants.MATCH_LAYOUT_FILE;
break;
return NewConstants.MATCH_LAYOUT_FILE;
case DECK_EDITOR_CONSTRUCTED:
case DECK_EDITOR_LIMITED:
case DECK_EDITOR_QUEST:
case DRAFTING_PROCESS:
case QUEST_CARD_SHOP:
file = NewConstants.EDITOR_LAYOUT_FILE;
break;
return NewConstants.EDITOR_LAYOUT_FILE;
case QUEST_BAZAAR:
file = null;
break;
return null;
default:
throw new IllegalStateException("Layout load failed; UI state unknown.");
}
}
}

View File

@@ -296,8 +296,8 @@ public final class SRearrangingUtil {
FView.SINGLETON_INSTANCE.removeDragCell(cellSrc);
}
cellNew.setRoughBounds();
cellTarget.setRoughBounds();
cellNew.updateRoughBounds();
cellTarget.updateRoughBounds();
cellSrc.setSelected(srcSelectedDoc);
cellSrc.refresh();
@@ -351,7 +351,7 @@ public final class SRearrangingUtil {
if (foundT && foundB) {
for (final DragCell cell : cellsToResize) {
cell.setBounds(cell.getX(), cell.getY(), cell.getW() + srcW, cell.getH());
cell.setRoughBounds();
cell.updateRoughBounds();
}
return;
}
@@ -377,7 +377,7 @@ public final class SRearrangingUtil {
if (foundT && foundB) {
for (final DragCell cell : cellsToResize) {
cell.setBounds(cellSrc.getX(), cell.getY(), cell.getW() + srcW, cell.getH());
cell.setRoughBounds();
cell.updateRoughBounds();
}
return;
}
@@ -404,7 +404,7 @@ public final class SRearrangingUtil {
for (final DragCell cell : cellsToResize) {
cell.setBounds(cell.getX(), cellSrc.getY(), cell.getW(), cell.getH() + srcH);
cell.setRoughBounds();
cell.updateRoughBounds();
}
return;
}
@@ -431,7 +431,7 @@ public final class SRearrangingUtil {
for (final DragCell cell : cellsToResize) {
cell.setBounds(cell.getX(), cell.getY(), cell.getW(), cell.getH() + srcH);
cell.setRoughBounds();
cell.updateRoughBounds();
}
return;
}

View File

@@ -141,28 +141,31 @@ public final class SResizingUtil {
// 10% = 9.8px -> 10px -> x 3 = 30px
// 30% = 29.4px -> 29px (!)
for (final DragCell cellA : cells) {
roughVal = cellA.getRoughX() * w + cellA.getRoughW() * w;
RectangleOfDouble cellSizeA = cellA.getRoughBounds();
roughVal = cellSizeA.getX() * w + cellSizeA.getW() * w;
smoothVal = (int) Math.round(roughVal);
for (final DragCell cellB : cells) {
if ((cellB.getRoughX() * w + cellB.getRoughW() * w) == roughVal) {
cellB.setSmoothW(smoothVal - (int) Math.round(cellB.getRoughX() * w));
RectangleOfDouble cellSizeB = cellB.getRoughBounds();
if ((cellSizeB.getX() * w + cellSizeB.getW() * w) == roughVal) {
cellB.setSmoothW(smoothVal - (int) Math.round(cellSizeB.getX() * w));
}
}
cellA.setSmoothW(smoothVal - (int) Math.round(cellA.getRoughX() * w));
cellA.setSmoothW(smoothVal - (int) Math.round(cellSizeA.getX() * w));
roughVal = cellA.getRoughY() * h + cellA.getRoughH() * h;
roughVal = cellSizeA.getY() * h + cellSizeA.getH() * h;
smoothVal = (int) Math.round(roughVal);
for (final DragCell cellB : cells) {
if (cellB.getRoughY() * h + cellB.getRoughH() * h == roughVal) {
cellB.setSmoothH(smoothVal - (int) Math.round(cellB.getRoughY() * h));
RectangleOfDouble cellSizeB = cellB.getRoughBounds();
if (cellSizeB.getY() * h + cellSizeB.getH() * h == roughVal) {
cellB.setSmoothH(smoothVal - (int) Math.round(cellSizeB.getY() * h));
}
}
cellA.setSmoothH(smoothVal - (int) Math.round(cellA.getRoughY() * h));
cellA.setSmoothH(smoothVal - (int) Math.round(cellSizeA.getY() * h));
// X and Y coordinate can be rounded as usual.
cellA.setSmoothX((int) Math.round(cellA.getRoughX() * w));
cellA.setSmoothY((int) Math.round(cellA.getRoughY() * h));
cellA.setSmoothX((int) Math.round(cellSizeA.getX() * w));
cellA.setSmoothY((int) Math.round(cellSizeA.getY() * h));
// only add component if not already in container; otherwise the keyboard focus
// jumps around to the most recenly added component

View File

@@ -81,7 +81,7 @@ public enum CMatchUI {
* @param numFieldPanels int
* @param numHandPanels int
*/
public void initMatch(final List<Player> players, Player localPlayer) {
public void initMatch(final List<Player> players, LobbyPlayer localPlayer) {
// TODO fix for use with multiplayer
final String[] indices = Singletons.getModel().getPreferences().getPref(FPref.UI_AVATARS).split(",");
@@ -89,19 +89,19 @@ public enum CMatchUI {
// Instantiate all required field slots (user at 0) <-- that's not guaranteed
final List<VField> fields = new ArrayList<VField>();
final List<VCommand> commands = new ArrayList<VCommand>();
final List<VHand> hands = new ArrayList<VHand>();
// get an arranged list so that the first local player is at index 0
List<Player> sortedPlayers = Lists.newArrayList(players);
int ixLocal = -1;
int ixFirstHuman = -1;
for(int i = 0; i < players.size(); i++) {
if( sortedPlayers.get(i) == localPlayer ) {
ixLocal = i;
if( sortedPlayers.get(i).getLobbyPlayer() == localPlayer ) {
ixFirstHuman = i;
break;
}
}
if( ixLocal > 0 ) {
Player p0 = sortedPlayers.remove(ixLocal);
sortedPlayers.add(0, p0);
if( ixFirstHuman > 0 ) {
sortedPlayers.add(0, sortedPlayers.remove(ixFirstHuman));
}
@@ -109,8 +109,8 @@ public enum CMatchUI {
for (Player p : sortedPlayers) {
// A field must be initialized after it's instantiated, to update player info.
// No player, no init.
VField f = new VField(EDocID.valueOf("FIELD_" + i), p, localPlayer);
VCommand c = new VCommand(EDocID.valueOf("COMMAND_" + i), p);
VField f = new VField(EDocID.Fields[i], p, localPlayer);
VCommand c = new VCommand(EDocID.Commands[i], p);
fields.add(f);
commands.add(c);
@@ -118,22 +118,20 @@ public enum CMatchUI {
setAvatar(f, getPlayerAvatar(p, Integer.parseInt(indices[i > 2 ? 1 : 0])));
f.getLayoutControl().initialize();
c.getLayoutControl().initialize();
if (p.getLobbyPlayer() == localPlayer) {
VHand newHand = new VHand(EDocID.Hands[i], p);
newHand.getLayoutControl().initialize();
hands.add(newHand);
}
i++;
}
// Instantiate all required hand slots (user at 0)
final List<VHand> hands = new ArrayList<VHand>();
VHand newHand = new VHand(EDocID.HAND_0, localPlayer);
newHand.getLayoutControl().initialize();
hands.add(newHand);
// Max: 2+ hands are needed at 2HG (but this is quite far from now) - yet it's nice to have this possibility
// for (int i = 0; i < numHandPanels; i++) {
// switch (i) {
// hands.add(i, new VHand(EDocID.valueOf("HAND_" + i), null));
// }
// }
if(hands.isEmpty()) { // add empty hand for matches without human
VHand newHand = new VHand(EDocID.Hands[0], null);
newHand.getLayoutControl().initialize();
hands.add(newHand);
}
// Replace old instances
VMatchUI.SINGLETON_INSTANCE.setCommandViews(commands);

View File

@@ -40,23 +40,10 @@ public enum VMatchUI implements IVTopLevelUI {
private final CMatchUI control = null;
private VMatchUI() {
// Create empty docs for all field slots
for (int i = 0; i < 8; i++) {
EDocID.valueOf("FIELD_" + i).setDoc(
new VEmptyDoc(EDocID.valueOf("FIELD_" + i)));
}
// Create empty docs for all field slots
for (int i = 0; i < 8; i++) {
EDocID.valueOf("COMMAND_" + i).setDoc(
new VEmptyDoc(EDocID.valueOf("COMMAND_" + i)));
}
// Create empty docs for all hand slots
for (int i = 0; i < 4; i++) {
EDocID.valueOf("HAND_" + i).setDoc(
new VEmptyDoc(EDocID.valueOf("HAND_" + i)));
}
// Create empty docs for all slots
for (int i = 0; i < 8; i++) EDocID.Fields[i].setDoc(new VEmptyDoc(EDocID.Fields[i]));
for (int i = 0; i < 8; i++) EDocID.Commands[i].setDoc(new VEmptyDoc(EDocID.Commands[i]));
for (int i = 0; i < 8; i++) EDocID.Hands[i].setDoc(new VEmptyDoc(EDocID.Hands[i]));
}
/** */
@@ -108,7 +95,7 @@ public enum VMatchUI implements IVTopLevelUI {
}
// Add extra hands to existing hand panel.
for (int i = 0; i < lstHands.size(); i++) {
for (int i = 1; i < lstHands.size(); i++) {
// If already in layout, no need to add again.
if (lstHands.get(i).getParentCell() == null) { // if i == 0, we get NPE in two lines
DragCell cellWithHand = lstHands.get(0).getParentCell();

View File

@@ -27,10 +27,9 @@ import java.util.Map.Entry;
import java.util.TreeMap;
import javax.swing.JOptionPane;
import javax.swing.SwingWorker;
import forge.Card;
import forge.CardLists;
import forge.FThreads;
import forge.CardPredicates.Presets;
import forge.Command;
import forge.deck.Deck;
@@ -94,54 +93,44 @@ public enum CDock implements ICDoc {
SOverlayUtils.genericOverlay();
FView.SINGLETON_INSTANCE.getPnlContent().removeAll();
final SwingWorker<Void, Void> w = new SwingWorker<Void, Void>() {
@Override
public Void doInBackground() {
FThreads.invokeInEdtLater(new Runnable(){
@Override public void run() {
SLayoutIO.loadLayout(null);
SOverlayUtils.hideOverlay();
return null;
}
};
w.execute();
});
}
private void saveLayout() {
final SwingWorker<Void, Void> w = new SwingWorker<Void, Void>() {
@Override
public Void doInBackground() {
final SaveOpenDialog dlgSave = new SaveOpenDialog();
final File defFile = new File(SLayoutIO.getFilePreferred());
final File saveFile = dlgSave.SaveDialog(defFile, Filetypes.LAYOUT);
if (saveFile != null) {
SLayoutIO.saveLayout(saveFile);
}
return null;
}
};
w.execute();
final SaveOpenDialog dlgSave = new SaveOpenDialog();
final File defFile = new File(SLayoutIO.getFilePreferred());
final File saveFile = dlgSave.SaveDialog(defFile, Filetypes.LAYOUT);
if (saveFile != null) {
SLayoutIO.saveLayout(saveFile);
}
}
private void openLayout() {
SOverlayUtils.genericOverlay();
final SaveOpenDialog dlgOpen = new SaveOpenDialog();
final File defFile = new File(SLayoutIO.getFilePreferred());
final File loadFile = dlgOpen.OpenDialog(defFile, Filetypes.LAYOUT);
FView.SINGLETON_INSTANCE.getPnlContent().removeAll();
// let it redraw everything first
final SwingWorker<Void, Void> w = new SwingWorker<Void, Void>() {
FThreads.invokeInEdtLater(new Runnable() {
@Override
public Void doInBackground() {
final SaveOpenDialog dlgOpen = new SaveOpenDialog();
final File defFile = new File(SLayoutIO.getFilePreferred());
final File loadFile = dlgOpen.OpenDialog(defFile, Filetypes.LAYOUT);
public void run() {
if (loadFile != null) {
SLayoutIO.loadLayout(loadFile);
SLayoutIO.saveLayout(null);
}
SOverlayUtils.hideOverlay();
return null;
}
};
w.execute();
});
}
/**

View File

@@ -46,6 +46,7 @@ public enum CMessage implements ICDoc, Observer {
private InputProxy inputControl = new InputProxy();
private Component lastFocusedButton = null;
private VMessage view = VMessage.SINGLETON_INSTANCE;
private final ActionListener actCancel = new ActionListener() {
@Override
@@ -63,7 +64,7 @@ public enum CMessage implements ICDoc, Observer {
private final FocusListener onFocus = new FocusAdapter() {
@Override
public void focusGained(FocusEvent e) {
if (null != VMessage.SINGLETON_INSTANCE.getParentCell() && VMessage.SINGLETON_INSTANCE == VMessage.SINGLETON_INSTANCE.getParentCell().getSelected()) {
if (null != view.getParentCell() && view == view.getParentCell().getSelected()) {
// only record focus changes when we're showing -- otherwise it is due to a tab visibility change
lastFocusedButton = e.getComponent();
}
@@ -81,8 +82,8 @@ public enum CMessage implements ICDoc, Observer {
@Override
public void initialize() {
_initButton(VMessage.SINGLETON_INSTANCE.getBtnCancel(), actCancel);
_initButton(VMessage.SINGLETON_INSTANCE.getBtnOK(), actOK);
_initButton(view.getBtnCancel(), actCancel);
_initButton(view.getBtnOK(), actOK);
}
/**
@@ -96,12 +97,12 @@ public enum CMessage implements ICDoc, Observer {
/** @param s0 &emsp; {@link java.lang.String} */
public void setMessage(String s0) {
VMessage.SINGLETON_INSTANCE.getTarMessage().setText(s0);
view.getTarMessage().setText(s0);
}
/** Flashes animation on input panel if play is currently waiting on input. */
public void remind() {
SDisplayUtil.remind(VMessage.SINGLETON_INSTANCE);
SDisplayUtil.remind(view);
}
/* (non-Javadoc)
@@ -117,7 +118,7 @@ public enum CMessage implements ICDoc, Observer {
*/
@Override
public void update(Observable o, Object arg) {
VMessage.SINGLETON_INSTANCE.getLblGames().setText(
view.getLblGames().setText(
match.getGameType().toString() + ": Game #"
+ (match.getPlayedGames().size() + 1)
+ " of " + match.getGamesPerMatch()

View File

@@ -38,6 +38,7 @@ import forge.control.input.Input;
import forge.control.input.InputPayManaBase;
import forge.game.GameState;
import forge.game.player.HumanPlay;
import forge.game.player.LobbyPlayer;
import forge.game.player.Player;
import forge.game.zone.ZoneType;
import forge.gui.ForgeAction.MatchConstants;
@@ -53,7 +54,7 @@ public class CField implements ICDoc {
// The one who owns cards on this side of table
private final Player player;
// Tho one who looks at screen and 'performs actions'
private final Player playerViewer;
private final LobbyPlayer viewer;
private final VField view;
private boolean initializedAlready = false;
@@ -127,9 +128,9 @@ public class CField implements ICDoc {
* @param playerViewer
*/
@SuppressWarnings("serial")
public CField(final Player p0, final VField v0, Player playerViewer) {
public CField(final Player p0, final VField v0, LobbyPlayer playerViewer) {
this.player = p0;
this.playerViewer = playerViewer;
this.viewer = playerViewer;
this.view = v0;
handAction = new ZoneAction(player.getZone(ZoneType.Hand), MatchConstants.HUMANHAND);
@@ -144,16 +145,18 @@ public class CField implements ICDoc {
@Override
protected void doAction(final Card c) {
// activate opponents cards only via your own flashback button
if (player != CField.this.playerViewer) {
// activate cards only via your own flashback button
if (player.getLobbyPlayer() != CField.this.viewer) {
return;
}
final GameState game = player.getGame();
// TODO: "can play" check needed!
// should I check for who owns these cards? Are there any abilities to be played from opponent's graveyard?
final SpellAbility ab = CField.this.playerViewer.getController().getAbilityToPlay(game.getAbilitesOfCard(c, CField.this.playerViewer));
final SpellAbility ab = player.getController().getAbilityToPlay(game.getAbilitesOfCard(c, player));
if ( null != ab) {
FThreads.invokeInNewThread(new Runnable(){ @Override public void run(){
HumanPlay.playSpellAbility(CField.this.playerViewer, c, ab);
HumanPlay.playSpellAbility(player, c, ab);
}});
}
}
@@ -161,7 +164,7 @@ public class CField implements ICDoc {
}
private void handClicked() {
if ( player == playerViewer || Preferences.DEV_MODE || player.hasKeyword("Play with your hand revealed.")) {
if ( player.getLobbyPlayer() == viewer || Preferences.DEV_MODE || player.hasKeyword("Play with your hand revealed.")) {
handAction.actionPerformed(null);
}
}
@@ -199,7 +202,7 @@ public class CField implements ICDoc {
/** */
private void manaAction(byte colorCode) {
if (CField.this.player == CField.this.playerViewer) {
if (CField.this.player.getLobbyPlayer() == CField.this.viewer) {
final Input in = CField.this.player.getGame().getInputQueue().getInput();
if (in instanceof InputPayManaBase) {
// Do something

View File

@@ -34,7 +34,6 @@ import forge.Card;
import forge.Command;
import forge.Singletons;
import forge.game.player.Player;
import forge.game.zone.PlayerZone;
import forge.game.zone.ZoneType;
import forge.gui.framework.ICDoc;
import forge.gui.match.CMatchUI;
@@ -47,7 +46,7 @@ import forge.view.arcane.util.Animation;
* Controls Swing components of a player's hand instance.
*
*/
public class CHand implements ICDoc {
public class CHand implements ICDoc, Observer {
private final Player player;
private final VHand view;
private boolean initializedAlready = false;
@@ -58,9 +57,6 @@ public class CHand implements ICDoc {
public void mousePressed(final MouseEvent e) {
cardclickAction(e); } };
private final Observer o1 = new Observer() { @Override
public void update(final Observable a, final Object b) {
observerAction(a); } };
/**
* Controls Swing components of a player's hand instance.
@@ -78,8 +74,8 @@ public class CHand implements ICDoc {
if (initializedAlready) { return; }
initializedAlready = true;
if ( player != null)
player.getZone(ZoneType.Hand).addObserver(o1);
if (player != null)
player.getZone(ZoneType.Hand).addObserver(this);
view.getHandArea().addMouseListener(madCardClick);
}
@@ -136,48 +132,6 @@ public class CHand implements ICDoc {
//this.view.refreshLayout();
}
/**
* Gets the cards.
*
* @return List<Card>
*/
public List<Card> getCards() {
return this.cardsInPanel;
}
/**
* Removes the card.
*
* @param c
* &emsp; Card object
*/
public void removeCard(final Card c) {
this.cardsInPanel.remove(c);
//this.view.refreshLayout();
}
/**
* Removes the cards.
*
* @param c
* &emsp; List of Card objects
*/
public void removeCards(final List<Card> c) {
this.cardsInPanel.removeAll(c);
//this.view.refreshLayout();
}
/**
* Reset cards.
*
* @param c
* &emsp; List of Card objects
*/
public void resetCards(final List<Card> c) {
this.cardsInPanel.clear();
this.addCards(c);
}
private void cardclickAction(final MouseEvent e) {
if (e.getButton() != MouseEvent.BUTTON1) {
return;
@@ -188,13 +142,12 @@ public class CHand implements ICDoc {
}
}
private void observerAction(final Observable a) {
final PlayerZone pZone = (PlayerZone) a;
public void update(final Observable a, final Object b) {
final HandArea p = view.getHandArea();
final Rectangle rctLibraryLabel = CMatchUI.SINGLETON_INSTANCE
.getFieldControls().get(0)
.getView().getLblLibrary().getBounds();
final List<Card> c = pZone.getCards();
final List<Card> c = player.getZone(ZoneType.Hand).getCards();
// Animation starts from the library label and runs to the hand panel.
// This check prevents animation running if label hasn't been realized yet.

View File

@@ -42,6 +42,7 @@ import forge.card.MagicColor;
import forge.card.cardfactory.CardFactoryUtil;
import forge.card.mana.ManaPool;
import forge.game.phase.PhaseType;
import forge.game.player.LobbyPlayer;
import forge.game.player.Player;
import forge.game.zone.ZoneType;
import forge.gui.framework.DragCell;
@@ -117,7 +118,7 @@ public class VField implements IVDoc<CField> {
* @param playerOnwer &emsp; {@link forge.game.player.Player}
* @param id0 &emsp; {@link forge.gui.framework.EDocID}
*/
public VField(final EDocID id0, final Player playerOnwer, Player playerViewer) {
public VField(final EDocID id0, final Player playerOnwer, LobbyPlayer playerViewer) {
this.docID = id0;
id0.setDoc(this);

View File

@@ -50,16 +50,16 @@ public class VHand implements IVDoc<CHand> {
* Assembles Swing components of a player hand instance.
*
* @param id0 &emsp; {@link forge.gui.framework.EDocID}
* @param player0 &emsp; {@link forge.game.player.Player}
* @param owner &emsp; {@link forge.game.player.Player}
*/
public VHand(final EDocID id0, final Player player0) {
public VHand(final EDocID id0, final Player owner) {
docID = id0;
id0.setDoc(this);
if (player0 == null) {
if (owner == null) {
tab.setText("NO PLAYER Hand");
} else {
tab.setText(player0.getName() + " Hand");
tab.setText(owner.getName() + " Hand");
}
scroller.setBorder(null);
@@ -69,7 +69,7 @@ public class VHand implements IVDoc<CHand> {
hand.setOpaque(false);
control = new CHand(player0, this);
control = new CHand(owner, this);
}
//========= Overridden methods