X-Git-Url: https://git.lyx.org/gitweb/?a=blobdiff_plain;f=src%2Finsets%2Finsettabular.C;h=8e6e8e98dc70d19733fbb658c02ee6e3a3d106fd;hb=3c8aba3b556871fb1100a2f98cd93d5d4e3f70c9;hp=f14093d0706dfc795858e9f125be5ed9c59d9443;hpb=33868acd2c62d5d5393962bdc3bf1351cf8434c8;p=lyx.git diff --git a/src/insets/insettabular.C b/src/insets/insettabular.C index f14093d070..8e6e8e98dc 100644 --- a/src/insets/insettabular.C +++ b/src/insets/insettabular.C @@ -3,7 +3,7 @@ * * LyX, The Document Processor * - * Copyright (C) 2000 The LyX Team. + * Copyright 2000 The LyX Team. * *====================================================== */ @@ -26,50 +26,58 @@ #include "LaTeXFeatures.h" #include "Painter.h" #include "font.h" +#include "lyxtext.h" #include "insets/insettext.h" const int ADD_TO_HEIGHT = 2; -const int ADD_TO_TABLE_WIDTH = 2; +const int ADD_TO_TABULAR_WIDTH = 2; using std::ostream; using std::ifstream; +using std::max; +using std::endl; -InsetTabular::InsetTabular(Buffer * buf, int rows=1, int columns=1) + +InsetTabular::InsetTabular(Buffer * buf, int rows, int columns) { if (rows <= 0) rows = 1; if (columns <= 0) columns = 1; - tabular = new LyXTable(rows,columns,buf); + tabular = new LyXTabular(rows,columns,buf); + // for now make it always display as display() inset + // just for test!!! + tabular->SetLongTabular(true); the_locking_inset = 0; buffer = buf; cursor_visible = false; - old_x = -1; - sel_pos_start = sel_pos_end = 0; + cursor.x_fix = -1; + actcell = cursor.pos = sel_pos_start = sel_pos_end = 0; no_selection = false; init = true; } + InsetTabular::InsetTabular(InsetTabular const & tab, Buffer * buf) { - tabular = new LyXTable(*(tab.tabular), buf); + tabular = new LyXTabular(*(tab.tabular), buf); the_locking_inset = 0; buffer = buf; cursor_visible = false; - old_x = -1; - sel_pos_start = sel_pos_end = 0; + cursor.x_fix = -1; + actcell = cursor.pos = sel_pos_start = sel_pos_end = 0; no_selection = false; init = true; } + InsetTabular::~InsetTabular() { - if (tabular) - delete tabular; + delete tabular; } -InsetTabular * InsetTabular::Clone() const +Inset * InsetTabular::Clone() const { InsetTabular * t = new InsetTabular(*this, buffer); return t; @@ -78,19 +86,31 @@ InsetTabular * InsetTabular::Clone() const void InsetTabular::Write(ostream & os) const { - os << "\\begin_inset Tabular\n"; - tabular->Write(os,false); - os << "\\end_inset\n"; + os << " Tabular" << endl; + tabular->Write(os); } void InsetTabular::Read(LyXLex & lex) { +// bool old_format = (lex.GetString() == "\\LyXTable"); + string token; + if (tabular) delete tabular; + tabular = new LyXTabular(lex, buffer); -// bool old_format = (lex.GetString() == "\\LyXTable"); - tabular = new LyXTable(lex, buffer); + lex.nextToken(); + token = lex.GetString(); + while (lex.IsOK() && (token != "\\end_inset")) { + lex.nextToken(); + token = lex.GetString(); + } + if (token != "\\end_inset") { + lex.printError("Missing \\end_inset at this point. " + "Read: `$$Token'"); + } + tabular->SetLongTabular(true); init = true; } @@ -101,7 +121,7 @@ int InsetTabular::ascent(Painter & pain, LyXFont const & font) const calculate_width_of_cells(pain, font); init = false; } - return tabular->AscentOfRow(0); + return tabular->GetAscentOfRow(0); } @@ -111,7 +131,7 @@ int InsetTabular::descent(Painter & pain, LyXFont const & font) const calculate_width_of_cells(pain, font); init = false; } - return tabular->HeightOfTable() - tabular->AscentOfRow(0); + return tabular->GetHeightOfTabular() - tabular->GetAscentOfRow(0); } @@ -121,18 +141,74 @@ int InsetTabular::width(Painter & pain, LyXFont const & font) const calculate_width_of_cells(pain, font); init = false; } - return tabular->WidthOfTable() + (2 * ADD_TO_TABLE_WIDTH); + return tabular->GetWidthOfTabular() + (2 * ADD_TO_TABULAR_WIDTH); } -void InsetTabular::draw(Painter & pain, const LyXFont & font, int, - float &) const +void InsetTabular::draw(Painter & pain, const LyXFont & font, int baseline, + float & x) const { - calculate_width_of_cells(pain, font); + int i, j, cell=0; + int nx; + float cx; + + UpdatableInset::draw(pain,font,baseline,x); + if ((top_x != int(x)) || (top_baseline != baseline)) { + top_x = int(x); + top_baseline = baseline; + resetPos(pain); + } + for(i=0;irows();++i) { + nx = int(x); + for(j=0;jcolumns();++j) { + cx = nx + tabular->GetBeginningOfTextInCell(cell); + tabular->GetCellInset(cell)->draw(pain, font, baseline, cx); + DrawCellLines(pain, nx, baseline, i, cell); + nx += tabular->GetWidthOfColumn(cell); + ++cell; + } + baseline += tabular->GetDescentOfRow(i) + tabular->GetAscentOfRow(i+1) + + tabular->GetAdditionalHeight(cell+1); + } } -const char * InsetTabular::EditMessage() const +void InsetTabular::DrawCellLines(Painter & pain, int x, int baseline, + int row, int cell) const +{ + int x2 = x + tabular->GetWidthOfColumn(cell); + bool on_off; + + if (!tabular->TopAlreadyDrawed(cell)) { + on_off = !tabular->TopLine(cell); + pain.line(x, baseline - tabular->GetAscentOfRow(row), + x2, baseline - tabular->GetAscentOfRow(row), + on_off ? LColor::tabularonoffline:LColor::tabularline, + on_off ? Painter::line_onoffdash:Painter::line_solid); + } + on_off = !tabular->BottomLine(cell); + pain.line(x,baseline + tabular->GetDescentOfRow(row), + x2, baseline + tabular->GetDescentOfRow(row), + on_off ? LColor::tabularonoffline:LColor::tabularline, + on_off ? Painter::line_onoffdash:Painter::line_solid); + if (!tabular->LeftAlreadyDrawed(cell)) { + on_off = !tabular->LeftLine(cell); + pain.line(x, baseline - tabular->GetAscentOfRow(row), + x, baseline + tabular->GetDescentOfRow(row), + on_off ? LColor::tabularonoffline:LColor::tabularline, + on_off ? Painter::line_onoffdash:Painter::line_solid); + } + on_off = !tabular->RightLine(cell); + pain.line(x2 - tabular->GetAdditionalWidth(cell), + baseline - tabular->GetAscentOfRow(row), + x2 - tabular->GetAdditionalWidth(cell), + baseline + tabular->GetDescentOfRow(row), + on_off ? LColor::tabularonoffline:LColor::tabularline, + on_off ? Painter::line_onoffdash:Painter::line_solid); +} + + +char const * InsetTabular::EditMessage() const { return _("Opened Tabular Inset"); } @@ -142,57 +218,88 @@ void InsetTabular::Edit(BufferView * bv, int x, int y, unsigned int button) { UpdatableInset::Edit(bv, x, y, button); - bv->lockInset(this); + if (!bv->lockInset(this)) { + lyxerr[Debug::INSETS] << "InsetTabular::Cannot lock inset" << endl; + return; + } the_locking_inset = 0; - inset_pos = inset_x = inset_y = 0; - no_selection = true; - setPos(x,y); - sel_pos_start = sel_pos_end = actpos; - sel_cell_start = sel_cell_end = actcell; -// bv->getOwner()->getPopups().updateFormTable(); + sel_pos_start = sel_pos_end = inset_pos = inset_x = inset_y = 0; + setPos(bv->painter(), x, y); + sel_pos_start = sel_pos_end = cursor.pos; + bv->text->FinishUndo(); + if (InsetHit(bv, x, y)) { + ActivateCellInset(bv, x, y, button); + } + UpdateLocal(bv, true); +// bv->getOwner()->getPopups().updateFormTabular(); } void InsetTabular::InsetUnlock(BufferView * bv) { - if (the_locking_inset) + if (the_locking_inset) { the_locking_inset->InsetUnlock(bv); + the_locking_inset = 0; + } HideInsetCursor(bv); - the_locking_inset = 0; if (hasCharSelection()) { - sel_pos_start = sel_pos_end = actpos; + sel_pos_start = sel_pos_end = cursor.pos; UpdateLocal(bv, false); } else - sel_pos_start = sel_pos_end = actpos; + sel_pos_start = sel_pos_end = cursor.pos; no_selection = false; } -bool InsetTabular::LockInsetInInset(UpdatableInset *) +void InsetTabular::UpdateLocal(BufferView * bv, bool flag) { - return true; + if (flag) + calculate_width_of_cells(bv->painter(), LyXFont(LyXFont::ALL_SANE)); + bv->updateInset(this, flag); } - -bool InsetTabular::UnlockInsetInInset(BufferView * bv, UpdatableInset * inset, - bool lr) +bool InsetTabular::LockInsetInInset(BufferView * bv, UpdatableInset * inset) { - if (!the_locking_inset) + lyxerr[Debug::INSETS] << "InsetTabular::LockInsetInInset(" <InsetUnlock(bv); - the_locking_inset = 0; - if (lr) - moveRight(false); + if (inset == tabular->GetCellInset(actcell)) { + lyxerr[Debug::INSETS] << "OK" << endl; + the_locking_inset = tabular->GetCellInset(actcell); + resetPos(bv->painter()); + inset_x = cursor.x - top_x + tabular->GetBeginningOfTextInCell(actcell); + inset_y = cursor.y; + inset_pos = cursor.pos; return true; + } else if (the_locking_inset && (the_locking_inset == inset)) { + if (cursor.pos == inset_pos) { + lyxerr[Debug::INSETS] << "OK" << endl; + resetPos(bv->painter()); + inset_x = cursor.x - top_x + tabular->GetBeginningOfTextInCell(actcell); + inset_y = cursor.y; + } else { + lyxerr[Debug::INSETS] << "cursor.pos != inset_pos" << endl; + } + } else if (the_locking_inset) { + lyxerr[Debug::INSETS] << "MAYBE" << endl; + return the_locking_inset->LockInsetInInset(bv, inset); } - return the_locking_inset->UnlockInsetInInset(bv, inset, lr); + lyxerr[Debug::INSETS] << "NOT OK" << endl; + return false; } - -void InsetTabular::UpdateLocal(BufferView * bv, bool flag) +bool InsetTabular::UnlockInsetInInset(BufferView * bv, UpdatableInset * inset, + bool lr) { - resetPos(); - bv->updateInset(this, flag); + if (!the_locking_inset) + return false; + if (the_locking_inset == inset) { + the_locking_inset->InsetUnlock(bv); + the_locking_inset = 0; + if (lr) + moveRight(bv, false); + return true; + } + return the_locking_inset->UnlockInsetInInset(bv, inset, lr); } bool InsetTabular::UpdateInsetInInset(BufferView * bv, Inset * inset) @@ -205,59 +312,59 @@ bool InsetTabular::UpdateInsetInInset(BufferView * bv, Inset * inset) return true; } -void InsetTabular::InsetButtonRelease(BufferView *bv, int x, int y, int button) + +int InsetTabular::InsetInInsetY() +{ + if (!the_locking_inset) + return 0; + + return (inset_y + the_locking_inset->InsetInInsetY()); +} + +void InsetTabular::InsetButtonRelease(BufferView * bv, + int x, int y, int button) { if (the_locking_inset) { - the_locking_inset->InsetButtonRelease(bv, x-inset_x,y-inset_y,button); + the_locking_inset->InsetButtonRelease(bv, x-inset_x, y-inset_y,button); return; } no_selection = false; } -void InsetTabular::InsetButtonPress(BufferView *bv, int x, int y, int) + +void InsetTabular::InsetButtonPress(BufferView * bv, int x, int y, int button) { if (hasCharSelection()) { sel_pos_start = sel_pos_end = 0; UpdateLocal(bv, false); } no_selection = false; - setPos(x,y,false); - if (the_locking_inset) { -#if 0 - UpdatableInset - * inset=0; - if (par->GetChar(actpos)==LYX_META_INSET) - inset=(UpdatableInset*)par->GetInset(actpos); - if (the_locking_inset == inset) { - the_locking_inset->InsetButtonPress(bv,x-inset_x,y-inset_y,button); - return; - } else if (inset) { - // otherwise unlock the_locking_inset and lock the new inset - inset_x = cx-top_x; - inset_y = cy; - inset_pos = actpos; - the_locking_inset->InsetUnlock(bv); - the_locking_inset = inset; - the_locking_inset->Edit(bv, x - inset_x, y - inset_y, button); - return; - } -#endif - // otherwise only unlock the_locking_inset + + int oldcell = actcell; + + setPos(bv->painter(), x, y); + + bool inset_hit = InsetHit(bv, x, y); + + if ((oldcell == actcell) && the_locking_inset && inset_hit) { + the_locking_inset->InsetButtonPress(bv, x-inset_x, y-inset_y, button); + return; + } else if (the_locking_inset) { the_locking_inset->InsetUnlock(bv); } -#if 0 - int - oldcell = actcell; -#endif - setPos(x,y); the_locking_inset = 0; - sel_pos_start = sel_pos_end = actpos; + sel_pos_start = sel_pos_end = cursor.pos; sel_cell_start = sel_cell_end = actcell; + if (inset_hit && bv->the_locking_inset) { + ActivateCellInset(bv, x, y, button); + the_locking_inset->InsetButtonPress(bv, x-inset_x, y-inset_y, button); + } + #if 0 if (button == 3) - bview->getOwner()->getPopups().showFormTable(); + bview->getOwner()->getPopups().showFormTabular(); else if (oldcell != actcell) - bview->getOwner()->getPopups().updateFormTable(); + bview->getOwner()->getPopups().updateFormTabular(); #endif } @@ -265,22 +372,22 @@ void InsetTabular::InsetButtonPress(BufferView *bv, int x, int y, int) void InsetTabular::InsetMotionNotify(BufferView * bv, int x, int y, int button) { if (the_locking_inset) { - the_locking_inset->InsetMotionNotify(bv, x-inset_x,y-inset_y,button); + the_locking_inset->InsetMotionNotify(bv, x - inset_x, + y - inset_y, button); return; } if (!no_selection) { - int -// oldcell = actcell, - old = sel_pos_end; + // int oldcell = actcell, + int old = sel_pos_end; - setPos(x,y); - sel_pos_end = actpos; + setPos(bv->painter(), x, y); + sel_pos_end = cursor.pos; sel_cell_end = actcell; if (old != sel_pos_end) UpdateLocal(bv, false); #if 0 if (oldcell != actcell) - bview->getOwner()->getPopups().updateFormTable(); + bview->getOwner()->getPopups().updateFormTabular(); #endif } no_selection = false; @@ -296,35 +403,41 @@ void InsetTabular::InsetKeyPress(XKeyEvent * xke) } -UpdatableInset::RESULT InsetTabular::LocalDispatch(BufferView *bv, int action, +UpdatableInset::RESULT InsetTabular::LocalDispatch(BufferView * bv, int action, string const & arg) { + UpdatableInset::RESULT + result; + no_selection = false; - if (UpdatableInset::LocalDispatch(bv, action, arg)) { - resetPos(); - return DISPATCHED; + if (((result=UpdatableInset::LocalDispatch(bv, action, arg)) == DISPATCHED) + || (result == DISPATCHED_NOUPDATE)) { + + resetPos(bv->painter()); + return result; } + result=DISPATCHED; - UpdatableInset::RESULT - result=DISPATCHED; if ((action < 0) && arg.empty()) return FINISHED; if ((action != LFUN_DOWN) && (action != LFUN_UP) && (action != LFUN_DOWNSEL) && (action != LFUN_UPSEL)) - old_x = -1; + cursor.x_fix = -1; if (the_locking_inset) { result=the_locking_inset->LocalDispatch(bv, action, arg); - if (result == DISPATCHED) { - setWidthOfCell(actpos,actcell,actrow); + if (result == DISPATCHED_NOUPDATE) + return result; + else if (result == DISPATCHED) { + bool upd = SetCellDimensions(bv->painter(), actcell, actrow); the_locking_inset->ToggleInsetCursor(bv); - UpdateLocal(bv, false); + UpdateLocal(bv, upd); the_locking_inset->ToggleInsetCursor(bv); return result; } else if (result == FINISHED) { if ((action == LFUN_RIGHT) || (action == -1)) { - actpos = inset_pos + 1; - resetPos(); + cursor.pos = inset_pos + 1; + resetPos(bv->painter()); } the_locking_inset=0; result = DISPATCHED; @@ -339,56 +452,56 @@ UpdatableInset::RESULT InsetTabular::LocalDispatch(BufferView *bv, int action, break; // --- Cursor Movements --------------------------------------------- case LFUN_RIGHTSEL: - moveRight(false); - sel_pos_end = actpos; + moveRight(bv, false); + sel_pos_end = cursor.pos; UpdateLocal(bv, false); break; case LFUN_RIGHT: - result= DISPATCH_RESULT(moveRight()); + result = moveRight(bv); if (hasCharSelection()) { - sel_pos_start = sel_pos_end = actpos; + sel_pos_start = sel_pos_end = cursor.pos; UpdateLocal(bv, false); } else - sel_pos_start = sel_pos_end = actpos; + sel_pos_start = sel_pos_end = cursor.pos; break; case LFUN_LEFTSEL: - moveLeft(false); - sel_pos_end = actpos; + moveLeft(bv, false); + sel_pos_end = cursor.pos; UpdateLocal(bv, false); break; case LFUN_LEFT: - result= DISPATCH_RESULT(moveLeft()); + result = moveLeft(bv); if (hasCharSelection()) { - sel_pos_start = sel_pos_end = actpos; + sel_pos_start = sel_pos_end = cursor.pos; UpdateLocal(bv, false); } else - sel_pos_start = sel_pos_end = actpos; + sel_pos_start = sel_pos_end = cursor.pos; break; case LFUN_DOWNSEL: - moveDown(false); - sel_pos_end = actpos; + moveDown(); + sel_pos_end = cursor.pos; UpdateLocal(bv, false); break; case LFUN_DOWN: - result= DISPATCH_RESULT(moveDown()); + result= moveDown(); if (hasCharSelection()) { - sel_pos_start = sel_pos_end = actpos; + sel_pos_start = sel_pos_end = cursor.pos; UpdateLocal(bv, false); } else - sel_pos_start = sel_pos_end = actpos; + sel_pos_start = sel_pos_end = cursor.pos; break; case LFUN_UPSEL: - moveUp(false); - sel_pos_end = actpos; + moveUp(); + sel_pos_end = cursor.pos; UpdateLocal(bv, false); break; case LFUN_UP: - result= DISPATCH_RESULT(moveUp()); + result= moveUp(); if (hasCharSelection()) { - sel_pos_start = sel_pos_end = actpos; + sel_pos_start = sel_pos_end = cursor.pos; UpdateLocal(bv, false); } else - sel_pos_start = sel_pos_end = actpos; + sel_pos_start = sel_pos_end = cursor.pos; break; case LFUN_BACKSPACE: break; @@ -400,10 +513,10 @@ UpdatableInset::RESULT InsetTabular::LocalDispatch(BufferView *bv, int action, break; case LFUN_TAB: if (hasCharSelection()) { - sel_pos_start = sel_pos_end = actpos; + sel_pos_start = sel_pos_end = cursor.pos; UpdateLocal(bv, false); } - sel_pos_start = sel_pos_end = actpos; + sel_pos_start = sel_pos_end = cursor.pos; moveNextCell(); break; default: @@ -414,7 +527,7 @@ UpdatableInset::RESULT InsetTabular::LocalDispatch(BufferView *bv, int action, if (!the_locking_inset) { #if 0 if (oldcell != actcell) - bview->getOwner()->getPopups().updateFormTable(); + bview->getOwner()->getPopups().updateFormTabular(); #endif ShowInsetCursor(bv); } @@ -429,94 +542,59 @@ int InsetTabular::Latex(ostream & os, bool, bool) const return tabular->Latex(os); } + +int InsetTabular::Ascii(ostream &) const +{ + return 0; +} + int InsetTabular::Linuxdoc(ostream &) const { return 0; } + int InsetTabular::DocBook(ostream &) const { return 0; } + void InsetTabular::Validate(LaTeXFeatures & features) const { - if (tabular->IsLongTable()) + if (tabular->IsLongTabular()) features.longtable = true; } -void InsetTabular::calculate_width_of_cells(Painter & pain, LyXFont const & font) const +void InsetTabular::calculate_width_of_cells(Painter & pain, + LyXFont const & font) const { - int - cell=-1, - i,j, - maxAsc, maxDesc; - InsetText - *inset; + int cell = -1; + int maxAsc, maxDesc; + InsetText * inset; - for(i=0; i < tabular->rows; ++i) { - maxAsc = maxDesc = 0; - for(j=0; j < tabular->columns; ++j) { - if (tabular->IsPartOfMultiColumn(i,j)) - continue; - ++cell; + for(int i = 0; i < tabular->rows(); ++i) { + maxAsc = maxDesc = 0; + for(int j= 0; j < tabular->columns(); ++j) { + if (tabular->IsPartOfMultiColumn(i,j)) + continue; + ++cell; inset = tabular->GetCellInset(cell); maxAsc = max(maxAsc, inset->ascent(pain, font)); maxDesc = max(maxDesc, inset->descent(pain, font)); - tabular->SetWidthOfCell(cell, inset->width(pain, font)); - } - tabular->SetAscentOfRow(i,maxAsc+ADD_TO_HEIGHT); - tabular->SetDescentOfRow(i,maxDesc+ADD_TO_HEIGHT); + tabular->SetWidthOfCell(cell, inset->width(pain, font)); + } + tabular->SetAscentOfRow(i, maxAsc + ADD_TO_HEIGHT); + tabular->SetDescentOfRow(i, maxDesc + ADD_TO_HEIGHT); } } -void InsetTabular::DrawCellLines(Painter & pain, int x, int baseline, - int row, int cell) +void InsetTabular::GetCursorPos(int & x, int & y) const { - // Juergen, have you thought about drawing the on-off lines in a - // different color (gray of some kind), especially since those - // lines will not be there on the hardcopy anyway. (Lgb) - int - x_old = x; - bool - on_off; - - x_old -= tabular->WidthOfColumn(cell); - on_off = !tabular->TopLine(cell); - if ((!on_off || !tabular->TopAlreadyDrawed(cell)) && - !tabular->IsContRow(cell)) - pain.line(x_old, baseline - tabular->AscentOfRow(row), - x, baseline - tabular->AscentOfRow(row), - LColor::tableline, - on_off ? Painter::line_onoffdash:Painter::line_solid); - on_off = !tabular->BottomLine(cell); - if ((!on_off && !tabular->RowHasContRow(cell)) || - tabular->VeryLastRow(cell)) - pain.line(x_old ,baseline + tabular->DescentOfRow(row), - x, baseline + tabular->DescentOfRow(row), - LColor::tableline, - on_off ? Painter::line_onoffdash:Painter::line_solid); - on_off = !tabular->LeftLine(cell); - pain.line(x_old, baseline - tabular->AscentOfRow(row), - x_old, baseline + tabular->DescentOfRow(row), - LColor::tableline, - on_off ? Painter::line_onoffdash:Painter::line_solid); - on_off = !tabular->RightLine(cell); - pain.line(x - tabular->AdditionalWidth(cell), - baseline - tabular->AscentOfRow(row), - x - tabular->AdditionalWidth(cell), - baseline + tabular->DescentOfRow(row), - LColor::tableline, - on_off ? Painter::line_onoffdash:Painter::line_solid); -} - - -void InsetTabular::GetCursorPos(int & x, int & y) -{ - x = cx-top_x; - y = cy; + x = cursor.x-top_x; + y = cursor.y; } @@ -526,20 +604,16 @@ void InsetTabular::ToggleInsetCursor(BufferView * bv) the_locking_inset->ToggleInsetCursor(bv); return; } - int - x=0,y=0, - asc,desc; - LyXFont - font; // = the_locking_inset->GetFont(par, actpos); + LyXFont font; // = the_locking_inset->GetFont(par, cursor.pos); - asc = lyxfont::maxAscent(font); - desc = lyxfont::maxDescent(font); + int asc = lyxfont::maxAscent(font); + int desc = lyxfont::maxDescent(font); if (cursor_visible) bv->hideLockedInsetCursor(); else - bv->showLockedInsetCursor(cx+x, cy+y, asc, desc); + bv->showLockedInsetCursor(cursor.x, cursor.y, asc, desc); cursor_visible = !cursor_visible; } @@ -547,15 +621,12 @@ void InsetTabular::ToggleInsetCursor(BufferView * bv) void InsetTabular::ShowInsetCursor(BufferView * bv) { if (!cursor_visible) { - int - asc,desc; - LyXFont - font; // = GetFont(par, actpos); + LyXFont font; // = GetFont(par, cursor.pos); - asc = lyxfont::maxAscent(font); - desc = lyxfont::maxDescent(font); - bv->fitLockedInsetCursor(cx, cy, asc, desc); - bv->showLockedInsetCursor(cx, cy, asc, desc); + int asc = lyxfont::maxAscent(font); + int desc = lyxfont::maxDescent(font); + bv->fitLockedInsetCursor(cursor.x, cursor.y, asc, desc); + bv->showLockedInsetCursor(cursor.x, cursor.y, asc, desc); cursor_visible = true; } } @@ -568,64 +639,166 @@ void InsetTabular::HideInsetCursor(BufferView * bv) } -void InsetTabular::setPos(int, int, bool) +void InsetTabular::setPos(Painter & pain, int x, int y) const { + cursor.y = cursor.pos = actcell = actrow = actcol = 0; + int ly = tabular->GetDescentOfRow(actrow); + + // first search the right row + while((ly < y) && (actrow < tabular->rows())) { + cursor.y += tabular->GetDescentOfRow(actrow) + + tabular->GetAscentOfRow(actrow+1) + + tabular->GetAdditionalHeight(tabular->GetCellNumber(actcol,actrow+1)); + ++actrow; + ly = cursor.y + tabular->GetDescentOfRow(actrow); + } + actcell = tabular->GetCellNumber(actcol, actrow); + + // now search the right column + int lx = tabular->GetWidthOfColumn(actcell) - + tabular->GetAdditionalWidth(actcell); + for(; !tabular->IsLastCellInRow(actcell) && (lx < x); + ++actcell,lx += tabular->GetWidthOfColumn(actcell) + + tabular->GetAdditionalWidth(actcell-1)); + cursor.pos = ((actcell+1) * 2) - 1; + resetPos(pain); + if ((lx - (tabular->GetWidthOfColumn(actcell)/2)) < x) { + cursor.x = lx + top_x - 2; + } else { + --cursor.pos; + cursor.x = lx - tabular->GetWidthOfColumn(actcell) + top_x + 2; + } + resetPos(pain); } -void InsetTabular::setWidthOfCell(int, int, int) + +void InsetTabular::resetPos(Painter & pain) const { + actrow = cursor.y = actcol = 0; + + int cell = 0; + for(; (cellIsLastRow(cell); ++cell) { + if (tabular->IsLastCellInRow(cell)) { + cursor.y += tabular->GetDescentOfRow(actrow) + + tabular->GetAscentOfRow(actrow+1) + + tabular->GetAdditionalHeight(cell+1); + ++actrow; + } + } + for(cell=actcell;!tabular->IsFirstCellInRow(cell);--cell) + ; + int lx = tabular->GetWidthOfColumn(actcell); + for(; (cell < actcell); ++cell) { + lx += tabular->GetWidthOfColumn(cell); + ++actcol; + } + cursor.x = lx - tabular->GetWidthOfColumn(actcell) + top_x + 2; + if (cursor.pos % 2) { + LyXFont font(LyXFont::ALL_SANE); + cursor.x += tabular->GetCellInset(actcell)->width(pain,font) + + tabular->GetBeginningOfTextInCell(actcell); + } } -bool InsetTabular::moveRight(bool) + +bool InsetTabular::SetCellDimensions(Painter & pain, int cell, int row) { - return false; + InsetText * inset = tabular->GetCellInset(cell); + LyXFont font(LyXFont::ALL_SANE); + int asc = inset->ascent(pain, font) + ADD_TO_HEIGHT; + int desc = inset->descent(pain, font) + ADD_TO_HEIGHT; + int maxAsc = tabular->GetAscentOfRow(row); + int maxDesc = tabular->GetDescentOfRow(row); + bool ret = tabular->SetWidthOfCell(cell, inset->width(pain, font)); + + if (maxAsc < asc) { + ret = true; + tabular->SetAscentOfRow(row, asc); + } + if (maxDesc < desc) { + ret = true; + tabular->SetDescentOfRow(row, desc); + } + return ret; } -bool InsetTabular::moveLeft(bool) + +UpdatableInset::RESULT InsetTabular::moveRight(BufferView * bv, bool lock) { - return false; + if (cursor.pos % 2) { // behind the inset + ++actcell; + if (actcell >= tabular->GetNumberOfCells()) + return FINISHED; + ++cursor.pos; + } else if (lock) { + if (ActivateCellInset(bv)) + return DISPATCHED; + } else { // before the inset + ++cursor.pos; + } + resetPos(bv->painter()); + return DISPATCHED_NOUPDATE; } -bool InsetTabular::moveUp(bool) + +UpdatableInset::RESULT InsetTabular::moveLeft(BufferView * bv, bool lock) { - return false; + if (!cursor.pos) + return FINISHED; + --cursor.pos; + if (cursor.pos % 2) { // behind the inset + --actcell; + } else if (lock) { // behind the inset + if (ActivateCellInset(bv, -1, -1)) + return DISPATCHED; + } + resetPos(bv->painter()); + return DISPATCHED_NOUPDATE; } -bool InsetTabular::moveDown(bool) + +UpdatableInset::RESULT InsetTabular::moveUp() { - return false; + return DISPATCHED_NOUPDATE; +} + + +UpdatableInset::RESULT InsetTabular::moveDown() +{ + return DISPATCHED_NOUPDATE; } + bool InsetTabular::moveNextCell() { return false; } + bool InsetTabular::movePrevCell() { return false; } -void InsetTabular::resetPos() -{ -} bool InsetTabular::Delete() { return true; } -void InsetTabular::SetFont(LyXFont const &) + +void InsetTabular::SetFont(BufferView *, LyXFont const &, bool) { } -void InsetTabular::TableFeatures(int, string) + +void InsetTabular::TabularFeatures(int, string) { #if 0 int i, - selection_start, - selection_end, + sel_pos_start, + sel_pos_end, setLines = 0, setAlign = LYX_ALIGN_LEFT, lineSet; @@ -633,13 +806,13 @@ void InsetTabular::TableFeatures(int, string) what; switch (feature) { - case LyXTable::ALIGN_LEFT: + case LyXTabular::ALIGN_LEFT: setAlign=LYX_ALIGN_LEFT; break; - case LyXTable::ALIGN_RIGHT: + case LyXTabular::ALIGN_RIGHT: setAlign=LYX_ALIGN_RIGHT; break; - case LyXTable::ALIGN_CENTER: + case LyXTabular::ALIGN_CENTER: setAlign=LYX_ALIGN_CENTER; break; default: @@ -647,26 +820,26 @@ void InsetTabular::TableFeatures(int, string) } if (hasCellSelection()) { if (sel_cell_start > sel_cell_end) { - selection_start = sel_cell_end; - selection_end = sel_cell_start; + sel_pos_start = sel_cell_end; + sel_pos_end = sel_cell_start; } else { - selection_start = sel_cell_start; - selection_end = sel_cell_end; + sel_pos_start = sel_cell_start; + sel_pos_end = sel_cell_end; } } else - selection_start = selection_end = actcell; + sel_pos_start = sel_pos_end = actcell; switch (feature) { - case LyXTable::SET_PWIDTH: + case LyXTabular::SET_PWIDTH: tabular->SetPWidth(actcell,val); break; - case LyXTable::SET_SPECIAL_COLUMN: - case LyXTable::SET_SPECIAL_MULTI: + case LyXTabular::SET_SPECIAL_COLUMN: + case LyXTabular::SET_SPECIAL_MULTI: tabular->SetAlignSpecial(actcell,val,feature); break; - case LyXTable::APPEND_ROW: + case LyXTabular::APPEND_ROW: { int - pos = actpos, + pos = cursor.pos, cell_org = actcell, cell = actcell; @@ -704,16 +877,16 @@ void InsetTabular::TableFeatures(int, string) for (i=0; iInsertChar(pos, LYX_META_NEWLINE); - // append the row into the table + // append the row into the tabular tabular->AppendRow(cell_org); calculate_width_of_cells(); UpdateLocal(); return; } - case LyXTable::APPEND_CONT_ROW: + case LyXTabular::APPEND_CONT_ROW: { int - pos = actpos, + pos = cursor.pos, cell_org = actcell, cell = actcell; @@ -739,13 +912,13 @@ void InsetTabular::TableFeatures(int, string) int number = tabular->NumberOfCellsInRow(cell_org); for (i=0; iInsertChar(pos, LYX_META_NEWLINE); - // append the row into the table + // append the row into the tabular tabular->AppendContRow(cell_org); calculate_width_of_cells(); UpdateLocal(); return; } - case LyXTable::APPEND_COLUMN: + case LyXTabular::APPEND_COLUMN: { int pos = 0, @@ -755,8 +928,8 @@ void InsetTabular::TableFeatures(int, string) if (pos && (par->IsNewline(pos-1))) { if (tabular->AppendCellAfterCell(cell_org, cell)) { par->InsertChar(pos, LYX_META_NEWLINE); - if (pos <= actpos) - ++actpos; + if (pos <= cursor.pos) + ++cursor.pos; ++pos; } ++cell; @@ -764,21 +937,21 @@ void InsetTabular::TableFeatures(int, string) ++pos; } while (pos <= par->last()); // remember that the very last cell doesn't end with a newline. - // This saves one byte memory per table ;-) + // This saves one byte memory per tabular ;-) if (tabular->AppendCellAfterCell(cell_org, cell)) par->InsertChar(par->last(), LYX_META_NEWLINE); - // append the column into the table + // append the column into the tabular tabular->AppendColumn(cell_org); calculate_width_of_cells(); UpdateLocal(); return; } - case LyXTable::DELETE_ROW: - RemoveTableRow(); + case LyXTabular::DELETE_ROW: + RemoveTabularRow(); calculate_width_of_cells(); UpdateLocal(); return; - case LyXTable::DELETE_COLUMN: + case LyXTabular::DELETE_COLUMN: { int pos = 0; int cell = 0; @@ -792,61 +965,61 @@ void InsetTabular::TableFeatures(int, string) par->Erase(pos); else par->Erase(pos - 1); // the missing newline - // at the end of a table + // at the end of a tabular --pos; // because of ++pos below } ++cell; } ++pos; } while (pos <= par->last()); - /* delete the column from the table */ + /* delete the column from the tabular */ tabular->DeleteColumn(actcell); calculate_width_of_cells(); UpdateLocal(); return; } - case LyXTable::TOGGLE_LINE_TOP: + case LyXTabular::TOGGLE_LINE_TOP: lineSet = !tabular->TopLine(actcell); - for(i=selection_start; i<=selection_end; ++i) + for(i=sel_pos_start; i<=sel_pos_end; ++i) tabular->SetTopLine(i,lineSet); calculate_width_of_cells(); UpdateLocal(); return; - case LyXTable::TOGGLE_LINE_BOTTOM: + case LyXTabular::TOGGLE_LINE_BOTTOM: lineSet = !tabular->BottomLine(actcell); - for(i=selection_start; i<=selection_end; ++i) + for(i=sel_pos_start; i<=sel_pos_end; ++i) tabular->SetBottomLine(i,lineSet); calculate_width_of_cells(); UpdateLocal(); return; - case LyXTable::TOGGLE_LINE_LEFT: + case LyXTabular::TOGGLE_LINE_LEFT: lineSet = !tabular->LeftLine(actcell); - for(i=selection_start; i<=selection_end; ++i) + for(i=sel_pos_start; i<=sel_pos_end; ++i) tabular->SetLeftLine(i,lineSet); calculate_width_of_cells(); UpdateLocal(); return; - case LyXTable::TOGGLE_LINE_RIGHT: + case LyXTabular::TOGGLE_LINE_RIGHT: lineSet = !tabular->RightLine(actcell); - for(i=selection_start; i<=selection_end; ++i) + for(i=sel_pos_start; i<=sel_pos_end; ++i) tabular->SetRightLine(i,lineSet); calculate_width_of_cells(); UpdateLocal(); return; - case LyXTable::ALIGN_LEFT: - case LyXTable::ALIGN_RIGHT: - case LyXTable::ALIGN_CENTER: - for(i=selection_start; i<=selection_end; ++i) + case LyXTabular::ALIGN_LEFT: + case LyXTabular::ALIGN_RIGHT: + case LyXTabular::ALIGN_CENTER: + for(i=sel_pos_start; i<=sel_pos_end; ++i) tabular->SetAlignment(i,setAlign); UpdateLocal(); return; - case LyXTable::MULTICOLUMN: + case LyXTabular::MULTICOLUMN: { - if (tabular->row_of_cell(selection_start) != - tabular->row_of_cell(selection_end)) { + if (tabular->row_of_cell(sel_pos_start) != + tabular->row_of_cell(sel_pos_end)) { WriteAlert(_("Impossible Operation!"), _("Multicolumns can only be horizontally."), _("Sorry.")); @@ -858,7 +1031,7 @@ void InsetTabular::TableFeatures(int, string) if (tabular->IsMultiColumn(actcell)) { int newlines, - pos = actpos; + pos = cursor.pos; if ((newlines=tabular->UnsetMultiColumn(actcell))) { while ((pos < par->last()) && !par->IsNewline(pos)) ++pos; @@ -897,61 +1070,61 @@ void InsetTabular::TableFeatures(int, string) ++number; } } - tabular->SetMultiColumn(selection_start,number); - actpos = s_start; + tabular->SetMultiColumn(sel_pos_start,number); + cursor.pos = s_start; sel_cell_end = sel_cell_start; calculate_width_of_cells(); UpdateLocal(); return; } - case LyXTable::SET_ALL_LINES: + case LyXTabular::SET_ALL_LINES: setLines = 1; - case LyXTable::UNSET_ALL_LINES: - for(i=selection_start; i<=selection_end; ++i) + case LyXTabular::UNSET_ALL_LINES: + for(i=sel_pos_start; i<=sel_pos_end; ++i) tabular->SetAllLines(i, setLines); calculate_width_of_cells(); UpdateLocal(); return; - case LyXTable::SET_LONGTABLE: - tabular->SetLongTable(true); + case LyXTabular::SET_LONGTABULAR: + tabular->SetLongTabular(true); UpdateLocal(); // because this toggles displayed return; - case LyXTable::UNSET_LONGTABLE: - tabular->SetLongTable(false); + case LyXTabular::UNSET_LONGTABULAR: + tabular->SetLongTabular(false); UpdateLocal(); // because this toggles displayed return; - case LyXTable::SET_ROTATE_TABLE: - tabular->SetRotateTable(true); + case LyXTabular::SET_ROTATE_TABULAR: + tabular->SetRotateTabular(true); return; - case LyXTable::UNSET_ROTATE_TABLE: - tabular->SetRotateTable(false); + case LyXTabular::UNSET_ROTATE_TABULAR: + tabular->SetRotateTabular(false); return; - case LyXTable::SET_ROTATE_CELL: - for(i=selection_start; i<=selection_end; ++i) + case LyXTabular::SET_ROTATE_CELL: + for(i=sel_pos_start; i<=sel_pos_end; ++i) tabular->SetRotateCell(i,true); return; - case LyXTable::UNSET_ROTATE_CELL: - for(i=selection_start; i<=selection_end; ++i) + case LyXTabular::UNSET_ROTATE_CELL: + for(i=sel_pos_start; i<=sel_pos_end; ++i) tabular->SetRotateCell(i,false); return; - case LyXTable::SET_LINEBREAKS: + case LyXTabular::SET_LINEBREAKS: what = !tabular->Linebreaks(tabular->FirstVirtualCell(actcell)); - for(i=selection_start; i<=selection_end; ++i) + for(i=sel_pos_start; i<=sel_pos_end; ++i) tabular->SetLinebreaks(i,what); return; - case LyXTable::SET_LTFIRSTHEAD: + case LyXTabular::SET_LTFIRSTHEAD: tabular->SetLTHead(actcell,true); return; - case LyXTable::SET_LTHEAD: + case LyXTabular::SET_LTHEAD: tabular->SetLTHead(actcell,false); return; - case LyXTable::SET_LTFOOT: + case LyXTabular::SET_LTFOOT: tabular->SetLTFoot(actcell,false); return; - case LyXTable::SET_LTLASTFOOT: + case LyXTabular::SET_LTLASTFOOT: tabular->SetLTFoot(actcell,true); return; - case LyXTable::SET_LTNEWPAGE: + case LyXTabular::SET_LTNEWPAGE: what = !tabular->LTNewPage(actcell); tabular->SetLTNewPage(actcell,what); return; @@ -959,6 +1132,47 @@ void InsetTabular::TableFeatures(int, string) #endif } -void InsetTabular::RemoveTableRow() +void InsetTabular::RemoveTabularRow() +{ +} + +bool InsetTabular::ActivateCellInset(BufferView * bv, int x, int y, int button) { + // the cursor.pos has to be before the inset so if it isn't now just + // reset the curor pos first! + if (cursor.pos % 2) { // behind the inset + --cursor.pos; + resetPos(bv->painter()); + } + UpdatableInset * inset = + static_cast(tabular->GetCellInset(actcell)); + LyXFont font(LyXFont::ALL_SANE); + if (x < 0) + x = inset->width(bv->painter(), font) + top_x; + if (y < 0) + y = inset->descent(bv->painter(), font); + inset_x = cursor.x - top_x + tabular->GetBeginningOfTextInCell(actcell); + inset_y = cursor.y; + inset->Edit(bv, x-inset_x, y-inset_y, button); + if (!the_locking_inset) + return false; + UpdateLocal(bv, true); + return true; +} + +bool InsetTabular::InsetHit(BufferView * bv, int x, int ) const +{ + InsetText * inset = tabular->GetCellInset(actcell); + int x1 = x + top_x; + + if (cursor.pos % 2) { // behind the inset + return (((x+top_x) < cursor.x) && + ((x+top_x) > (cursor.x - inset->width(bv->painter(), + LyXFont(LyXFont::ALL_SANE))))); + } else { + int x2 = cursor.x + tabular->GetBeginningOfTextInCell(actcell); + return ((x1 > x2) && + (x1 < (x2 + inset->width(bv->painter(), + LyXFont(LyXFont::ALL_SANE))))); + } }