diff options
Diffstat (limited to 'khtml/rendering/render_list.cpp')
-rw-r--r-- | khtml/rendering/render_list.cpp | 586 |
1 files changed, 0 insertions, 586 deletions
diff --git a/khtml/rendering/render_list.cpp b/khtml/rendering/render_list.cpp deleted file mode 100644 index 769b79670..000000000 --- a/khtml/rendering/render_list.cpp +++ /dev/null @@ -1,586 +0,0 @@ -/** - * This file is part of the HTML rendering engine for KDE. - * - * Copyright (C) 1999-2003 Lars Knoll (knoll@kde.org) - * (C) 1999 Antti Koivisto (koivisto@kde.org) - * (C) 2000-2002 Dirk Mueller (mueller@kde.org) - * (C) 2003 Apple Computer, Inc. - * (C) 2004-2005 Allan Sandfeld Jensen (kde@carewolf.com) - * - * This library is free software; you can redistribute it and/or - * modify it under the terms of the GNU Library General Public - * License as published by the Free Software Foundation; either - * version 2 of the License, or (at your option) any later version. - * - * This library is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU - * Library General Public License for more details. - * - * You should have received a copy of the GNU Library General Public License - * along with this library; see the file COPYING.LIB. If not, write to - * the Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor, - * Boston, MA 02110-1301, USA. - * - */ - -#include "rendering/render_list.h" -#include "rendering/render_canvas.h" -#include "rendering/enumerate.h" -#include "rendering/counter_tree.h" -#include "html/html_listimpl.h" -#include "misc/helper.h" -#include "misc/htmltags.h" -#include "misc/loader.h" -#include "xml/dom_docimpl.h" - -#include <kdebug.h> -#include <kglobal.h> -#include <tqvaluelist.h> - -//#define BOX_DEBUG - -using namespace khtml; -using namespace Enumerate; - -const int cMarkerPadding = 7; - -// ------------------------------------------------------------------------- - -RenderListItem::RenderListItem(DOM::NodeImpl* node) - : RenderBlock(node) -{ - // init RenderObject attributes - setInline(false); // our object is not Inline - - predefVal = -1; - m_marker = 0; - m_counter = 0; - m_insideList = false; - m_deleteMarker = false; -} - -void RenderListItem::setStyle(RenderStyle *_style) -{ - RenderBlock::setStyle(_style); - - RenderStyle *newStyle = new RenderStyle(); - newStyle->ref(); - - newStyle->inheritFrom(style()); - - if(!m_marker && style()->listStyleType() != LNONE) { - m_marker = new (renderArena()) RenderListMarker(element()); - m_marker->setIsAnonymous( true ); - m_marker->setStyle(newStyle); - m_marker->setListItem( this ); - m_deleteMarker = true; - } else if ( m_marker && style()->listStyleType() == LNONE) { - m_marker->detach(); - m_marker = 0; - } - else if ( m_marker ) { - m_marker->setStyle(newStyle); - } - - newStyle->deref(); -} - -void RenderListItem::detach() -{ - if ( m_marker && m_deleteMarker ) - m_marker->detach(); - RenderBlock::detach(); -} - -static RenderObject* getParentOfFirstLineBox(RenderObject* curr, RenderObject* marker) -{ - RenderObject* firstChild = curr->firstChild(); - if (!firstChild) - return 0; - - for (RenderObject* currChild = firstChild; - currChild; currChild = currChild->nextSibling()) { - if (currChild == marker) - continue; - - if (currChild->isInline()) - return curr; - - if (currChild->isFloating() || currChild->isPositioned()) - continue; - - if (currChild->isTable() || !currChild->isRenderBlock()) - break; - - if (currChild->style()->htmlHacks() && currChild->element() && - (currChild->element()->id() == ID_UL || currChild->element()->id() == ID_OL)) - break; - - RenderObject* lineBox = getParentOfFirstLineBox(currChild, marker); - if (lineBox) - return lineBox; - } - - return 0; -} - - -void RenderListItem::updateMarkerLocation() -{ - // Sanity check the location of our marker. - if (m_marker) { - RenderObject* markerPar = m_marker->parent(); - RenderObject* lineBoxParent = getParentOfFirstLineBox(this, m_marker); - if (!lineBoxParent) { - // If the marker is currently contained inside an anonymous box, - // then we are the only item in that anonymous box (since no line box - // parent was found). It's ok to just leave the marker where it is - // in this case. - if (markerPar && markerPar->isAnonymousBlock()) - lineBoxParent = markerPar; - else - lineBoxParent = this; - } - if (markerPar != lineBoxParent) - { - if (markerPar) - markerPar->removeChild(m_marker); - if (!lineBoxParent) - lineBoxParent = this; - lineBoxParent->addChild(m_marker, lineBoxParent->firstChild()); - m_deleteMarker = false; - if (!m_marker->minMaxKnown()) - m_marker->calcMinMaxWidth(); - recalcMinMaxWidths(); - } - } -} - -void RenderListItem::calcMinMaxWidth() -{ - // Make sure our marker is in the correct location. - updateMarkerLocation(); - if (!minMaxKnown()) - RenderBlock::calcMinMaxWidth(); -} -/* -short RenderListItem::marginLeft() const -{ - if (m_insideList) - return RenderBlock::marginLeft(); - else - return kMax(m_marker->markerWidth(), RenderBlock::marginLeft()); -} - -short RenderListItem::marginRight() const -{ - return RenderBlock::marginRight(); -}*/ - -void RenderListItem::layout( ) -{ - KHTMLAssert( needsLayout() ); - KHTMLAssert( minMaxKnown() ); - - updateMarkerLocation(); - RenderBlock::layout(); -} - -// ----------------------------------------------------------- - -RenderListMarker::RenderListMarker(DOM::NodeImpl* node) - : RenderBox(node), m_listImage(0), m_markerWidth(0) -{ - // init RenderObject attributes - setInline(true); // our object is Inline - setReplaced(true); // pretend to be replaced - // val = -1; - // m_listImage = 0; -} - -RenderListMarker::~RenderListMarker() -{ - if(m_listImage) - m_listImage->deref(this); - if (m_listItem) - m_listItem->resetListMarker(); -} - -void RenderListMarker::setStyle(RenderStyle *s) -{ - if ( s && style() && s->listStylePosition() != style()->listStylePosition() ) - setNeedsLayoutAndMinMaxRecalc(); - - RenderBox::setStyle(s); - - if ( m_listImage != style()->listStyleImage() ) { - if(m_listImage) m_listImage->deref(this); - m_listImage = style()->listStyleImage(); - if(m_listImage) m_listImage->ref(this); - } -} - - -void RenderListMarker::paint(PaintInfo& paintInfo, int _tx, int _ty) -{ - if (paintInfo.phase != PaintActionForeground) - return; - - if (style()->visibility() != VISIBLE) return; - - _tx += m_x; - _ty += m_y; - - if((_ty > paintInfo.r.bottom()) || (_ty + m_height <= paintInfo.r.top())) - return; - - if(shouldPaintBackgroundOrBorder()) - paintBoxDecorations(paintInfo, _tx, _ty); - - TQPainter* p = paintInfo.p; -#ifdef DEBUG_LAYOUT - kdDebug( 6040 ) << nodeName().string() << "(ListMarker)::paintObject(" << _tx << ", " << _ty << ")" << endl; -#endif - p->setFont(style()->font()); - const TQFontMetrics fm = p->fontMetrics(); - - - // The marker needs to adjust its tx, for the case where it's an outside marker. - RenderObject* listItem = 0; - int leftLineOffset = 0; - int rightLineOffset = 0; - if (!listPositionInside()) { - listItem = this; - int yOffset = 0; - int xOffset = 0; - while (listItem && listItem != m_listItem) { - yOffset += listItem->yPos(); - xOffset += listItem->xPos(); - listItem = listItem->parent(); - } - - // Now that we have our xoffset within the listbox, we need to adjust ourselves by the delta - // between our current xoffset and our desired position (which is just outside the border box - // of the list item). - if (style()->direction() == LTR) { - leftLineOffset = m_listItem->leftRelOffset(yOffset, m_listItem->leftOffset(yOffset)); - _tx -= (xOffset - leftLineOffset) + m_listItem->paddingLeft() + m_listItem->borderLeft(); - } - else { - rightLineOffset = m_listItem->rightRelOffset(yOffset, m_listItem->rightOffset(yOffset)); - _tx += (rightLineOffset-xOffset) + m_listItem->paddingRight() + m_listItem->borderRight(); - } - } - - int offset = fm.ascent()*2/3; - bool haveImage = m_listImage && !m_listImage->isErrorImage(); - if (haveImage) - offset = m_listImage->pixmap().width(); - - int xoff = 0; - int yoff = fm.ascent() - offset; - - int bulletWidth = offset/2; - if (offset%2) - bulletWidth++; - if (!listPositionInside()) { - if (listItem && listItem->style()->direction() == LTR) - xoff = -cMarkerPadding - offset; - else - xoff = cMarkerPadding + (haveImage ? 0 : (offset - bulletWidth)); - } - else if (style()->direction() == RTL) - xoff += haveImage ? cMarkerPadding : (m_width - bulletWidth); - - if ( m_listImage && !m_listImage->isErrorImage()) { - p->drawPixmap( TQPoint( _tx + xoff, _ty ), m_listImage->pixmap()); - return; - } - -#ifdef BOX_DEBUG - p->setPen( Qt::red ); - p->drawRect( _tx + xoff, _ty + yoff, offset, offset ); -#endif - - const TQColor color( style()->color() ); - p->setPen( color ); - - switch(style()->listStyleType()) { - case LDISC: - p->setBrush( color ); - p->drawEllipse( _tx + xoff, _ty + (3 * yoff)/2, (offset>>1)+1, (offset>>1)+1 ); - return; - case LCIRCLE: - p->setBrush( Qt::NoBrush ); - p->drawEllipse( _tx + xoff, _ty + (3 * yoff)/2, (offset>>1)+1, (offset>>1)+1 ); - return; - case LSQUARE: - p->setBrush( color ); - p->drawRect( _tx + xoff, _ty + (3 * yoff)/2, (offset>>1)+1, (offset>>1)+1 ); - return; - case LBOX: - p->setBrush( Qt::NoBrush ); - p->drawRect( _tx + xoff, _ty + (3 * yoff)/2, (offset>>1)+1, (offset>>1)+1 ); - return; - case LDIAMOND: { - static TQPointArray diamond(4); - int x = _tx + xoff; - int y = _ty + (3 * yoff)/2 - 1; - int s = (offset>>2)+1; - diamond[0] = TQPoint(x+s, y); - diamond[1] = TQPoint(x+2*s, y+s); - diamond[2] = TQPoint(x+s, y+2*s); - diamond[3] = TQPoint(x, y+s); - p->setBrush( color ); - p->drawConvexPolygon( diamond, 0, 4 ); - return; - } - case LNONE: - return; - default: - if (!m_item.isEmpty()) { - if(listPositionInside()) { - if( style()->direction() == LTR) { - p->drawText(_tx, _ty, 0, 0, Qt::AlignLeft|TQt::DontClip, m_item); - p->drawText(_tx + fm.width(m_item), _ty, 0, 0, Qt::AlignLeft|TQt::DontClip, - TQString::fromLatin1(". ")); - } - else { - const TQString& punct(TQString::fromLatin1(" .")); - p->drawText(_tx, _ty, 0, 0, Qt::AlignLeft|TQt::DontClip, punct); - p->drawText(_tx + fm.width(punct), _ty, 0, 0, Qt::AlignLeft|TQt::DontClip, m_item); - } - } else { - if (style()->direction() == LTR) { - const TQString& punct(TQString::fromLatin1(". ")); - p->drawText(_tx-offset/2, _ty, 0, 0, Qt::AlignRight|TQt::DontClip, punct); - p->drawText(_tx-offset/2-fm.width(punct), _ty, 0, 0, Qt::AlignRight|TQt::DontClip, m_item); - } - else { - const TQString& punct(TQString::fromLatin1(" .")); - p->drawText(_tx+offset/2, _ty, 0, 0, Qt::AlignLeft|TQt::DontClip, punct); - p->drawText(_tx+offset/2+fm.width(punct), _ty, 0, 0, Qt::AlignLeft|TQt::DontClip, m_item); - } - } - } - } -} - -void RenderListMarker::layout() -{ - KHTMLAssert( needsLayout() ); - - if ( !minMaxKnown() ) - calcMinMaxWidth(); - - setNeedsLayout(false); -} - -void RenderListMarker::setPixmap( const TQPixmap &p, const TQRect& r, CachedImage *o) -{ - if(o != m_listImage) { - RenderBox::setPixmap(p, r, o); - return; - } - - if(m_width != m_listImage->pixmap_size().width() || m_height != m_listImage->pixmap_size().height()) - setNeedsLayoutAndMinMaxRecalc(); - else - repaintRectangle(0, 0, m_width, m_height); -} - -void RenderListMarker::calcMinMaxWidth() -{ - KHTMLAssert( !minMaxKnown() ); - - m_markerWidth = m_width = 0; - - if(m_listImage && !m_listImage->isErrorImage()) { - m_markerWidth = m_listImage->pixmap().width() + cMarkerPadding; - if (listPositionInside()) - m_width = m_markerWidth; - m_height = m_listImage->pixmap().height(); - m_minWidth = m_maxWidth = m_width; - setMinMaxKnown(); - return; - } - - const TQFontMetrics &fm = style()->fontMetrics(); - m_height = fm.ascent(); - - // Skip uncounted elements - switch(style()->listStyleType()) { - // Glyphs: - case LDISC: - case LCIRCLE: - case LSQUARE: - case LBOX: - case LDIAMOND: - m_markerWidth = fm.ascent(); - goto end; - default: - break; - } - - { // variable scope - CounterNode *counter = m_listItem->m_counter; - if (!counter) { - counter = m_listItem->getCounter("list-item", true); - counter->setRenderer(this); - m_listItem->m_counter = counter; - } - - - assert(counter); - int value = counter->count(); - if (counter->isReset()) value = counter->value(); - int total = value; - if (counter->parent()) total = counter->parent()->total(); - - switch(style()->listStyleType()) - { -// Numeric: - case LDECIMAL: - m_item.setNum ( value ); - break; - case DECIMAL_LEADING_ZERO: { - int decimals = 2; - int t = total/100; - while (t>0) { - t = t/10; - decimals++; - } - decimals = kMax(decimals, 2); - TQString num = TQString::number(value); - m_item.fill('0',decimals-num.length()); - m_item.append(num); - break; - } - case ARABIC_INDIC: - m_item = toArabicIndic( value ); - break; - case LAO: - m_item = toLao( value ); - break; - case PERSIAN: - case URDU: - m_item = toPersianUrdu( value ); - break; - case THAI: - m_item = toThai( value ); - break; - case TIBETAN: - m_item = toTibetan( value ); - break; -// Algoritmic: - case LOWER_ROMAN: - m_item = toRoman( value, false ); - break; - case UPPER_ROMAN: - m_item = toRoman( value, true ); - break; - case HEBREW: - m_item = toHebrew( value ); - break; - case ARMENIAN: - m_item = toArmenian( value ); - break; - case GEORGIAN: - m_item = toGeorgian( value ); - break; -// Alphabetic: - case LOWER_ALPHA: - case LOWER_LATIN: - m_item = toLowerLatin( value ); - break; - case UPPER_ALPHA: - case UPPER_LATIN: - m_item = toUpperLatin( value ); - break; - case LOWER_GREEK: - m_item = toLowerGreek( value ); - break; - case UPPER_GREEK: - m_item = toUpperGreek( value ); - break; - case HIRAGANA: - m_item = toHiragana( value ); - break; - case HIRAGANA_IROHA: - m_item = toHiraganaIroha( value ); - break; - case KATAKANA: - m_item = toKatakana( value ); - break; - case KATAKANA_IROHA: - m_item = toKatakanaIroha( value ); - break; -// Ideographic: - case JAPANESE_FORMAL: - m_item = toJapaneseFormal( value ); - break; - case JAPANESE_INFORMAL: - m_item = toJapaneseInformal( value ); - break; - case SIMP_CHINESE_FORMAL: - m_item = toSimpChineseFormal( value ); - break; - case SIMP_CHINESE_INFORMAL: - m_item = toSimpChineseInformal( value ); - break; - case TRAD_CHINESE_FORMAL: - m_item = toTradChineseFormal( value ); - break; - case CJK_IDEOGRAPHIC: - // CSS 3 List says treat as trad-chinese-informal - case TRAD_CHINESE_INFORMAL: - m_item = toTradChineseInformal( value ); - break; -// special: - case LNONE: - break; - default: - KHTMLAssert(false); - } - m_markerWidth = fm.width(m_item) + fm.width(TQString::fromLatin1(". ")); - } - -end: - if(listPositionInside()) - m_width = m_markerWidth; - - m_minWidth = m_width; - m_maxWidth = m_width; - - setMinMaxKnown(); -} - -short RenderListMarker::lineHeight(bool /*b*/) const -{ - return height(); -} - -short RenderListMarker::baselinePosition(bool /*b*/) const -{ - return height(); -} - -void RenderListMarker::calcWidth() -{ - RenderBox::calcWidth(); -} - -/* -int CounterListItem::recount() const -{ - static_cast<RenderListItem*>(m_renderer)->m_marker->setNeedsLayoutAndMinMaxRecalc(); -} - -void CounterListItem::setSelfDirty() -{ - -}*/ - - -#undef BOX_DEBUG |