From 60e8122b8081d723f8b551aa548e744740c55abd Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Sergio=20Mart=C3=ADnez?= Date: Wed, 17 Oct 2018 18:40:08 +0200 Subject: [PATCH] GuiListView improvements --- examples/controls_review/controls_review.c | 2 +- src/raygui.h | 130 ++++++++++++--------- 2 files changed, 73 insertions(+), 59 deletions(-) diff --git a/examples/controls_review/controls_review.c b/examples/controls_review/controls_review.c index b66cf39..4a3f8f3 100644 --- a/examples/controls_review/controls_review.c +++ b/examples/controls_review/controls_review.c @@ -82,7 +82,7 @@ int main() if (GuiValueBox((Rectangle){ 25, 125, 125, 30 }, &ValueBox002Value, 0, 100, valueBoxEditMode)) valueBoxEditMode = !valueBoxEditMode; if (GuiTextBox((Rectangle){ 25, 175, 125, 30 }, TextBox003Text, 64, textBoxEditMode)) textBoxEditMode = !textBoxEditMode; - if (GuiListView((Rectangle){ 175, 25, 120, 135 }, ListView004TextList, 6, &ListView004Active, listViewEditMode)) listViewEditMode = !listViewEditMode; + if (GuiListView((Rectangle){ 175, 25, 120, 100 }, ListView004TextList, 6, &ListView004Active, listViewEditMode)) listViewEditMode = !listViewEditMode; if (GuiButton((Rectangle){ 25, 225, 125, 30 }, "SAMPLE TEXT")) Button005(); if (GuiTextBoxMulti((Rectangle){ 325, 25, 225, 175 }, TextBox006Text, 141, multiTextBoxEditMode)) multiTextBoxEditMode = !multiTextBoxEditMode; diff --git a/src/raygui.h b/src/raygui.h index 87bd27e..a30ac42 100644 --- a/src/raygui.h +++ b/src/raygui.h @@ -2833,13 +2833,28 @@ RAYGUIDEF bool GuiListView(Rectangle bounds, const char **text, int count, int * GuiControlState state = guiState; - static int startIndex = 0; - int visibleElements = bounds.height/(style[LISTVIEW_ELEMENTS_HEIGHT] + style[LISTVIEW_ELEMENTS_PADDING]); - int endIndex = startIndex + visibleElements; bool pressed = false; + + static int startIndex = 0; + bool useScrollBar = true; + bool pressedKey = false; + + int visibleElements = bounds.height/(style[LISTVIEW_ELEMENTS_HEIGHT] + style[LISTVIEW_ELEMENTS_PADDING]); + int endIndex = startIndex + visibleElements; + int auxActive = *active; + float barHeight = bounds.height; float minBarHeight = 10; + float barPosY = 0; + + // All the elements fit inside ListView and dont need scrollbar. + if (visibleElements >= count) + { + useScrollBar = false; + startIndex = 0; + endIndex = count; + } // Update control @@ -2850,7 +2865,7 @@ RAYGUIDEF bool GuiListView(Rectangle bounds, const char **text, int count, int * if (editMode) { - state = FOCUSED; + state = FOCUSED; // Change active with keys if (IsKeyPressed(KEY_UP)) @@ -2858,43 +2873,44 @@ RAYGUIDEF bool GuiListView(Rectangle bounds, const char **text, int count, int * if (auxActive > 0) { auxActive--; - if (auxActive < startIndex) startIndex--; + if ((useScrollBar) && (auxActive < startIndex)) startIndex--; } + pressedKey = true; } else if(IsKeyPressed(KEY_DOWN)) { if (auxActive < count - 1) { auxActive++; - if (auxActive >= endIndex) startIndex++; + if ((useScrollBar) && (auxActive >= endIndex)) startIndex++; } + pressedKey = true; } - - - int wheel = GetMouseWheelMove(); - - if (wheel < 0 && endIndex < count) + if (useScrollBar) { - startIndex -= wheel; - } - else if(wheel > 0 && startIndex > 0) - { - startIndex -= wheel; + endIndex = startIndex + visibleElements; + int wheel = GetMouseWheelMove(); + + if (wheel < 0 && endIndex < count) startIndex -= wheel; + else if(wheel > 0 && startIndex > 0) startIndex -= wheel; + + if (pressedKey) + { + pressedKey = false; + if ((auxActive < startIndex) || (auxActive >= endIndex)) startIndex = auxActive; + } + if (startIndex < 0) startIndex = 0; else if (startIndex > (count - (endIndex - startIndex))) { startIndex = count - (endIndex - startIndex); } + + endIndex = startIndex + visibleElements; + if (endIndex > count) endIndex = count; } - endIndex = startIndex + visibleElements; - if (endIndex > count) endIndex = count; - } - - - // Comprueba si caben todas las listas en la caja sin necesitar scrollbar. - if (count*style[LISTVIEW_ELEMENTS_HEIGHT] <= bounds.height) startIndex = 0; - + } // ------------------------------------------------------------------------------------ // Note: Changing editMode @@ -2910,69 +2926,67 @@ RAYGUIDEF bool GuiListView(Rectangle bounds, const char **text, int count, int * // Calculamos el porcentaje de elementos visibles, y aplicamos el mismo porcentaje al tamaño de la barra original. // Hay que tener en cuenta un valor mínimo para que la barra no sea de 1 px nunca y también que no sea mayor que la altura máxima. - float percentVisible = (endIndex - startIndex)*100/count; - barHeight *= percentVisible/100; - if (barHeight < minBarHeight) barHeight = minBarHeight; - else if(barHeight > bounds.height) barHeight = bounds.height; - // Posición Y a la que dibujamos la barra. - float barPosY = bounds.y + startIndex*((bounds.height - barHeight)/(count - (endIndex - startIndex))); + if (useScrollBar) + { + float percentVisible = (endIndex - startIndex)*100/count; + barHeight *= percentVisible/100; + if (barHeight < minBarHeight) barHeight = minBarHeight; + else if(barHeight > bounds.height) barHeight = bounds.height; + // Posición Y a la que dibujamos la barra. + barPosY = bounds.y + startIndex*((bounds.height - barHeight)/(count - (endIndex - startIndex))); + } //-------------------------------------------------------------------- // Draw control //-------------------------------------------------------------------- - if (editMode) + int posX = bounds.x + style[LISTVIEW_BAR_WIDTH] + style[LISTVIEW_ELEMENTS_PADDING]; + int elementWidth = bounds.width - style[LISTVIEW_BAR_WIDTH] - 2*style[LISTVIEW_ELEMENTS_PADDING] - LISTVIEW_LINE_THICK; + if (!useScrollBar) { - for (int i = startIndex; i < endIndex; i++) + posX = bounds.x + style[LISTVIEW_ELEMENTS_PADDING]; + elementWidth = bounds.width - 2*style[LISTVIEW_ELEMENTS_PADDING] - LISTVIEW_LINE_THICK; + } + + // Draw GuiListElements + for (int i = startIndex; i < endIndex; i++) + { + if (i == auxActive && editMode) { - if (i == auxActive) - { - if (GuiListElement((Rectangle){ bounds.x + style[LISTVIEW_BAR_WIDTH] + style[LISTVIEW_ELEMENTS_PADDING], bounds.y + style[LISTVIEW_ELEMENTS_PADDING] + LISTVIEW_LINE_THICK + (i - startIndex)*(style[LISTVIEW_ELEMENTS_HEIGHT] + style[LISTVIEW_ELEMENTS_PADDING]), bounds.width - style[LISTVIEW_BAR_WIDTH] - 2*style[LISTVIEW_ELEMENTS_PADDING] - LISTVIEW_LINE_THICK, style[LISTVIEW_ELEMENTS_HEIGHT] }, text[i], true, true) == false) auxActive -1; - } - else - { - if (GuiListElement((Rectangle){ bounds.x + style[LISTVIEW_BAR_WIDTH] + style[LISTVIEW_ELEMENTS_PADDING], bounds.y + style[LISTVIEW_ELEMENTS_PADDING] + LISTVIEW_LINE_THICK + (i - startIndex)*(style[LISTVIEW_ELEMENTS_HEIGHT] + style[LISTVIEW_ELEMENTS_PADDING]), bounds.width - style[LISTVIEW_BAR_WIDTH] - 2*style[LISTVIEW_ELEMENTS_PADDING] - LISTVIEW_LINE_THICK, style[LISTVIEW_ELEMENTS_HEIGHT] }, text[i], false, true) == true) auxActive = i; - } + if (GuiListElement((Rectangle){ posX, bounds.y + style[LISTVIEW_ELEMENTS_PADDING] + LISTVIEW_LINE_THICK + (i - startIndex)*(style[LISTVIEW_ELEMENTS_HEIGHT] + style[LISTVIEW_ELEMENTS_PADDING]), elementWidth, style[LISTVIEW_ELEMENTS_HEIGHT] }, text[i], true, true) == false) auxActive -1; + } + else + { + if (GuiListElement((Rectangle){ posX, bounds.y + style[LISTVIEW_ELEMENTS_PADDING] + LISTVIEW_LINE_THICK + (i - startIndex)*(style[LISTVIEW_ELEMENTS_HEIGHT] + style[LISTVIEW_ELEMENTS_PADDING]), elementWidth, style[LISTVIEW_ELEMENTS_HEIGHT] }, text[i], false, true) == true) auxActive = i; } } - else - { - for (int i = startIndex; i < endIndex; i++) if (GuiListElement((Rectangle){ bounds.x + style[LISTVIEW_BAR_WIDTH] + style[LISTVIEW_ELEMENTS_PADDING], bounds.y + style[LISTVIEW_ELEMENTS_PADDING] + LISTVIEW_LINE_THICK + (i - startIndex)*(style[LISTVIEW_ELEMENTS_HEIGHT] + style[LISTVIEW_ELEMENTS_PADDING]), bounds.width - style[LISTVIEW_BAR_WIDTH] - 2*style[LISTVIEW_ELEMENTS_PADDING] - LISTVIEW_LINE_THICK, style[LISTVIEW_ELEMENTS_HEIGHT] }, text[i], false, true) == true) auxActive = i; - } + // Draw scrollBar background + if (useScrollBar) DrawRectangle(bounds.x, bounds.y, style[LISTVIEW_BAR_WIDTH], bounds.height, Fade(LIGHTGRAY, guiAlpha)); - DrawRectangle(bounds.x, bounds.y, style[LISTVIEW_BAR_WIDTH], bounds.height, Fade(LIGHTGRAY, guiAlpha)); - - - // TODO: Review bar logic when bar size should be shorter than LISTVIEW_ELEMENT_HEIGHT - // if (bounds.height < ((count - (endIndex - startIndex))*style[LISTVIEW_ELEMENTS_HEIGHT])) - // { - // float newHeight = (float)(endIndex - startIndex)*(float)(style[LISTVIEW_ELEMENTS_HEIGHT]/2)/(float)(endIndex - startIndex); - // barHeight = (float)bounds.height - (float)((count - (endIndex - startIndex))*newHeight); - // } - + // Draw ListView states switch (state) { case NORMAL: case LOCKED: { - DrawRectangle(bounds.x, barPosY, style[LISTVIEW_BAR_WIDTH], barHeight, Fade(GetColor(style[SLIDERBAR_BORDER_COLOR_NORMAL]), guiAlpha)); + if (useScrollBar) DrawRectangle(bounds.x, barPosY, style[LISTVIEW_BAR_WIDTH], barHeight, Fade(GetColor(style[SLIDERBAR_BORDER_COLOR_NORMAL]), guiAlpha)); DrawRectangleLinesEx(bounds, LISTVIEW_LINE_THICK, Fade(GetColor(style[LISTVIEW_BORDER_COLOR_NORMAL]), guiAlpha)); } break; case FOCUSED: { - DrawRectangle(bounds.x, barPosY, style[LISTVIEW_BAR_WIDTH], barHeight, Fade(GetColor(style[SLIDERBAR_BASE_COLOR_FOCUSED]), guiAlpha)); + if (useScrollBar) DrawRectangle(bounds.x, barPosY, style[LISTVIEW_BAR_WIDTH], barHeight, Fade(GetColor(style[SLIDERBAR_BASE_COLOR_FOCUSED]), guiAlpha)); DrawRectangleLinesEx(bounds, LISTVIEW_LINE_THICK, Fade(GetColor(style[LISTVIEW_BORDER_COLOR_FOCUSED]), guiAlpha)); } break; case PRESSED: { - DrawRectangle(bounds.x, barPosY, style[LISTVIEW_BAR_WIDTH], barHeight, Fade(GetColor(style[SLIDERBAR_BASE_COLOR_PRESSED]), guiAlpha)); + if (useScrollBar) DrawRectangle(bounds.x, barPosY, style[LISTVIEW_BAR_WIDTH], barHeight, Fade(GetColor(style[SLIDERBAR_BASE_COLOR_PRESSED]), guiAlpha)); DrawRectangleLinesEx(bounds, LISTVIEW_LINE_THICK, Fade(GetColor(style[LISTVIEW_BORDER_COLOR_PRESSED]), guiAlpha)); } break; case DISABLED: { - DrawRectangle(bounds.x, barPosY, style[LISTVIEW_BAR_WIDTH], barHeight, Fade(GetColor(style[LISTVIEW_BASE_COLOR_DISABLED]), guiAlpha)); + if (useScrollBar) DrawRectangle(bounds.x, barPosY, style[LISTVIEW_BAR_WIDTH], barHeight, Fade(GetColor(style[LISTVIEW_BASE_COLOR_DISABLED]), guiAlpha)); DrawRectangleLinesEx(bounds, LISTVIEW_LINE_THICK, Fade(GetColor(style[LISTVIEW_BORDER_COLOR_DISABLED]), guiAlpha)); } break; default: break;