KickJava   Java API By Example, From Geeks To Geeks.

Java > Open Source Codes > org > netbeans > editor > view > spi > ViewLayoutState


1 /*
2  * The contents of this file are subject to the terms of the Common Development
3  * and Distribution License (the License). You may not use this file except in
4  * compliance with the License.
5  *
6  * You can obtain a copy of the License at http://www.netbeans.org/cddl.html
7  * or http://www.netbeans.org/cddl.txt.
8  *
9  * When distributing Covered Code, include this CDDL Header Notice in each file
10  * and include the License file at http://www.netbeans.org/cddl.txt.
11  * If applicable, add the following below the CDDL Header, with the fields
12  * enclosed by brackets [] replaced by your own identifying information:
13  * "Portions Copyrighted [year] [name of copyright owner]"
14  *
15  * The Original Software is NetBeans. The Initial Developer of the Original
16  * Software is Sun Microsystems, Inc. Portions Copyright 1997-2006 Sun
17  * Microsystems, Inc. All Rights Reserved.
18  */

19
20 package org.netbeans.editor.view.spi;
21
22 import javax.swing.text.View JavaDoc;
23
24 /**
25  * Wrapper around a view that caches computed layout information
26  * about preferred, minimum and maximum span along minor axis
27  * and the preferred span along the major axis.
28  * <br>
29  * It's primarily intended to be used for views being children
30  * of <code>GapBoxView</code> based implementations.
31  * <br>
32  * After a change occurs in the wrapped view it calls
33  * <code>getParent().preferenceChanged(this, width, height)</code>
34  * the parent view will notify the layout state by calling
35  * {@link #viewPreferenceChanged(width, height)} to mark
36  * that the cached values need to be updated.
37  * <br>
38  * At some point later the parent view calls
39  * {@link #updateLayout()} to update the layout of the child
40  * and synchronize the caching variables.
41  *
42  * <p>
43  * The layout state keeps one of the axes (either <code>View.X_AXIS</code>
44  * or <code>View.Y_AXIS</code> as the major one i.e. the children
45  * are laid out along that axis. The other axis is called minor.
46  * <br>
47  * The layout along the major axis dedicates the span
48  * equal to preferred span of the given view (wrapped by a layout state).
49  * <br>
50  * Span along minor axis is more complex and it's specific
51  * to particular implementations of {@link ViewLayoutState.Parent}.
52  *
53  * <p>
54  * It's encouraged that all the view implementations
55  * wishing to be used as children
56  * of <code>GapBoxView</code> based implementations
57  * in this framework implement this interface.
58  * <br>
59  * The benefit for the view implementing this interface
60  * is that no default wrapper object implementing
61  * this interface needs to be created which saves memory.
62  * <br>
63  * Moreover unlike the default wrapper
64  * the view can better decide which values really need to be cached
65  * and which (e.g. maximum or minimum span being equal to preferred span)
66  * do not need to be cached
67  * which can furhter eliminate certain caching variables
68  * and save additional memory.
69  * <br>
70  * Another reason is faster finding of the index value of the child view
71  * in its parent view (e.g. in preferenceChanged())
72  * which is constant time compared to logartihmic time (binary search used).
73  *
74  * @author Miloslav Metelka
75  * @version 1.00
76  */

77
78 public interface ViewLayoutState {
79     
80     /**
81      * Get the view that this layout state is wrapping.
82      * @return view that this layout state is wrapping.
83      */

84     public View JavaDoc getView();
85     
86     /**
87      * Check whether this layout state and its associated
88      * view is flyweight (there is just one immutable shared instance of it).
89      *
90      * @return true if this layout state and its associated view
91      * are flyweight or false if not.
92      */

93     public boolean isFlyweight();
94     
95     /**
96      * Get the raw index of the view (wrapped by this layout state)
97      * in its parent view.
98      * <br>
99      * Storing of the index is useful for the parent which
100      * can then find the child's index in a constant time.
101      * <br>
102      *
103      * @return raw integer index that must be post-processed
104      * by parent (if it uses gap-based storage) to become a real index.
105      * <br>
106      * Returned valud is undefined for flyweight layout states.
107      */

108     public int getViewRawIndex();
109     
110     /**
111      * Parent can set the index of the view (wrapped by this layout state)
112      * in itself.
113      * <br>
114      * This method must not be called on flyweight layout states.
115      *
116      * @param viewRawIndex raw index value. It can differ from
117      * the real index because parent could preprocess
118      * it because of possible use of a gap translation.
119      */

120     public void setViewRawIndex(int viewRawIndex);
121
122     /**
123      * Select which axis will be used as major axis by this layout state.
124      * @param majorAxis major axis either <code>View.X_AXIS</code>
125      * or <code>View.Y_AXIS</code>.
126      * @return either this layout state if this state
127      * is able to work with the given major axis
128      * or another layout state if this state is only
129      * able to work over the other major axis.
130      *
131      * <p>
132      * A view (e.g. a flyweight view)
133      * that implements this interface can decide to only allow
134      * one axis as the major one.
135      * <br>
136      * That should mostly be fine because usually the view is tiled
137      * only along one axis.
138      * <br>
139      * The view may throw <code>IllegalStateException</code>
140      * in such case.
141      */

142     public ViewLayoutState selectLayoutMajorAxis(int majorAxis);
143
144     /**
145      * Get the preferred span along major axis.
146      * <br>
147      * The value is expected to be cached for fast access.
148      *
149      * <p>
150      * If the preferred span of the wrapped view changes
151      * then the value of the major axis span must change as well
152      * typically once the next layout state update takes place.
153      * <br>
154      * The wrapped view should call <code>View.preferenceChanged</code>
155      * in its parent once its preferred span changes.
156      * The parent view will later call
157      * i.e. <code>updateLayout()</code> to update
158      * the variable holding the preferred span along major axis.
159      * <br>
160      * <code>Parent.majorAxisPreferenceChanged()</code>
161      * must be called immediately after that change
162      * to notify the parent.
163      *
164      * <p>
165      * Although the value is returned as double
166      * (see {@link #getLayoutMajorAxisOffset()})
167      * it can be maintained as float if the resolution of the float
168      * is sufficient to create proper deltas
169      * in <code>Parent#majorAxisPreferenceChanged()</code>.
170      * <br>
171      * For example if a document has millions of lines it's necessary
172      * to maintain line offsets in document view as doubles
173      * but assuming that each line is only up to several tenths of pixels high
174      * it's enough to hold line height as float in line view layout state.
175      */

176     public double getLayoutMajorAxisPreferredSpan();
177
178     /**
179      * Get the raw visual offset of the view along the parent view's
180      * major axis.
181      *
182      * <p>
183      * Double is chosen instead of float because for y as major axis
184      * the truncation could occur when computing the offset
185      * for large files with many lines or for very long lines.
186      * <br>
187      * The resolution of mantissa of floats is 23 bits
188      * so assuming the line height is e.g. 17 pixels
189      * and we have more than 250.000 lines in the docuemnt
190      * (which is a lot to write but not so much for e.g.
191      * generated xml files) the last bit would be lost
192      * resulting in every odd line being shifted one
193      * pixel above incorrectly.
194      * <br>
195      * The views can still decide to use floats for internal storage
196      * of this value if the precision is sufficient.
197      *
198      * @return raw double visual offset along major axis. It must be post-processed
199      * by parent (if it uses gap-based storage) to become a real index.
200      * <br>
201      * Returned valud is undefined for flyweight layout states.
202      */

203     public double getLayoutMajorAxisRawOffset();
204     
205     /**
206      * Parent can set the view's raw offset along the parent view's
207      * major axis using this method.
208      * <br>
209      * This method must not be called on flyweight layout states.
210      *
211      * @param layoutMajorAxisRawOffset raw offset value along the major axis.
212      * It is not particularly useful without postprocessing by the parent.
213      */

214     public void setLayoutMajorAxisRawOffset(double layoutMajorAxisRawOffset);
215     
216     /**
217      * Get the preferred span of the view along minor axis.
218      * <br>
219      * The value is expected to be cached for fast access.
220      *
221      * <p>
222      * If there is a dedicated variable for this value then
223      * that variable should be updated during {@link #updateLayout()}
224      * which usually happens some time after the view
225      * has called <code>View.preferenceChanged()</code>
226      * in the parent.
227      * <br>
228      * After the value gets updated the layout state must immediately call
229      * <code>Parent.minorAxisPreferenceChanged()</code>
230      * to notify the parent about the change of minor span.
231      */

232     public float getLayoutMinorAxisPreferredSpan();
233
234     /**
235      * Get the minimum span of the view along minor axis.
236      * <br>
237      * The value is expected to be cached for fast access.
238      * <br>
239      * By default <code>GapBoxView</code> implementations
240      * do not use the minimum span of their children
241      * so the particular layout state may decide not to cache
242      * the minimum span value and return preferred span instead
243      * to save memory that would otherwise be used for caching variables.
244      *
245      * <p>
246      * If there is a dedicated variable for this value then
247      * that variable should be updated during {@link #updateLayout()}
248      * which usually happens once the view
249      * has called <code>View.preferenceChanged()</code>
250      * in the parent.
251      * <br>
252      * After the value gets updated the layout state must immediately call
253      * <code>Parent.minorAxisPreferenceChanged()</code>
254      * to notify the parent about the change of minor span.
255      */

256     public float getLayoutMinorAxisMinimumSpan();
257
258     /**
259      * Get the maximum span of the view along minor axis.
260      * <br>
261      * The value is expected to be cached for fast access.
262      * <br>
263      * As the default <code>GapBoxView</code> implementations
264      * do not use the maximum span of their children
265      * the particular layout state may decide not to cache
266      * the maximum span value and return preferred span instead
267      * to save memory that would otherwise be used for caching variables.
268      *
269      * <p>
270      * If there is a dedicated variable for this value then
271      * that variable gets updated by {@link #updateLayout()}
272      * which usually happens once the view
273      * has called <code>View.preferenceChanged()</code>
274      * in the parent.
275      * <br>
276      * After the value gets updated the layout state must immediately call
277      * <code>Parent.minorAxisPreferenceChanged()</code>
278      * to notify the parent about the change of minor span.
279      */

280     public float getLayoutMinorAxisMaximumSpan();
281     
282     /**
283      * Get alignment along the minor axis.
284      * <br>
285      * The value is expected to be cached for fast access.
286      *
287      * <p>
288      * If there is a dedicated variable for this value then
289      * that variable gets updated by {@link #updateLayout()}
290      * which usually happens once the view
291      * has called <code>View.preferenceChanged()</code>
292      * in its parent view which in turn calls {@link #viewPreferenceChanged()}.
293      * <br>
294      * After the value gets updated the layout state must call
295      * <code>Parent.minorAxisPreferenceChanged()</code>
296      * to notify the parent about the change of minor span.
297      */

298     public float getLayoutMinorAxisAlignment();
299
300     /**
301      * Do actual layout updating.
302      * <br>
303      * The first thing to do
304      * is to see if any work actually needs to be done.
305      * <br>
306      * Certain views such as line-wrapping views may react
307      * to <code>View.setSize()</code> being called on them
308      * by changing its preferred span along an axis.
309      * For such views the actual internal updating must be done twice
310      * (because of another call to <code>parent.preferenceChanged()</code>).
311      * <br>
312      * Anyway upon exit of this method the {@link #isLayoutValid()}
313      * must return true.
314      * <br>
315      * This method must be no-op for flyweight layout states
316      * because they should have their values up-to-date since
317      * their construction without ever calling this method.
318      * <br>
319      * The view is responsible for repainting itself if that's necessary.
320      *
321      * Prior to asking the component to repaint the appropriate region
322      */

323     public void updateLayout();
324
325     /**
326      * Notify this layout state that the preferences has changed
327      * for the view that it wraps.
328      * <br>
329      * This gets called in response to the wrapped view calling
330      * <code>View.preferenceChanged()</code> in its parent.
331      * <br>
332      * Usually this method only makes sense when the layout state
333      * is a generic wrapper around a black-box view. If layout state
334      * and the view are one object then this method is usually no-op.
335      * <br>
336      * The layout state should just mark its internal state as changed
337      * but wait for layout update (that will be called by parent)
338      * to update the layout variables.
339      * <br>
340      * This method must be no-op for flyweight layout states.
341      *
342      * @param width true if the width preference has changed
343      * @param height true if the height preference has changed
344      */

345     public void viewPreferenceChanged(boolean width, boolean height);
346     
347     /**
348      * Parent calls this method to mark the current size of the view as invalid
349      * so that the next layout update of this layout state
350      * will call <code>View.setSize()</code>
351      * using {@link #getLayoutMajorAxisPreferredSpan()} for major axis span
352      * and {@link ViewLayoutState.Parent#getMinorAxisSpan(ViewLayoutState)}
353      * for minor axis span.
354      * <br>
355      * Parent is responsible for scheduling of layout update for the child
356      * after calling this method.
357      * <br>
358      * This method must be no-op for flyweight layout states.
359      */

360     public void markViewSizeInvalid();
361     
362     /**
363      * Check whether there are any layout duties present.
364      *
365      * @return true if there are no layout duties or false
366      * if the layout needs to be udpated.
367      * <br>
368      * Flyweight layout states must always return <code>true</code> here.
369      */

370     public boolean isLayoutValid();
371
372     /**
373      * Interface that the parent view of the view
374      * wrapped by <code>ViewLayoutState</code>
375      * is expected to implement.
376      */

377     public interface Parent {
378         
379         /**
380          * By using this method a child layout state notifies its parent that
381          * its requirement for span along the major axis has changed
382          * against the previous value.
383          * <br>
384          * It can be done anytime but typically during
385          * {@link #updateLayout()} execution.
386          * <br>
387          * The child will be automatically scheduled for repaint (together
388          * with all children that follow it in the parent view) after
389          * this method gets called.
390          *
391          * @param child child layout state which preference has changed.
392          * @param majorAxisSpanDelta delta between the new span and the original span.
393          */

394         public void majorAxisPreferenceChanged(ViewLayoutState child,
395         double majorAxisSpanDelta);
396         
397         /**
398          * By using this method a child layout state notifies its parent that
399          * either preferred, minimum or maximum spans or aligment
400          * along the minor axis has changed against their previous values.
401          * <br>
402          * It can be done anytime but typically during
403          * {@link #updateLayout()} execution.
404          *
405          * @param child child layout state which preference has changed.
406          */

407         public void minorAxisPreferenceChanged(ViewLayoutState child);
408         
409         /**
410          * Notify this view that layout of the particular child
411          * has become invalid and needs to be updated.
412          * <br>
413          * The parent can update the child's layout either immediately
414          * or later.
415          */

416         public void layoutInvalid(ViewLayoutState child);
417         
418         /**
419          * Get span of the given child along the minor axis.
420          * <br>
421          * Parent computes the span according to its own layout policy
422          * for the children.
423          * <br>
424          * This method is typically called from the layout state's methods
425          * and is thus useful for non-flyweight layout states only
426          * as flyweights do not maintain the parent.
427          *
428          * @param child child layout state for which the span is being
429          * determined.
430          */

431         public float getMinorAxisSpan(ViewLayoutState child);
432
433         /**
434          * Inform the parent that the child layout state needs a repaint.
435          * <br>
436          * This method can be called anytime although usually
437          * it's called during the layout state's <code>updateLayout()</code>.
438          * <br>
439          * This method can be called repetively. The lowest offsets
440          * should finally be used by the parent.
441          *
442          * @param child child that needs its area to be repainted.
443          * @param majorAxisOffset offset along the major axis defining
444          * the begining of the repaint region. If the allocation
445          * has changed along the major axis the view is fully repainted
446          * (see <code>majorAxisPreferenceChanged()</code>).
447          * <br>
448          * This parameter is typically zero but can be used
449          * e.g. for line-wrapping views when typing on the last line.
450          * @param minorAxisOffset offset along the minor axis
451          * defining the begining of the repaint region.
452          * @param majorAxisSpan span along the major axis
453          * that should be repainted. If it is set to zero then
454          * it means that the end of the repaint region along the major axis
455          * span is determined by the span allocated for the child
456          * in this parent.
457          * @param minorAxisSpan span along the minor axis
458          * that should be repainted. If it is set to zero then
459          * it means that the end of the repaint region along the minor axis
460          * span is determined by the span of this parent.
461          */

462         public void repaint(ViewLayoutState child,
463         double majorAxisOffset, double majorAxisSpan,
464         float minorAxisOffset, float minorAxisSpan);
465
466     }
467
468 }
469
Popular Tags