]> gerrit.simantics Code Review - simantics/platform.git/blobdiff - bundles/org.simantics.browsing.ui.nattable/src/org/simantics/browsing/ui/nattable/override/AbstractRowHideShowLayer2.java
Fixed all line endings of the repository
[simantics/platform.git] / bundles / org.simantics.browsing.ui.nattable / src / org / simantics / browsing / ui / nattable / override / AbstractRowHideShowLayer2.java
index 44f4b7c15375ab5433f417c62174cd9b4d8475da..86b2a3d2cb6bae864aaf7c90812c6217a983cf00 100644 (file)
-/*******************************************************************************\r
- * Copyright (c) 2012 Original authors and others.\r
- * All rights reserved. This program and the accompanying materials\r
- * are made available under the terms of the Eclipse Public License v1.0\r
- * which accompanies this distribution, and is available at\r
- * http://www.eclipse.org/legal/epl-v10.html\r
- * \r
- * Contributors:\r
- *     Original authors and others - initial API and implementation\r
- ******************************************************************************/\r
-package org.simantics.browsing.ui.nattable.override;\r
-\r
-import java.util.ArrayList;\r
-import java.util.Collection;\r
-\r
-import org.eclipse.nebula.widgets.nattable.coordinate.Range;\r
-import org.eclipse.nebula.widgets.nattable.layer.AbstractLayerTransform;\r
-import org.eclipse.nebula.widgets.nattable.layer.ILayer;\r
-import org.eclipse.nebula.widgets.nattable.layer.IUniqueIndexLayer;\r
-import org.eclipse.nebula.widgets.nattable.layer.LayerUtil;\r
-import org.eclipse.nebula.widgets.nattable.layer.event.ILayerEvent;\r
-import org.eclipse.nebula.widgets.nattable.layer.event.IStructuralChangeEvent;\r
-import org.eclipse.nebula.widgets.nattable.layer.event.VisualRefreshEvent;\r
-\r
-import it.unimi.dsi.fastutil.ints.Int2IntOpenHashMap;\r
-import it.unimi.dsi.fastutil.ints.IntOpenHashSet;\r
-\r
-/**\r
- * AbstractRowHideShowLayer implementation with FastUtils hashmaps.\r
- * \r
- * @see org.eclipse.nebula.widgets.nattable.hideshow.AbstractRowHideShowLayer\r
- * \r
- * @author MLMARKO\r
- *\r
- */\r
-public abstract class AbstractRowHideShowLayer2 extends AbstractLayerTransform implements IUniqueIndexLayer {\r
-\r
-       private Int2IntOpenHashMap cachedVisibleRowIndexOrder;\r
-       private Int2IntOpenHashMap cachedVisibleRowPositionOrder;\r
-       \r
-       private Int2IntOpenHashMap cachedHiddenRowIndexToPositionMap;\r
-\r
-       protected final Int2IntOpenHashMap startYCache = new Int2IntOpenHashMap();      \r
-       \r
-       \r
-       public AbstractRowHideShowLayer2(IUniqueIndexLayer underlyingLayer) {\r
-               super(underlyingLayer);\r
-       }\r
-       \r
-        @Override\r
-           public void handleLayerEvent(ILayerEvent event) {\r
-               if (event instanceof IStructuralChangeEvent) {\r
-                   IStructuralChangeEvent structuralChangeEvent = (IStructuralChangeEvent) event;\r
-                   if (structuralChangeEvent.isVerticalStructureChanged()) {\r
-                       // vertical structure has changed, update cached row information\r
-                       invalidateCache();\r
-                   }\r
-               } else if (event instanceof VisualRefreshEvent) {\r
-                   // visual change, e.g. font change, the startYCache needs to be\r
-                   // cleared in order to re-render correctly\r
-                   this.startYCache.clear();\r
-               }\r
-               super.handleLayerEvent(event);\r
-           }\r
-\r
-           // Horizontal features\r
-\r
-           // Columns\r
-\r
-           @Override\r
-           public int getColumnPositionByIndex(int columnIndex) {\r
-               return ((IUniqueIndexLayer) getUnderlyingLayer()).getColumnPositionByIndex(columnIndex);\r
-           }\r
-\r
-           // Vertical features\r
-\r
-           // Rows\r
-\r
-           @Override\r
-           public int getRowCount() {\r
-               return getCachedVisibleRowIndexes().size();\r
-           }\r
-\r
-           @Override\r
-           public int getRowIndexByPosition(int rowPosition) {\r
-               if (rowPosition < 0 || rowPosition >= getRowCount()) {\r
-                   return -1;\r
-               }\r
-               return getCachedVisibleRowPositons().get(rowPosition);\r
-           }\r
-\r
-           @Override\r
-           public int getRowPositionByIndex(int rowIndex) {\r
-               return getCachedVisibleRowIndexes().get(rowIndex);\r
-           }\r
-\r
-           public Collection<Integer> getRowPositionsByIndexes(Collection<Integer> rowIndexes) {\r
-               IntOpenHashSet rowPositions = new IntOpenHashSet();\r
-               for (int rowIndex : rowIndexes) {\r
-                   rowPositions.add(getRowPositionByIndex(rowIndex));\r
-               }\r
-               return rowPositions;\r
-           }\r
-\r
-           @Override\r
-           public int localToUnderlyingRowPosition(int localRowPosition) {\r
-               int rowIndex = getRowIndexByPosition(localRowPosition);\r
-               return ((IUniqueIndexLayer) getUnderlyingLayer()).getRowPositionByIndex(rowIndex);\r
-           }\r
-\r
-           @Override\r
-           public int underlyingToLocalRowPosition(ILayer sourceUnderlyingLayer, int underlyingRowPosition) {\r
-               int rowIndex = getUnderlyingLayer().getRowIndexByPosition(underlyingRowPosition);\r
-               int rowPosition = getRowPositionByIndex(rowIndex);\r
-               if (rowPosition >= 0) {\r
-                   return rowPosition;\r
-               } else {\r
-                       if (this.cachedHiddenRowIndexToPositionMap.containsKey(rowIndex)) {\r
-                     return this.cachedHiddenRowIndexToPositionMap.get(rowIndex);\r
-                   } else {\r
-                       return -1;\r
-                   }\r
-               }\r
-           }\r
-\r
-           @Override\r
-           public Collection<Range> underlyingToLocalRowPositions(\r
-                   ILayer sourceUnderlyingLayer, Collection<Range> underlyingRowPositionRanges) {\r
-               Collection<Range> localRowPositionRanges = new ArrayList<Range>();\r
-\r
-               for (Range underlyingRowPositionRange : underlyingRowPositionRanges) {\r
-                   int startRowPosition = getAdjustedUnderlyingToLocalStartPosition(\r
-                           sourceUnderlyingLayer,\r
-                           underlyingRowPositionRange.start,\r
-                           underlyingRowPositionRange.end);\r
-                   int endRowPosition = getAdjustedUnderlyingToLocalEndPosition(\r
-                           sourceUnderlyingLayer,\r
-                           underlyingRowPositionRange.end,\r
-                           underlyingRowPositionRange.start);\r
-\r
-                   // teichstaedt: fixes the problem that ranges where added even if\r
-                   // the corresponding startPosition weren't found in the underlying\r
-                   // layer. Without that fix a bunch of ranges of kind Range [-1, 180]\r
-                   // which causes strange behaviour in Freeze- and other Layers were\r
-                   // returned.\r
-                   if (startRowPosition > -1) {\r
-                       localRowPositionRanges.add(new Range(startRowPosition, endRowPosition));\r
-                   }\r
-               }\r
-\r
-               return localRowPositionRanges;\r
-           }\r
-\r
-           private int getAdjustedUnderlyingToLocalStartPosition(\r
-                   ILayer sourceUnderlyingLayer,\r
-                   int startUnderlyingPosition,\r
-                   int endUnderlyingPosition) {\r
-               int localStartRowPosition = underlyingToLocalRowPosition(sourceUnderlyingLayer, startUnderlyingPosition);\r
-               int offset = 0;\r
-               while (localStartRowPosition < 0\r
-                       && (startUnderlyingPosition + offset < endUnderlyingPosition)) {\r
-                   localStartRowPosition =\r
-                           underlyingToLocalRowPosition(sourceUnderlyingLayer, startUnderlyingPosition + offset++);\r
-               }\r
-               return localStartRowPosition;\r
-           }\r
-\r
-           private int getAdjustedUnderlyingToLocalEndPosition(\r
-                   ILayer sourceUnderlyingLayer,\r
-                   int endUnderlyingPosition,\r
-                   int startUnderlyingPosition) {\r
-               int localEndRowPosition = underlyingToLocalRowPosition(sourceUnderlyingLayer, endUnderlyingPosition - 1);\r
-               int offset = 0;\r
-               while (localEndRowPosition < 0\r
-                       && (endUnderlyingPosition - offset > startUnderlyingPosition)) {\r
-                   localEndRowPosition =\r
-                           underlyingToLocalRowPosition(sourceUnderlyingLayer, endUnderlyingPosition - offset++);\r
-               }\r
-               return localEndRowPosition + 1;\r
-           }\r
-\r
-           // Height\r
-\r
-           @Override\r
-           public int getHeight() {\r
-               int lastRowPosition = getRowCount() - 1;\r
-               return getStartYOfRowPosition(lastRowPosition) + getRowHeightByPosition(lastRowPosition);\r
-           }\r
-\r
-           // Y\r
-\r
-           @Override\r
-           public int getRowPositionByY(int y) {\r
-               return LayerUtil.getRowPositionByY(this, y);\r
-           }\r
-\r
-           @Override\r
-           public int getStartYOfRowPosition(int localRowPosition) {\r
-               int index = this.startYCache.get(localRowPosition);\r
-               if (index >= 0)\r
-                       return index;\r
-\r
-               IUniqueIndexLayer underlyingLayer = (IUniqueIndexLayer) getUnderlyingLayer();\r
-               int underlyingPosition = localToUnderlyingRowPosition(localRowPosition);\r
-               if (underlyingPosition < 0) {\r
-                   return -1;\r
-               }\r
-               int underlyingStartY = underlyingLayer.getStartYOfRowPosition(underlyingPosition);\r
-               if (underlyingStartY < 0) {\r
-                   return -1;\r
-               }\r
-\r
-               for (Integer hiddenIndex : getHiddenRowIndexes()) {\r
-                   int hiddenPosition = underlyingLayer.getRowPositionByIndex(hiddenIndex);\r
-                   // if the hidden position is -1, it is hidden in the underlying\r
-                   // layertherefore the underlying layer should handle the positioning\r
-                   if (hiddenPosition >= 0 && hiddenPosition <= underlyingPosition) {\r
-                       underlyingStartY -= underlyingLayer.getRowHeightByPosition(hiddenPosition);\r
-                   }\r
-               }\r
-\r
-               this.startYCache.put(localRowPosition, underlyingStartY);\r
-               return underlyingStartY;\r
-           }\r
-\r
-           // Hide/show\r
-\r
-           /**\r
-            * Will check if the row at the specified index is hidden or not. Checks\r
-            * this layer and also the sublayers for the visibility.\r
-            *\r
-            * @param rowIndex\r
-            *            The row index of the row whose visibility state should be\r
-            *            checked.\r
-            * @return <code>true</code> if the row at the specified index is hidden,\r
-            *         <code>false</code> if it is visible.\r
-            */\r
-           public abstract boolean isRowIndexHidden(int rowIndex);\r
-\r
-           /**\r
-            * Will collect and return all indexes of the rows that are hidden in this\r
-            * layer. Note: It is not intended that it also collects the row indexes of\r
-            * underlying layers. This would cause issues on calculating positions as\r
-            * every layer is responsible for those calculations itself.\r
-            *\r
-            * @return Collection of all row indexes that are hidden in this layer.\r
-            */\r
-           public abstract Collection<Integer> getHiddenRowIndexes();\r
-\r
-           // Cache\r
-\r
-           /**\r
-            * Invalidate the cache to ensure that information is rebuild.\r
-            */\r
-           protected void invalidateCache() {\r
-               this.cachedVisibleRowIndexOrder = null;\r
-               this.cachedVisibleRowPositionOrder = null;\r
-               this.cachedHiddenRowIndexToPositionMap = null;\r
-               this.startYCache.clear();\r
-           }\r
-\r
-           private Int2IntOpenHashMap getCachedVisibleRowIndexes() {\r
-               if (this.cachedVisibleRowIndexOrder == null) {\r
-                   cacheVisibleRowIndexes();\r
-               }\r
-               return this.cachedVisibleRowIndexOrder;\r
-           }\r
-\r
-           private Int2IntOpenHashMap getCachedVisibleRowPositons() {\r
-               if (this.cachedVisibleRowPositionOrder == null) {\r
-                   cacheVisibleRowIndexes();\r
-               }\r
-               return this.cachedVisibleRowPositionOrder;\r
-           }\r
-\r
-           protected void cacheVisibleRowIndexes() {\r
-               this.cachedVisibleRowIndexOrder = new Int2IntOpenHashMap();\r
-               this.cachedVisibleRowPositionOrder = new Int2IntOpenHashMap();\r
-               this.cachedHiddenRowIndexToPositionMap = new Int2IntOpenHashMap();\r
-               this.startYCache.clear();\r
-               \r
-               cachedVisibleRowPositionOrder.defaultReturnValue(-1);\r
-               cachedVisibleRowIndexOrder.defaultReturnValue(-1);\r
-               cachedHiddenRowIndexToPositionMap.defaultReturnValue(-1);\r
-               startYCache.defaultReturnValue(-1);\r
-\r
-               ILayer underlyingLayer = getUnderlyingLayer();\r
-               int rowPosition = 0;\r
-               for (int parentRowPosition = 0; parentRowPosition < underlyingLayer.getRowCount(); parentRowPosition++) {\r
-                   int rowIndex = underlyingLayer.getRowIndexByPosition(parentRowPosition);\r
-\r
-                   if (!isRowIndexHidden(rowIndex)) {\r
-                       this.cachedVisibleRowIndexOrder.put(rowIndex, rowPosition);\r
-                       this.cachedVisibleRowPositionOrder.put(rowPosition, rowIndex);\r
-                       rowPosition++;\r
-                   } else {\r
-                       this.cachedHiddenRowIndexToPositionMap.put(rowIndex, rowPosition);\r
-                   }\r
-               }\r
-           }\r
-}\r
+/*******************************************************************************
+ * Copyright (c) 2012 Original authors and others.
+ * All rights reserved. This program and the accompanying materials
+ * are made available under the terms of the Eclipse Public License v1.0
+ * which accompanies this distribution, and is available at
+ * http://www.eclipse.org/legal/epl-v10.html
+ * 
+ * Contributors:
+ *     Original authors and others - initial API and implementation
+ ******************************************************************************/
+package org.simantics.browsing.ui.nattable.override;
+
+import java.util.ArrayList;
+import java.util.Collection;
+
+import org.eclipse.nebula.widgets.nattable.coordinate.Range;
+import org.eclipse.nebula.widgets.nattable.layer.AbstractLayerTransform;
+import org.eclipse.nebula.widgets.nattable.layer.ILayer;
+import org.eclipse.nebula.widgets.nattable.layer.IUniqueIndexLayer;
+import org.eclipse.nebula.widgets.nattable.layer.LayerUtil;
+import org.eclipse.nebula.widgets.nattable.layer.event.ILayerEvent;
+import org.eclipse.nebula.widgets.nattable.layer.event.IStructuralChangeEvent;
+import org.eclipse.nebula.widgets.nattable.layer.event.VisualRefreshEvent;
+
+import it.unimi.dsi.fastutil.ints.Int2IntOpenHashMap;
+import it.unimi.dsi.fastutil.ints.IntOpenHashSet;
+
+/**
+ * AbstractRowHideShowLayer implementation with FastUtils hashmaps.
+ * 
+ * @see org.eclipse.nebula.widgets.nattable.hideshow.AbstractRowHideShowLayer
+ * 
+ * @author MLMARKO
+ *
+ */
+public abstract class AbstractRowHideShowLayer2 extends AbstractLayerTransform implements IUniqueIndexLayer {
+
+       private Int2IntOpenHashMap cachedVisibleRowIndexOrder;
+       private Int2IntOpenHashMap cachedVisibleRowPositionOrder;
+       
+       private Int2IntOpenHashMap cachedHiddenRowIndexToPositionMap;
+
+       protected final Int2IntOpenHashMap startYCache = new Int2IntOpenHashMap();      
+       
+       
+       public AbstractRowHideShowLayer2(IUniqueIndexLayer underlyingLayer) {
+               super(underlyingLayer);
+       }
+       
+        @Override
+           public void handleLayerEvent(ILayerEvent event) {
+               if (event instanceof IStructuralChangeEvent) {
+                   IStructuralChangeEvent structuralChangeEvent = (IStructuralChangeEvent) event;
+                   if (structuralChangeEvent.isVerticalStructureChanged()) {
+                       // vertical structure has changed, update cached row information
+                       invalidateCache();
+                   }
+               } else if (event instanceof VisualRefreshEvent) {
+                   // visual change, e.g. font change, the startYCache needs to be
+                   // cleared in order to re-render correctly
+                   this.startYCache.clear();
+               }
+               super.handleLayerEvent(event);
+           }
+
+           // Horizontal features
+
+           // Columns
+
+           @Override
+           public int getColumnPositionByIndex(int columnIndex) {
+               return ((IUniqueIndexLayer) getUnderlyingLayer()).getColumnPositionByIndex(columnIndex);
+           }
+
+           // Vertical features
+
+           // Rows
+
+           @Override
+           public int getRowCount() {
+               return getCachedVisibleRowIndexes().size();
+           }
+
+           @Override
+           public int getRowIndexByPosition(int rowPosition) {
+               if (rowPosition < 0 || rowPosition >= getRowCount()) {
+                   return -1;
+               }
+               return getCachedVisibleRowPositons().get(rowPosition);
+           }
+
+           @Override
+           public int getRowPositionByIndex(int rowIndex) {
+               return getCachedVisibleRowIndexes().get(rowIndex);
+           }
+
+           public Collection<Integer> getRowPositionsByIndexes(Collection<Integer> rowIndexes) {
+               IntOpenHashSet rowPositions = new IntOpenHashSet();
+               for (int rowIndex : rowIndexes) {
+                   rowPositions.add(getRowPositionByIndex(rowIndex));
+               }
+               return rowPositions;
+           }
+
+           @Override
+           public int localToUnderlyingRowPosition(int localRowPosition) {
+               int rowIndex = getRowIndexByPosition(localRowPosition);
+               return ((IUniqueIndexLayer) getUnderlyingLayer()).getRowPositionByIndex(rowIndex);
+           }
+
+           @Override
+           public int underlyingToLocalRowPosition(ILayer sourceUnderlyingLayer, int underlyingRowPosition) {
+               int rowIndex = getUnderlyingLayer().getRowIndexByPosition(underlyingRowPosition);
+               int rowPosition = getRowPositionByIndex(rowIndex);
+               if (rowPosition >= 0) {
+                   return rowPosition;
+               } else {
+                       if (this.cachedHiddenRowIndexToPositionMap.containsKey(rowIndex)) {
+                     return this.cachedHiddenRowIndexToPositionMap.get(rowIndex);
+                   } else {
+                       return -1;
+                   }
+               }
+           }
+
+           @Override
+           public Collection<Range> underlyingToLocalRowPositions(
+                   ILayer sourceUnderlyingLayer, Collection<Range> underlyingRowPositionRanges) {
+               Collection<Range> localRowPositionRanges = new ArrayList<Range>();
+
+               for (Range underlyingRowPositionRange : underlyingRowPositionRanges) {
+                   int startRowPosition = getAdjustedUnderlyingToLocalStartPosition(
+                           sourceUnderlyingLayer,
+                           underlyingRowPositionRange.start,
+                           underlyingRowPositionRange.end);
+                   int endRowPosition = getAdjustedUnderlyingToLocalEndPosition(
+                           sourceUnderlyingLayer,
+                           underlyingRowPositionRange.end,
+                           underlyingRowPositionRange.start);
+
+                   // teichstaedt: fixes the problem that ranges where added even if
+                   // the corresponding startPosition weren't found in the underlying
+                   // layer. Without that fix a bunch of ranges of kind Range [-1, 180]
+                   // which causes strange behaviour in Freeze- and other Layers were
+                   // returned.
+                   if (startRowPosition > -1) {
+                       localRowPositionRanges.add(new Range(startRowPosition, endRowPosition));
+                   }
+               }
+
+               return localRowPositionRanges;
+           }
+
+           private int getAdjustedUnderlyingToLocalStartPosition(
+                   ILayer sourceUnderlyingLayer,
+                   int startUnderlyingPosition,
+                   int endUnderlyingPosition) {
+               int localStartRowPosition = underlyingToLocalRowPosition(sourceUnderlyingLayer, startUnderlyingPosition);
+               int offset = 0;
+               while (localStartRowPosition < 0
+                       && (startUnderlyingPosition + offset < endUnderlyingPosition)) {
+                   localStartRowPosition =
+                           underlyingToLocalRowPosition(sourceUnderlyingLayer, startUnderlyingPosition + offset++);
+               }
+               return localStartRowPosition;
+           }
+
+           private int getAdjustedUnderlyingToLocalEndPosition(
+                   ILayer sourceUnderlyingLayer,
+                   int endUnderlyingPosition,
+                   int startUnderlyingPosition) {
+               int localEndRowPosition = underlyingToLocalRowPosition(sourceUnderlyingLayer, endUnderlyingPosition - 1);
+               int offset = 0;
+               while (localEndRowPosition < 0
+                       && (endUnderlyingPosition - offset > startUnderlyingPosition)) {
+                   localEndRowPosition =
+                           underlyingToLocalRowPosition(sourceUnderlyingLayer, endUnderlyingPosition - offset++);
+               }
+               return localEndRowPosition + 1;
+           }
+
+           // Height
+
+           @Override
+           public int getHeight() {
+               int lastRowPosition = getRowCount() - 1;
+               return getStartYOfRowPosition(lastRowPosition) + getRowHeightByPosition(lastRowPosition);
+           }
+
+           // Y
+
+           @Override
+           public int getRowPositionByY(int y) {
+               return LayerUtil.getRowPositionByY(this, y);
+           }
+
+           @Override
+           public int getStartYOfRowPosition(int localRowPosition) {
+               int index = this.startYCache.get(localRowPosition);
+               if (index >= 0)
+                       return index;
+
+               IUniqueIndexLayer underlyingLayer = (IUniqueIndexLayer) getUnderlyingLayer();
+               int underlyingPosition = localToUnderlyingRowPosition(localRowPosition);
+               if (underlyingPosition < 0) {
+                   return -1;
+               }
+               int underlyingStartY = underlyingLayer.getStartYOfRowPosition(underlyingPosition);
+               if (underlyingStartY < 0) {
+                   return -1;
+               }
+
+               for (Integer hiddenIndex : getHiddenRowIndexes()) {
+                   int hiddenPosition = underlyingLayer.getRowPositionByIndex(hiddenIndex);
+                   // if the hidden position is -1, it is hidden in the underlying
+                   // layertherefore the underlying layer should handle the positioning
+                   if (hiddenPosition >= 0 && hiddenPosition <= underlyingPosition) {
+                       underlyingStartY -= underlyingLayer.getRowHeightByPosition(hiddenPosition);
+                   }
+               }
+
+               this.startYCache.put(localRowPosition, underlyingStartY);
+               return underlyingStartY;
+           }
+
+           // Hide/show
+
+           /**
+            * Will check if the row at the specified index is hidden or not. Checks
+            * this layer and also the sublayers for the visibility.
+            *
+            * @param rowIndex
+            *            The row index of the row whose visibility state should be
+            *            checked.
+            * @return <code>true</code> if the row at the specified index is hidden,
+            *         <code>false</code> if it is visible.
+            */
+           public abstract boolean isRowIndexHidden(int rowIndex);
+
+           /**
+            * Will collect and return all indexes of the rows that are hidden in this
+            * layer. Note: It is not intended that it also collects the row indexes of
+            * underlying layers. This would cause issues on calculating positions as
+            * every layer is responsible for those calculations itself.
+            *
+            * @return Collection of all row indexes that are hidden in this layer.
+            */
+           public abstract Collection<Integer> getHiddenRowIndexes();
+
+           // Cache
+
+           /**
+            * Invalidate the cache to ensure that information is rebuild.
+            */
+           protected void invalidateCache() {
+               this.cachedVisibleRowIndexOrder = null;
+               this.cachedVisibleRowPositionOrder = null;
+               this.cachedHiddenRowIndexToPositionMap = null;
+               this.startYCache.clear();
+           }
+
+           private Int2IntOpenHashMap getCachedVisibleRowIndexes() {
+               if (this.cachedVisibleRowIndexOrder == null) {
+                   cacheVisibleRowIndexes();
+               }
+               return this.cachedVisibleRowIndexOrder;
+           }
+
+           private Int2IntOpenHashMap getCachedVisibleRowPositons() {
+               if (this.cachedVisibleRowPositionOrder == null) {
+                   cacheVisibleRowIndexes();
+               }
+               return this.cachedVisibleRowPositionOrder;
+           }
+
+           protected void cacheVisibleRowIndexes() {
+               this.cachedVisibleRowIndexOrder = new Int2IntOpenHashMap();
+               this.cachedVisibleRowPositionOrder = new Int2IntOpenHashMap();
+               this.cachedHiddenRowIndexToPositionMap = new Int2IntOpenHashMap();
+               this.startYCache.clear();
+               
+               cachedVisibleRowPositionOrder.defaultReturnValue(-1);
+               cachedVisibleRowIndexOrder.defaultReturnValue(-1);
+               cachedHiddenRowIndexToPositionMap.defaultReturnValue(-1);
+               startYCache.defaultReturnValue(-1);
+
+               ILayer underlyingLayer = getUnderlyingLayer();
+               int rowPosition = 0;
+               for (int parentRowPosition = 0; parentRowPosition < underlyingLayer.getRowCount(); parentRowPosition++) {
+                   int rowIndex = underlyingLayer.getRowIndexByPosition(parentRowPosition);
+
+                   if (!isRowIndexHidden(rowIndex)) {
+                       this.cachedVisibleRowIndexOrder.put(rowIndex, rowPosition);
+                       this.cachedVisibleRowPositionOrder.put(rowPosition, rowIndex);
+                       rowPosition++;
+                   } else {
+                       this.cachedHiddenRowIndexToPositionMap.put(rowIndex, rowPosition);
+                   }
+               }
+           }
+}