00001 #ifndef KWTABLEFRAMESET_H
00002 #define KWTABLEFRAMESET_H
00003
00004
00005
00006
00007
00008
00009
00010
00011
00012
00013
00014
00015
00016
00017
00018
00019
00020
00021
00022
00023
00024
00025
00026
00027
00028
00029
00030 #include "KWFrame.h"
00031 #include "KWTextFrameSet.h"
00032
00033 #include <qptrlist.h>
00034 #include <qvaluevector.h>
00035 #include <qobject.h>
00036 #include <qstring.h>
00037 #include <KoRichText.h>
00038
00039 class KWDocument;
00040 class KWTableFrameSetEdit;
00041 class QPainter;
00042 class KWAnchor;
00043 class KWordFrameSetIface;
00044 class KWFrameViewManager;
00045
00046 class RemovedRow;
00047 class RemovedColumn;
00048
00058 class KWTableFrameSet : public KWFrameSet
00059 {
00060 Q_OBJECT
00061 public:
00062
00067 class Cell : public KWTextFrameSet
00068 {
00069 unsigned int m_row, m_col;
00070 unsigned int m_rows, m_cols;
00071
00072 bool m_isJoinedCell;
00073 bool m_marker;
00074 void calcIfJoinedCell() {
00075 m_isJoinedCell = ( (m_rows > 1) || (m_cols > 1) );
00076 }
00077
00078 public:
00080 Cell( KWTableFrameSet *table, unsigned int row, unsigned int col, const QString & name = QString::null );
00081 Cell( KWTableFrameSet *table, const Cell &original );
00082
00083 virtual ~Cell();
00084
00085 uint firstRow() const { return m_row; }
00086 uint firstColumn() const { return m_col; }
00087 uint rowSpan() const { return m_rows; }
00088 uint columnSpan() const { return m_cols; }
00089
00090 uint lastRow() const { return m_row + m_rows - 1; }
00091 uint lastColumn() const { return m_col + m_cols - 1; }
00092 uint rowAfter() const { return m_row + m_rows; }
00093 uint columnAfter() const { return m_col + m_cols; }
00094
00095 void setFirstRow(uint row) { m_row = row; }
00096 void setFirstColumn(uint col) { m_col = col; }
00097 void setRowSpan(uint rows) {
00098 m_rows = rows;
00099 calcIfJoinedCell();
00100 }
00101 void setColumnSpan(uint cols) {
00102 m_cols = cols;
00103 calcIfJoinedCell();
00104 }
00105
00106 bool isFirstGridPosn(uint row, uint col) const {
00107 return (row == m_row) && (col == m_col);
00108 }
00109
00110 bool isFirstGridPosnFast(uint row, uint col) const {
00111 if(!m_isJoinedCell) return true;
00112 return (row == m_row) && (col == m_col);
00113 }
00114 virtual void addFrame(KWFrame *_frame, bool recalc = true);
00116 virtual void frameDeleted( KWFrame* frm, bool recalc );
00117
00118 bool isAboveOrLeftOf( unsigned row, unsigned column ) const;
00119 bool containsCell( unsigned row, unsigned column ) const;
00120
00121 double leftBorder();
00122 double rightBorder();
00123 double topBorder();
00124 double bottomBorder();
00125
00126 void setLeftBorder(KoBorder newBorder);
00127 void setRightBorder(KoBorder newBorder);
00128 void setTopBorder(KoBorder newBorder);
00129 void setBottomBorder(KoBorder newBorder);
00133 void setZOrder();
00134 bool isJoinedCell() const { return m_isJoinedCell; }
00135 void clearMark() { m_marker = false; }
00136 void setMark() { m_marker = true; }
00137 bool marked() const { return m_marker; }
00138
00140 void drawContents( QPainter *painter, const QRect & crect,
00141 const QColorGroup & cg, bool onlyChanged, bool resetChanged,
00142 KWFrameSetEdit * edit, KWViewMode * viewMode,
00143 KWFrameViewManager *frameViewManager );
00144
00145 };
00146 friend class Cell;
00147
00149 class Row {
00150 public:
00151 Cell* operator[] ( uint i ) const { return i < size() ? m_cellArray[i] : 0; }
00152 uint size() const { return m_cellArray.size(); }
00153 uint count() const { return m_cellArray.count(); }
00154
00155 void addCell( Cell *cell );
00156 void removeCell( Cell* cell );
00157
00164 QPtrVector< Cell > m_cellArray;
00165
00166 };
00167
00169 enum VisitType {
00175 VISIT_GRID = 1,
00176
00182 VISIT_CELL = 2,
00186 CHECKED = 3
00187 };
00188
00241 template<int VisitStyle = VISIT_CELL>
00242 class TableIterator {
00243 public:
00248 TableIterator (KWTableFrameSet *table);
00249
00250 Cell* toFirstCell ();
00251 void goToCell(Cell*);
00252
00253 operator Cell* () const { return m_cell; }
00254 Cell * current() const;
00255 Cell * operator->() { return m_cell; }
00256 Cell * operator++ ();
00257
00258 protected:
00259 KWTableFrameSet *m_table;
00260 void set_limits(uint left, uint right, uint high, uint low)
00261 {
00262 m_limit[LEFT] = left;
00263 m_limit[RIGHT] = right;
00264 m_limit[HIGH] = high;
00265 m_limit[LOW] = low;
00266 }
00267 private:
00268
00269 Cell *m_cell;
00270 uint m_row;
00271 uint m_col;
00272
00273 enum Direction {LEFT, RIGHT, HIGH, LOW};
00274 static const uint DIRECTION_SIZE = 4;
00275 uint m_limit[DIRECTION_SIZE];
00276 };
00277
00278 typedef TableIterator<VISIT_CELL> TableIter;
00279 typedef TableIterator<VISIT_GRID> GridIter;
00280 typedef TableIterator<CHECKED> CheckedIter;
00281
00291 class MarkedIterator : public GridIter {
00292 public:
00293 MarkedIterator(KWTableFrameSet *table);
00294 Cell *operator++();
00295
00296 };
00297
00298
00302 virtual FrameSetType type() const { return FT_TABLE; }
00303
00304 virtual KWordFrameSetIface* dcopObject();
00305
00306 virtual void addTextFrameSets( QPtrList<KWTextFrameSet> & lst, bool onlyReadWrite =false );
00307
00309 KWTableFrameSet( KWDocument *_doc, const QString & name );
00311 virtual ~KWTableFrameSet();
00312
00313 virtual KWFrameSetEdit * createFrameSetEdit( KWCanvas * canvas );
00314
00321 virtual void createEmptyRegion( const QRect & crect, QRegion & emptyRegion, KWViewMode *viewMode );
00322 void drawBorders( QPainter& painter, const QRect &crect, KWViewMode *viewMode );
00323 virtual void drawContents( QPainter * painter, const QRect & crect,
00324 const QColorGroup & cg, bool onlyChanged, bool resetChanged,
00325 KWFrameSetEdit *edit, KWViewMode *viewMode,
00326 KWFrameViewManager *frameViewManager );
00328 virtual void drawFrame(KWFrame *, QPainter *, const QRect &, const QRect&,
00329 const QPoint&,
00330 KWFrame *, const QColorGroup &, bool, bool,
00331 KWFrameSetEdit *, KWViewMode *, bool ) {}
00332
00333
00334 Cell *cell( unsigned int row, unsigned int column ) const;
00335 Cell *cellByPos( double x, double y ) const;
00336
00337 enum CellSize {
00338 TblAuto = 0,
00339 TblManual
00340 };
00341
00347 KoRect boundingRect();
00348
00353 void setBoundingRect( KoRect rect, CellSize widthMode, CellSize heightMode );
00354
00359 double topWithoutBorder();
00360
00365 double leftWithoutBorder();
00366
00371 void resizeWidth( double width );
00372
00374 void recalcCols(uint column, uint row);
00375 void recalcRows(uint column, uint row);
00376
00378 void resizeColumn( unsigned int col, double x );
00380 void resizeRow( unsigned int row, double y );
00381
00382 double columnSize( unsigned int col );
00383 double rowSize( unsigned int col );
00384
00386 int columnEdgeAt( double x ) const;
00388 int rowEdgeAt( double y ) const;
00389
00391 unsigned int getRows() const { return m_rows; }
00393 unsigned int getColumns() const { return m_cols; }
00394
00397 unsigned int getNumCells()const { return m_nr_cells; }
00398
00399
00401 void moveBy( double dx, double dy );
00402
00404 void insertNewRow( uint _idx, bool _recalc = true, bool _removeable = false );
00406 void insertNewColumn( uint _idx, double width = KWTableFrameSet::m_sDefaultColWidth);
00407
00409 void deleteRow( uint _idx, RemovedRow &rr, bool _recalc = true);
00410
00412 void deleteColumn( uint _idx, RemovedColumn &rc);
00413
00415 void reInsertRow(RemovedRow &row);
00417 void reInsertColumn(RemovedColumn &col);
00418
00421 void ungroup();
00422
00423 void group();
00424
00425 bool isActive()const { return m_active; }
00426
00433 KCommand *joinCells(unsigned int firstColumn,unsigned int firstRow, unsigned int endColumn,unsigned int endRow);
00443 KCommand * splitCell(unsigned int intoRows, unsigned int intoColumns, unsigned int column,
00444 unsigned int row, QPtrList<KWFrameSet> listFrameSet=QPtrList<KWFrameSet>(),
00445 QPtrList<KWFrame>listFrame=QPtrList<KWFrame>() );
00446
00448 void viewFormatting( QPainter &painter, int zoom );
00451 void validate();
00452
00454 virtual QDomElement save( QDomElement &parentElem, bool saveFrames = true );
00455
00456 virtual void saveOasis( KoXmlWriter&, KoSavingContext&, bool saveFrames ) const;
00457 void loadOasis( const QDomElement& tag, KoOasisContext& context );
00458 virtual bool canBeSavedAsInlineCharacter() const { return false; }
00459
00461 Cell* loadCell( QDomElement &frameElem, bool loadFrames = true, bool useNames = true );
00462
00464 virtual QDomElement toXML( QDomElement &parentElem, bool saveFrames = true );
00465 virtual void fromXML( QDomElement &framesetElem, bool loadFrames = true, bool useNames = true );
00466
00468 virtual int paragraphs();
00469 virtual int paragraphsSelected();
00470 virtual bool statistics( QProgressDialog *progress, ulong & charsWithSpace, ulong & charsWithoutSpace, ulong & words,
00471 ulong & sentences, ulong & syllables,ulong & lines, bool selected );
00472
00473 virtual void finalize();
00474 virtual void invalidate();
00475 virtual void layout();
00476
00477 virtual void updateFrames( int flags = 0xff );
00478
00479
00480 virtual void moveFloatingFrame( int frameNum, const KoPoint &position );
00481 virtual KoSize floatingFrameSize( int frameNum = 0 );
00482 virtual KCommand * anchoredObjectCreateCommand( int frameNum );
00483 virtual KCommand * anchoredObjectDeleteCommand( int frameNum );
00484 virtual KWAnchor * createAnchor( KoTextDocument *txt, int frameNum );
00485
00486 virtual void setVisible( bool v );
00487 virtual bool canRemovePage( int num );
00488
00492 void addCell( Cell *cell );
00493
00496 void removeCell( Cell* cell );
00497
00498
00499
00500 virtual void setProtectContent ( bool ) {}
00501 virtual bool protectContent() const { return false; }
00502
00503 virtual KWTextFrameSet* nextTextObject( KWFrameSet * );
00507 void setZOrder();
00508
00509 QByteArray convertTableToText();
00510
00511 #ifndef NDEBUG
00512 virtual void printDebug( KWFrame * frame );
00513 virtual void printDebug();
00514 void printArrayDebug();
00515 #endif
00516 static const uint m_sDefaultColWidth = 60;
00517 protected:
00518
00520 virtual void deleteAnchors();
00522 virtual void createAnchors( KoTextParag * parag, int index, bool placeHolderExists = false, bool repaint = true );
00523
00524 private:
00525 void addCellToArray( Cell* cell );
00526 void afterLoadingCell( Cell* cell );
00527 void parseInsideOfTable( const QDomElement& parent, KoOasisContext& context,
00528 const QMemArray<double> & columnLefts, uint& row, uint& column,
00529 double currentRowHeight );
00530 void loadOasisCell( const QDomElement& element, KoOasisContext& context,
00531 const QMemArray<double> & columnLefts, uint row, uint column,
00532 double currentRowHeight );
00533
00544 void position(Cell *theCell, bool setMinFrameHeight=false);
00545
00555 double getPositionOfRow(unsigned int row, bool bottom=false);
00556
00557 void insertEmptyColumn(uint index);
00562 void insertRowVector(uint index, Row *row);
00568 Row* removeRowVector(uint index);
00569
00570 private:
00571 unsigned int m_rows, m_cols, m_nr_cells;
00572 bool m_active;
00573 QPtrVector< Row > m_rowArray;
00574
00581 QValueList<unsigned int> m_pageBoundaries;
00582 unsigned int m_redrawFromCol;
00583 QValueList<double> m_rowPositions, m_colPositions;
00584 };
00585
00586
00587
00588 template<>
00589 KWTableFrameSet::Cell*
00590 KWTableFrameSet::TableIterator<KWTableFrameSet::VISIT_CELL>::operator++ ();
00591
00592 template<>
00593 KWTableFrameSet::Cell*
00594 KWTableFrameSet::TableIterator<KWTableFrameSet::VISIT_GRID>::operator++ ();
00595
00596 template<>
00597 KWTableFrameSet::Cell*
00598 KWTableFrameSet::TableIterator<KWTableFrameSet::CHECKED>::operator++ ();
00599
00600 template<int VisitStyle>
00601 KWTableFrameSet::TableIterator<VisitStyle>::TableIterator(KWTableFrameSet *table) :
00602 m_table(table)
00603 {
00604 Q_ASSERT(m_table);
00605 set_limits(0, m_table->getColumns() - 1, 0, m_table->getRows() - 1);
00606 toFirstCell();
00607 }
00608
00609
00610 template<>
00611 KWTableFrameSet::TableIterator<KWTableFrameSet::CHECKED>::TableIterator(KWTableFrameSet *table);
00612
00613
00614 template<int VisitStyle>
00615 KWTableFrameSet::Cell*
00616 KWTableFrameSet::TableIterator<VisitStyle>::toFirstCell (){
00617 m_cell = m_table->cell(m_limit[HIGH], m_limit[LEFT]);
00618 Q_ASSERT(m_cell);
00619 if ( !m_cell )
00620 return 0;
00621 m_row = m_cell->firstRow();
00622 m_col = m_cell->firstColumn();
00623 return m_cell;
00624 }
00625
00626 template<int VisitStyle>
00627 void
00628 KWTableFrameSet::TableIterator<VisitStyle>::goToCell(KWTableFrameSet::Cell *cell)
00629 {
00630 m_cell = cell;
00631 Q_ASSERT( m_cell );
00632 if ( m_cell )
00633 {
00634 m_row = m_cell->firstRow();
00635 m_col = m_cell->firstColumn();
00636 }
00637 }
00638
00639
00640 template<>
00641 KWTableFrameSet::Cell*
00642 KWTableFrameSet::TableIterator<KWTableFrameSet::CHECKED>::toFirstCell ();
00643
00644
00645 template<int VisitStyle>
00646 KWTableFrameSet::Cell*
00647 KWTableFrameSet::TableIterator<VisitStyle>::current() const {
00648 return m_cell;
00649 }
00650
00654 class RemovedRow {
00655
00656 KWTableFrameSet::Row *m_row;
00658 uint m_index;
00659 double m_rowHeight;
00660
00661 uint index() const { return m_index; }
00662 double height() const { return m_rowHeight; }
00663 KWTableFrameSet::Row *takeRow();
00664 KWTableFrameSet::Row *row() { return m_row; }
00665
00666 friend class KWTableFrameSet;
00667 public:
00668 RemovedRow();
00669 ~RemovedRow();
00670 };
00671
00672 class RemovedColumn {
00673
00674 QPtrList<KWTableFrameSet::Cell> m_column;
00675 QValueList<bool> m_removed;
00676 uint m_index;
00677 double m_width;
00678 bool m_initialized;
00679
00680 friend class KWTableFrameSet;
00681 public:
00682 RemovedColumn();
00683 };
00684
00691 class KWTableFrameSetEdit : public KWFrameSetEdit
00692 {
00693 public:
00694 KWTableFrameSetEdit( KWTableFrameSet * fs, KWCanvas * canvas )
00695 : KWFrameSetEdit( fs, canvas ), m_currentCell( 0L ) {}
00696 virtual ~KWTableFrameSetEdit();
00697
00698 KWTableFrameSet * tableFrameSet() const {
00699 return static_cast<KWTableFrameSet *>( m_fs );
00700 }
00701
00702 virtual KWFrameSetEdit* currentTextEdit();
00703
00704 KWFrameSetEdit* currentCell() const { return m_currentCell; }
00705
00706
00707 virtual void keyPressEvent( QKeyEvent * e );
00708 virtual void keyReleaseEvent( QKeyEvent * e );
00709 virtual void mousePressEvent( QMouseEvent * e, const QPoint &, const KoPoint & );
00710 virtual void mouseMoveEvent( QMouseEvent * e, const QPoint & n, const KoPoint & d )
00711 { if ( m_currentCell ) m_currentCell->mouseMoveEvent( e, n, d ); }
00712 virtual void mouseReleaseEvent( QMouseEvent * e, const QPoint & n, const KoPoint & d )
00713 { if ( m_currentCell ) m_currentCell->mouseReleaseEvent( e, n, d ); }
00714 virtual void mouseDoubleClickEvent( QMouseEvent * e, const QPoint & n, const KoPoint & d )
00715 { if ( m_currentCell ) m_currentCell->mouseDoubleClickEvent( e, n, d ); }
00716
00717 virtual void dragEnterEvent( QDragEnterEvent * e )
00718 { if ( m_currentCell ) m_currentCell->dragEnterEvent( e ); }
00719 virtual void dragMoveEvent( QDragMoveEvent * e, const QPoint &n, const KoPoint &d );
00720 virtual void dragLeaveEvent( QDragLeaveEvent * e )
00721 { if ( m_currentCell ) m_currentCell->dragLeaveEvent( e ); }
00722 virtual void dropEvent( QDropEvent * e, const QPoint &n, const KoPoint &d, KWView* view )
00723 { if ( m_currentCell ) m_currentCell->dropEvent( e, n, d, view ); }
00724
00725 virtual void focusInEvent() { if ( m_currentCell ) m_currentCell->focusInEvent(); }
00726 virtual void focusOutEvent() { if ( m_currentCell ) m_currentCell->focusOutEvent(); }
00727 virtual void copy() { if ( m_currentCell ) m_currentCell->copy(); }
00728 virtual void cut() { if ( m_currentCell ) m_currentCell->cut(); }
00729 virtual void paste() { if ( m_currentCell ) m_currentCell->paste(); }
00731 virtual void selectAll() { if ( m_currentCell ) m_currentCell->selectAll(); }
00732
00734 void setCurrentCell( KWFrameSet * fs, bool eraseSelection=true );
00736 void setCurrentCell( const KoPoint & dPoint );
00737
00738 void showPopup( KWFrame* frame, KWView* view, const QPoint & _point );
00739
00740 protected:
00741 KWFrameSetEdit * m_currentCell;
00742
00743 };
00744 #endif