Пример #1
0
	void BlockBox::handleLayout(LayoutEngine& eng, const Dimensions& containing)
	{
		if(isReplaceable()) {
			layoutChildren(eng);
		} else {
			layoutChildren(eng);
			layoutHeight(containing);
		}

		if(isFloat()) {
			FixedPoint top = 0;
			const FixedPoint lh = getStyleNode()->getHeight()->isAuto() ? getLineHeight() : getStyleNode()->getHeight()->getLength().compute(containing.content_.height);
			const FixedPoint box_w = getDimensions().content_.width;

			FixedPoint y = 0;
			FixedPoint x = 0;

			FixedPoint y1 = y + getOffset().y;
			FixedPoint left = getStyleNode()->getFloat() == Float::LEFT ? eng.getXAtPosition(y1, y1 + lh) + x : eng.getX2AtPosition(y1, y1 + lh);
			FixedPoint w = eng.getWidthAtPosition(y1, y1 + lh, containing.content_.width);
			bool placed = false;
			while(!placed) {
				if(w >= box_w) {
					left = left - (getStyleNode()->getFloat() == Float::LEFT ? x : box_w) + getMBPLeft();
					top = y + getMBPTop() + containing.content_.height;
					placed = true;
				} else {
					y += lh;
					y1 = y + getOffset().y;
					left = getStyleNode()->getFloat() == Float::LEFT ? eng.getXAtPosition(y1, y1 + lh) + x : eng.getX2AtPosition(y1, y1 + lh);
					w = eng.getWidthAtPosition(y1, y1 + lh, containing.content_.width);
				}
			}
			setContentX(left);
			setContentY(top);

		} else {
			for(auto& child : getChildren()) {
				setContentHeight(child->getTop() + child->getHeight() + child->getMBPBottom());
			}
		}
	}
Пример #2
0
	void ListItemBox::handleLayout(LayoutEngine& eng, const Dimensions& containing) 
	{
		auto lst = getStyleNode()->getListStyleType();
		switch(lst) {
			case ListStyleType::DISC: /* is the default */ break;
			case ListStyleType::CIRCLE:
				marker_ = utils::codepoint_to_utf8(marker_circle);
				break;
			case ListStyleType::SQUARE:
				marker_ = utils::codepoint_to_utf8(marker_square);
				break;
			case ListStyleType::DECIMAL: {
				std::ostringstream ss;
				ss << std::dec << count_ << ".";
				marker_ = ss.str();
				break;
			}
			case ListStyleType::DECIMAL_LEADING_ZERO: {
				std::ostringstream ss;
				ss << std::dec << std::setfill('0') << std::setw(2) << count_ << ".";
				marker_ = ss.str();
				break;
			}
			case ListStyleType::LOWER_ROMAN:
				if(count_ < 4000) {
					marker_ = to_roman(count_, true) + ".";
				}
				break;
			case ListStyleType::UPPER_ROMAN:
				if(count_ < 4000) {
					marker_ = to_roman(count_, false) + ".";
				}
				break;
			case ListStyleType::LOWER_GREEK:
				if(count_ <= (marker_lower_greek_end - marker_lower_greek + 1)) {
					marker_ = utils::codepoint_to_utf8(marker_lower_greek + count_) + ".";
				}
				break;
			case ListStyleType::LOWER_ALPHA:
			case ListStyleType::LOWER_LATIN:
				if(count_ <= (marker_lower_latin_end - marker_lower_latin + 1)) {
					marker_ = utils::codepoint_to_utf8(marker_lower_latin + count_) + ".";
				}
				break;
			case ListStyleType::UPPER_ALPHA:
			case ListStyleType::UPPER_LATIN:
				if(count_ <= (marker_upper_latin_end - marker_upper_latin + 1)) {
					marker_ = utils::codepoint_to_utf8(marker_upper_latin + count_) + ".";
				}
				break;
			case ListStyleType::ARMENIAN:
				if(count_ <= (marker_armenian_end - marker_armenian + 1)) {
					marker_ = utils::codepoint_to_utf8(marker_armenian + count_) + ".";
				}
				break;
			case ListStyleType::GEORGIAN:
				if(count_ <= (marker_georgian_end - marker_georgian + 1)) {
					marker_ = utils::codepoint_to_utf8(marker_georgian + count_) + ".";
				}
				break;
			case ListStyleType::NONE:
			default: 
				marker_.clear();
				break;
		}

		FixedPoint top = getMBPTop() + containing.content_.height;
		FixedPoint left = getMBPLeft();

		if(isFloat()) {
			// XXX fixme to use a more intelligent approach than iterating every pixel!
			const FixedPoint lh = 65536;//getDimensions().content_.height;
			const FixedPoint box_w = getDimensions().content_.width;

			FixedPoint y = getMBPTop();
			FixedPoint x = getMBPLeft();

			FixedPoint y1 = y + getOffset().y;
			left = getStyleNode()->getFloat() == Float::LEFT ? eng.getXAtPosition(y1, y1 + lh) + x : eng.getX2AtPosition(y1, y1 + lh);
			FixedPoint w = eng.getWidthAtPosition(y1, y1 + lh, containing.content_.width);
			bool placed = false;
			while(!placed) {
				if(w >= box_w) {
					left = left - (getStyleNode()->getFloat() == Float::LEFT ? x : box_w);
					top = y;
					placed = true;
				} else {
					y += lh;
					y1 = y + getOffset().y;
					left = getStyleNode()->getFloat() == Float::LEFT ? eng.getXAtPosition(y1, y1 + lh) + x : eng.getX2AtPosition(y1, y1 + lh);
					w = eng.getWidthAtPosition(y1, y1 + lh, containing.content_.width);
				}
			}
		}

		setContentX(left);
		setContentY(top);

		auto& css_height = getStyleNode()->getHeight();
		if(!css_height->isAuto()) {
			FixedPoint h = css_height->getLength().compute(containing.content_.height);
			//if(h > child_height_) {
			//	/* apply overflow properties */
			//}
			setContentHeight(h);
		}

	}