You are viewing a plain text version of this content. The canonical link for it is here.
Posted to commits@pivot.apache.org by gb...@apache.org on 2009/07/30 22:37:31 UTC

svn commit: r799436 - in /incubator/pivot/trunk: demos/src/org/apache/pivot/demos/dnd/ tutorials/src/org/apache/pivot/tutorials/lists/ wtk/src/org/apache/pivot/wtk/ wtk/src/org/apache/pivot/wtk/skin/terra/

Author: gbrown
Date: Thu Jul 30 20:37:30 2009
New Revision: 799436

URL: http://svn.apache.org/viewvc?rev=799436&view=rev
Log:
Preliminary work for PIVOT-197. Most functionality is implemented, but multiple selection is not currently hooked up.

Added:
    incubator/pivot/trunk/wtk/src/org/apache/pivot/wtk/ListSelection.java
    incubator/pivot/trunk/wtk/src/org/apache/pivot/wtk/ListSelectionSequence.java
Removed:
    incubator/pivot/trunk/wtk/src/org/apache/pivot/wtk/SpanSequence.java
Modified:
    incubator/pivot/trunk/demos/src/org/apache/pivot/demos/dnd/FileDropTargetDemo.java
    incubator/pivot/trunk/tutorials/src/org/apache/pivot/tutorials/lists/ListViews.java
    incubator/pivot/trunk/wtk/src/org/apache/pivot/wtk/ListView.java
    incubator/pivot/trunk/wtk/src/org/apache/pivot/wtk/Span.java
    incubator/pivot/trunk/wtk/src/org/apache/pivot/wtk/SplitPane.java
    incubator/pivot/trunk/wtk/src/org/apache/pivot/wtk/TableView.java
    incubator/pivot/trunk/wtk/src/org/apache/pivot/wtk/skin/terra/TerraSplitPaneSkin.java

Modified: incubator/pivot/trunk/demos/src/org/apache/pivot/demos/dnd/FileDropTargetDemo.java
URL: http://svn.apache.org/viewvc/incubator/pivot/trunk/demos/src/org/apache/pivot/demos/dnd/FileDropTargetDemo.java?rev=799436&r1=799435&r2=799436&view=diff
==============================================================================
--- incubator/pivot/trunk/demos/src/org/apache/pivot/demos/dnd/FileDropTargetDemo.java (original)
+++ incubator/pivot/trunk/demos/src/org/apache/pivot/demos/dnd/FileDropTargetDemo.java Thu Jul 30 20:37:30 2009
@@ -84,8 +84,8 @@
 
                     for (int i = selectedRanges.getLength() - 1; i >= 0; i--) {
                         Span range = selectedRanges.get(i);
-                        int index = range.getStart();
-                        int count = range.getEnd() - index + 1;
+                        int index = range.start;
+                        int count = range.end - index + 1;
                         fileList.remove(index, count);
                     }
                 }

Modified: incubator/pivot/trunk/tutorials/src/org/apache/pivot/tutorials/lists/ListViews.java
URL: http://svn.apache.org/viewvc/incubator/pivot/trunk/tutorials/src/org/apache/pivot/tutorials/lists/ListViews.java?rev=799436&r1=799435&r2=799436&view=diff
==============================================================================
--- incubator/pivot/trunk/tutorials/src/org/apache/pivot/tutorials/lists/ListViews.java (original)
+++ incubator/pivot/trunk/tutorials/src/org/apache/pivot/tutorials/lists/ListViews.java Thu Jul 30 20:37:30 2009
@@ -54,8 +54,8 @@
             for (int i = 0, n = selectedRanges.getLength(); i < n; i++) {
                 Span selectedRange = selectedRanges.get(i);
 
-                for (int j = selectedRange.getStart();
-                    j <= selectedRange.getEnd();
+                for (int j = selectedRange.start;
+                    j <= selectedRange.end;
                     j++) {
                     if (selectionText.length() > 0) {
                         selectionText += ", ";

Added: incubator/pivot/trunk/wtk/src/org/apache/pivot/wtk/ListSelection.java
URL: http://svn.apache.org/viewvc/incubator/pivot/trunk/wtk/src/org/apache/pivot/wtk/ListSelection.java?rev=799436&view=auto
==============================================================================
--- incubator/pivot/trunk/wtk/src/org/apache/pivot/wtk/ListSelection.java (added)
+++ incubator/pivot/trunk/wtk/src/org/apache/pivot/wtk/ListSelection.java Thu Jul 30 20:37:30 2009
@@ -0,0 +1,230 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one or more
+ * contributor license agreements.  See the NOTICE file distributed with
+ * this work for additional information regarding copyright ownership.
+ * The ASF licenses this file to you under the Apache License,
+ * Version 2.0 (the "License"); you may not use this file except in
+ * compliance with the License.  You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+package org.apache.pivot.wtk;
+
+import java.util.Comparator;
+
+import org.apache.pivot.collections.ArrayList;
+import org.apache.pivot.collections.Sequence;
+
+/**
+ * Class for managing a set of indexed range selections.
+ *
+ * @author gbrown
+ */
+class ListSelection {
+    /**
+     * Determines the relative order of two ranges.
+     *
+     * @author gbrown
+     */
+    public static class IntersectionComparator implements Comparator<Span> {
+        /**
+         * Compares two range values. A range is considered less than or greater
+         * than another range if and only if it is absolutely less than or
+         * greater than the other range; if the ranges overlap in any way,
+         * they are considered equal.
+         *
+         * @return
+         * A positive value if <tt>range1</tt> is greater than <tt>range2</tt>;
+         * a negative value if <tt>range1</tt> is less than <tt>range2</tt>; a
+         * value of zero if <tt>range1</tt> intersects with <tt>range2</tt>.
+         */
+        public int compare(Span range1, Span range2) {
+            return (range1.start > range2.end) ? 1 : (range2.start > range1.end) ? -1 : 0;
+        }
+    }
+
+    private ArrayList<Span> selectedRanges = new ArrayList<Span>();
+
+    public static final IntersectionComparator INTERSECTION_COMPARATOR = new IntersectionComparator();
+
+    /**
+     * Adds a range to the selection, merging and removing intersecting ranges
+     * as needed.
+     *
+     * @param start
+     * @param end
+     *
+     * @return
+     * A sequence containing the ranges that were added.
+     */
+    public Sequence<Span> addRange(int start, int end) {
+        ArrayList<Span> added = new ArrayList<Span>();
+
+        Span range = normalize(start, end);
+
+        if (range.getLength() > 0) {
+            int n = selectedRanges.getLength();
+
+            if (n == 0) {
+                // Nothing is currently selected
+                selectedRanges.add(range);
+                added.add(range);
+            } else {
+                // TODO
+            }
+        }
+
+        return added;
+    }
+
+    /**
+     * Removes a range from the selection, truncating and removing intersecting
+     * ranges as needed.
+     *
+     * @param start
+     * @param end
+     *
+     * @return
+     * A sequence containing the ranges that were removed.
+     */
+    public Sequence<Span> removeRange(int start, int end) {
+        ArrayList<Span> removed = new ArrayList<Span>();
+
+        Span range = normalize(start, end);
+
+        if (range.getLength() > 0
+            && selectedRanges.getLength() > 0) {
+            // TODO
+        }
+
+        return removed;
+    }
+
+    public void clear() {
+        selectedRanges.clear();
+    }
+
+    /**
+     * Returns the range at a given index.
+     *
+     * @param index
+     */
+    public Span get(int index) {
+        return selectedRanges.get(index);
+    }
+
+    /**
+     * Returns the number of ranges in the selection.
+     */
+    public int getLength() {
+        return selectedRanges.getLength();
+    }
+
+    /**
+     * Determines the index of a range in the selection.
+     *
+     * @param range
+     *
+     * @return
+     * The index of the range, if it exists in the selection in its entirety;
+     * <tt>-1</tt>, otherwise.
+     */
+    public int indexOf(Span range) {
+        assert (range != null);
+
+        int index = -1;
+        int i = ArrayList.binarySearch(selectedRanges, range, INTERSECTION_COMPARATOR);
+
+        if (i >= 0) {
+            index = (range.equals(selectedRanges.get(i))) ? i : -1;
+        }
+
+        return index;
+    }
+
+    /**
+     * Tests for the presence of an index in the selection.
+     *
+     * @param index
+     *
+     * @return
+     * <tt>true</tt> if the index is selected; <tt>false</tt>, otherwise.
+     */
+    public boolean containsIndex(int index) {
+        return (indexOf(new Span(index, index)) != -1);
+    }
+
+    /**
+     * Inserts an index into the span sequence (e.g. when items are inserted
+     * into the model data).
+     *
+     * @param index
+     */
+    public void insertIndex(int index) {
+        // Get the insertion point for the range corresponding to the given index
+        Span range = new Span(index, index);
+        int i = indexOf(range);
+
+        if (i < 0) {
+            // The inserted item does not intersect with a selected range
+            i = -(i + 1);
+        } else {
+            // The inserted item intersects with a currently selected range
+            Span selectedRange = selectedRanges.get(i);
+
+            // If the ranges' start values are equal, shift the selection;
+            // otherwise, insert the index into the selection
+            if (selectedRange.start > range.start) {
+                selectedRanges.update(i, new Span(selectedRange.start, selectedRange.end + 1));
+
+                // Start incrementing range bounds beginning at the next range index
+                i++;
+            }
+        }
+
+        // Increment any subsequent selection indexes
+        int n = selectedRanges.getLength();
+        while (i < n) {
+            Span selectedRange = selectedRanges.get(i);
+            selectedRanges.update(i, new Span(selectedRange.start + 1, selectedRange.end + 1));
+            i++;
+        }
+    }
+
+    /**
+     * Removes a range of indexes from the span sequence (e.g. when items
+     * are removed from the model data).
+     *
+     * @param index
+     * @param count
+     */
+    public void removeIndexes(int index, int count) {
+        // Clear any selections in the given range
+        removeRange(index, (index + count) - 1);
+
+        // Decrement any subsequent selection indexes
+        Span range = new Span(index, index);
+        int i = indexOf(range);
+        assert (i < 0) : "i should be negative, since index should no longer be selected";
+
+        i = -(i + 1);
+
+        // Determine the number of ranges to modify
+        int n = selectedRanges.getLength();
+        while (i < n) {
+            Span selectedRange = selectedRanges.get(i);
+            selectedRanges.update(i, new Span(selectedRange.start - count, selectedRange.end - count));
+            i++;
+        }
+    }
+
+    public static Span normalize(int start, int end) {
+        return new Span(Math.min(start, end), Math.max(start, end));
+    }
+}

Added: incubator/pivot/trunk/wtk/src/org/apache/pivot/wtk/ListSelectionSequence.java
URL: http://svn.apache.org/viewvc/incubator/pivot/trunk/wtk/src/org/apache/pivot/wtk/ListSelectionSequence.java?rev=799436&view=auto
==============================================================================
--- incubator/pivot/trunk/wtk/src/org/apache/pivot/wtk/ListSelectionSequence.java (added)
+++ incubator/pivot/trunk/wtk/src/org/apache/pivot/wtk/ListSelectionSequence.java Thu Jul 30 20:37:30 2009
@@ -0,0 +1,64 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one or more
+ * contributor license agreements.  See the NOTICE file distributed with
+ * this work for additional information regarding copyright ownership.
+ * The ASF licenses this file to you under the Apache License,
+ * Version 2.0 (the "License"); you may not use this file except in
+ * compliance with the License.  You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+package org.apache.pivot.wtk;
+
+import org.apache.pivot.collections.Sequence;
+
+/**
+ * Exposes the contents of a {@link ListSelection} as a sequence.
+ *
+ * @author gbrown
+ */
+class ListSelectionSequence implements Sequence<Span> {
+    private ListSelection listSelection;
+
+    public ListSelectionSequence(ListSelection listSelection) {
+        this.listSelection = listSelection;
+    }
+
+    public int add(Span span) {
+        throw new UnsupportedOperationException();
+    }
+
+    public void insert(Span span, int index) {
+        throw new UnsupportedOperationException();
+    }
+
+    public Span update(int index, Span span) {
+        throw new UnsupportedOperationException();
+    }
+
+    public int remove(Span span) {
+        throw new UnsupportedOperationException();
+    }
+
+    public Sequence<Span> remove(int index, int count) {
+        throw new UnsupportedOperationException();
+    }
+
+    public Span get(int index) {
+        return listSelection.get(index);
+    }
+
+    public int indexOf(Span span) {
+        return listSelection.indexOf(span);
+    }
+
+    public int getLength() {
+        return listSelection.getLength();
+    }
+}

Modified: incubator/pivot/trunk/wtk/src/org/apache/pivot/wtk/ListView.java
URL: http://svn.apache.org/viewvc/incubator/pivot/trunk/wtk/src/org/apache/pivot/wtk/ListView.java?rev=799436&r1=799435&r2=799436&view=diff
==============================================================================
--- incubator/pivot/trunk/wtk/src/org/apache/pivot/wtk/ListView.java (original)
+++ incubator/pivot/trunk/wtk/src/org/apache/pivot/wtk/ListView.java Thu Jul 30 20:37:30 2009
@@ -263,7 +263,7 @@
     private ListListener<Object> listDataListener = new ListListener<Object>() {
         public void itemInserted(List<Object> list, int index) {
             // Increment selected ranges
-            selectedRanges.insertIndex(index);
+            listSelection.insertIndex(index);
 
             int i, n;
 
@@ -287,7 +287,7 @@
             int count = items.getLength();
 
             // Decrement selected ranges
-            selectedRanges.removeIndexes(index, count);
+            listSelection.removeIndexes(index, count);
 
             int i, n;
 
@@ -314,7 +314,7 @@
         public void listCleared(List<Object> list) {
             // All items were removed; clear the selection and notify
             // listeners
-            selectedRanges.clear();
+            listSelection.clear();
             checkedIndexes.clear();
 
             listViewItemListeners.itemsCleared(ListView.this);
@@ -323,7 +323,7 @@
         public void comparatorChanged(List<Object> list,
             Comparator<Object> previousComparator) {
             if (list.getComparator() != null) {
-                selectedRanges.clear();
+                listSelection.clear();
                 checkedIndexes.clear();
 
                 listViewItemListeners.itemsSorted(ListView.this);
@@ -334,7 +334,7 @@
     private ItemRenderer itemRenderer = null;
     private ItemEditor itemEditor = null;
 
-    private SpanSequence selectedRanges = new SpanSequence();
+    private ListSelection listSelection = new ListSelection();
     private SelectMode selectMode = SelectMode.SINGLE;
 
     private boolean checkmarksEnabled = false;
@@ -400,7 +400,7 @@
         if (previousListData != listData) {
             if (previousListData != null) {
                 // Clear any existing selection
-                selectedRanges.clear();
+                listSelection.clear();
                 checkedIndexes.clear();
 
                 ((List<Object>)previousListData).getListListeners().remove(listDataListener);
@@ -504,7 +504,7 @@
             throw new IllegalStateException("List view is not in single-select mode.");
         }
 
-        return (selectedRanges.getLength() == 0) ? -1 : selectedRanges.get(0).getStart();
+        return (listSelection.getLength() == 0) ? -1 : listSelection.get(0).start;
     }
 
     /**
@@ -527,20 +527,12 @@
      * Returns the list's current selection.
      */
     public Sequence<Span> getSelectedRanges() {
-        // Return a copy of the selection list (including copies of the
-        // list contents)
-        ArrayList<Span> selection = new ArrayList<Span>();
-
-        for (int i = 0, n = selectedRanges.getLength(); i < n; i++) {
-            selection.add(new Span(selectedRanges.get(i)));
-        }
-
-        return selection;
+        return new ListSelectionSequence(listSelection);
     }
 
     /**
-     * Sets the selection to the given span sequence. Any overlapping or
-     * connecting spans will be consolidated, and the resulting selection will
+     * Sets the selection to the given range sequence. Any overlapping or
+     * connecting ranges will be consolidated, and the resulting selection will
      * be sorted in ascending order.
      *
      * @param selectedRanges
@@ -571,8 +563,9 @@
         }
 
         // Update the selection
-        SpanSequence ranges = new SpanSequence();
+        ListSelectionSequence previousSelectedRanges = new ListSelectionSequence(listSelection);
 
+        ListSelection listSelection = new ListSelection();
         for (int i = 0, n = selectedRanges.getLength(); i < n; i++) {
             Span range = selectedRanges.get(i);
 
@@ -580,15 +573,14 @@
                 throw new IllegalArgumentException("range is null.");
             }
 
-            if (range.getStart() < 0 || range.getEnd() >= listData.getLength()) {
+            if (range.start < 0 || range.end >= listData.getLength()) {
                 throw new IndexOutOfBoundsException();
             }
 
-            ranges.add(range);
+            listSelection.addRange(range.start, range.end);
         }
 
-        SpanSequence previousSelectedRanges = this.selectedRanges;
-        this.selectedRanges = ranges;
+        this.listSelection = listSelection;
 
         // Notify listeners
         listViewSelectionListeners.selectedRangesChanged(this, previousSelectedRanges);
@@ -601,8 +593,7 @@
      * The first selected index, or <tt>-1</tt> if nothing is selected.
      */
     public int getFirstSelectedIndex() {
-        return (selectedRanges.getLength() > 0) ?
-            selectedRanges.get(0).getStart() : -1;
+        return (listSelection.getLength() > 0) ? listSelection.get(0).start : -1;
     }
 
     /**
@@ -612,8 +603,8 @@
      * The last selected index, or <tt>-1</tt> if nothing is selected.
      */
     public int getLastSelectedIndex() {
-        return (selectedRanges.getLength() > 0) ?
-            selectedRanges.get(selectedRanges.getLength() - 1).getEnd() : -1;
+        return (listSelection.getLength() > 0) ?
+            listSelection.get(listSelection.getLength() - 1).end : -1;
     }
 
     /**
@@ -629,14 +620,27 @@
     /**
      * Adds a range of indexes to the selection.
      *
-     * @param rangeStart
+     * @param start
      * The first index in the range.
      *
-     * @param rangeEnd
+     * @param end
      * The last index in the range.
      */
-    public void addSelectedRange(int rangeStart, int rangeEnd) {
-        addSelectedRange(new Span(rangeStart, rangeEnd));
+    public void addSelectedRange(int start, int end) {
+        if (selectMode != SelectMode.MULTI) {
+            throw new IllegalStateException("List view is not in multi-select mode.");
+        }
+
+        if (start < 0 || end >= listData.getLength()) {
+            throw new IndexOutOfBoundsException();
+        }
+
+        Sequence<Span> added = listSelection.addRange(start, end);
+
+        for (int i = 0, n = added.getLength(); i < n; i++) {
+            Span addedRange = added.get(i);
+            listViewSelectionListeners.selectedRangeAdded(this, addedRange.start, addedRange.end);
+        }
     }
 
     /**
@@ -646,22 +650,11 @@
      * The range to add.
      */
     public void addSelectedRange(Span range) {
-        if (selectMode != SelectMode.MULTI) {
-            throw new IllegalStateException("List view is not in multi-select mode.");
-        }
-
         if (range == null) {
             throw new IllegalArgumentException("range is null.");
         }
 
-        if (range.getStart() < 0 || range.getEnd() >= listData.getLength()) {
-            throw new IndexOutOfBoundsException();
-        }
-
-        selectedRanges.add(range);
-
-        listViewSelectionListeners.selectedRangeAdded(this, range.getStart(),
-            range.getEnd());
+        addSelectedRange(range.start, range.end);
     }
 
     /**
@@ -677,14 +670,27 @@
     /**
      * Removes a range of indexes from the selection.
      *
-     * @param rangeStart
+     * @param start
      * The start of the range to remove.
      *
-     * @param rangeEnd
+     * @param end
      * The end of the range to remove.
      */
-    public void removeSelectedRange(int rangeStart, int rangeEnd) {
-        removeSelectedRange(new Span(rangeStart, rangeEnd));
+    public void removeSelectedRange(int start, int end) {
+        if (selectMode != SelectMode.MULTI) {
+            throw new IllegalStateException("List view is not in multi-select mode.");
+        }
+
+        if (start < 0 || end >= listData.getLength()) {
+            throw new IndexOutOfBoundsException();
+        }
+
+        Sequence<Span> removed = listSelection.removeRange(start, end);
+
+        for (int i = 0, n = removed.getLength(); i < n; i++) {
+            Span removedRange = removed.get(i);
+            listViewSelectionListeners.selectedRangeRemoved(this, removedRange.start, removedRange.end);
+        }
     }
 
     /**
@@ -694,34 +700,23 @@
      * The range to remove.
      */
     public void removeSelectedRange(Span range) {
-        if (selectMode != SelectMode.MULTI) {
-            throw new IllegalStateException("List view is not in multi-select mode.");
-        }
-
         if (range == null) {
             throw new IllegalArgumentException("range is null.");
         }
 
-        if (range.getStart() < 0 || range.getEnd() >= listData.getLength()) {
-            throw new IndexOutOfBoundsException();
-        }
-
-        selectedRanges.remove(range);
-
-        listViewSelectionListeners.selectedRangeRemoved(this, range.getStart(),
-            range.getEnd());
+        removeSelectedRange(range.start, range.end);
     }
 
     /**
      * Clears the selection.
      */
     public void clearSelection() {
-        if (selectedRanges.getLength() > 0) {
-            SpanSequence previousSelectedSpans = this.selectedRanges;
-            selectedRanges = new SpanSequence();
+        if (listSelection.getLength() > 0) {
+            Sequence<Span> previousSelectedRanges = new ListSelectionSequence(listSelection);
+            listSelection = new ListSelection();
 
             listViewSelectionListeners.selectedRangesChanged(this,
-                previousSelectedSpans);
+                previousSelectedRanges);
         }
     }
 
@@ -735,56 +730,11 @@
      * otherwise.
      */
     public boolean isItemSelected(int index) {
-        return isRangeSelected(index, index);
-    }
-
-    /**
-     * Returns the selection state of a given range.
-     *
-     * @param rangeStart
-     * The first index in the range.
-     *
-     * @param rangeEnd
-     * The last index in the range.
-     *
-     * @return <tt>true</tt> if the entire range is selected; <tt>false</tt>,
-     * otherwise.
-     */
-    public boolean isRangeSelected(int rangeStart, int rangeEnd) {
-        return isRangeSelected(new Span(rangeStart, rangeEnd));
-    }
-
-    /**
-     * Returns the selection state of a given range.
-     *
-     * @param range
-     * The range whose selection state is to be tested.
-     *
-     * @return <tt>true</tt> if the entire range is selected; <tt>false</tt>,
-     * otherwise.
-     */
-    public boolean isRangeSelected(Span range) {
-        boolean selected = false;
-
-        if (range == null) {
-            throw new IllegalArgumentException("range is null.");
-        }
-
-        if (range.getStart() < 0 || range.getEnd() >= listData.getLength()) {
+        if (index < 0 || index >= listData.getLength()) {
             throw new IndexOutOfBoundsException();
         }
 
-        // Locate the span in the selection
-        int i = selectedRanges.indexOf(range);
-
-        // If the selected span contains the given span, it is considered
-        // selected
-        if (i >= 0) {
-            Span selectedSpan = selectedRanges.get(i);
-            selected = selectedSpan.contains(range);
-        }
-
-        return selected;
+        return (listSelection.containsIndex(index));
     }
 
     public Object getSelectedItem() {
@@ -815,10 +765,10 @@
     public Sequence<Object> getSelectedItems() {
         ArrayList<Object> items = new ArrayList<Object>();
 
-        for (int i = 0, n = selectedRanges.getLength(); i < n; i++) {
-            Span span = selectedRanges.get(i);
+        for (int i = 0, n = listSelection.getLength(); i < n; i++) {
+            Span range = listSelection.get(i);
 
-            for (int index = span.getStart(), end = span.getEnd(); index <= end; index++) {
+            for (int index = range.start; index <= range.end; index++) {
                 Object item = listData.get(index);
                 items.add(item);
             }
@@ -871,7 +821,7 @@
 
         if (previousSelectMode != selectMode) {
             // Clear any current selection
-            selectedRanges = new SpanSequence();
+            listSelection = new ListSelection();
 
             // Update the selection mode
             this.selectMode = selectMode;

Modified: incubator/pivot/trunk/wtk/src/org/apache/pivot/wtk/Span.java
URL: http://svn.apache.org/viewvc/incubator/pivot/trunk/wtk/src/org/apache/pivot/wtk/Span.java?rev=799436&r1=799435&r2=799436&view=diff
==============================================================================
--- incubator/pivot/trunk/wtk/src/org/apache/pivot/wtk/Span.java (original)
+++ incubator/pivot/trunk/wtk/src/org/apache/pivot/wtk/Span.java Thu Jul 30 20:37:30 2009
@@ -20,20 +20,31 @@
 
 /**
  * Class representing a range of integer values. The range includes all
- * values in the interval <i>[start, end]</i>. Values may be negative, but the
- * value of <tt>start</tt> must be less than or equal to the value of
+ * values in the interval <i>[start, end]</i>. Values may be negative, and the
+ * value of <tt>start</tt> may be less than or equal to the value of
  * <tt>end</tt>.
  *
  * @author gbrown
  */
-public class Span {
-    private int start = 0;
-    private int end = 0;
+public final class Span {
+    public final int start;
+    public final int end;
 
     public static final String START_KEY = "start";
     public static final String END_KEY = "end";
 
-    public Span() {
+    public Span(int start, int end) {
+        this.start = start;
+        this.end = end;
+    }
+
+    public Span(Span span) {
+        if (span == null) {
+            throw new IllegalArgumentException("span is null.");
+        }
+
+        start = span.start;
+        end = span.end;
     }
 
     public Span(Dictionary<String, ?> span) {
@@ -49,85 +60,18 @@
             throw new IllegalArgumentException(END_KEY + " is required.");
         }
 
-        setRange((Integer)span.get(START_KEY), (Integer)span.get(END_KEY));
-    }
-
-    public Span(Span span) {
-        if (span == null) {
-            throw new IllegalArgumentException("span is null.");
-        }
-
-        setRange(span.start, span.end);
-    }
-
-    public Span(int start, int end) {
-        setRange(start, end);
-    }
-
-    /**
-     * Returns the first value in the span.
-     */
-    public int getStart() {
-        return start;
-    }
-
-    /**
-     * Sets the first value in the span.
-     *
-     * @param start
-     * The first value in the span. Must be less than or equal to
-     * the end value.
-     */
-    public void setStart(int start) {
-        setRange(start, end);
-    }
-
-    /**
-     * Returns the last value in the span.
-     */
-    public int getEnd() {
-        return end;
-    }
-
-    /**
-     * Sets the last value in the span.
-     *
-     * @param end
-     * The last value in the span. Must be greater than or equal to
-     * the start value.
-     */
-    public void setEnd(int end) {
-        setRange(start, end);
+        start = (Integer)span.get(START_KEY);
+        end = (Integer)span.get(END_KEY);
     }
 
     /**
      * Returns the length of the span.
      *
      * @return
-     * The length of the span (<tt>end</tt> minus <tt>start</tt> + 1).
+     * The absolute value of (<tt>end</tt> minus <tt>start</tt>) + 1.
      */
     public long getLength() {
-        return (end - start) + 1;
-    }
-
-    /**
-     * Sets the range of the span.
-     *
-     * @param start
-     * The first value in the span. Must be less than or equal to
-     * <tt>end</tt>.
-     *
-     * @param end
-     * The last value in the span. Must be greater than or equal to
-     * <tt>start</tt>.
-     */
-    public void setRange(int start, int end) {
-        if (start > end) {
-            throw new IllegalArgumentException("start is greater than end.");
-        }
-
-        this.start = start;
-        this.end = end;
+        return Math.abs(end - start) + 1;
     }
 
     /**
@@ -169,7 +113,7 @@
     }
 
     /**
-     * Determines the intersection of this span and another span.
+     * Calculates the intersection of this span and another span.
      *
      * @param span
      * The span to intersect with this span.
@@ -178,7 +122,7 @@
      * A new Span instance representing the intersection of this span and
      * <tt>span</tt>, or null if the spans do not intersect.
      */
-    public Span createIntersection(Span span) {
+    public Span intersect(Span span) {
         if (span == null) {
             throw new IllegalArgumentException("span is null.");
         }
@@ -194,7 +138,7 @@
     }
 
     /**
-     * Determines the union of this span and another span.
+     * Calculates the union of this span and another span.
      *
      * @param span
      * The span to union with this span.
@@ -203,7 +147,7 @@
      * A new Span instance representing the union of this span and
      * <tt>span</tt>.
      */
-    public Span createUnion(Span span) {
+    public Span union(Span span) {
         if (span == null) {
             throw new IllegalArgumentException("span is null.");
         }

Modified: incubator/pivot/trunk/wtk/src/org/apache/pivot/wtk/SplitPane.java
URL: http://svn.apache.org/viewvc/incubator/pivot/trunk/wtk/src/org/apache/pivot/wtk/SplitPane.java?rev=799436&r1=799435&r2=799436&view=diff
==============================================================================
--- incubator/pivot/trunk/wtk/src/org/apache/pivot/wtk/SplitPane.java (original)
+++ incubator/pivot/trunk/wtk/src/org/apache/pivot/wtk/SplitPane.java Thu Jul 30 20:37:30 2009
@@ -271,33 +271,22 @@
     }
 
     public void setSplitBounds(Span splitBounds) {
-        // Check if this is a no-op.
-        if (this.splitBounds == null) {
-           if (splitBounds == null) {
-              return;
-           }
-        } else {
-           if (this.splitBounds.equals(splitBounds)) {
-              return;
-           }
-        }
+        Span previousSplitBounds = this.splitBounds;
 
-        int start = splitBounds.getStart();
-        int end = splitBounds.getEnd();
+        if (previousSplitBounds != splitBounds) {
+            this.splitBounds = new Span(splitBounds);
 
-        Span previousSplitBounds = this.splitBounds;
-        this.splitBounds = new Span(start, end);
+            // Reposition the splitter if necessary
+            if (splitBounds != null) {
+               if (splitLocation < splitBounds.start) {
+                  setSplitLocation(splitBounds.start);
+               } else if (splitLocation > splitBounds.end) {
+                  setSplitLocation(splitBounds.end);
+               }
+            }
 
-        // Reposition the splitter if necessary.
-        if (splitBounds != null) {
-           if (splitLocation < start) {
-              setSplitLocation(start);
-           } else if (splitLocation > end) {
-              setSplitLocation(end);
-           }
+            splitPaneListeners.splitBoundsChanged(this, previousSplitBounds);
         }
-
-        splitPaneListeners.splitBoundsChanged(this, previousSplitBounds);
     }
 
     public final void setSplitBounds(Dictionary<String, ?> splitBounds) {

Modified: incubator/pivot/trunk/wtk/src/org/apache/pivot/wtk/TableView.java
URL: http://svn.apache.org/viewvc/incubator/pivot/trunk/wtk/src/org/apache/pivot/wtk/TableView.java?rev=799436&r1=799435&r2=799436&view=diff
==============================================================================
--- incubator/pivot/trunk/wtk/src/org/apache/pivot/wtk/TableView.java (original)
+++ incubator/pivot/trunk/wtk/src/org/apache/pivot/wtk/TableView.java Thu Jul 30 20:37:30 2009
@@ -778,10 +778,10 @@
     private ColumnSequence columnSequence = new ColumnSequence();
 
     private List<?> tableData = null;
-    private ListListener<Object> tableDataListener =     new ListListener<Object>() {
+    private ListListener<Object> tableDataListener = new ListListener<Object>() {
         public void itemInserted(List<Object> list, int index) {
             // Increment selected ranges
-            selectedRanges.insertIndex(index);
+            tableSelection.insertIndex(index);
 
             // Notify listeners that items were inserted
             tableViewRowListeners.rowInserted(TableView.this, index);
@@ -791,7 +791,7 @@
             int count = items.getLength();
 
             // Decrement selected ranges
-            selectedRanges.removeIndexes(index, count);
+            tableSelection.removeIndexes(index, count);
 
             // Notify listeners that items were removed
             tableViewRowListeners.rowsRemoved(TableView.this, index, count);
@@ -804,7 +804,7 @@
         public void listCleared(List<Object> list) {
             // All items were removed; clear the selection and notify
             // listeners
-            selectedRanges.clear();
+            tableSelection.clear();
 
             tableViewRowListeners.rowsCleared(TableView.this);
         }
@@ -812,14 +812,14 @@
         public void comparatorChanged(List<Object> list,
             Comparator<Object> previousComparator) {
             if (list.getComparator() != null) {
-                selectedRanges.clear();
+                tableSelection.clear();
 
                 tableViewRowListeners.rowsSorted(TableView.this);
             }
         }
     };
 
-    private SpanSequence selectedRanges = new SpanSequence();
+    private ListSelection tableSelection = new ListSelection();
     private SelectMode selectMode = SelectMode.SINGLE;
 
     private Filter<?> disabledRowFilter = null;
@@ -963,7 +963,7 @@
             throw new IllegalStateException("Table view is not in single-select mode.");
         }
 
-        return (selectedRanges.getLength() == 0) ? -1 : selectedRanges.get(0).getStart();
+        return (tableSelection.getLength() == 0) ? -1 : tableSelection.get(0).start;
     }
 
     /**
@@ -986,20 +986,12 @@
      * Returns the table's current selection.
      */
     public Sequence<Span> getSelectedRanges() {
-        // Return a copy of the selection list (including copies of the
-        // list contents)
-        ArrayList<Span> selectedRanges = new ArrayList<Span>();
-
-        for (int i = 0, n = this.selectedRanges.getLength(); i < n; i++) {
-            selectedRanges.add(new Span(this.selectedRanges.get(i)));
-        }
-
-        return selectedRanges;
+        return new ListSelectionSequence(tableSelection);
     }
 
     /**
-     * Sets the selection to the given span sequence. Any overlapping or
-     * connecting spans will be consolidated, and the resulting selection will
+     * Sets the selection to the given range sequence. Any overlapping or
+     * connecting ranges will be consolidated, and the resulting selection will
      * be sorted in ascending order.
      *
      * @param selectedRanges
@@ -1031,8 +1023,9 @@
         }
 
         // Update the selection
-        SpanSequence ranges = new SpanSequence();
+        ListSelectionSequence previousSelectedRanges = new ListSelectionSequence(tableSelection);
 
+        ListSelection tableSelection = new ListSelection();
         for (int i = 0, n = selectedRanges.getLength(); i < n; i++) {
             Span range = selectedRanges.get(i);
 
@@ -1040,15 +1033,14 @@
                 throw new IllegalArgumentException("range is null.");
             }
 
-            if (range.getStart() < 0 || range.getEnd() >= tableData.getLength()) {
+            if (range.start < 0 || range.end >= tableData.getLength()) {
                 throw new IndexOutOfBoundsException();
             }
 
-            ranges.add(range);
+            tableSelection.addRange(range.start, range.end);
         }
 
-        SpanSequence previousSelectedRanges = this.selectedRanges;
-        this.selectedRanges = ranges;
+        this.tableSelection = tableSelection;
 
         // Notify listeners
         tableViewSelectionListeners.selectedRangesChanged(this, previousSelectedRanges);
@@ -1061,8 +1053,7 @@
      * The first selected index, or <tt>-1</tt> if nothing is selected.
      */
     public int getFirstSelectedIndex() {
-        return (selectedRanges.getLength() > 0) ?
-            selectedRanges.get(0).getStart() : -1;
+        return (tableSelection.getLength() > 0) ? tableSelection.get(0).start : -1;
     }
 
     /**
@@ -1072,8 +1063,8 @@
      * The last selected index, or <tt>-1</tt> if nothing is selected.
      */
     public int getLastSelectedIndex() {
-        return (selectedRanges.getLength() > 0) ?
-            selectedRanges.get(selectedRanges.getLength() - 1).getEnd() : -1;
+        return (tableSelection.getLength() > 0) ?
+            tableSelection.get(tableSelection.getLength() - 1).end : -1;
     }
 
     /**
@@ -1089,14 +1080,27 @@
     /**
      * Adds a range of indexes to the selection.
      *
-     * @param rangeStart
+     * @param start
      * The first index in the range.
      *
-     * @param rangeEnd
+     * @param end
      * The last index in the range.
      */
-    public void addSelectedRange(int rangeStart, int rangeEnd) {
-        addSelectedRange(new Span(rangeStart, rangeEnd));
+    public void addSelectedRange(int start, int end) {
+        if (selectMode != SelectMode.MULTI) {
+            throw new IllegalStateException("Table view is not in multi-select mode.");
+        }
+
+        if (start < 0 || end >= tableData.getLength()) {
+            throw new IndexOutOfBoundsException();
+        }
+
+        Sequence<Span> added = tableSelection.addRange(start, end);
+
+        for (int i = 0, n = added.getLength(); i < n; i++) {
+            Span addedRange = added.get(i);
+            tableViewSelectionListeners.selectedRangeAdded(this, addedRange.start, addedRange.end);
+        }
     }
 
     /**
@@ -1106,22 +1110,11 @@
      * The range to add.
      */
     public void addSelectedRange(Span range) {
-        if (selectMode != SelectMode.MULTI) {
-            throw new IllegalStateException("Table view is not in multi-select mode.");
-        }
-
         if (range == null) {
             throw new IllegalArgumentException("range is null.");
         }
 
-        if (range.getStart() < 0 || range.getEnd() >= tableData.getLength()) {
-            throw new IndexOutOfBoundsException();
-        }
-
-        selectedRanges.add(range);
-
-        tableViewSelectionListeners.selectedRangeAdded(this, range.getStart(),
-            range.getEnd());
+        addSelectedRange(range.start, range.end);
     }
 
     /**
@@ -1137,14 +1130,27 @@
     /**
      * Removes a range of indexes from the selection.
      *
-     * @param rangeStart
+     * @param start
      * The start of the range to remove.
      *
-     * @param rangeEnd
+     * @param end
      * The end of the range to remove.
      */
-    public void removeSelectedRange(int rangeStart, int rangeEnd) {
-        removeSelectedRange(new Span(rangeStart, rangeEnd));
+    public void removeSelectedRange(int start, int end) {
+        if (selectMode != SelectMode.MULTI) {
+            throw new IllegalStateException("Table view is not in multi-select mode.");
+        }
+
+        if (start < 0 || end >= tableData.getLength()) {
+            throw new IndexOutOfBoundsException();
+        }
+
+        Sequence<Span> removed = tableSelection.removeRange(start, end);
+
+        for (int i = 0, n = removed.getLength(); i < n; i++) {
+            Span removedRange = removed.get(i);
+            tableViewSelectionListeners.selectedRangeRemoved(this, removedRange.start, removedRange.end);
+        }
     }
 
     /**
@@ -1154,33 +1160,23 @@
      * The range to remove.
      */
     public void removeSelectedRange(Span range) {
-        if (selectMode != SelectMode.MULTI) {
-            throw new IllegalStateException("Table view is not in multi-select mode.");
-        }
-
         if (range == null) {
             throw new IllegalArgumentException("range is null.");
         }
 
-        if (range.getStart() < 0 || range.getEnd() >= tableData.getLength()) {
-            throw new IndexOutOfBoundsException();
-        }
-
-        selectedRanges.remove(range);
-
-        tableViewSelectionListeners.selectedRangeRemoved(this, range.getStart(),
-            range.getEnd());
+        removeSelectedRange(range.start, range.end);
     }
 
     /**
      * Clears the selection.
      */
     public void clearSelection() {
-        if (selectedRanges.getLength() > 0) {
-            SpanSequence previousSelectedSpans = this.selectedRanges;
-            selectedRanges = new SpanSequence();
+        if (tableSelection.getLength() > 0) {
+            Sequence<Span> previousSelectedRanges = new ListSelectionSequence(tableSelection);
+            tableSelection = new ListSelection();
 
-            tableViewSelectionListeners.selectedRangesChanged(this, previousSelectedSpans);
+            tableViewSelectionListeners.selectedRangesChanged(this,
+                previousSelectedRanges);
         }
     }
 
@@ -1194,56 +1190,11 @@
      * otherwise.
      */
     public boolean isRowSelected(int index) {
-        return isRangeSelected(index, index);
-    }
-
-    /**
-     * Returns the selection state of a given range.
-     *
-     * @param rangeStart
-     * The first index in the range.
-     *
-     * @param rangeEnd
-     * The last index in the range.
-     *
-     * @return <tt>true</tt> if the entire range is selected; <tt>false</tt>,
-     * otherwise.
-     */
-    public boolean isRangeSelected(int rangeStart, int rangeEnd) {
-        return isRangeSelected(new Span(rangeStart, rangeEnd));
-    }
-
-    /**
-     * Returns the selection state of a given range.
-     *
-     * @param range
-     * The range whose selection state is to be tested.
-     *
-     * @return <tt>true</tt> if the entire range is selected; <tt>false</tt>,
-     * otherwise.
-     */
-    public boolean isRangeSelected(Span range) {
-        boolean selected = false;
-
-        if (range == null) {
-            throw new IllegalArgumentException("range is null.");
-        }
-
-        if (range.getStart() < 0 || range.getEnd() >= tableData.getLength()) {
+        if (index < 0 || index >= tableData.getLength()) {
             throw new IndexOutOfBoundsException();
         }
 
-        // Locate the span in the selection
-        int i = selectedRanges.indexOf(range);
-
-        // If the selected span contains the given span, it is considered
-        // selected
-        if (i >= 0) {
-            Span selectedSpan = selectedRanges.get(i);
-            selected = selectedSpan.contains(range);
-        }
-
-        return selected;
+        return (tableSelection.containsIndex(index));
     }
 
     public Object getSelectedRow() {
@@ -1260,10 +1211,10 @@
     public Sequence<Object> getSelectedRows() {
         ArrayList<Object> rows = new ArrayList<Object>();
 
-        for (int i = 0, n = selectedRanges.getLength(); i < n; i++) {
-            Span span = selectedRanges.get(i);
+        for (int i = 0, n = tableSelection.getLength(); i < n; i++) {
+            Span range = tableSelection.get(i);
 
-            for (int index = span.getStart(), end = span.getEnd(); index <= end; index++) {
+            for (int index = range.start; index <= range.end; index++) {
                 Object row = tableData.get(index);
                 rows.add(row);
             }

Modified: incubator/pivot/trunk/wtk/src/org/apache/pivot/wtk/skin/terra/TerraSplitPaneSkin.java
URL: http://svn.apache.org/viewvc/incubator/pivot/trunk/wtk/src/org/apache/pivot/wtk/skin/terra/TerraSplitPaneSkin.java?rev=799436&r1=799435&r2=799436&view=diff
==============================================================================
--- incubator/pivot/trunk/wtk/src/org/apache/pivot/wtk/skin/terra/TerraSplitPaneSkin.java (original)
+++ incubator/pivot/trunk/wtk/src/org/apache/pivot/wtk/skin/terra/TerraSplitPaneSkin.java Thu Jul 30 20:37:30 2009
@@ -247,8 +247,8 @@
 
             Span bounds = splitPane.getSplitBounds();
             if (bounds != null) {
-                lower = Math.max(lower, bounds.getStart());
-                upper = Math.min(upper, bounds.getEnd());
+                lower = Math.max(lower, bounds.start);
+                upper = Math.min(upper, bounds.end);
             }
 
             if (splitLocation < lower) {