12 * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
13 * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
14 * version 2 for more details (a copy is included in the LICENSE file that
15 * accompanied this code).
16 *
17 * You should have received a copy of the GNU General Public License version
18 * 2 along with this work; if not, write to the Free Software Foundation,
19 * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
20 *
21 * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
22 * or visit www.oracle.com if you need additional information or have any
23 * questions.
24 */
25
26 package sun.swing;
27
28 import java.awt.BorderLayout;
29 import java.awt.Color;
30 import java.awt.Component;
31 import java.awt.Container;
32 import java.awt.EventQueue;
33 import java.awt.Graphics;
34 import java.awt.Graphics2D;
35 import java.awt.Rectangle;
36 import java.awt.image.BufferedImage;
37 import java.awt.image.DataBufferInt;
38 import java.security.AccessController;
39
40 import javax.swing.JLayeredPane;
41 import javax.swing.JPanel;
42 import javax.swing.JRootPane;
43 import javax.swing.LayoutFocusTraversalPolicy;
44 import javax.swing.RootPaneContainer;
45
46 import sun.awt.LightweightFrame;
47 import sun.security.action.GetPropertyAction;
48
49 /**
50 * The frame serves as a lightweight container which paints its content
51 * to an offscreen image and provides access to the image's data via the
52 * {@link LightweightContent} interface. Note, that it may not be shown
53 * as a standalone toplevel frame. Its purpose is to provide functionality
54 * for lightweight embedding.
55 *
56 * @author Artem Ananiev
57 * @author Anton Tarasov
63 private LightweightContent content;
64
65 private Component component;
66 private JPanel contentPane;
67
68 private BufferedImage bbImage;
69
70 /**
71 * {@code copyBufferEnabled}, true by default, defines the following strategy.
72 * A duplicating (copy) buffer is created for the original pixel buffer.
73 * The copy buffer is synchronized with the original buffer every time the
74 * latter changes. {@code JLightweightFrame} passes the copy buffer array
75 * to the {@link LightweightContent#imageBufferReset} method. The code spot
76 * which synchronizes two buffers becomes the only critical section guarded
77 * by the lock (managed with the {@link LightweightContent#paintLock()},
78 * {@link LightweightContent#paintUnlock()} methods).
79 */
80 private boolean copyBufferEnabled;
81 private int[] copyBuffer;
82
83 /**
84 * Constructs a new, initially invisible {@code JLightweightFrame}
85 * instance.
86 */
87 public JLightweightFrame() {
88 super();
89 copyBufferEnabled = "true".equals(AccessController.
90 doPrivileged(new GetPropertyAction("jlf.copyBufferEnabled", "true")));
91
92 add(rootPane, BorderLayout.CENTER);
93 setFocusTraversalPolicy(new LayoutFocusTraversalPolicy());
94 if (getGraphicsConfiguration().isTranslucencyCapable()) {
95 setBackground(new Color(0, 0, 0, 0));
96 }
97 }
98
99 /**
100 * Sets the {@link LightweightContent} instance for this frame.
101 * The {@code JComponent} object returned by the
102 * {@link LightweightContent#getComponent()} method is immediately
103 * added to the frame's content pane.
104 *
105 * @param content the {@link LightweightContent} instance
106 */
107 public void setContent(LightweightContent content) {
108 this.content = content;
109 this.component = content.getComponent();
110
111 initInterior();
112 }
113
114 @Override
115 public Graphics getGraphics() {
116 if (bbImage == null) return null;
117
118 Graphics2D g = bbImage.createGraphics();
119 g.setBackground(getBackground());
120 g.setColor(getForeground());
121 g.setFont(getFont());
122 return g;
123 }
124
125 /**
126 * {@inheritDoc}
127 *
128 * @see LightweightContent#focusGrabbed()
129 */
130 @Override
185 if (copyBufferEnabled) {
186 syncCopyBuffer(false, clip.x, clip.y, clip.width, clip.height);
187 }
188 content.imageUpdated(clip.x, clip.y, clip.width, clip.height);
189 }
190 });
191 } finally {
192 if (!copyBufferEnabled) {
193 content.paintUnlock();
194 }
195 }
196 }
197 @Override
198 protected boolean isPaintingOrigin() {
199 return true;
200 }
201 };
202 contentPane.setLayout(new BorderLayout());
203 contentPane.add(component);
204 setContentPane(contentPane);
205 }
206
207 @SuppressWarnings("deprecation")
208 @Override public void reshape(int x, int y, int width, int height) {
209 super.reshape(x, y, width, height);
210
211 if (width == 0 || height == 0) {
212 return;
213 }
214 if (!copyBufferEnabled) {
215 content.paintLock();
216 }
217 try {
218 if ((bbImage == null) || (width != bbImage.getWidth()) || (height != bbImage.getHeight())) {
219 boolean createBB = true;
220 int newW = width;
221 int newH = height;
222 if (bbImage != null) {
223 int oldW = bbImage.getWidth();
224 int oldH = bbImage.getHeight();
|
12 * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
13 * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
14 * version 2 for more details (a copy is included in the LICENSE file that
15 * accompanied this code).
16 *
17 * You should have received a copy of the GNU General Public License version
18 * 2 along with this work; if not, write to the Free Software Foundation,
19 * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
20 *
21 * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
22 * or visit www.oracle.com if you need additional information or have any
23 * questions.
24 */
25
26 package sun.swing;
27
28 import java.awt.BorderLayout;
29 import java.awt.Color;
30 import java.awt.Component;
31 import java.awt.Container;
32 import java.awt.Dimension;
33 import java.awt.EventQueue;
34 import java.awt.Graphics;
35 import java.awt.Graphics2D;
36 import java.awt.Rectangle;
37 import java.awt.event.ComponentListener;
38 import java.awt.event.ContainerEvent;
39 import java.awt.event.ContainerListener;
40 import java.awt.image.BufferedImage;
41 import java.awt.image.DataBufferInt;
42 import java.beans.PropertyChangeEvent;
43 import java.beans.PropertyChangeListener;
44 import java.security.AccessController;
45
46 import javax.swing.JLayeredPane;
47 import javax.swing.JPanel;
48 import javax.swing.JRootPane;
49 import javax.swing.LayoutFocusTraversalPolicy;
50 import javax.swing.RootPaneContainer;
51
52 import sun.awt.LightweightFrame;
53 import sun.security.action.GetPropertyAction;
54
55 /**
56 * The frame serves as a lightweight container which paints its content
57 * to an offscreen image and provides access to the image's data via the
58 * {@link LightweightContent} interface. Note, that it may not be shown
59 * as a standalone toplevel frame. Its purpose is to provide functionality
60 * for lightweight embedding.
61 *
62 * @author Artem Ananiev
63 * @author Anton Tarasov
69 private LightweightContent content;
70
71 private Component component;
72 private JPanel contentPane;
73
74 private BufferedImage bbImage;
75
76 /**
77 * {@code copyBufferEnabled}, true by default, defines the following strategy.
78 * A duplicating (copy) buffer is created for the original pixel buffer.
79 * The copy buffer is synchronized with the original buffer every time the
80 * latter changes. {@code JLightweightFrame} passes the copy buffer array
81 * to the {@link LightweightContent#imageBufferReset} method. The code spot
82 * which synchronizes two buffers becomes the only critical section guarded
83 * by the lock (managed with the {@link LightweightContent#paintLock()},
84 * {@link LightweightContent#paintUnlock()} methods).
85 */
86 private boolean copyBufferEnabled;
87 private int[] copyBuffer;
88
89 private PropertyChangeListener layoutSizeListener;
90
91 /**
92 * Constructs a new, initially invisible {@code JLightweightFrame}
93 * instance.
94 */
95 public JLightweightFrame() {
96 super();
97 copyBufferEnabled = "true".equals(AccessController.
98 doPrivileged(new GetPropertyAction("jlf.copyBufferEnabled", "true")));
99
100 add(rootPane, BorderLayout.CENTER);
101 setFocusTraversalPolicy(new LayoutFocusTraversalPolicy());
102 if (getGraphicsConfiguration().isTranslucencyCapable()) {
103 setBackground(new Color(0, 0, 0, 0));
104 }
105
106 layoutSizeListener = new PropertyChangeListener() {
107 @Override
108 public void propertyChange(PropertyChangeEvent e) {
109 Dimension d = (Dimension)e.getNewValue();
110
111 if ("preferredSize".equals(e.getPropertyName())) {
112 content.preferredSizeChanged(d.width, d.height);
113
114 } else if ("maximumSize".equals(e.getPropertyName())) {
115 content.maximumSizeChanged(d.width, d.height);
116
117 } else if ("minimumSize".equals(e.getPropertyName())) {
118 content.minimumSizeChanged(d.width, d.height);
119 }
120 }
121 };
122 }
123
124 /**
125 * Sets the {@link LightweightContent} instance for this frame.
126 * The {@code JComponent} object returned by the
127 * {@link LightweightContent#getComponent()} method is immediately
128 * added to the frame's content pane.
129 *
130 * @param content the {@link LightweightContent} instance
131 */
132 public void setContent(final LightweightContent content) {
133 if (content == null) {
134 System.err.println("JLightweightFrame.setContent: content may not be null!");
135 return;
136 }
137 this.content = content;
138 this.component = content.getComponent();
139
140 Dimension d = this.component.getPreferredSize();
141 content.preferredSizeChanged(d.width, d.height);
142
143 d = this.component.getMaximumSize();
144 content.maximumSizeChanged(d.width, d.height);
145
146 d = this.component.getMinimumSize();
147 content.minimumSizeChanged(d.width, d.height);
148
149 initInterior();
150 }
151
152 @Override
153 public Graphics getGraphics() {
154 if (bbImage == null) return null;
155
156 Graphics2D g = bbImage.createGraphics();
157 g.setBackground(getBackground());
158 g.setColor(getForeground());
159 g.setFont(getFont());
160 return g;
161 }
162
163 /**
164 * {@inheritDoc}
165 *
166 * @see LightweightContent#focusGrabbed()
167 */
168 @Override
223 if (copyBufferEnabled) {
224 syncCopyBuffer(false, clip.x, clip.y, clip.width, clip.height);
225 }
226 content.imageUpdated(clip.x, clip.y, clip.width, clip.height);
227 }
228 });
229 } finally {
230 if (!copyBufferEnabled) {
231 content.paintUnlock();
232 }
233 }
234 }
235 @Override
236 protected boolean isPaintingOrigin() {
237 return true;
238 }
239 };
240 contentPane.setLayout(new BorderLayout());
241 contentPane.add(component);
242 setContentPane(contentPane);
243
244 contentPane.addContainerListener(new ContainerListener() {
245 @Override
246 public void componentAdded(ContainerEvent e) {
247 Component c = JLightweightFrame.this.component;
248 if (e.getChild() == c) {
249 c.addPropertyChangeListener("preferredSize", layoutSizeListener);
250 c.addPropertyChangeListener("maximumSize", layoutSizeListener);
251 c.addPropertyChangeListener("minimumSize", layoutSizeListener);
252 }
253 }
254 @Override
255 public void componentRemoved(ContainerEvent e) {
256 Component c = JLightweightFrame.this.component;
257 if (e.getChild() == c) {
258 c.removePropertyChangeListener(layoutSizeListener);
259 }
260 }
261 });
262 }
263
264 @SuppressWarnings("deprecation")
265 @Override public void reshape(int x, int y, int width, int height) {
266 super.reshape(x, y, width, height);
267
268 if (width == 0 || height == 0) {
269 return;
270 }
271 if (!copyBufferEnabled) {
272 content.paintLock();
273 }
274 try {
275 if ((bbImage == null) || (width != bbImage.getWidth()) || (height != bbImage.getHeight())) {
276 boolean createBB = true;
277 int newW = width;
278 int newH = height;
279 if (bbImage != null) {
280 int oldW = bbImage.getWidth();
281 int oldH = bbImage.getHeight();
|