Home | History | Annotate | Download | only in views
      1 
      2 /*
      3  * Copyright 2011 Google Inc.
      4  *
      5  * Use of this source code is governed by a BSD-style license that can be
      6  * found in the LICENSE file.
      7  */
      8 #include "SkWidgetViews.h"
      9 #include "SkTextBox.h"
     10 
     11 #ifdef SK_DEBUG
     12 static void assert_no_attr(const SkDOM& dom, const SkDOM::Node* node, const char attr[])
     13 {
     14     const char* value = dom.findAttr(node, attr);
     15     if (value)
     16         SkDebugf("unknown attribute %s=\"%s\"\n", attr, value);
     17 }
     18 #else
     19     #define assert_no_attr(dom, node, attr)
     20 #endif
     21 
     22 SkStaticTextView::SkStaticTextView()
     23 {
     24 	fMargin.set(0, 0);
     25 	fMode = kFixedSize_Mode;
     26 	fSpacingAlign = SkTextBox::kStart_SpacingAlign;
     27 
     28 //	init_skin_paint(kStaticText_SkinEnum, &fPaint);
     29 }
     30 
     31 SkStaticTextView::~SkStaticTextView()
     32 {
     33 }
     34 
     35 void SkStaticTextView::computeSize()
     36 {
     37 	if (fMode == kAutoWidth_Mode)
     38 	{
     39 		SkScalar width = fPaint.measureText(fText.c_str(), fText.size());
     40 		this->setWidth(width + fMargin.fX * 2);
     41 	}
     42 	else if (fMode == kAutoHeight_Mode)
     43 	{
     44 		SkScalar width = this->width() - fMargin.fX * 2;
     45 		int lines = width > 0 ? SkTextLineBreaker::CountLines(fText.c_str(), fText.size(), fPaint, width) : 0;
     46 
     47 		this->setHeight(lines * fPaint.getFontSpacing() + fMargin.fY * 2);
     48 	}
     49 }
     50 
     51 void SkStaticTextView::setMode(Mode mode)
     52 {
     53 	SkASSERT((unsigned)mode < kModeCount);
     54 
     55 	if (fMode != mode)
     56 	{
     57 		fMode = SkToU8(mode);
     58 		this->computeSize();
     59 	}
     60 }
     61 
     62 void SkStaticTextView::setSpacingAlign(SkTextBox::SpacingAlign align)
     63 {
     64 	fSpacingAlign = SkToU8(align);
     65 	this->inval(NULL);
     66 }
     67 
     68 void SkStaticTextView::getMargin(SkPoint* margin) const
     69 {
     70 	if (margin)
     71 		*margin = fMargin;
     72 }
     73 
     74 void SkStaticTextView::setMargin(SkScalar dx, SkScalar dy)
     75 {
     76 	if (fMargin.fX != dx || fMargin.fY != dy)
     77 	{
     78 		fMargin.set(dx, dy);
     79 		this->computeSize();
     80 		this->inval(NULL);
     81 	}
     82 }
     83 
     84 size_t SkStaticTextView::getText(SkString* text) const
     85 {
     86 	if (text)
     87 		*text = fText;
     88 	return fText.size();
     89 }
     90 
     91 size_t SkStaticTextView::getText(char text[]) const
     92 {
     93 	if (text)
     94 		memcpy(text, fText.c_str(), fText.size());
     95 	return fText.size();
     96 }
     97 
     98 void SkStaticTextView::setText(const SkString& text)
     99 {
    100 	this->setText(text.c_str(), text.size());
    101 }
    102 
    103 void SkStaticTextView::setText(const char text[])
    104 {
    105 	if (text == NULL)
    106 		text = "";
    107 	this->setText(text, strlen(text));
    108 }
    109 
    110 void SkStaticTextView::setText(const char text[], size_t len)
    111 {
    112 	if (!fText.equals(text, len))
    113 	{
    114 		fText.set(text, len);
    115 		this->computeSize();
    116 		this->inval(NULL);
    117 	}
    118 }
    119 
    120 void SkStaticTextView::getPaint(SkPaint* paint) const
    121 {
    122 	if (paint)
    123 		*paint = fPaint;
    124 }
    125 
    126 void SkStaticTextView::setPaint(const SkPaint& paint)
    127 {
    128 	if (fPaint != paint)
    129 	{
    130 		fPaint = paint;
    131 		this->computeSize();
    132 		this->inval(NULL);
    133 	}
    134 }
    135 
    136 void SkStaticTextView::onDraw(SkCanvas* canvas)
    137 {
    138 	this->INHERITED::onDraw(canvas);
    139 
    140 	if (fText.isEmpty())
    141 		return;
    142 
    143 	SkTextBox	box;
    144 
    145 	box.setMode(fMode == kAutoWidth_Mode ? SkTextBox::kOneLine_Mode : SkTextBox::kLineBreak_Mode);
    146 	box.setSpacingAlign(this->getSpacingAlign());
    147 	box.setBox(fMargin.fX, fMargin.fY, this->width() - fMargin.fX, this->height() - fMargin.fY);
    148 	box.draw(canvas, fText.c_str(), fText.size(), fPaint);
    149 }
    150 
    151 void SkStaticTextView::onInflate(const SkDOM& dom, const SkDOM::Node* node)
    152 {
    153 #if 0
    154 	this->INHERITED::onInflate(dom, node);
    155 
    156 	int	index;
    157 	if ((index = dom.findList(node, "mode", "fixed,auto-width,auto-height")) >= 0)
    158 		this->setMode((Mode)index);
    159 	else
    160 		assert_no_attr(dom, node, "mode");
    161 
    162 	if ((index = dom.findList(node, "spacing-align", "start,center,end")) >= 0)
    163 		this->setSpacingAlign((SkTextBox::SpacingAlign)index);
    164 	else
    165 		assert_no_attr(dom, node, "spacing-align");
    166 
    167 	SkScalar s[2];
    168 	if (dom.findScalars(node, "margin", s, 2))
    169 		this->setMargin(s[0], s[1]);
    170 	else
    171 		assert_no_attr(dom, node, "margin");
    172 
    173 	const char* text = dom.findAttr(node, "text");
    174 	if (text)
    175 		this->setText(text);
    176 
    177 	if ((node = dom.getFirstChild(node, "paint")) != NULL &&
    178 		(node = dom.getFirstChild(node, "screenplay")) != NULL)
    179 	{
    180 		inflate_paint(dom, node, &fPaint);
    181 	}
    182 #endif
    183 }
    184 
    185