Left: Implement composite structures
This commit is contained in:
Executable
+41
@@ -0,0 +1,41 @@
|
||||
package view;
|
||||
|
||||
public enum EventName {
|
||||
CHOOSE_SHAPE{
|
||||
@Override
|
||||
public String toString() {
|
||||
return "CHOOSE SHAPE";
|
||||
}
|
||||
},
|
||||
CHOOSE_PRIMARY_COLOR {
|
||||
@Override
|
||||
public String toString() {
|
||||
return "CHOOSE PRIMARY COLOR";
|
||||
}
|
||||
},
|
||||
CHOOSE_SECONDARY_COLOR {
|
||||
@Override
|
||||
public String toString() {
|
||||
return "CHOOSE SECONDARY COLOR";
|
||||
}
|
||||
},
|
||||
CHOOSE_SHADING_TYPE {
|
||||
@Override
|
||||
public String toString() {
|
||||
return "CHOOSE SHADING TYPE";
|
||||
}
|
||||
},
|
||||
CHOOSE_MOUSE_MODE {
|
||||
@Override
|
||||
public String toString() {
|
||||
return "CHOOSE MOUSE MODE";
|
||||
}
|
||||
},
|
||||
UNDO,
|
||||
REDO,
|
||||
COPY,
|
||||
PASTE,
|
||||
DELETE,
|
||||
GROUP,
|
||||
UNGROUP
|
||||
}
|
||||
@@ -0,0 +1,62 @@
|
||||
package view.gui;
|
||||
|
||||
import java.awt.BasicStroke;
|
||||
import java.awt.Color;
|
||||
import java.awt.Graphics2D;
|
||||
import java.awt.Stroke;
|
||||
import java.util.EnumMap;
|
||||
|
||||
import model.AbstractShape;
|
||||
import model.ShapeColor;
|
||||
import model.ShapeShadingType;
|
||||
import view.interfaces.IDrawShape;
|
||||
import view.interfaces.PaintCanvasBase;
|
||||
|
||||
/**
|
||||
* DrawEllipse class
|
||||
*
|
||||
* Responsibility: Contains strategy for drawing an ellipse.
|
||||
*
|
||||
* @author Minh Bui
|
||||
*/
|
||||
|
||||
public class DrawEllipse implements IDrawShape {
|
||||
|
||||
@Override
|
||||
public void draw(AbstractShape shape, PaintCanvasBase canvas, EnumMap<ShapeColor, Color> colorMap,
|
||||
Stroke selectStroke, boolean offset) {
|
||||
Graphics2D graphics2d = canvas.getGraphics2D();
|
||||
|
||||
graphics2d.setColor(colorMap.get(shape.getPrimaryColor()));
|
||||
|
||||
Stroke customStroke = new BasicStroke(5f);
|
||||
|
||||
int width = Math.abs(shape.getEndX() - shape.getStartX());
|
||||
int height = Math.abs(shape.getEndY() - shape.getStartY());
|
||||
|
||||
int x = Math.min(shape.getStartX(), shape.getEndX());
|
||||
int y = Math.min(shape.getStartY(), shape.getEndY());
|
||||
|
||||
if (offset) {
|
||||
x = x - SELECT_STROKE_OFFSET;
|
||||
y = y - SELECT_STROKE_OFFSET;
|
||||
width = width + SELECT_WIDTH_HEIGHT_OFFSET;
|
||||
height = height + SELECT_WIDTH_HEIGHT_OFFSET;
|
||||
graphics2d.setStroke(selectStroke);
|
||||
} else {
|
||||
graphics2d.setStroke(customStroke);
|
||||
}
|
||||
|
||||
if (shape.getShadingType() == ShapeShadingType.FILLED_IN) {
|
||||
graphics2d.fillOval(x, y, width, height);
|
||||
} else if (shape.getShadingType() == ShapeShadingType.OUTLINE) {
|
||||
graphics2d.drawOval(x, y, width, height);
|
||||
} else {
|
||||
graphics2d.fillOval(x, y, width, height);
|
||||
graphics2d.setColor(colorMap.get(shape.getSecondaryColor()));
|
||||
graphics2d.drawOval(x, y, width, height);
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
@@ -0,0 +1,61 @@
|
||||
package view.gui;
|
||||
|
||||
import java.awt.BasicStroke;
|
||||
import java.awt.Color;
|
||||
import java.awt.Graphics2D;
|
||||
import java.awt.Stroke;
|
||||
import java.util.EnumMap;
|
||||
|
||||
import model.AbstractShape;
|
||||
import model.ShapeColor;
|
||||
import model.ShapeShadingType;
|
||||
import view.interfaces.IDrawShape;
|
||||
import view.interfaces.PaintCanvasBase;
|
||||
|
||||
/**
|
||||
* DrawRectangle class
|
||||
*
|
||||
* Responsibility: Contains strategy for drawing rectangle.
|
||||
*
|
||||
* @author Minh Bui
|
||||
*/
|
||||
|
||||
public class DrawRectangle implements IDrawShape {
|
||||
|
||||
@Override
|
||||
public void draw(AbstractShape shape, PaintCanvasBase canvas, EnumMap<ShapeColor, Color> colorMap,
|
||||
Stroke selectStroke, boolean offset) {
|
||||
Graphics2D graphics2d = canvas.getGraphics2D();
|
||||
|
||||
int width = Math.abs(shape.getEndX() - shape.getStartX());
|
||||
int height = Math.abs(shape.getEndY() - shape.getStartY());
|
||||
|
||||
int x = Math.min(shape.getStartX(), shape.getEndX());
|
||||
int y = Math.min(shape.getStartY(), shape.getEndY());
|
||||
|
||||
Stroke customStroke = new BasicStroke(5f);
|
||||
|
||||
if (offset) {
|
||||
x = x - SELECT_STROKE_OFFSET;
|
||||
y = y - SELECT_STROKE_OFFSET;
|
||||
width = width + SELECT_WIDTH_HEIGHT_OFFSET;
|
||||
height = height + SELECT_WIDTH_HEIGHT_OFFSET;
|
||||
graphics2d.setStroke(selectStroke);
|
||||
} else {
|
||||
graphics2d.setStroke(customStroke);
|
||||
}
|
||||
|
||||
graphics2d.setColor(colorMap.get(shape.getPrimaryColor()));
|
||||
|
||||
if (shape.getShadingType() == ShapeShadingType.FILLED_IN) {
|
||||
graphics2d.fillRect(x, y, width, height);
|
||||
} else if (shape.getShadingType() == ShapeShadingType.OUTLINE) {
|
||||
graphics2d.drawRect(x, y, width, height);
|
||||
} else {
|
||||
graphics2d.fillRect(x, y, width, height);
|
||||
graphics2d.setColor(colorMap.get(shape.getSecondaryColor()));
|
||||
graphics2d.drawRect(x, y, width, height);
|
||||
}
|
||||
}
|
||||
|
||||
}
|
||||
@@ -0,0 +1,72 @@
|
||||
package view.gui;
|
||||
|
||||
import java.awt.BasicStroke;
|
||||
import java.awt.Color;
|
||||
import java.awt.Graphics2D;
|
||||
import java.awt.Polygon;
|
||||
import java.awt.Stroke;
|
||||
import java.util.EnumMap;
|
||||
|
||||
import model.AbstractShape;
|
||||
import model.Shape;
|
||||
import model.ShapeColor;
|
||||
import model.ShapeShadingType;
|
||||
import view.interfaces.IDrawShape;
|
||||
import view.interfaces.PaintCanvasBase;
|
||||
|
||||
/**
|
||||
* DrawTriangle class
|
||||
*
|
||||
* Responsibility: Contains strategy for drawing a triangle.
|
||||
**
|
||||
* @author Minh Bui
|
||||
*/
|
||||
|
||||
public class DrawTriangle implements IDrawShape {
|
||||
|
||||
@Override
|
||||
public void draw(AbstractShape shape, PaintCanvasBase canvas, EnumMap<ShapeColor, Color> colorMap,
|
||||
Stroke selectStroke, boolean offset) {
|
||||
Graphics2D graphics2d = canvas.getGraphics2D();
|
||||
graphics2d.setColor(colorMap.get(shape.getPrimaryColor()));
|
||||
Stroke customStroke = new BasicStroke(5f);
|
||||
|
||||
//int width = Math.abs(shape.getEndX() - shape.getStartX());
|
||||
int height = Math.abs(shape.getEndY() - shape.getStartY());
|
||||
|
||||
int x = Math.min(shape.getStartX(), shape.getEndX());
|
||||
int y = Math.min(shape.getStartY(), shape.getEndY());
|
||||
|
||||
int xMax = Math.max(shape.getStartX(), shape.getEndX());
|
||||
int yMax = Math.max(shape.getStartY(), shape.getEndY());
|
||||
|
||||
int[] xPoints = new int[3];
|
||||
int[] yPoints = new int[3];
|
||||
|
||||
if (!offset) {
|
||||
xPoints[0] = x; xPoints[1] = xMax; xPoints[2] = x;
|
||||
yPoints[0] = y; yPoints[1] = yMax; yPoints[2] = y + height;
|
||||
graphics2d.setStroke(customStroke);
|
||||
} else {
|
||||
xPoints[0] = x - SELECT_STROKE_OFFSET;
|
||||
xPoints[1] = xMax + SELECT_STROKE_OFFSET * 2;
|
||||
xPoints[2] = x - SELECT_STROKE_OFFSET;
|
||||
|
||||
yPoints[0] = y - SELECT_STROKE_OFFSET * 2;
|
||||
yPoints[1] = yMax + SELECT_STROKE_OFFSET;
|
||||
yPoints[2] = y - SELECT_STROKE_OFFSET + height + SELECT_WIDTH_HEIGHT_OFFSET;
|
||||
graphics2d.setStroke(selectStroke);
|
||||
}
|
||||
|
||||
Polygon triangle = new Polygon(xPoints, yPoints, 3);
|
||||
if (shape.getShadingType() == ShapeShadingType.FILLED_IN) {
|
||||
graphics2d.fillPolygon(triangle);
|
||||
} else if (shape.getShadingType() == ShapeShadingType.OUTLINE) {
|
||||
graphics2d.drawPolygon(triangle);
|
||||
} else {
|
||||
graphics2d.fillPolygon(triangle);
|
||||
graphics2d.setColor(colorMap.get(shape.getSecondaryColor()));
|
||||
graphics2d.drawPolygon(triangle);
|
||||
}
|
||||
}
|
||||
}
|
||||
Executable
+129
@@ -0,0 +1,129 @@
|
||||
package view.gui;
|
||||
|
||||
import java.awt.BasicStroke;
|
||||
import java.awt.Color;
|
||||
import java.awt.Graphics2D;
|
||||
import java.awt.Stroke;
|
||||
import java.util.EnumMap;
|
||||
import java.util.Iterator;
|
||||
import java.util.List;
|
||||
|
||||
import model.*;
|
||||
import model.interfaces.IShapeListObserver;
|
||||
import view.interfaces.IDrawShape;
|
||||
import view.interfaces.PaintCanvasBase;
|
||||
|
||||
/**
|
||||
* Drawer class
|
||||
*
|
||||
* Responsibility: Responsible for selecting specific algorithm to draw shapes and their
|
||||
* corresponding boundaries from a ShapeList object.
|
||||
*
|
||||
* @author Minh Bui
|
||||
*/
|
||||
|
||||
public class Drawer implements IShapeListObserver {
|
||||
|
||||
private static Drawer uniqueInstance;
|
||||
|
||||
private PaintCanvasBase canvas;
|
||||
private final EnumMap<ShapeColor, Color> colorMap;
|
||||
private final EnumMap<ShapeType, IDrawShape> strategies;
|
||||
private IDrawShape strategy;
|
||||
|
||||
private final Stroke selectStroke;
|
||||
|
||||
private Drawer(PaintCanvasBase canvas) {
|
||||
this.canvas = canvas;
|
||||
|
||||
colorMap = new EnumMap<>(ShapeColor.class);
|
||||
colorMap.put(ShapeColor.BLACK, Color.BLACK);
|
||||
colorMap.put(ShapeColor.BLUE, Color.BLUE);
|
||||
colorMap.put(ShapeColor.CYAN, Color.CYAN);
|
||||
colorMap.put(ShapeColor.DARK_GRAY, Color.DARK_GRAY);
|
||||
colorMap.put(ShapeColor.GRAY, Color.GRAY);
|
||||
colorMap.put(ShapeColor.GREEN, Color.GREEN);
|
||||
colorMap.put(ShapeColor.LIGHT_GRAY, Color.LIGHT_GRAY);
|
||||
colorMap.put(ShapeColor.MAGENTA, Color.MAGENTA);
|
||||
colorMap.put(ShapeColor.ORANGE, Color.ORANGE);
|
||||
colorMap.put(ShapeColor.PINK, Color.PINK);
|
||||
colorMap.put(ShapeColor.RED, Color.RED);
|
||||
colorMap.put(ShapeColor.WHITE, Color.WHITE);
|
||||
colorMap.put(ShapeColor.YELLOW, Color.YELLOW);
|
||||
|
||||
strategies = new EnumMap<>(ShapeType.class);
|
||||
|
||||
strategies.put(ShapeType.RECTANGLE, new DrawRectangle());
|
||||
strategies.put(ShapeType.ELLIPSE, new DrawEllipse());
|
||||
strategies.put(ShapeType.TRIANGLE, new DrawTriangle());
|
||||
|
||||
strategy = null;
|
||||
|
||||
selectStroke = new BasicStroke(3, BasicStroke.CAP_BUTT, BasicStroke.JOIN_BEVEL,
|
||||
1, new float[]{9}, 0);
|
||||
}
|
||||
|
||||
public static Drawer getInstance(PaintCanvasBase canvas) {
|
||||
if (uniqueInstance == null)
|
||||
uniqueInstance = new Drawer(canvas);
|
||||
else
|
||||
uniqueInstance.canvas = canvas;
|
||||
return uniqueInstance;
|
||||
}
|
||||
|
||||
@Override
|
||||
public void update(List<AbstractShape> shapeList) {
|
||||
// Clear the canvas for redraw
|
||||
Graphics2D graphics2d = canvas.getGraphics2D();
|
||||
graphics2d.setColor(canvas.getBackground());
|
||||
graphics2d.fillRect(0, 0, canvas.getWidth(), canvas.getHeight());
|
||||
|
||||
Iterator<AbstractShape> shapeListIter = shapeList.iterator();
|
||||
while (shapeListIter.hasNext()) {
|
||||
AbstractShape curShape = shapeListIter.next();
|
||||
//this.draw2(curShape, curShape.isSelected());
|
||||
this.draw(curShape);
|
||||
}
|
||||
}
|
||||
|
||||
public void draw2(AbstractShape aShape, boolean isSelected) {
|
||||
if (aShape != null) {
|
||||
// Draw the abstract shape first.
|
||||
strategy = strategies.get(aShape.getShapeType());
|
||||
if (strategy != null) {
|
||||
if (!aShape.isBoundary() && !aShape.isComposite())
|
||||
strategy.draw(aShape, canvas, colorMap, selectStroke, false);
|
||||
else
|
||||
if (isSelected && !aShape.isInGroup())
|
||||
strategy.draw(aShape, canvas, colorMap, selectStroke, true);
|
||||
}
|
||||
|
||||
// Draw its children.
|
||||
List<AbstractShape> aShapeComponents = aShape.getComponents();
|
||||
if (aShapeComponents == null) return;
|
||||
Iterator<AbstractShape> componentsIter = aShapeComponents.iterator();
|
||||
|
||||
while(componentsIter.hasNext()) {
|
||||
AbstractShape component = componentsIter.next();
|
||||
draw2(component, isSelected);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
public void draw(AbstractShape aShape) {
|
||||
strategy = strategies.get(aShape.getShapeType());
|
||||
if (strategy != null) {
|
||||
strategy.draw(aShape, canvas, colorMap, selectStroke, false);
|
||||
|
||||
if (aShape instanceof Shape) {
|
||||
Shape shape = (Shape) aShape;
|
||||
if (shape.isInGroup() && shape.isSelected()) {
|
||||
strategy = strategies.get(ShapeType.RECTANGLE);
|
||||
strategy.draw(shape.getGroupBoundary(), canvas, colorMap, selectStroke, true);
|
||||
} else if (shape.isSelected()) {
|
||||
strategy.draw(shape.getBoundary(), canvas, colorMap, selectStroke, true);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
Executable
+38
@@ -0,0 +1,38 @@
|
||||
package view.gui;
|
||||
|
||||
import javax.swing.*;
|
||||
|
||||
import view.EventName;
|
||||
import view.interfaces.IDialogChoice;
|
||||
import view.interfaces.IEventCallback;
|
||||
import view.interfaces.IGuiWindow;
|
||||
import view.interfaces.IUiModule;
|
||||
|
||||
public class Gui implements IUiModule {
|
||||
|
||||
private final IGuiWindow GUI;
|
||||
|
||||
public Gui(IGuiWindow gui) {
|
||||
this.GUI = gui;
|
||||
}
|
||||
|
||||
@Override
|
||||
public void addEvent(EventName eventName, IEventCallback callback) {
|
||||
JButton button = GUI.getButton(eventName);
|
||||
button.addActionListener((ActionEvent) -> callback.run());
|
||||
}
|
||||
|
||||
@Override
|
||||
public <T> T getDialogResponse(IDialogChoice dialogSettings) {
|
||||
Object selectedValue = JOptionPane.showInputDialog(null,
|
||||
dialogSettings.getDialogText(),
|
||||
dialogSettings.getDialogTitle(),
|
||||
JOptionPane.PLAIN_MESSAGE,
|
||||
null,
|
||||
dialogSettings.getDialogOptions(),
|
||||
dialogSettings.getCurrentSelection());
|
||||
return selectedValue == null
|
||||
? (T)dialogSettings.getCurrentSelection()
|
||||
: (T)selectedValue;
|
||||
}
|
||||
}
|
||||
Executable
+96
@@ -0,0 +1,96 @@
|
||||
package view.gui;
|
||||
|
||||
import java.util.HashMap;
|
||||
import java.util.Map;
|
||||
import java.util.NoSuchElementException;
|
||||
|
||||
import javax.swing.*;
|
||||
import javax.swing.border.*;
|
||||
|
||||
import view.interfaces.IGuiWindow;
|
||||
import view.EventName;
|
||||
|
||||
import java.awt.*;
|
||||
|
||||
public class GuiWindow extends JFrame implements IGuiWindow {
|
||||
private final int DEFAULT_WIDTH = 1250;
|
||||
private final int DEFAULT_HEIGHT = 800;
|
||||
private final String DEFAULT_TITLE = "JPaint";
|
||||
private final Insets defaultButtonDimensions
|
||||
= new Insets(5, 8, 5, 8);
|
||||
private final Map<EventName, JButton> eventButtons = new HashMap<>();
|
||||
|
||||
public GuiWindow(JComponent canvas){
|
||||
setVisible(true);
|
||||
setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
|
||||
setTitle(DEFAULT_TITLE);
|
||||
setSize(DEFAULT_WIDTH, DEFAULT_HEIGHT);
|
||||
setBackground(new Color(155, 155, 155));
|
||||
setExtendedState(JFrame.MAXIMIZED_BOTH);
|
||||
JPanel window = createWindow();
|
||||
window.add(canvas, BorderLayout.CENTER);
|
||||
validate();
|
||||
}
|
||||
|
||||
@Override
|
||||
public JButton getButton(EventName eventName) {
|
||||
if(!eventButtons.containsKey(eventName))
|
||||
throw new NoSuchElementException("No button exists for action " + eventName.toString());
|
||||
|
||||
return eventButtons.get(eventName);
|
||||
}
|
||||
|
||||
private JPanel createWindow() {
|
||||
JPanel contentPane = createBackgroundPanel();
|
||||
JPanel buttonPanel = createMenu();
|
||||
contentPane.add(buttonPanel, BorderLayout.NORTH);
|
||||
return contentPane;
|
||||
}
|
||||
|
||||
private JPanel createMenu() {
|
||||
JPanel buttonPanel = createButtonPanel();
|
||||
|
||||
for(EventName eventName : EventName.values()){
|
||||
addButtonToPanel(eventName, buttonPanel);
|
||||
}
|
||||
|
||||
return buttonPanel;
|
||||
}
|
||||
|
||||
private void addButtonToPanel(EventName eventName, JPanel panel) {
|
||||
JButton newButton = createButton(eventName);
|
||||
eventButtons.put(eventName, newButton);
|
||||
panel.add(newButton);
|
||||
}
|
||||
|
||||
private JButton createButton(EventName eventName) {
|
||||
JButton newButton = new JButton(eventName.toString());
|
||||
newButton.setForeground(Color.BLACK);
|
||||
newButton.setBackground(Color.WHITE);
|
||||
newButton.setBorder(createButtonBorder());
|
||||
return newButton;
|
||||
}
|
||||
|
||||
private Border createButtonBorder() {
|
||||
Border line = new LineBorder(Color.BLACK);
|
||||
Border margin = new EmptyBorder(defaultButtonDimensions);
|
||||
return new CompoundBorder(line, margin);
|
||||
}
|
||||
|
||||
private JPanel createButtonPanel() {
|
||||
JPanel panel = new JPanel();
|
||||
FlowLayout flowLayout = (FlowLayout) panel.getLayout();
|
||||
flowLayout.setAlignment(FlowLayout.LEFT);
|
||||
panel.setBackground(Color.lightGray);
|
||||
return panel;
|
||||
}
|
||||
|
||||
private JPanel createBackgroundPanel() {
|
||||
JPanel contentPane = new JPanel();
|
||||
contentPane.setBorder(new EmptyBorder(0, 0, 0, 0));
|
||||
contentPane.setLayout(new BorderLayout(0, 0));
|
||||
contentPane.setBackground(Color.WHITE);
|
||||
setContentPane(contentPane);
|
||||
return contentPane;
|
||||
}
|
||||
}
|
||||
Executable
+13
@@ -0,0 +1,13 @@
|
||||
package view.gui;
|
||||
|
||||
import view.interfaces.PaintCanvasBase;
|
||||
|
||||
import javax.swing.JComponent;
|
||||
import java.awt.*;
|
||||
|
||||
public class PaintCanvas extends PaintCanvasBase {
|
||||
|
||||
public Graphics2D getGraphics2D() {
|
||||
return (Graphics2D)getGraphics();
|
||||
}
|
||||
}
|
||||
Executable
+11
@@ -0,0 +1,11 @@
|
||||
package view.interfaces;
|
||||
|
||||
public interface IDialogChoice<T> {
|
||||
String getDialogTitle();
|
||||
|
||||
String getDialogText();
|
||||
|
||||
T[] getDialogOptions();
|
||||
|
||||
T getCurrentSelection();
|
||||
}
|
||||
@@ -0,0 +1,27 @@
|
||||
package view.interfaces;
|
||||
|
||||
import java.awt.Color;
|
||||
import java.awt.Stroke;
|
||||
import java.util.EnumMap;
|
||||
|
||||
import model.AbstractShape;
|
||||
import model.ShapeColor;
|
||||
|
||||
/**
|
||||
* IDrawShape interface
|
||||
*
|
||||
* Responsibility: Interface for the strategy pattern for drawing shapes.
|
||||
*
|
||||
* Note that if offset is true, an algorithm for drawing boundary is used instead.
|
||||
*
|
||||
* @author Minh Bui
|
||||
*
|
||||
*/
|
||||
|
||||
public interface IDrawShape {
|
||||
int SELECT_STROKE_OFFSET = 5;
|
||||
int SELECT_WIDTH_HEIGHT_OFFSET = 10;
|
||||
|
||||
void draw(AbstractShape shape, PaintCanvasBase canvas, EnumMap<ShapeColor, Color> colorMap, Stroke selectStroke,
|
||||
boolean offset);
|
||||
}
|
||||
Executable
+5
@@ -0,0 +1,5 @@
|
||||
package view.interfaces;
|
||||
|
||||
public interface IEventCallback {
|
||||
void run();
|
||||
}
|
||||
Executable
+9
@@ -0,0 +1,9 @@
|
||||
package view.interfaces;
|
||||
|
||||
import view.EventName;
|
||||
|
||||
import javax.swing.*;
|
||||
|
||||
public interface IGuiWindow {
|
||||
JButton getButton(EventName eventName);
|
||||
}
|
||||
Executable
+8
@@ -0,0 +1,8 @@
|
||||
package view.interfaces;
|
||||
|
||||
import view.EventName;
|
||||
|
||||
public interface IUiModule {
|
||||
void addEvent(EventName eventName, IEventCallback command);
|
||||
<T> T getDialogResponse(IDialogChoice dialogChoice);
|
||||
}
|
||||
Executable
+8
@@ -0,0 +1,8 @@
|
||||
package view.interfaces;
|
||||
|
||||
import javax.swing.*;
|
||||
import java.awt.*;
|
||||
|
||||
public abstract class PaintCanvasBase extends JComponent {
|
||||
public abstract Graphics2D getGraphics2D();
|
||||
}
|
||||
Reference in New Issue
Block a user