Mercurial > projects > dwt2
comparison org.eclipse.jface.text/src/org/eclipse/jface/internal/text/html/BrowserInformationControl.d @ 12:bc29606a740c
Added dwt-addons in original directory structure of eclipse.org
author | Frank Benoit <benoit@tionex.de> |
---|---|
date | Sat, 14 Mar 2009 18:23:29 +0100 |
parents | |
children | dbfb303e8fb0 |
comparison
equal
deleted
inserted
replaced
11:43904fec5dca | 12:bc29606a740c |
---|---|
1 /******************************************************************************* | |
2 * Copyright (c) 2000, 2008 IBM Corporation and others. | |
3 * All rights reserved. This program and the accompanying materials | |
4 * are made available under the terms of the Eclipse Public License v1.0 | |
5 * which accompanies this distribution, and is available at | |
6 * http://www.eclipse.org/legal/epl-v10.html | |
7 * | |
8 * Contributors: | |
9 * IBM Corporation - initial API and implementation | |
10 * Port to the D programming language: | |
11 * Frank Benoit <benoit@tionex.de> | |
12 *******************************************************************************/ | |
13 module org.eclipse.jface.internal.text.html.BrowserInformationControl; | |
14 | |
15 import org.eclipse.jface.internal.text.html.HTML2TextReader; // packageimport | |
16 import org.eclipse.jface.internal.text.html.HTMLPrinter; // packageimport | |
17 import org.eclipse.jface.internal.text.html.SubstitutionTextReader; // packageimport | |
18 import org.eclipse.jface.internal.text.html.HTMLTextPresenter; // packageimport | |
19 import org.eclipse.jface.internal.text.html.BrowserInput; // packageimport | |
20 import org.eclipse.jface.internal.text.html.SingleCharReader; // packageimport | |
21 import org.eclipse.jface.internal.text.html.BrowserInformationControlInput; // packageimport | |
22 import org.eclipse.jface.internal.text.html.HTMLMessages; // packageimport | |
23 | |
24 import java.lang.all; | |
25 import java.util.Iterator; | |
26 import java.util.Set; | |
27 | |
28 import org.eclipse.swt.widgets.Shell; | |
29 import org.eclipse.swt.widgets.Composite; | |
30 import org.eclipse.jface.text.AbstractInformationControl; | |
31 import org.eclipse.jface.text.IInformationControlExtension2; | |
32 import org.eclipse.jface.text.IDelayedInputChangeProvider; | |
33 import org.eclipse.jface.text.IInputChangedListener; | |
34 | |
35 //pragma( msg, "org.eclipse.jface.internal.text.html.BrowserInformationControl: SWT browser control missing" ); | |
36 class BrowserInformationControl : AbstractInformationControl , IInformationControlExtension2, IDelayedInputChangeProvider { | |
37 public this(Shell parent, String symbolicFontName, bool resizable){ | |
38 super(parent, resizable); | |
39 implMissing(__FILE__,__LINE__); | |
40 } | |
41 public static bool isAvailable(Composite parent){ | |
42 implMissing(__FILE__,__LINE__); | |
43 return false; | |
44 } | |
45 public void setInformation(String content) { | |
46 implMissing(__FILE__,__LINE__); | |
47 } | |
48 protected void createContent(Composite parent) { | |
49 implMissing(__FILE__,__LINE__); | |
50 } | |
51 public void setInput(Object input) { | |
52 implMissing(__FILE__,__LINE__); | |
53 } | |
54 public void setDelayedInputChangeListener(IInputChangedListener inputChangeListener) { | |
55 implMissing(__FILE__,__LINE__); | |
56 } | |
57 public bool hasContents() { | |
58 implMissing(__FILE__,__LINE__); | |
59 return false; | |
60 } | |
61 } | |
62 | |
63 // FIXME needs Browser :/ | |
64 /++ | |
65 | |
66 import org.eclipse.dwtxhelper.StringReader; | |
67 | |
68 import org.eclipse.swt.SWT; | |
69 import org.eclipse.swt.SWTError; | |
70 import org.eclipse.swt.browser.Browser; | |
71 import org.eclipse.swt.browser.LocationListener; | |
72 import org.eclipse.swt.browser.ProgressAdapter; | |
73 import org.eclipse.swt.browser.ProgressEvent; | |
74 import org.eclipse.swt.custom.StyleRange; | |
75 import org.eclipse.swt.events.KeyEvent; | |
76 import org.eclipse.swt.events.KeyListener; | |
77 import org.eclipse.swt.graphics.Color; | |
78 import org.eclipse.swt.graphics.Font; | |
79 import org.eclipse.swt.graphics.FontData; | |
80 import org.eclipse.swt.graphics.GC; | |
81 import org.eclipse.swt.graphics.Point; | |
82 import org.eclipse.swt.graphics.Rectangle; | |
83 import org.eclipse.swt.graphics.TextLayout; | |
84 import org.eclipse.swt.graphics.TextStyle; | |
85 import org.eclipse.swt.widgets.Composite; | |
86 import org.eclipse.swt.widgets.Display; | |
87 import org.eclipse.swt.widgets.Menu; | |
88 import org.eclipse.swt.widgets.Shell; | |
89 import org.eclipse.swt.widgets.Slider; | |
90 import org.eclipse.core.runtime.Assert; | |
91 import org.eclipse.core.runtime.ListenerList; | |
92 import org.eclipse.jface.action.ToolBarManager; | |
93 import org.eclipse.jface.resource.JFaceResources; | |
94 import org.eclipse.jface.text.AbstractInformationControl; | |
95 import org.eclipse.jface.text.IDelayedInputChangeProvider; | |
96 import org.eclipse.jface.text.IInformationControlExtension2; | |
97 import org.eclipse.jface.text.IInputChangedListener; | |
98 import org.eclipse.jface.text.TextPresentation; | |
99 | |
100 | |
101 /** | |
102 * Displays HTML information in a {@link org.eclipse.swt.browser.Browser} widget. | |
103 * <p> | |
104 * This {@link IInformationControlExtension2} expects {@link #setInput(Object)} to be | |
105 * called with an argument of type {@link BrowserInformationControlInput}. | |
106 * </p> | |
107 * <p> | |
108 * Moved into this package from <code>org.eclipse.jface.internal.text.revisions</code>.</p> | |
109 * <p> | |
110 * This class may be instantiated; it is not intended to be subclassed.</p> | |
111 * <p> | |
112 * Current problems: | |
113 * <ul> | |
114 * <li>the size computation is too small</li> | |
115 * <li>focusLost event is not sent - see https://bugs.eclipse.org/bugs/show_bug.cgi?id=84532</li> | |
116 * </ul> | |
117 * </p> | |
118 * | |
119 * @since 3.2 | |
120 */ | |
121 public class BrowserInformationControl : AbstractInformationControl , IInformationControlExtension2, IDelayedInputChangeProvider { | |
122 | |
123 | |
124 /** | |
125 * Tells whether the SWT Browser widget and hence this information | |
126 * control is available. | |
127 * | |
128 * @param parent the parent component used for checking or <code>null</code> if none | |
129 * @return <code>true</code> if this control is available | |
130 */ | |
131 public static bool isAvailable(Composite parent) { | |
132 if (!fgAvailabilityChecked) { | |
133 try { | |
134 Browser browser= new Browser(parent, SWT.NONE); | |
135 browser.dispose(); | |
136 fgIsAvailable= true; | |
137 | |
138 Slider sliderV= new Slider(parent, SWT.VERTICAL); | |
139 Slider sliderH= new Slider(parent, SWT.HORIZONTAL); | |
140 int width= sliderV.computeSize(SWT.DEFAULT, SWT.DEFAULT).x; | |
141 int height= sliderH.computeSize(SWT.DEFAULT, SWT.DEFAULT).y; | |
142 fgScrollBarSize= new Point(width, height); | |
143 sliderV.dispose(); | |
144 sliderH.dispose(); | |
145 } catch (SWTError er) { | |
146 fgIsAvailable= false; | |
147 } finally { | |
148 fgAvailabilityChecked= true; | |
149 } | |
150 } | |
151 | |
152 return fgIsAvailable; | |
153 } | |
154 | |
155 | |
156 /** | |
157 * Minimal size constraints. | |
158 * @since 3.2 | |
159 */ | |
160 private static const int MIN_WIDTH= 80; | |
161 private static const int MIN_HEIGHT= 50; | |
162 | |
163 | |
164 /** | |
165 * Availability checking cache. | |
166 */ | |
167 private static bool fgIsAvailable= false; | |
168 private static bool fgAvailabilityChecked= false; | |
169 | |
170 /** | |
171 * Cached scroll bar width and height | |
172 * @since 3.4 | |
173 */ | |
174 private static Point fgScrollBarSize; | |
175 | |
176 /** The control's browser widget */ | |
177 private Browser fBrowser; | |
178 /** Tells whether the browser has content */ | |
179 private bool fBrowserHasContent; | |
180 /** Text layout used to approximate size of content when rendered in browser */ | |
181 private TextLayout fTextLayout; | |
182 /** Bold text style */ | |
183 private TextStyle fBoldStyle; | |
184 | |
185 private BrowserInformationControlInput fInput; | |
186 | |
187 /** | |
188 * <code>true</code> iff the browser has completed loading of the last | |
189 * input set via {@link #setInformation(String)}. | |
190 * @since 3.4 | |
191 */ | |
192 private bool fCompleted= false; | |
193 | |
194 /** | |
195 * The listener to be notified when a delayed location changing event happened. | |
196 * @since 3.4 | |
197 */ | |
198 private IInputChangedListener fDelayedInputChangeListener; | |
199 | |
200 /** | |
201 * The listeners to be notified when the input changed. | |
202 * @since 3.4 | |
203 */ | |
204 private ListenerList/*<IInputChangedListener>*/ fInputChangeListeners= new ListenerList(ListenerList.IDENTITY); | |
205 | |
206 /** | |
207 * The symbolic name of the font used for size computations, or <code>null</code> to use dialog font. | |
208 * @since 3.4 | |
209 */ | |
210 private const String fSymbolicFontName; | |
211 | |
212 | |
213 /** | |
214 * Creates a browser information control with the given shell as parent. | |
215 * | |
216 * @param parent the parent shell | |
217 * @param symbolicFontName the symbolic name of the font used for size computations | |
218 * @param resizable <code>true</code> if the control should be resizable | |
219 * @since 3.4 | |
220 */ | |
221 public this(Shell parent, String symbolicFontName, bool resizable) { | |
222 super(parent, resizable); | |
223 fSymbolicFontName= symbolicFontName; | |
224 create(); | |
225 } | |
226 | |
227 /** | |
228 * Creates a browser information control with the given shell as parent. | |
229 * | |
230 * @param parent the parent shell | |
231 * @param symbolicFontName the symbolic name of the font used for size computations | |
232 * @param statusFieldText the text to be used in the optional status field | |
233 * or <code>null</code> if the status field should be hidden | |
234 * @since 3.4 | |
235 */ | |
236 public this(Shell parent, String symbolicFontName, String statusFieldText) { | |
237 super(parent, statusFieldText); | |
238 fSymbolicFontName= symbolicFontName; | |
239 create(); | |
240 } | |
241 | |
242 /** | |
243 * Creates a browser information control with the given shell as parent. | |
244 * | |
245 * @param parent the parent shell | |
246 * @param symbolicFontName the symbolic name of the font used for size computations | |
247 * @param toolBarManager the manager or <code>null</code> if toolbar is not desired | |
248 * @since 3.4 | |
249 */ | |
250 public this(Shell parent, String symbolicFontName, ToolBarManager toolBarManager) { | |
251 super(parent, toolBarManager); | |
252 fSymbolicFontName= symbolicFontName; | |
253 create(); | |
254 } | |
255 | |
256 /* | |
257 * @see org.eclipse.jface.text.AbstractInformationControl#createContent(org.eclipse.swt.widgets.Composite) | |
258 */ | |
259 protected void createContent(Composite parent) { | |
260 fBrowser= new Browser(parent, SWT.NONE); | |
261 | |
262 Display display= getShell().getDisplay(); | |
263 fBrowser.setForeground(display.getSystemColor(SWT.COLOR_INFO_FOREGROUND)); | |
264 fBrowser.setBackground(display.getSystemColor(SWT.COLOR_INFO_BACKGROUND)); | |
265 fBrowser.addKeyListener(new class() KeyListener { | |
266 | |
267 public void keyPressed(KeyEvent e) { | |
268 if (e.character is 0x1B) // ESC | |
269 getShell().dispose(); // XXX: Just hide? Would avoid constant recreations. | |
270 } | |
271 | |
272 public void keyReleased(KeyEvent e) {} | |
273 }); | |
274 | |
275 fBrowser.addProgressListener(new class() ProgressAdapter { | |
276 public void completed(ProgressEvent event) { | |
277 fCompleted= true; | |
278 } | |
279 }); | |
280 | |
281 // Replace browser's built-in context menu with none | |
282 fBrowser.setMenu(new Menu(getShell(), SWT.NONE)); | |
283 | |
284 createTextLayout(); | |
285 } | |
286 | |
287 /** | |
288 * {@inheritDoc} | |
289 * @deprecated use {@link #setInput(Object)} | |
290 */ | |
291 public void setInformation(String content) { | |
292 setInput(new class(null,content) BrowserInformationControlInput { | |
293 String content_; | |
294 this(BrowserInformationControlInput input, String a){ | |
295 super(input); | |
296 content_=a; | |
297 } | |
298 public String getHtml() { | |
299 return content_; | |
300 } | |
301 | |
302 public String getInputName() { | |
303 return ""; //$NON-NLS-1$ | |
304 } | |
305 | |
306 public Object getInputElement() { | |
307 return stringcast(content_); | |
308 } | |
309 }); | |
310 } | |
311 | |
312 /** | |
313 * {@inheritDoc} This control can handle {@link String} and | |
314 * {@link BrowserInformationControlInput}. | |
315 */ | |
316 public void setInput(Object input) { | |
317 Assert.isLegal(input is null || cast(String)input || cast(BrowserInformationControlInput)input ); | |
318 | |
319 if ( cast(String)input ) { | |
320 setInformation(cast(String)input); | |
321 return; | |
322 } | |
323 | |
324 fInput= cast(BrowserInformationControlInput)input; | |
325 | |
326 String content= null; | |
327 if (fInput !is null) | |
328 content= fInput.getHtml(); | |
329 | |
330 fBrowserHasContent= content !is null && content.length() > 0; | |
331 | |
332 if (!fBrowserHasContent) | |
333 content= "<html><body ></html>"; //$NON-NLS-1$ | |
334 | |
335 bool RTL= (getShell().getStyle() & SWT.RIGHT_TO_LEFT) !is 0; | |
336 bool resizable= isResizable(); | |
337 | |
338 // The default "overflow:auto" would not result in a predictable width for the client area | |
339 // and the re-wrapping would cause visual noise | |
340 String[] styles= null; | |
341 if (RTL && resizable) | |
342 styles= [ "direction:rtl;", "overflow:scroll;", "word-wrap:break-word;" ]; //$NON-NLS-1$ //$NON-NLS-2$ //$NON-NLS-3$ | |
343 else if (RTL && !resizable) | |
344 styles= [ "direction:rtl;", "overflow:hidden;", "word-wrap:break-word;" ]; //$NON-NLS-1$ //$NON-NLS-2$ //$NON-NLS-3$ | |
345 else if (!resizable) | |
346 //XXX: In IE, "word-wrap: break-word;" causes bogus wrapping even in non-broken words :-(see e.g. Javadoc of String). | |
347 // Re-check whether we really still need this now that the Javadoc Hover header already sets this style. | |
348 styles= [ "overflow:hidden;"/*, "word-wrap: break-word;"*/ ]; //$NON-NLS-1$ | |
349 else | |
350 styles= [ "overflow:scroll;" ]; //$NON-NLS-1$ | |
351 | |
352 StringBuffer buffer= new StringBuffer(content); | |
353 HTMLPrinter.insertStyles(buffer, styles); | |
354 content= buffer.toString(); | |
355 | |
356 /* | |
357 * XXX: Should add some JavaScript here that shows something like | |
358 * "(continued...)" or "..." at the end of the visible area when the page overflowed | |
359 * with "overflow:hidden;". | |
360 */ | |
361 | |
362 fCompleted= false; | |
363 fBrowser.setText(content); | |
364 | |
365 Object[] listeners= fInputChangeListeners.getListeners(); | |
366 for (int i= 0; i < listeners.length; i++) | |
367 (cast(IInputChangedListener)listeners[i]).inputChanged(fInput); | |
368 } | |
369 | |
370 /* | |
371 * @see IInformationControl#setVisible(bool) | |
372 */ | |
373 public void setVisible(bool visible) { | |
374 Shell shell= getShell(); | |
375 if (shell.isVisible() is visible) | |
376 return; | |
377 | |
378 if (!visible) { | |
379 super.setVisible(false); | |
380 setInput(null); | |
381 return; | |
382 } | |
383 | |
384 /* | |
385 * The Browser widget flickers when made visible while it is not completely loaded. | |
386 * The fix is to delay the call to setVisible until either loading is completed | |
387 * (see ProgressListener in constructor), or a timeout has been reached. | |
388 */ | |
389 final Display display= shell.getDisplay(); | |
390 | |
391 // Make sure the display wakes from sleep after timeout: | |
392 display.timerExec(100, new class() Runnable { | |
393 public void run() { | |
394 fCompleted= true; | |
395 } | |
396 }); | |
397 | |
398 while (!fCompleted) { | |
399 // Drive the event loop to process the events required to load the browser widget's contents: | |
400 if (!display.readAndDispatch()) { | |
401 display.sleep(); | |
402 } | |
403 } | |
404 | |
405 shell= getShell(); | |
406 if (shell is null || shell.isDisposed()) | |
407 return; | |
408 | |
409 /* | |
410 * Avoids flickering when replacing hovers, especially on Vista in ON_CLICK mode. | |
411 * Causes flickering on GTK. Carbon does not care. | |
412 */ | |
413 if ("win32".equals(SWT.getPlatform())) //$NON-NLS-1$ | |
414 shell.moveAbove(null); | |
415 | |
416 super.setVisible(true); | |
417 } | |
418 | |
419 /* | |
420 * @see org.eclipse.jface.text.AbstractInformationControl#setSize(int, int) | |
421 */ | |
422 public void setSize(int width, int height) { | |
423 fBrowser.setRedraw(false); // avoid flickering | |
424 try { | |
425 super.setSize(width, height); | |
426 } finally { | |
427 fBrowser.setRedraw(true); | |
428 } | |
429 } | |
430 | |
431 /** | |
432 * Creates and initializes the text layout used | |
433 * to compute the size hint. | |
434 * | |
435 * @since 3.2 | |
436 */ | |
437 private void createTextLayout() { | |
438 fTextLayout= new TextLayout(fBrowser.getDisplay()); | |
439 | |
440 // Initialize fonts | |
441 Font font= fSymbolicFontName is null ? JFaceResources.getDialogFont() : JFaceResources.getFont(fSymbolicFontName); | |
442 fTextLayout.setFont(font); | |
443 fTextLayout.setWidth(-1); | |
444 FontData[] fontData= font.getFontData(); | |
445 for (int i= 0; i < fontData.length; i++) | |
446 fontData[i].setStyle(SWT.BOLD); | |
447 font= new Font(getShell().getDisplay(), fontData); | |
448 fBoldStyle= new TextStyle(font, null, null); | |
449 | |
450 // Compute and set tab width | |
451 fTextLayout.setText(" "); //$NON-NLS-1$ | |
452 int tabWidth = fTextLayout.getBounds().width; | |
453 fTextLayout.setTabs([tabWidth]); | |
454 | |
455 fTextLayout.setText(""); //$NON-NLS-1$ | |
456 } | |
457 | |
458 /* | |
459 * @see IInformationControl#dispose() | |
460 */ | |
461 public void dispose() { | |
462 if (fTextLayout !is null) { | |
463 fTextLayout.dispose(); | |
464 fTextLayout= null; | |
465 } | |
466 if (fBoldStyle !is null) { | |
467 fBoldStyle.font.dispose(); | |
468 fBoldStyle= null; | |
469 } | |
470 fBrowser= null; | |
471 | |
472 super.dispose(); | |
473 } | |
474 | |
475 /* | |
476 * @see IInformationControl#computeSizeHint() | |
477 */ | |
478 public Point computeSizeHint() { | |
479 Point sizeConstraints= getSizeConstraints(); | |
480 Rectangle trim= computeTrim(); | |
481 int height= trim.height; | |
482 | |
483 //FIXME: The HTML2TextReader does not render <p> like a browser. | |
484 // Instead of inserting an empty line, it just adds a single line break. | |
485 // Furthermore, the indentation of <dl><dd> elements is too small (e.g with a long @see line) | |
486 TextPresentation presentation= new TextPresentation(); | |
487 HTML2TextReader reader= new HTML2TextReader(new StringReader(fInput.getHtml()), presentation); | |
488 String text; | |
489 try { | |
490 text= reader.getString(); | |
491 } catch (IOException e) { | |
492 text= ""; //$NON-NLS-1$ | |
493 } | |
494 | |
495 fTextLayout.setText(text); | |
496 fTextLayout.setWidth(sizeConstraints is null ? SWT.DEFAULT : sizeConstraints.x - trim.width); | |
497 Iterator iter= presentation.getAllStyleRangeIterator(); | |
498 while (iter.hasNext()) { | |
499 StyleRange sr= cast(StyleRange)iter.next(); | |
500 if (sr.fontStyle is SWT.BOLD) | |
501 fTextLayout.setStyle(fBoldStyle, sr.start, sr.start + sr.length - 1); | |
502 } | |
503 | |
504 Rectangle bounds= fTextLayout.getBounds(); // does not return minimum width, see https://bugs.eclipse.org/bugs/show_bug.cgi?id=217446 | |
505 int lineCount= fTextLayout.getLineCount(); | |
506 int textWidth= 0; | |
507 for (int i= 0; i < lineCount; i++) { | |
508 Rectangle rect= fTextLayout.getLineBounds(i); | |
509 int lineWidth= rect.x + rect.width; | |
510 if (i is 0) | |
511 lineWidth += fInput.getLeadingImageWidth(); | |
512 textWidth= Math.max(textWidth, lineWidth); | |
513 } | |
514 bounds.width= textWidth; | |
515 fTextLayout.setText(""); //$NON-NLS-1$ | |
516 | |
517 int minWidth= bounds.width; | |
518 height= height + bounds.height; | |
519 | |
520 // Add some air to accommodate for different browser renderings | |
521 minWidth+= 15; | |
522 height+= 15; | |
523 | |
524 | |
525 // Apply max size constraints | |
526 if (sizeConstraints !is null) { | |
527 if (sizeConstraints.x !is SWT.DEFAULT) | |
528 minWidth= Math.min(sizeConstraints.x, minWidth + trim.width); | |
529 if (sizeConstraints.y !is SWT.DEFAULT) | |
530 height= Math.min(sizeConstraints.y, height); | |
531 } | |
532 | |
533 // Ensure minimal size | |
534 int width= Math.max(MIN_WIDTH, minWidth); | |
535 height= Math.max(MIN_HEIGHT, height); | |
536 | |
537 return new Point(width, height); | |
538 } | |
539 | |
540 /* | |
541 * @see org.eclipse.jface.text.IInformationControlExtension3#computeTrim() | |
542 */ | |
543 public Rectangle computeTrim() { | |
544 Rectangle trim= super.computeTrim(); | |
545 if (isResizable()) { | |
546 bool RTL= (getShell().getStyle() & SWT.RIGHT_TO_LEFT) !is 0; | |
547 if (RTL) { | |
548 trim.x-= fgScrollBarSize.x; | |
549 } | |
550 trim.width+= fgScrollBarSize.x; | |
551 trim.height+= fgScrollBarSize.y; | |
552 } | |
553 return trim; | |
554 } | |
555 | |
556 /** | |
557 * Adds the listener to the collection of listeners who will be | |
558 * notified when the current location has changed or is about to change. | |
559 * | |
560 * @param listener the location listener | |
561 * @since 3.4 | |
562 */ | |
563 public void addLocationListener(LocationListener listener) { | |
564 fBrowser.addLocationListener(listener); | |
565 } | |
566 | |
567 /* | |
568 * @see IInformationControl#setForegroundColor(Color) | |
569 */ | |
570 public void setForegroundColor(Color foreground) { | |
571 super.setForegroundColor(foreground); | |
572 fBrowser.setForeground(foreground); | |
573 } | |
574 | |
575 /* | |
576 * @see IInformationControl#setBackgroundColor(Color) | |
577 */ | |
578 public void setBackgroundColor(Color background) { | |
579 super.setBackgroundColor(background); | |
580 fBrowser.setBackground(background); | |
581 } | |
582 | |
583 /* | |
584 * @see IInformationControlExtension#hasContents() | |
585 */ | |
586 public bool hasContents() { | |
587 return fBrowserHasContent; | |
588 } | |
589 | |
590 /** | |
591 * Adds a listener for input changes to this input change provider. | |
592 * Has no effect if an identical listener is already registered. | |
593 * | |
594 * @param inputChangeListener the listener to add | |
595 * @since 3.4 | |
596 */ | |
597 public void addInputChangeListener(IInputChangedListener inputChangeListener) { | |
598 Assert.isNotNull(inputChangeListener); | |
599 fInputChangeListeners.add(inputChangeListener); | |
600 } | |
601 | |
602 /** | |
603 * Removes the given input change listener from this input change provider. | |
604 * Has no effect if an identical listener is not registered. | |
605 * | |
606 * @param inputChangeListener the listener to remove | |
607 * @since 3.4 | |
608 */ | |
609 public void removeInputChangeListener(IInputChangedListener inputChangeListener) { | |
610 fInputChangeListeners.remove(inputChangeListener); | |
611 } | |
612 | |
613 /* | |
614 * @see org.eclipse.jface.text.IDelayedInputChangeProvider#setDelayedInputChangeListener(org.eclipse.jface.text.IInputChangedListener) | |
615 * @since 3.4 | |
616 */ | |
617 public void setDelayedInputChangeListener(IInputChangedListener inputChangeListener) { | |
618 fDelayedInputChangeListener= inputChangeListener; | |
619 } | |
620 | |
621 /** | |
622 * Tells whether a delayed input change listener is registered. | |
623 * | |
624 * @return <code>true</code> iff a delayed input change | |
625 * listener is currently registered | |
626 * @since 3.4 | |
627 */ | |
628 public bool hasDelayedInputChangeListener() { | |
629 return fDelayedInputChangeListener !is null; | |
630 } | |
631 | |
632 /** | |
633 * Notifies listeners of a delayed input change. | |
634 * | |
635 * @param newInput the new input, or <code>null</code> to request cancellation | |
636 * @since 3.4 | |
637 */ | |
638 public void notifyDelayedInputChange(Object newInput) { | |
639 if (fDelayedInputChangeListener !is null) | |
640 fDelayedInputChangeListener.inputChanged(newInput); | |
641 } | |
642 | |
643 /* | |
644 * @see java.lang.Object#toString() | |
645 * @since 3.4 | |
646 */ | |
647 public override String toString() { | |
648 String style= (getShell().getStyle() & SWT.RESIZE) is 0 ? "fixed" : "resizeable"; //$NON-NLS-1$ //$NON-NLS-2$ | |
649 return super.toString() + " - style: " + style; //$NON-NLS-1$ | |
650 } | |
651 | |
652 /** | |
653 * @return the current browser input or <code>null</code> | |
654 */ | |
655 public BrowserInformationControlInput getInput() { | |
656 return fInput; | |
657 } | |
658 | |
659 /* | |
660 * @see org.eclipse.jface.text.IInformationControlExtension5#computeSizeConstraints(int, int) | |
661 */ | |
662 public Point computeSizeConstraints(int widthInChars, int heightInChars) { | |
663 if (fSymbolicFontName is null) | |
664 return null; | |
665 | |
666 GC gc= new GC(fBrowser); | |
667 Font font= fSymbolicFontName is null ? JFaceResources.getDialogFont() : JFaceResources.getFont(fSymbolicFontName); | |
668 gc.setFont(font); | |
669 int width= gc.getFontMetrics().getAverageCharWidth(); | |
670 int height= gc.getFontMetrics().getHeight(); | |
671 gc.dispose(); | |
672 | |
673 return new Point(widthInChars * width, heightInChars * height); | |
674 } | |
675 | |
676 } | |
677 | |
678 ++/ |