diff --git a/changes.txt b/changes.txt index 329e3dce..2fef41ce 100644 --- a/changes.txt +++ b/changes.txt @@ -1,5 +1,13 @@ Changes in 1.8 (??.??.2011) + - IGUIEditBox: added missing serialization for Border + + - IGUIEditBox: remove bug that added spaces to the end of each line + + - IGUIEditBox: fix crash that happened when wordwrapping was enabled, spaces were entered beyond the border and then cursor-key was pressed. + + - IGUIEditBox::setDrawBackground added. + - CGUISkin::draw3DSunkenPane no longer ignores fillBackGround in non-flat mode. Also borderlines are no longer drawn overlapping to avoid ugly corners. - CDummyTransformationSceneNode::clone() added. diff --git a/include/IGUIEditBox.h b/include/IGUIEditBox.h index e3bba6eb..8b97174e 100644 --- a/include/IGUIEditBox.h +++ b/include/IGUIEditBox.h @@ -51,6 +51,9 @@ namespace gui /** \return true if the override color is enabled, false otherwise */ virtual bool isOverrideColorEnabled(void) const = 0; + //! Sets whether to draw the background + virtual void setDrawBackground(bool draw) = 0; + //! Turns the border on or off /** \param border: true if you want the border to be drawn, false if not */ virtual void setDrawBorder(bool border) = 0; diff --git a/source/Irrlicht/CGUIEditBox.cpp b/source/Irrlicht/CGUIEditBox.cpp index 756100c3..cb52d24d 100644 --- a/source/Irrlicht/CGUIEditBox.cpp +++ b/source/Irrlicht/CGUIEditBox.cpp @@ -32,7 +32,7 @@ CGUIEditBox::CGUIEditBox(const wchar_t* text, bool border, IGUIEnvironment* environment, IGUIElement* parent, s32 id, const core::rect& rectangle) : IGUIEditBox(environment, parent, id, rectangle), MouseMarking(false), - Border(border), OverrideColorEnabled(false), MarkBegin(0), MarkEnd(0), + Border(border), Background(true), OverrideColorEnabled(false), MarkBegin(0), MarkEnd(0), OverrideColor(video::SColor(101,255,255,255)), OverrideFont(0), LastBreakFont(0), Operator(0), BlinkStartTime(0), CursorPos(0), HScrollPos(0), VScrollPos(0), Max(0), WordWrap(false), MultiLine(false), AutoScroll(true), PasswordBox(false), @@ -121,6 +121,11 @@ void CGUIEditBox::setDrawBorder(bool border) Border = border; } +//! Sets whether to draw the background +void CGUIEditBox::setDrawBackground(bool draw) +{ + Background = draw; +} //! Sets if the text should use the overide color or the color in the gui skin. void CGUIEditBox::enableOverrideColor(bool enable) @@ -704,21 +709,25 @@ void CGUIEditBox::draw() FrameRect = AbsoluteRect; - // draw the border + EGUI_DEFAULT_COLOR bgCol = EGDC_GRAY_EDITABLE; + if ( isEnabled() ) + bgCol = focus ? EGDC_FOCUSED_EDITABLE : EGDC_EDITABLE; + + if (!Border && Background) + { + skin->draw2DRectangle(this, skin->getColor(bgCol), FrameRect, &AbsoluteClippingRect); + } if (Border) { - EGUI_DEFAULT_COLOR col = EGDC_GRAY_EDITABLE; - if ( isEnabled() ) - col = focus ? EGDC_FOCUSED_EDITABLE : EGDC_EDITABLE; - skin->draw3DSunkenPane(this, skin->getColor(col), - false, true, FrameRect, &AbsoluteClippingRect); - + // draw the border + skin->draw3DSunkenPane(this, skin->getColor(bgCol), false, Background, FrameRect, &AbsoluteClippingRect); FrameRect.UpperLeftCorner.X += skin->getSize(EGDS_TEXT_DISTANCE_X)+1; FrameRect.UpperLeftCorner.Y += skin->getSize(EGDS_TEXT_DISTANCE_Y)+1; FrameRect.LowerRightCorner.X -= skin->getSize(EGDS_TEXT_DISTANCE_X)+1; FrameRect.LowerRightCorner.Y -= skin->getSize(EGDS_TEXT_DISTANCE_Y)+1; } + core::rect localClipRect = FrameRect; localClipRect.clipAgainst(AbsoluteClippingRect); @@ -1056,7 +1065,10 @@ s32 CGUIEditBox::getCursorPos(s32 x, s32 y) if (x < CurrentTextRect.UpperLeftCorner.X) x = CurrentTextRect.UpperLeftCorner.X; - s32 idx = txtLine ? font->getCharacterFromPos(txtLine->c_str(), x - CurrentTextRect.UpperLeftCorner.X) : -1; + if ( !txtLine ) + return 0; + + s32 idx = font->getCharacterFromPos(txtLine->c_str(), x - CurrentTextRect.UpperLeftCorner.X); // click was on or left of the line if (idx != -1) @@ -1104,7 +1116,7 @@ void CGUIEditBox::breakText() if (c == L'\r') // Mac or Windows breaks { lineBreak = true; - c = ' '; + c = 0; if (Text[i+1] == L'\n') // Windows breaks { Text.erase(i+1); @@ -1114,7 +1126,7 @@ void CGUIEditBox::breakText() else if (c == L'\n') // Unix breaks { lineBreak = true; - c = ' '; + c = 0; } // don't break if we're not a multi-line edit box @@ -1123,35 +1135,35 @@ void CGUIEditBox::breakText() if (c == L' ' || c == 0 || i == (size-1)) { - if (word.size()) + // here comes the next whitespace, look if + // we can break the last word to the next line + // We also break whitespace, otherwise cursor would vanish beside the right border. + s32 whitelgth = font->getDimension(whitespace.c_str()).Width; + s32 worldlgth = font->getDimension(word.c_str()).Width; + + if (WordWrap && length + worldlgth + whitelgth > elWidth) { - // here comes the next whitespace, look if - // we can break the last word to the next line. - s32 whitelgth = font->getDimension(whitespace.c_str()).Width; - s32 worldlgth = font->getDimension(word.c_str()).Width; - - if (WordWrap && length + worldlgth + whitelgth > elWidth) - { - // break to next line - length = worldlgth; - BrokenText.push_back(line); - BrokenTextPositions.push_back(lastLineStart); - lastLineStart = i - (s32)word.size(); - line = word; - } - else - { - // add word to line - line += whitespace; - line += word; - length += whitelgth + worldlgth; - } - - word = L""; - whitespace = L""; + // break to next line + length = worldlgth; + BrokenText.push_back(line); + BrokenTextPositions.push_back(lastLineStart); + lastLineStart = i - (s32)word.size(); + line = word; + } + else + { + // add word to line + line += whitespace; + line += word; + length += whitelgth + worldlgth; } - whitespace += c; + word = L""; + whitespace = L""; + + + if ( c ) + whitespace += c; // compute line break if (lineBreak) @@ -1183,7 +1195,8 @@ void CGUIEditBox::breakText() void CGUIEditBox::setTextRect(s32 line) { - core::dimension2du d; + if ( line < 0 ) + return; IGUISkin* skin = Environment->getSkin(); if (!skin) @@ -1194,6 +1207,8 @@ void CGUIEditBox::setTextRect(s32 line) if (!font) return; + core::dimension2du d; + // get text dimension const u32 lineCount = (WordWrap || MultiLine) ? BrokenText.size() : 1; if (WordWrap || MultiLine) @@ -1321,6 +1336,8 @@ void CGUIEditBox::calculateScrollPos() // calculate horizontal scroll position s32 cursLine = getLineFromPos(CursorPos); + if ( cursLine < 0 ) + return; setTextRect(cursLine); // don't do horizontal scrolling when wordwrap is enabled. @@ -1395,6 +1412,8 @@ void CGUIEditBox::serializeAttributes(io::IAttributes* out, io::SAttributeReadWr { // IGUIEditBox::serializeAttributes(out,options); + out->addBool ("Border", Border); + out->addBool ("Background", Background); out->addBool ("OverrideColorEnabled",OverrideColorEnabled ); out->addColor ("OverrideColor", OverrideColor); // out->addFont("OverrideFont",OverrideFont); @@ -1418,6 +1437,8 @@ void CGUIEditBox::deserializeAttributes(io::IAttributes* in, io::SAttributeReadW { IGUIEditBox::deserializeAttributes(in,options); + setDrawBorder( in->getAttributeAsBool("Border") ); + setDrawBackground( in->getAttributeAsBool("Background") ); setOverrideColor(in->getAttributeAsColor("OverrideColor")); enableOverrideColor(in->getAttributeAsBool("OverrideColorEnabled")); setMax(in->getAttributeAsInt("MaxChars")); diff --git a/source/Irrlicht/CGUIEditBox.h b/source/Irrlicht/CGUIEditBox.h index 39ae7498..744d47a5 100644 --- a/source/Irrlicht/CGUIEditBox.h +++ b/source/Irrlicht/CGUIEditBox.h @@ -44,6 +44,9 @@ namespace gui /** \return true if the override color is enabled, false otherwise */ virtual bool isOverrideColorEnabled(void) const; + //! Sets whether to draw the background + virtual void setDrawBackground(bool draw); + //! Turns the border on or off virtual void setDrawBorder(bool border); @@ -135,6 +138,7 @@ namespace gui bool MouseMarking; bool Border; + bool Background; bool OverrideColorEnabled; s32 MarkBegin; s32 MarkEnd; diff --git a/source/Irrlicht/CGUIStaticText.cpp b/source/Irrlicht/CGUIStaticText.cpp index 4ae7b6a3..89943576 100644 --- a/source/Irrlicht/CGUIStaticText.cpp +++ b/source/Irrlicht/CGUIStaticText.cpp @@ -204,7 +204,7 @@ void CGUIStaticText::setTextRestrainedInside(bool restrainTextInside) { RestrainTextInside = restrainTextInside; } - + bool CGUIStaticText::isTextRestrainedInside() const { @@ -334,7 +334,7 @@ void CGUIStaticText::breakText() // we must break the last word to the next line. const s32 whitelgth = font->getDimension(whitespace.c_str()).Width; const s32 wordlgth = font->getDimension(word.c_str()).Width; - + if (wordlgth > elWidth) { // This word is too long to fit in the available space, look for @@ -347,7 +347,7 @@ void CGUIStaticText::breakText() core::stringw second = word.subString(where, word.size() - where); BrokenText.push_back(line + first + L"-"); const s32 secondLength = font->getDimension(second.c_str()).Width; - + length = secondLength; line = second; }