GroupCell *GroupCell::Fold() { if (!IsFoldable() || m_hiddenTree) // already folded?? shouldn't happen return NULL; if (m_next == NULL) return NULL; int nextgct = dynamic_cast<GroupCell*>(m_next)->GetGroupType(); // groupType of the next cell if ((m_groupType == nextgct) || IsLesserGCType(nextgct)) return NULL; // if the next gc shouldn't be folded, exit // now there is at least one cell to fold (at least m_next) GroupCell *end = dynamic_cast<GroupCell*>(m_next); GroupCell *start = end; // first to fold while (end) { GroupCell *tmp = dynamic_cast<GroupCell*>(end->m_next); if (tmp == NULL) break; if ((m_groupType == tmp->GetGroupType()) || IsLesserGCType(tmp->GetGroupType())) break; // the next one of the end is not suitable for folding, break end = tmp; } // cell(s) to fold are between start and end (including these two) MathCell *next = end->m_next; m_next = m_nextToDraw = next; // may be NULL, it's ok if (next) next->m_previous = next->m_previousToDraw = this; start->m_previous = start->m_previousToDraw = NULL; end->m_next = end->m_nextToDraw = NULL; m_hiddenTree = start; // save the torn out tree into m_hiddenTree m_hiddenTree->SetHiddenTreeParent(this); return this; }
// unfolds recursivly its contents // if (all) then also calls it on it's m_next GroupCell *GroupCell::UnfoldAll(bool all) { if (all && m_next) dynamic_cast<GroupCell*>(m_next)->UnfoldAll(true); if (!IsFoldable() || !m_hiddenTree) return NULL; m_hiddenTree->UnfoldAll(true); return Unfold(); }
// when all=false (default) only reset input label of the current (code) cell // if all = true, then also reset next cells and folded cells void GroupCell::ResetInputLabel(bool all) { if (m_groupType == GC_TYPE_CODE) { if (m_input) m_input->SetValue(EMPTY_INPUT_LABEL); } // if all, also reset input labels in the folded cells else if (all && IsFoldable() && m_hiddenTree) m_hiddenTree->ResetInputLabel(true); // reset the next cell if (all && m_next) dynamic_cast<GroupCell*>(m_next)->ResetInputLabel(true); }
void GroupCell::Hide(bool hide) { if (IsFoldable()) return; if (m_hide == hide) return; m_hide = hide; if ((m_groupType == GC_TYPE_TEXT) || (m_groupType == GC_TYPE_CODE)) GetEditable()->SetFirstLineOnly(m_hide); ResetSize(); GetEditable()->ResetSize(); }
GroupCell *GroupCell::FoldAll(bool all) { GroupCell *result = this; if (IsFoldable() && !m_hiddenTree) { Fold(); if (m_hiddenTree) m_hiddenTree->FoldAll(true); } else result = NULL; if (all && m_next) return dynamic_cast<GroupCell*>(m_next)->FoldAll(true); else return result; }
void GroupCell::Number(int §ion, int &subsection, int &subsubsection, int &image) { switch (m_groupType) { case GC_TYPE_TITLE: section = subsection = subsubsection = 0; break; case GC_TYPE_SECTION: section++; subsection = subsubsection = 0; { wxString num = wxT(" "); num << section << wxT(" "); ((TextCell*)m_input)->SetValue(num); } break; case GC_TYPE_SUBSECTION: subsubsection = 0; subsection++; { wxString num = wxT(" "); num << section << wxT(".") << subsection << wxT(" "); ((TextCell*)m_input)->SetValue(num); } break; case GC_TYPE_SUBSUBSECTION: subsubsection++; { wxString num = wxT(" "); num << section << wxT(".") << subsection << wxT(".") << subsubsection << wxT(" "); ((TextCell*)m_input)->SetValue(num); } break; case GC_TYPE_IMAGE: image++; { wxString num = wxString::Format(_("Figure %d:"), image); ((TextCell*)m_input)->SetValue(num); } break; default: break; } if (IsFoldable() && m_hiddenTree) m_hiddenTree->Number(section, subsection, subsubsection, image); if (m_next) dynamic_cast<GroupCell*>(m_next)->Number(section, subsection, subsubsection, image); }
// unfolds the m_hiddenTree beneath this cell // be careful to update m_last if this happens in the main tree in MathCtrl GroupCell *GroupCell::Unfold() { if (!IsFoldable() || !m_hiddenTree) return NULL; MathCell *next = m_next; // sew together this cell with m_hiddenTree m_next = m_nextToDraw = m_hiddenTree; m_hiddenTree->m_previous = m_hiddenTree->m_previousToDraw = this; MathCell *tmp = m_hiddenTree; while (tmp->m_next) tmp = tmp->m_next; // tmp holds the last element of m_hiddenTree tmp->m_next = tmp->m_nextToDraw = next; if (next) next->m_previous = next->m_previousToDraw = tmp; m_hiddenTree = NULL; return dynamic_cast<GroupCell*>(tmp); }
/* Driver program to test mirror() */ int main(void) { /* The constructed binary tree is 1 / \ 2 3 \ / 4 5 */ struct node *root = newNode(1); root->left = newNode(2); root->right = newNode(3); root->left->right = newNode(4); root->right->left = newNode(5); if(IsFoldable(root) == true) { printf("\n tree is foldable"); } else { printf("\n tree is not foldable"); } getchar(); return 0; }
void GroupCell::Hide(bool hide) { if (IsFoldable()) return; if (m_hide == hide) return; else { if (m_hide == false) { if ((m_groupType == GC_TYPE_TEXT) || (m_groupType == GC_TYPE_CODE)) GetEditable()->SetFirstLineOnly(true); m_hide = true; } else { if ((m_groupType == GC_TYPE_TEXT) || (m_groupType == GC_TYPE_CODE)) GetEditable()->SetFirstLineOnly(false); m_hide = false; } ResetSize(); GetEditable()->ResetSize(); } }
void GroupCell::Draw(CellParser& parser, wxPoint point, int fontsize) { double scale = parser.GetScale(); wxDC& dc = parser.GetDC(); if (m_width == -1 || m_height == -1) { RecalculateWidths(parser, fontsize); RecalculateSize(parser, fontsize); } if (DrawThisCell(parser, point)) { // draw a thick line for 'page break' // and return if (m_groupType == GC_TYPE_PAGEBREAK) { wxRect rect = GetRect(false); int y = rect.GetY(); wxPen pen(parser.GetColor(TS_CURSOR), 1, wxPENSTYLE_DOT); dc.SetPen(pen); dc.DrawLine(0, y , 10000, y); MathCell::Draw(parser, point, fontsize); return; } // // Paint background if we have a text cell // if (m_groupType == GC_TYPE_TEXT) { wxRect rect = GetRect(false); int y = rect.GetY(); if (m_height > 0 && m_width > 0 && y>=0) { wxBrush br(parser.GetColor(TS_TEXT_BACKGROUND)); dc.SetBrush(br); wxPen pen(parser.GetColor(TS_TEXT_BACKGROUND)); dc.SetPen(pen); dc.DrawRectangle(0, y , 10000, rect.GetHeight()); } } // // Draw input and output // SetPen(parser); wxPoint in(point); parser.Outdated(false); m_input->DrawList(parser, in, fontsize); if (m_groupType == GC_TYPE_CODE && m_input->m_next) parser.Outdated(((EditorCell *)(m_input->m_next))->ContainsChanges()); if (m_output != NULL && !m_hide) { MathCell *tmp = m_output; int drop = tmp->GetMaxDrop(); in.y += m_input->GetMaxDrop() + m_output->GetMaxCenter(); m_outputRect.y = in.y - m_output->GetMaxCenter(); m_outputRect.x = in.x; while (tmp != NULL) { if (!tmp->m_isBroken) { tmp->m_currentPoint.x = in.x; tmp->m_currentPoint.y = in.y; if (tmp->DrawThisCell(parser, in)) tmp->Draw(parser, in, MAX(tmp->IsMath() ? m_mathFontSize : m_fontSize, MC_MIN_SIZE)); if (tmp->m_nextToDraw != NULL) { if (tmp->m_nextToDraw->BreakLineHere()) { in.x = m_indent; in.y += drop + tmp->m_nextToDraw->GetMaxCenter(); if (tmp->m_bigSkip) in.y += MC_LINE_SKIP; drop = tmp->m_nextToDraw->GetMaxDrop(); } else in.x += (tmp->GetWidth() + MC_CELL_SKIP); } } else { if (tmp->m_nextToDraw != NULL && tmp->m_nextToDraw->BreakLineHere()) { in.x = m_indent; in.y += drop + tmp->m_nextToDraw->GetMaxCenter(); if (tmp->m_bigSkip) in.y += MC_LINE_SKIP; drop = tmp->m_nextToDraw->GetMaxDrop(); } } tmp = tmp->m_nextToDraw; } } parser.Outdated(false); MathCell *editable = GetEditable(); if (editable != NULL && editable->IsActive()) { dc.SetPen( *(wxThePenList->FindOrCreatePen(parser.GetColor(TS_ACTIVE_CELL_BRACKET), 2, wxPENSTYLE_SOLID))); // window linux, set a pen dc.SetBrush( *(wxTheBrushList->FindOrCreateBrush(parser.GetColor(TS_ACTIVE_CELL_BRACKET)))); //highlight c. } else { dc.SetPen( *(wxThePenList->FindOrCreatePen(parser.GetColor(TS_CELL_BRACKET), 1, wxPENSTYLE_SOLID))); // window linux, set a pen dc.SetBrush( *(wxTheBrushList->FindOrCreateBrush(parser.GetColor(TS_CELL_BRACKET)))); //highlight c. } if ((!m_hide) && (!m_hiddenTree)) { dc.SetBrush(*wxTRANSPARENT_BRUSH); } if (IsFoldable()) { // draw a square wxPoint *points = new wxPoint[4]; points[0].x = point.x - SCALE_PX(10, scale); points[0].y = point.y - m_center; points[1].x = point.x - SCALE_PX(10, scale); points[1].y = point.y - m_center + SCALE_PX(10, scale); points[2].x = point.x; points[2].y = point.y - m_center + SCALE_PX(10, scale); points[3].x = point.x; points[3].y = point.y - m_center; dc.DrawPolygon(4, points); delete [] points; } else { // draw a triangle and line wxPoint *points = new wxPoint[3]; points[0].x = point.x - SCALE_PX(10, scale); points[0].y = point.y - m_center; points[1].x = point.x - SCALE_PX(10, scale); points[1].y = point.y - m_center + SCALE_PX(10, scale); points[2].x = point.x; points[2].y = point.y - m_center; dc.DrawPolygon(3, points); delete [] points; // vertical dc.DrawLine(point.x - SCALE_PX(10, scale), point.y - m_center, point.x - SCALE_PX(10, scale), point.y - m_center + m_height); // bottom horizontal dc.DrawLine(point.x - SCALE_PX(10, scale), point.y - m_center + m_height, point.x - SCALE_PX(2, scale) , point.y - m_center + m_height); // middle horizontal if (m_groupType == GC_TYPE_CODE && m_output != NULL && !m_hide) { dc.DrawLine(point.x - SCALE_PX(6, scale), point.y - m_center + m_input->GetMaxHeight(), point.x - SCALE_PX(10, scale), point.y - m_center + m_input->GetMaxHeight()); } } UnsetPen(parser); } MathCell::Draw(parser, point, fontsize); }