From 0af779569095af43a2762843f40d2d5e88168bf9 Mon Sep 17 00:00:00 2001 From: that Date: Wed, 25 Feb 2015 08:52:19 +0100 Subject: gui: introduce virtual RenderItem method in ScrollList - so derived lists can draw whatever they want (multi-line etc.) - replace GetListItem with RenderItem - minor cleanup Change-Id: I062e0a354f1c18ce0a5232b7542c4987b480e232 --- gui/fileselector.cpp | 14 ++++--- gui/listbox.cpp | 14 +++---- gui/objects.hpp | 15 +++---- gui/partitionlist.cpp | 14 +++---- gui/scrolllist.cpp | 106 +++++++++++++++++++++++++------------------------- 5 files changed, 83 insertions(+), 80 deletions(-) diff --git a/gui/fileselector.cpp b/gui/fileselector.cpp index 8f6a7fa72..a97ff34b1 100644 --- a/gui/fileselector.cpp +++ b/gui/fileselector.cpp @@ -308,19 +308,23 @@ size_t GUIFileSelector::GetItemCount() return folderSize + fileSize; } -int GUIFileSelector::GetListItem(size_t item_index, ImageResource*& icon, std::string &text) +void GUIFileSelector::RenderItem(size_t itemindex, int yPos, bool selected) { size_t folderSize = mShowFolders ? mFolderList.size() : 0; size_t fileSize = mShowFiles ? mFileList.size() : 0; - if (item_index < folderSize) { - text = mFolderList.at(item_index).fileName; + ImageResource* icon; + std::string text; + + if (itemindex < folderSize) { + text = mFolderList.at(itemindex).fileName; icon = mFolderIcon; } else { - text = mFileList.at(item_index - folderSize).fileName; + text = mFileList.at(itemindex - folderSize).fileName; icon = mFileIcon; } - return 0; + + RenderStdItem(yPos, selected, icon, text.c_str()); } void GUIFileSelector::NotifySelect(size_t item_selected) diff --git a/gui/listbox.cpp b/gui/listbox.cpp index 625b4b7d1..a60769979 100644 --- a/gui/listbox.cpp +++ b/gui/listbox.cpp @@ -141,14 +141,14 @@ size_t GUIListBox::GetItemCount() return mList.size(); } -int GUIListBox::GetListItem(size_t item_index, ImageResource*& icon, std::string &text) +void GUIListBox::RenderItem(size_t itemindex, int yPos, bool selected) { - text = mList.at(item_index).displayName; - if (mList.at(item_index).selected) - icon = mIconSelected; - else - icon = mIconUnselected; - return 0; + // note: the "selected" parameter above is for the currently touched item + // don't confuse it with the more persistent "selected" flag per list item used below + ImageResource* icon = mList.at(itemindex).selected ? mIconSelected : mIconUnselected; + const std::string& text = mList.at(itemindex).displayName; + + RenderStdItem(yPos, selected, icon, text.c_str()); } void GUIListBox::NotifySelect(size_t item_selected) diff --git a/gui/objects.hpp b/gui/objects.hpp index 0f853ac59..d5c3b2738 100644 --- a/gui/objects.hpp +++ b/gui/objects.hpp @@ -533,12 +533,14 @@ protected: // derived classes need to implement these // get number of items virtual size_t GetItemCount() { return 0; } - // get data for one item - virtual int GetListItem(size_t item_index, ImageResource*& icon, std::string &text) - { icon = NULL; text = ""; return -1; } + // render a single item in rect (mRenderX, yPos, mRenderW, actualItemHeight) + virtual void RenderItem(size_t itemindex, int yPos, bool selected); // an item was selected virtual void NotifySelect(size_t item_selected) {} + // render a standard-layout list item with optional icon and text + void RenderStdItem(int yPos, bool selected, ImageResource* icon, const char* text, int iconAndTextH = 0); + enum { NO_ITEM = (size_t)-1 }; // returns item index at coordinates or NO_ITEM if there is no item there size_t HitTestItem(int x, int y); @@ -562,7 +564,6 @@ protected: // Background COLOR mBackgroundColor; ImageResource* mBackground; // background image, if any, automatically centered - int mBackgroundW, mBackgroundH; // background width and height if using an image for the background // Header COLOR mHeaderBackgroundColor; @@ -630,7 +631,7 @@ public: virtual void SetPageFocus(int inFocus); virtual size_t GetItemCount(); - virtual int GetListItem(size_t item_index, ImageResource*& icon, std::string &text); + virtual void RenderItem(size_t itemindex, int yPos, bool selected); virtual void NotifySelect(size_t item_selected); protected: @@ -685,7 +686,7 @@ public: virtual void SetPageFocus(int inFocus); virtual size_t GetItemCount(); - virtual int GetListItem(size_t item_index, ImageResource*& icon, std::string &text); + virtual void RenderItem(size_t itemindex, int yPos, bool selected); virtual void NotifySelect(size_t item_selected); protected: @@ -721,7 +722,7 @@ public: virtual void SetPageFocus(int inFocus); virtual size_t GetItemCount(); - virtual int GetListItem(size_t item_index, ImageResource*& icon, std::string &text); + virtual void RenderItem(size_t itemindex, int yPos, bool selected); virtual void NotifySelect(size_t item_selected); protected: diff --git a/gui/partitionlist.cpp b/gui/partitionlist.cpp index ba8a94bb7..102802d7d 100644 --- a/gui/partitionlist.cpp +++ b/gui/partitionlist.cpp @@ -197,14 +197,14 @@ size_t GUIPartitionList::GetItemCount() return mList.size(); } -int GUIPartitionList::GetListItem(size_t item_index, ImageResource*& icon, std::string &text) +void GUIPartitionList::RenderItem(size_t itemindex, int yPos, bool selected) { - text = mList.at(item_index).Display_Name; - if (mList.at(item_index).selected) - icon = mIconSelected; - else - icon = mIconUnselected; - return 0; + // note: the "selected" parameter above is for the currently touched item + // don't confuse it with the more persistent "selected" flag per list item used below + ImageResource* icon = mList.at(itemindex).selected ? mIconSelected : mIconUnselected; + const std::string& text = mList.at(itemindex).Display_Name; + + RenderStdItem(yPos, selected, icon, text.c_str()); } void GUIPartitionList::NotifySelect(size_t item_selected) diff --git a/gui/scrolllist.cpp b/gui/scrolllist.cpp index 70a54e5ac..aa9623c68 100644 --- a/gui/scrolllist.cpp +++ b/gui/scrolllist.cpp @@ -42,7 +42,6 @@ GUIScrollList::GUIScrollList(xml_node<>* node) : GUIObject(node) mHeaderIsStatic = false; mBackground = mHeaderIcon = NULL; mFont = NULL; - mBackgroundW = mBackgroundH = 0; mFastScrollW = mFastScrollLineW = mFastScrollRectW = mFastScrollRectH = 0; mFastScrollRectCurrentY = mFastScrollRectCurrentH = mFastScrollRectTouchY = 0; lastY = last2Y = fastScroll = 0; @@ -142,12 +141,6 @@ GUIScrollList::GUIScrollList(xml_node<>* node) : GUIObject(node) if (actualItemHeight / 3 > 6) touchDebounce = actualItemHeight / 3; - - if (mBackground && mBackground->GetResource()) - { - mBackgroundW = mBackground->GetWidth(); - mBackgroundH = mBackground->GetHeight(); - } } GUIScrollList::~GUIScrollList() @@ -207,16 +200,18 @@ int GUIScrollList::Render(void) // Next, render the background resource (if it exists) if (mBackground && mBackground->GetResource()) { - int mBackgroundX = mRenderX + ((mRenderW - mBackgroundW) / 2); - int mBackgroundY = mRenderY + ((mRenderH - mBackgroundH) / 2); - gr_blit(mBackground->GetResource(), 0, 0, mBackgroundW, mBackgroundH, mBackgroundX, mBackgroundY); + int BackgroundW = mBackground->GetWidth(); + int BackgroundH = mBackground->GetHeight(); + int BackgroundX = mRenderX + ((mRenderW - BackgroundW) / 2); + int BackgroundY = mRenderY + ((mRenderH - BackgroundH) / 2); + gr_blit(mBackground->GetResource(), 0, 0, BackgroundW, BackgroundH, BackgroundX, BackgroundY); } // This tells us how many full lines we can actually render size_t lines = GetDisplayItemCount(); size_t listSize = GetItemCount(); - int listW = mRenderW; + int listW = mRenderW; // this is only used for the separators - the list items are rendered in the full width of the list if (listSize <= lines) { hasScroll = false; @@ -231,11 +226,7 @@ int GUIScrollList::Render(void) lines++; } - void* fontResource = NULL; - if (mFont) fontResource = mFont->GetResource(); - int yPos = mRenderY + mHeaderH + y_offset; - int fontOffsetY = (int)((actualItemHeight - mFontHeight) / 2); // render all visible items for (size_t line = 0; line < lines; line++) @@ -244,38 +235,7 @@ int GUIScrollList::Render(void) if (itemindex >= listSize) break; - // get item data - ImageResource* icon; - std::string label; - if (GetListItem(itemindex, icon, label)) - break; - - if (hasHighlightColor && itemindex == selectedItem) { - // Highlight the item background of the selected item - gr_color(mHighlightColor.red, mHighlightColor.green, mHighlightColor.blue, mHighlightColor.alpha); - gr_fill(mRenderX, yPos, mRenderW, actualItemHeight); - } - - if (itemindex == selectedItem) { - // Use the highlight color for the font - gr_color(mFontHighlightColor.red, mFontHighlightColor.green, mFontHighlightColor.blue, mFontHighlightColor.alpha); - } else { - // Set the color for the font - gr_color(mFontColor.red, mFontColor.green, mFontColor.blue, mFontColor.alpha); - } - - // render icon - if (icon && icon->GetResource()) { - int currentIconHeight = icon->GetHeight(); - int currentIconWidth = icon->GetWidth(); - int currentIconOffsetY = (actualItemHeight - currentIconHeight) / 2; - int currentIconOffsetX = (maxIconWidth - currentIconWidth) / 2; - int image_y = (yPos + currentIconOffsetY); - gr_blit(icon->GetResource(), 0, 0, currentIconWidth, currentIconHeight, mRenderX + currentIconOffsetX, image_y); - } - - // render label text - gr_textEx(mRenderX + maxIconWidth + 5, yPos + fontOffsetY, label.c_str(), fontResource); + RenderItem(itemindex, yPos, itemindex == selectedItem); // Add the separator gr_color(mSeparatorColor.red, mSeparatorColor.green, mSeparatorColor.blue, mSeparatorColor.alpha); @@ -285,26 +245,25 @@ int GUIScrollList::Render(void) yPos += actualItemHeight; } - // Render the Header + // Render the Header (last so that it overwrites the top most row for per pixel scrolling) yPos = mRenderY; if (mHeaderH > 0) { // First step, fill background gr_color(mHeaderBackgroundColor.red, mHeaderBackgroundColor.green, mHeaderBackgroundColor.blue, mHeaderBackgroundColor.alpha); gr_fill(mRenderX, mRenderY, mRenderW, mHeaderH); - int mIconOffsetX = 0; + int IconOffsetX = 0; // render the icon if it exists - ImageResource* headerIcon = mHeaderIcon; - if (headerIcon && headerIcon->GetResource()) + if (mHeaderIcon && mHeaderIcon->GetResource()) { - gr_blit(headerIcon->GetResource(), 0, 0, mHeaderIconWidth, mHeaderIconHeight, mRenderX + ((mHeaderIconWidth - maxIconWidth) / 2), (yPos + (int)((mHeaderH - mHeaderIconHeight) / 2))); - mIconOffsetX = maxIconWidth; + gr_blit(mHeaderIcon->GetResource(), 0, 0, mHeaderIconWidth, mHeaderIconHeight, mRenderX + ((mHeaderIconWidth - maxIconWidth) / 2), (yPos + (int)((mHeaderH - mHeaderIconHeight) / 2))); + IconOffsetX = maxIconWidth; } // render the text gr_color(mHeaderFontColor.red, mHeaderFontColor.green, mHeaderFontColor.blue, mHeaderFontColor.alpha); - gr_textEx(mRenderX + mIconOffsetX + 5, yPos + (int)((mHeaderH - mFontHeight) / 2), mLastHeaderValue.c_str(), fontResource); + gr_textEx(mRenderX + IconOffsetX + 5, yPos + (int)((mHeaderH - mFontHeight) / 2), mLastHeaderValue.c_str(), mFont->GetResource()); // Add the separator gr_color(mHeaderSeparatorColor.red, mHeaderSeparatorColor.green, mHeaderSeparatorColor.blue, mHeaderSeparatorColor.alpha); @@ -349,6 +308,45 @@ int GUIScrollList::Render(void) return 0; } +void GUIScrollList::RenderItem(size_t itemindex, int yPos, bool selected) +{ + RenderStdItem(yPos, selected, NULL, "implement RenderItem!"); +} + +void GUIScrollList::RenderStdItem(int yPos, bool selected, ImageResource* icon, const char* text, int iconAndTextH) +{ + if (hasHighlightColor && selected) { + // Highlight the item background of the selected item + gr_color(mHighlightColor.red, mHighlightColor.green, mHighlightColor.blue, mHighlightColor.alpha); + gr_fill(mRenderX, yPos, mRenderW, actualItemHeight); + } + + if (selected) { + // Use the highlight color for the font + gr_color(mFontHighlightColor.red, mFontHighlightColor.green, mFontHighlightColor.blue, mFontHighlightColor.alpha); + } else { + // Set the color for the font + gr_color(mFontColor.red, mFontColor.green, mFontColor.blue, mFontColor.alpha); + } + + if (!iconAndTextH) + iconAndTextH = actualItemHeight; + + // render icon + if (icon && icon->GetResource()) { + int iconH = icon->GetHeight(); + int iconW = icon->GetWidth(); + int iconY = yPos + (iconAndTextH - iconH) / 2; + int iconX = mRenderX + (maxIconWidth - iconW) / 2; + gr_blit(icon->GetResource(), 0, 0, iconW, iconH, iconX, iconY); + } + + // render label text + int textX = mRenderX + maxIconWidth + 5; + int textY = yPos + (iconAndTextH - mFontHeight) / 2; + gr_textEx(textX, textY, text, mFont->GetResource()); +} + int GUIScrollList::Update(void) { if(!isConditionTrue()) -- cgit v1.2.3