1 /*
2  *
3  * Copyright (c) 2007, 2018, Oracle and/or its affiliates. All rights reserved.
4  *
5  * Redistribution and use in source and binary forms, with or without
6  * modification, are permitted provided that the following conditions
7  * are met:
8  *
9  *   - Redistributions of source code must retain the above copyright
10  *     notice, this list of conditions and the following disclaimer.
11  *
12  *   - Redistributions in binary form must reproduce the above copyright
13  *     notice, this list of conditions and the following disclaimer in the
14  *     documentation and/or other materials provided with the distribution.
15  *
16  *   - Neither the name of Oracle nor the names of its
17  *     contributors may be used to endorse or promote products derived
18  *     from this software without specific prior written permission.
19  *
20  * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS
21  * IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO,
22  * THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
23  * PURPOSE ARE DISCLAIMED.  IN NO EVENT SHALL THE COPYRIGHT OWNER OR
24  * CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,
25  * EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO,
26  * PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR
27  * PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF
28  * LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING
29  * NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
30  * SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
31  */
32 package java2d.demos.Clipping;
33 
34 
35 import java.awt.*;
36 import java.awt.event.*;
37 import java.awt.geom.Area;
38 import java.awt.geom.Ellipse2D;
39 import java.awt.geom.GeneralPath;
40 import javax.swing.*;
41 import java2d.ControlsSurface;
42 import java2d.CustomControls;
43 import static java.awt.Color.*;
44 
45 
46 /**
47  * The Areas class demonstrates the CAG (Constructive Area Geometry)
48  * operations: Add(union), Subtract, Intersect, and ExclusiveOR.
49  */
50 @SuppressWarnings("serial")
51 public class Areas extends ControlsSurface {
52 
53     protected String areaType = "nop";
54 
Areas()55     public Areas() {
56         setBackground(WHITE);
57         setControls(new Component[] { new DemoControls(this) });
58     }
59 
60     @Override
render(int w, int h, Graphics2D g2)61     public void render(int w, int h, Graphics2D g2) {
62         GeneralPath p1 = new GeneralPath();
63         p1.moveTo(w * .25f, 0.0f);
64         p1.lineTo(w * .75f, h * .5f);
65         p1.lineTo(w * .25f, h);
66         p1.lineTo(0.0f, h * .5f);
67         p1.closePath();
68 
69         GeneralPath p2 = new GeneralPath();
70         p2.moveTo(w * .75f, 0.0f);
71         p2.lineTo(w, h * .5f);
72         p2.lineTo(w * .75f, h);
73         p2.lineTo(w * .25f, h * .5f);
74         p2.closePath();
75 
76 
77         Area area = new Area(p1);
78         g2.setColor(YELLOW);
79         if (areaType.equals("nop")) {
80             g2.fill(p1);
81             g2.fill(p2);
82             g2.setColor(RED);
83             g2.draw(p1);
84             g2.draw(p2);
85             return;
86         } else if (areaType.equals("add")) {
87             area.add(new Area(p2));
88         } else if (areaType.equals("sub")) {
89             area.subtract(new Area(p2));
90         } else if (areaType.equals("xor")) {
91             area.exclusiveOr(new Area(p2));
92         } else if (areaType.equals("int")) {
93             area.intersect(new Area(p2));
94         } else if (areaType.equals("pear")) {
95 
96             double sx = w / 100;
97             double sy = h / 140;
98             g2.scale(sx, sy);
99             double x = w / sx / 2;
100             double y = h / sy / 2;
101 
102             // Creates the first leaf by filling the intersection of two Area
103             // objects created from an ellipse.
104             Ellipse2D leaf = new Ellipse2D.Double(x - 16, y - 29, 15.0, 15.0);
105             Area leaf1 = new Area(leaf);
106             leaf.setFrame(x - 14, y - 47, 30.0, 30.0);
107             Area leaf2 = new Area(leaf);
108             leaf1.intersect(leaf2);
109             g2.setColor(GREEN);
110             g2.fill(leaf1);
111 
112             // Creates the second leaf.
113             leaf.setFrame(x + 1, y - 29, 15.0, 15.0);
114             leaf1 = new Area(leaf);
115             leaf2.intersect(leaf1);
116             g2.fill(leaf2);
117 
118             // Creates the stem by filling the Area resulting from the
119             // subtraction of two Area objects created from an ellipse.
120             Ellipse2D stem = new Ellipse2D.Double(x, y - 42, 40.0, 40.0);
121             Area st1 = new Area(stem);
122             stem.setFrame(x + 3, y - 47, 50.0, 50.0);
123             st1.subtract(new Area(stem));
124             g2.setColor(BLACK);
125             g2.fill(st1);
126 
127             // Creates the pear itself by filling the Area resulting from the
128             // union of two Area objects created by two different ellipses.
129             Ellipse2D circle = new Ellipse2D.Double(x - 25, y, 50.0, 50.0);
130             Ellipse2D oval = new Ellipse2D.Double(x - 19, y - 20, 40.0, 70.0);
131             Area circ = new Area(circle);
132             circ.add(new Area(oval));
133 
134             g2.setColor(YELLOW);
135             g2.fill(circ);
136             return;
137         }
138 
139         g2.fill(area);
140         g2.setColor(RED);
141         g2.draw(area);
142     }
143 
main(String[] argv)144     public static void main(String[] argv) {
145         createDemoFrame(new Areas());
146     }
147 
148 
149     static final class DemoControls extends CustomControls implements
150             ActionListener {
151 
152         Areas demo;
153         JToolBar toolbar;
154         JComboBox combo;
155 
DemoControls(Areas demo)156         public DemoControls(Areas demo) {
157             super(demo.name);
158             this.demo = demo;
159             add(toolbar = new JToolBar());
160             toolbar.setFloatable(false);
161             addTool("nop", "no area operation", true);
162             addTool("add", "add", false);
163             addTool("sub", "subtract", false);
164             addTool("xor", "exclusiveOr", false);
165             addTool("int", "intersection", false);
166             addTool("pear", "pear", false);
167         }
168 
addTool(String str, String tooltip, boolean state)169         public void addTool(String str, String tooltip, boolean state) {
170             JToggleButton b =
171                     (JToggleButton) toolbar.add(new JToggleButton(str));
172             b.setFocusPainted(false);
173             b.setToolTipText(tooltip);
174             b.setSelected(state);
175             b.addActionListener(this);
176             int width = b.getPreferredSize().width;
177             Dimension prefSize = new Dimension(width, 21);
178             b.setPreferredSize(prefSize);
179             b.setMaximumSize(prefSize);
180             b.setMinimumSize(prefSize);
181         }
182 
183         @Override
actionPerformed(ActionEvent e)184         public void actionPerformed(ActionEvent e) {
185             for (Component comp : toolbar.getComponents()) {
186                 ((JToggleButton) comp).setSelected(false);
187             }
188             JToggleButton b = (JToggleButton) e.getSource();
189             b.setSelected(true);
190             demo.areaType = b.getText();
191             demo.repaint();
192         }
193 
194         @Override
getPreferredSize()195         public Dimension getPreferredSize() {
196             return new Dimension(200, 40);
197         }
198 
199         @Override
200         @SuppressWarnings("SleepWhileHoldingLock")
run()201         public void run() {
202             try {
203                 Thread.sleep(1111);
204             } catch (Exception e) {
205                 return;
206             }
207             Thread me = Thread.currentThread();
208             while (thread == me) {
209                 for (Component comp : toolbar.getComponents()) {
210                     ((AbstractButton) comp).doClick();
211                     try {
212                         Thread.sleep(4444);
213                     } catch (InterruptedException e) {
214                         return;
215                     }
216                 }
217             }
218             thread = null;
219         }
220     } // End DemoControls
221 } // End Areas
222 
223