// TipView.cpp #include "TipView.h" #include #include #include #include using namespace std; __USE_CORTEX_NAMESPACE // -------------------------------------------------------- // // constants // -------------------------------------------------------- // const float TipView::s_xPad = 5.0; const float TipView::s_yPad = 2.0; // -------------------------------------------------------- // // *** dtor/ctors // -------------------------------------------------------- // TipView::~TipView() {} TipView::TipView() : BView( BRect(0,0,0,0), "TipView", B_FOLLOW_NONE, B_WILL_DRAW|B_FRAME_EVENTS), m_font(be_plain_font) { _initColors(); _initFont(); } // -------------------------------------------------------- // // *** operations // -------------------------------------------------------- // void TipView::setText( const char* text) { _setText(text); } // -------------------------------------------------------- // // *** BView // -------------------------------------------------------- // // Adapted from c.lenz' ToolTipView::Draw() void TipView::Draw( BRect updateRect) { BRect r = Bounds(); // Draw border and fill SetDrawingMode(B_OP_ALPHA); SetHighColor(m_borderLoColor); StrokeLine(r.LeftBottom(), r.RightBottom()); StrokeLine(r.RightTop(), r.RightBottom()); SetHighColor(m_borderHiColor); StrokeLine(r.LeftTop(), r.RightTop()); StrokeLine(r.LeftTop(), r.LeftBottom()); SetHighColor(m_viewColor); SetDrawingMode(B_OP_ALPHA); r.InsetBy(1.0, 1.0); FillRect(r); // Draw text SetDrawingMode(B_OP_OVER); SetHighColor(m_textColor); BPoint p = m_offset; for(uint32 n = 0; n < m_lineSet.size(); ++n) { uint32 from = m_lineSet[n]; uint32 to = (n < m_lineSet.size()-1) ? m_lineSet[n+1]-1 : m_text.Length(); if(to > from) DrawString( m_text.String() + from, to - from, p); p.y += (m_fontHeight.ascent + m_fontHeight.descent + m_fontHeight.leading); } } void TipView::FrameResized( float width, float height) { _inherited::FrameResized(width, height); _updateLayout(width, height); Invalidate(); } void TipView::GetPreferredSize( float* outWidth, float* outHeight) { // *outWidth = ceil(m_font.StringWidth(m_text.String()) + s_xPad*2); *outWidth = ceil(_maxTextWidth() + s_xPad*2); *outHeight = ceil(_textHeight() + s_yPad*2); } // -------------------------------------------------------- // // implementation // -------------------------------------------------------- // void _make_color( rgb_color* outColor, uint8 red, uint8 green, uint8 blue, uint8 alpha=255); void _make_color( rgb_color* outColor, uint8 red, uint8 green, uint8 blue, uint8 alpha) { outColor->red = red; outColor->green = green; outColor->blue = blue; outColor->alpha = alpha; } void TipView::_initColors() { SetViewColor(B_TRANSPARENT_COLOR); _make_color(&m_textColor, 0, 0, 0, 255); _make_color(&m_borderHiColor, 0, 0, 0, 255 /*196*/); _make_color(&m_borderLoColor, 0, 0, 0, 255 /*196*/); _make_color(&m_viewColor, 255, 255, 240, 255 /*216*/); } void TipView::_initFont() { SetFont(&m_font); m_font.GetHeight(&m_fontHeight); } void TipView::_updateLayout( float width, float height) { // center text m_offset.x = (width - _maxTextWidth()) / 2; m_offset.y = (height - _textHeight()) / 2; m_offset.y += m_fontHeight.ascent; } void TipView::_setText( const char* text) { ASSERT(text); m_lineSet.clear(); m_text = text; // skip leading newlines int32 n = 0; while(n < m_text.Length() && m_text[n] == '\n') ++n; // mark first line m_lineSet.push_back(n); // break following lines while(n < m_text.Length()) { int32 nextBreak = m_text.FindFirst('\n', n); // no more line breaks? if(nextBreak < n) break; n = nextBreak + 1; m_lineSet.push_back(n); } } float TipView::_maxTextWidth() { float max = 0.0; for(uint32 n = 0; n < m_lineSet.size(); ++n) { uint32 from = m_lineSet[n]; uint32 to = (n < m_lineSet.size()-1) ? m_lineSet[n+1]-1 : m_text.Length(); float lineWidth = m_font.StringWidth( m_text.String() + from, to - from); if(lineWidth > max) max = lineWidth; } return max; } float TipView::_textHeight() { float height = m_fontHeight.ascent + m_fontHeight.descent; if(m_lineSet.size() > 1) height += (m_lineSet.size()-1) * (m_fontHeight.ascent + m_fontHeight.descent + m_fontHeight.leading); return height; } // END -- TipView.cpp --