Change the definition of ranges to exclude the upper bound.

This commit is contained in:
Dimitrie O. Paun 2002-10-17 21:36:29 +00:00 committed by Alexandre Julliard
parent bac35001fe
commit fa81ec674b
1 changed files with 48 additions and 42 deletions

View File

@ -442,7 +442,7 @@ static inline char* debugrange(const RANGE* lprng)
if (lprng) if (lprng)
{ {
char* buf = debug_getbuf(); char* buf = debug_getbuf();
snprintf(buf, DEBUG_BUFFER_SIZE, "(%d, %d)", lprng->lower, lprng->upper); snprintf(buf, DEBUG_BUFFER_SIZE, "[%d, %d)", lprng->lower, lprng->upper);
return buf; return buf;
} else return "(null)"; } else return "(null)";
} }
@ -701,6 +701,20 @@ static BOOL ranges_add(RANGES ranges, RANGE range);
static BOOL ranges_del(RANGES ranges, RANGE range); static BOOL ranges_del(RANGES ranges, RANGE range);
static void ranges_dump(RANGES ranges); static void ranges_dump(RANGES ranges);
static inline BOOL ranges_additem(RANGES ranges, INT nItem)
{
RANGE range = { nItem, nItem + 1 };
return ranges_add(ranges, range);
}
static inline BOOL ranges_delitem(RANGES ranges, INT nItem)
{
RANGE range = { nItem, nItem + 1 };
return ranges_del(ranges, range);
}
/*** /***
* ITERATOR DOCUMENTATION * ITERATOR DOCUMENTATION
* *
@ -778,7 +792,7 @@ static inline BOOL iterator_next(ITERATOR* i)
i->nItem++; i->nItem++;
testitem: testitem:
if (i->nItem == i->nSpecial) i->nItem++; if (i->nItem == i->nSpecial) i->nItem++;
if (i->nItem <= i->range.upper) return TRUE; if (i->nItem < i->range.upper) return TRUE;
pickarange: pickarange:
if (i->ranges) if (i->ranges)
@ -787,7 +801,7 @@ pickarange:
i->range = *(RANGE*)DPA_GetPtr(i->ranges->hdpa, i->index++); i->range = *(RANGE*)DPA_GetPtr(i->ranges->hdpa, i->index++);
else goto end; else goto end;
} }
else if (i->nItem > i->range.upper) goto end; else if (i->nItem >= i->range.upper) goto end;
i->nItem = i->range.lower; i->nItem = i->range.lower;
if (i->nItem >= 0) goto testitem; if (i->nItem >= 0) goto testitem;
@ -818,8 +832,8 @@ static inline BOOL iterator_prev(ITERATOR* i)
return FALSE; return FALSE;
} }
i->nItem--;
testitem: testitem:
i->nItem--;
if (i->nItem == i->nSpecial) i->nItem--; if (i->nItem == i->nSpecial) i->nItem--;
if (i->nItem >= i->range.lower) return TRUE; if (i->nItem >= i->range.lower) return TRUE;
@ -833,7 +847,7 @@ pickarange:
else if (!start && i->nItem < i->range.lower) goto end; else if (!start && i->nItem < i->range.lower) goto end;
i->nItem = i->range.upper; i->nItem = i->range.upper;
if (i->nItem >= 0) goto testitem; if (i->nItem > 0) goto testitem;
end: end:
return (i->nItem = i->nSpecial) != -1; return (i->nItem = i->nSpecial) != -1;
} }
@ -901,11 +915,12 @@ static BOOL iterator_frameditems(ITERATOR* i, LISTVIEW_INFO* infoPtr, const RECT
rcItem.right = rcItem.left + infoPtr->nItemWidth; rcItem.right = rcItem.left + infoPtr->nItemWidth;
rcItem.bottom = rcItem.top + infoPtr->nItemHeight; rcItem.bottom = rcItem.top + infoPtr->nItemHeight;
if (IntersectRect(&rcTemp, &rcItem, &frame)) if (IntersectRect(&rcTemp, &rcItem, &frame))
{ ranges_additem(i->ranges, nItem);
RANGE item_range = { nItem, nItem }; }
ranges_add(i->ranges, item_range); if (TRACE_ON(listview))
TRACE(" icon=%d\n", nItem); {
} TRACE(" icon items:\n");
ranges_dump(i->ranges);
} }
return TRUE; return TRUE;
} }
@ -920,7 +935,7 @@ static BOOL iterator_frameditems(ITERATOR* i, LISTVIEW_INFO* infoPtr, const RECT
upper = min((frame.bottom - 1) / infoPtr->nItemHeight, infoPtr->nItemCount - 1); upper = min((frame.bottom - 1) / infoPtr->nItemHeight, infoPtr->nItemCount - 1);
if (upper < lower) return TRUE; if (upper < lower) return TRUE;
i->range.lower = lower; i->range.lower = lower;
i->range.upper = upper; i->range.upper = upper + 1;
TRACE(" report=%s\n", debugrange(&i->range)); TRACE(" report=%s\n", debugrange(&i->range));
} }
else else
@ -944,7 +959,7 @@ static BOOL iterator_frameditems(ITERATOR* i, LISTVIEW_INFO* infoPtr, const RECT
{ {
item_range.lower = nCol * nPerCol + nFirstRow; item_range.lower = nCol * nPerCol + nFirstRow;
if(item_range.lower >= infoPtr->nItemCount) break; if(item_range.lower >= infoPtr->nItemCount) break;
item_range.upper = min(nCol * nPerCol + nLastRow, infoPtr->nItemCount - 1); item_range.upper = min(nCol * nPerCol + nLastRow + 1, infoPtr->nItemCount);
TRACE(" list=%s\n", debugrange(&item_range)); TRACE(" list=%s\n", debugrange(&item_range));
ranges_add(i->ranges, item_range); ranges_add(i->ranges, item_range);
} }
@ -993,10 +1008,7 @@ static BOOL iterator_visibleitems(ITERATOR* i, LISTVIEW_INFO *infoPtr, HDC hdc)
rcItem.right = rcItem.left + infoPtr->nItemWidth; rcItem.right = rcItem.left + infoPtr->nItemWidth;
rcItem.bottom = rcItem.top + infoPtr->nItemHeight; rcItem.bottom = rcItem.top + infoPtr->nItemHeight;
if (!RectVisible(hdc, &rcItem)) if (!RectVisible(hdc, &rcItem))
{ ranges_delitem(i->ranges, i->nItem);
RANGE item_range = { i->nItem, i->nItem };
ranges_del(i->ranges, item_range);
}
} }
/* the iterator should restart on the next iterator_next */ /* the iterator should restart on the next iterator_next */
@ -2154,15 +2166,15 @@ static void LISTVIEW_PrintSelectionRanges(LISTVIEW_INFO *infoPtr)
* [I] flags : flags * [I] flags : flags
* *
* RETURNS: * RETURNS:
* >0 : if Item 1 > Item 2 * > 0 : if range 1 > range 2
* <0 : if Item 2 > Item 1 * < 0 : if range 2 > range 1
* 0 : if Item 1 == Item 2 * = 0 : if range intersects range 2
*/ */
static INT CALLBACK ranges_cmp(LPVOID range1, LPVOID range2, LPARAM flags) static INT CALLBACK ranges_cmp(LPVOID range1, LPVOID range2, LPARAM flags)
{ {
if (((RANGE*)range1)->upper < ((RANGE*)range2)->lower) if (((RANGE*)range1)->upper <= ((RANGE*)range2)->lower)
return -1; return -1;
if (((RANGE*)range2)->upper < ((RANGE*)range1)->lower) if (((RANGE*)range2)->upper <= ((RANGE*)range1)->lower)
return 1; return 1;
return 0; return 0;
} }
@ -2195,7 +2207,7 @@ static void ranges_dump(RANGES ranges)
static inline BOOL ranges_contain(RANGES ranges, INT nItem) static inline BOOL ranges_contain(RANGES ranges, INT nItem)
{ {
RANGE srchrng = { nItem, nItem }; RANGE srchrng = { nItem, nItem + 1 };
TRACE("(nItem=%d)\n", nItem); TRACE("(nItem=%d)\n", nItem);
if (TRACE_ON(listview)) ranges_dump(ranges); if (TRACE_ON(listview)) ranges_dump(ranges);
@ -2209,7 +2221,7 @@ static INT ranges_itemcount(RANGES ranges)
for (i = 0; i < ranges->hdpa->nItemCount; i++) for (i = 0; i < ranges->hdpa->nItemCount; i++)
{ {
RANGE *sel = DPA_GetPtr(ranges->hdpa, i); RANGE *sel = DPA_GetPtr(ranges->hdpa, i);
count += sel->upper - sel->lower + 1; count += sel->upper - sel->lower;
} }
return count; return count;
@ -2217,12 +2229,9 @@ static INT ranges_itemcount(RANGES ranges)
static BOOL ranges_shift(RANGES ranges, INT nItem, INT delta, INT nUpper) static BOOL ranges_shift(RANGES ranges, INT nItem, INT delta, INT nUpper)
{ {
RANGE srchrng, *chkrng; RANGE srchrng = { nItem, nItem + 1 }, *chkrng;
INT index; INT index;
srchrng.upper = nItem;
srchrng.lower = nItem;
index = DPA_Search(ranges->hdpa, &srchrng, 0, ranges_cmp, 0, DPAS_SORTED | DPAS_INSERTAFTER); index = DPA_Search(ranges->hdpa, &srchrng, 0, ranges_cmp, 0, DPAS_SORTED | DPAS_INSERTAFTER);
if (index == -1) return TRUE; if (index == -1) return TRUE;
@ -2231,8 +2240,8 @@ static BOOL ranges_shift(RANGES ranges, INT nItem, INT delta, INT nUpper)
chkrng = DPA_GetPtr(ranges->hdpa, index); chkrng = DPA_GetPtr(ranges->hdpa, index);
if (chkrng->lower >= nItem) if (chkrng->lower >= nItem)
chkrng->lower = max(min(chkrng->lower + delta, nUpper - 1), 0); chkrng->lower = max(min(chkrng->lower + delta, nUpper - 1), 0);
if (chkrng->upper >= nItem) if (chkrng->upper > nItem)
chkrng->upper = max(min(chkrng->upper + delta, nUpper - 1), 0); chkrng->upper = max(min(chkrng->upper + delta, nUpper), 0);
} }
return TRUE; return TRUE;
} }
@ -2350,13 +2359,13 @@ static BOOL ranges_del(RANGES ranges, RANGE range)
else if ( (chkrgn->upper <= remrgn.upper) && else if ( (chkrgn->upper <= remrgn.upper) &&
(chkrgn->lower < remrgn.lower) ) (chkrgn->lower < remrgn.lower) )
{ {
chkrgn->upper = remrgn.lower - 1; chkrgn->upper = remrgn.lower;
} }
/* case 4: overlap lower */ /* case 4: overlap lower */
else if ( (chkrgn->upper > remrgn.upper) && else if ( (chkrgn->upper > remrgn.upper) &&
(chkrgn->lower >= remrgn.lower) ) (chkrgn->lower >= remrgn.lower) )
{ {
chkrgn->lower = remrgn.upper + 1; chkrgn->lower = remrgn.upper;
} }
/* case 5: fully internal */ /* case 5: fully internal */
else else
@ -2365,8 +2374,8 @@ static BOOL ranges_del(RANGES ranges, RANGE range)
if (!newrgn) return FALSE; if (!newrgn) return FALSE;
tmprgn = *chkrgn; tmprgn = *chkrgn;
newrgn->lower = chkrgn->lower; newrgn->lower = chkrgn->lower;
newrgn->upper = remrgn.lower - 1; newrgn->upper = remrgn.lower;
chkrgn->lower = remrgn.upper + 1; chkrgn->lower = remrgn.upper;
DPA_InsertPtr(ranges->hdpa, index, newrgn); DPA_InsertPtr(ranges->hdpa, index, newrgn);
chkrgn = &tmprgn; chkrgn = &tmprgn;
} }
@ -2822,15 +2831,13 @@ static BOOL set_owner_item(LISTVIEW_INFO *infoPtr, LPLVITEMW lpLVItem, BOOL isW,
/* and the selection is the only other state a virtual list may hold */ /* and the selection is the only other state a virtual list may hold */
if (lpLVItem->stateMask & LVIS_SELECTED) if (lpLVItem->stateMask & LVIS_SELECTED)
{ {
RANGE range = { lpLVItem->iItem, lpLVItem->iItem };
if (lpLVItem->state & LVIS_SELECTED) if (lpLVItem->state & LVIS_SELECTED)
{ {
if (lStyle & LVS_SINGLESEL) LISTVIEW_RemoveAllSelections(infoPtr, lpLVItem->iItem); if (lStyle & LVS_SINGLESEL) LISTVIEW_RemoveAllSelections(infoPtr, lpLVItem->iItem);
ranges_add(infoPtr->selectionRanges, range); ranges_additem(infoPtr->selectionRanges, lpLVItem->iItem);
} }
else else
ranges_del(infoPtr->selectionRanges, range); ranges_delitem(infoPtr->selectionRanges, lpLVItem->iItem);
} }
/* notify the parent now that things have changed */ /* notify the parent now that things have changed */
@ -2923,17 +2930,15 @@ static BOOL set_main_item(LISTVIEW_INFO *infoPtr, LPLVITEMW lpLVItem, BOOL isW,
if (uChanged & LVIF_STATE) if (uChanged & LVIF_STATE)
{ {
RANGE range = { lpLVItem->iItem, lpLVItem->iItem };
lpItem->state &= ~lpLVItem->stateMask; lpItem->state &= ~lpLVItem->stateMask;
lpItem->state |= (lpLVItem->state & lpLVItem->stateMask); lpItem->state |= (lpLVItem->state & lpLVItem->stateMask);
if (lpLVItem->state & lpLVItem->stateMask & ~infoPtr->uCallbackMask & LVIS_SELECTED) if (lpLVItem->state & lpLVItem->stateMask & ~infoPtr->uCallbackMask & LVIS_SELECTED)
{ {
if (lStyle & LVS_SINGLESEL) LISTVIEW_RemoveAllSelections(infoPtr, lpLVItem->iItem); if (lStyle & LVS_SINGLESEL) LISTVIEW_RemoveAllSelections(infoPtr, lpLVItem->iItem);
ranges_add(infoPtr->selectionRanges, range); ranges_additem(infoPtr->selectionRanges, lpLVItem->iItem);
} }
else if (lpLVItem->stateMask & LVIS_SELECTED) else if (lpLVItem->stateMask & LVIS_SELECTED)
ranges_del(infoPtr->selectionRanges, range); ranges_delitem(infoPtr->selectionRanges, lpLVItem->iItem);
/* if we are asked to change focus, and we manage it, do it */ /* if we are asked to change focus, and we manage it, do it */
if (lpLVItem->state & lpLVItem->stateMask & ~infoPtr->uCallbackMask & LVIS_FOCUSED) if (lpLVItem->state & lpLVItem->stateMask & ~infoPtr->uCallbackMask & LVIS_FOCUSED)
@ -3341,8 +3346,9 @@ static void LISTVIEW_RefreshOwnerDraw(LISTVIEW_INFO *infoPtr, HDC hdc)
RANGE range = iterator_range(&i); RANGE range = iterator_range(&i);
NMLVCACHEHINT nmlv; NMLVCACHEHINT nmlv;
ZeroMemory(&nmlv, sizeof(NMLVCACHEHINT));
nmlv.iFrom = range.lower; nmlv.iFrom = range.lower;
nmlv.iTo = range.upper; nmlv.iTo = range.upper - 1;
notify_hdr(infoPtr, LVN_ODCACHEHINT, &nmlv.hdr); notify_hdr(infoPtr, LVN_ODCACHEHINT, &nmlv.hdr);
} }