HTMLElementImpl *HTMLTableElementImpl::insertRow( long index, int &exceptioncode ) { // The DOM requires that we create a tbody if the table is empty // (cf DOM2TS HTMLTableElement31 test) // (note: this is different from "if the table has no sections", since we can have // <TABLE><TR>) if(!firstBody && !head && !foot && !hasChildNodes()) setTBody( new HTMLTableSectionElementImpl(docPtr(), ID_TBODY, true /* implicit */) ); //kdDebug(6030) << k_funcinfo << index << endl; // IE treats index=-1 as default value meaning 'append after last' // This isn't in the DOM. So, not implemented yet. HTMLTableSectionElementImpl* section = 0L; HTMLTableSectionElementImpl* lastSection = 0L; NodeImpl *node = firstChild(); bool append = (index == -1); bool found = false; for ( ; node && (index>=0 || append) ; node = node->nextSibling() ) { // there could be 2 tfoot elements in the table. Only the first one is the "foot", that's why we have the more // complicated if statement below. if ( node != foot && (node->id() == ID_THEAD || node->id() == ID_TFOOT || node->id() == ID_TBODY) ) { section = static_cast<HTMLTableSectionElementImpl *>(node); lastSection = section; //kdDebug(6030) << k_funcinfo << "section id=" << node->id() << " rows:" << section->numRows() << endl; if ( !append ) { int rows = section->numRows(); if ( rows > index ) { found = true; break; } else index -= rows; //kdDebug(6030) << " index is now " << index << endl; } } } if ( !found && foot ) section = static_cast<HTMLTableSectionElementImpl *>(foot); // Index == 0 means "insert before first row in current section" // or "append after last row" (if there's no current section anymore) if ( !section && ( index == 0 || append ) ) { section = lastSection; index = section ? section->numRows() : 0; } if ( section && (index >= 0 || append) ) { //kdDebug(6030) << "Inserting row into section " << section << " at index " << index << endl; return section->insertRow( index, exceptioncode ); } else { // No more sections => index is too big exceptioncode = DOMException::INDEX_SIZE_ERR; return 0L; } }
void HTMLTableElementImpl::deleteRow( long index, int &exceptioncode ) { long sectionIndex; HTMLTableSectionElementImpl* section; if ( findRowSection( index, section, sectionIndex ) ) section->deleteRow( sectionIndex, exceptioncode ); else if ( section && index == -1 ) section->deleteRow( -1, exceptioncode ); else exceptioncode = DOMException::INDEX_SIZE_ERR; }
void HTMLTableElementImpl::deleteRow( long index, int &exceptioncode ) { HTMLTableSectionElementImpl* section = 0L; NodeImpl *node = firstChild(); bool lastRow = index == -1; HTMLTableSectionElementImpl* lastSection = 0L; bool found = false; for ( ; node ; node = node->nextSibling() ) { if ( node != foot && (node->id() == ID_THEAD || node->id() == ID_TFOOT || node->id() == ID_TBODY) ) { section = static_cast<HTMLTableSectionElementImpl *>(node); lastSection = section; int rows = section->numRows(); if ( !lastRow ) { if ( rows > index ) { found = true; break; } else index -= rows; } } section = 0L; } if ( !found && foot ) section = static_cast<HTMLTableSectionElementImpl *>(foot); if ( lastRow ) lastSection->deleteRow( -1, exceptioncode ); else if ( section && index >= 0 && index < section->numRows() ) section->deleteRow( index, exceptioncode ); else exceptioncode = DOMException::INDEX_SIZE_ERR; }
long HTMLTableRowElementImpl::rowIndex() const { int rIndex = 0; NodeImpl *table = parentNode(); if ( !table ) return -1; table = table->parentNode(); if ( !table || table->id() != ID_TABLE ) return -1; HTMLTableSectionElementImpl *foot = static_cast<HTMLTableElementImpl *>(table)->tFoot(); NodeImpl *node = table->firstChild(); while ( node ) { if ( node != foot && (node->id() == ID_THEAD || node->id() == ID_TFOOT || node->id() == ID_TBODY) ) { HTMLTableSectionElementImpl* section = static_cast<HTMLTableSectionElementImpl *>(node); const NodeImpl *row = section->firstChild(); while ( row ) { if ( row == this ) return rIndex; rIndex++; row = row->nextSibling(); } } node = node->nextSibling(); } const NodeImpl *row = foot->firstChild(); while ( row ) { if ( row == this ) return rIndex; rIndex++; row = row->nextSibling(); } // should never happen return -1; }
HTMLElementImpl *HTMLTableElementImpl::insertRow( long index, int &exceptioncode ) { // The DOM requires that we create a tbody if the table is empty // (cf DOM2TS HTMLTableElement31 test). This includes even the cases where // there are <tr>'s immediately under the table, as they're essentially // ignored by these functions. HTMLTableSectionElementImpl* foot = tFoot(); HTMLTableSectionElementImpl* head = tHead(); if(!tFirstBody() && !foot && !head) setTBody( new HTMLTableSectionElementImpl(docPtr(), ID_TBODY, true /* implicit */) ); //kdDebug(6030) << k_funcinfo << index << endl; long sectionIndex; HTMLTableSectionElementImpl* section; if ( findRowSection( index, section, sectionIndex ) ) return section->insertRow( sectionIndex, exceptioncode ); else if ( index == -1 || sectionIndex == 0 ) return section->insertRow( section->numRows(), exceptioncode ); // The index is too big. exceptioncode = DOMException::INDEX_SIZE_ERR; return 0L; }
HTMLElementImpl *HTMLTableElementImpl::insertRow( long index, int &exceptioncode ) { // The DOM requires that we create a tbody if the table is empty // (cf DOM2TS HTMLTableElement31 test) // (note: this is different from "if the table has no sections", since we can have // <TABLE><TR>) if(!firstBody && !head && !foot && !hasChildNodes()) setTBody( new HTMLTableSectionElementImpl(docPtr(), ID_TBODY, true /* implicit */) ); //kdDebug(6030) << k_funcinfo << index << endl; // IE treats index=-1 as default value meaning 'append after last' // This isn't in the DOM. So, not implemented yet. HTMLTableSectionElementImpl* section = 0L; HTMLTableSectionElementImpl* lastSection = 0L; NodeImpl *node = firstChild(); bool append = index == -1; for ( ; node && (index>=0 || append) ; node = node->nextSibling() ) { if ( node->id() == ID_THEAD || node->id() == ID_TFOOT || node->id() == ID_TBODY ) { section = static_cast<HTMLTableSectionElementImpl *>(node); lastSection = section; //kdDebug(6030) << k_funcinfo << "section id=" << node->id() << " rows:" << section->numRows() << endl; if ( !append ) { int rows = section->numRows(); if ( rows > index ) break; else index -= rows; //kdDebug(6030) << " index is now " << index << endl; } } // Note: we now can have both TR and sections (THEAD/TBODY/TFOOT) as children of a TABLE else if ( node->id() == ID_TR ) { section = 0L; //kdDebug(6030) << k_funcinfo << "row" << endl; if (!append && !index) { // Insert row right here, before "node" HTMLTableRowElementImpl* row = new HTMLTableRowElementImpl(docPtr()); insertBefore(row, node, exceptioncode ); return row; } if ( !append ) index--; //kdDebug(6030) << " index is now " << index << endl; } section = 0L; } // Index == 0 means "insert before first row in current section" // or "append after last row" (if there's no current section anymore) if ( !section && ( index == 0 || append ) ) { section = lastSection; index = section ? section->numRows() : 0; } if ( section && ( index >= 0 || append ) ) { //kdDebug(6030) << "Inserting row into section " << section << " at index " << index << endl; return section->insertRow( index, exceptioncode ); } else { // No more sections => index is too big exceptioncode = DOMException::INDEX_SIZE_ERR; return 0L; } }