From 2b57c00a47909e45209cbfa69ba48bba76657b8b Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?L=C3=A9a=20Saviot?= Date: Thu, 19 Apr 2018 10:43:54 +0200 Subject: [PATCH] [poincare] Factorize computeBaseline/OperandHeight in ParLeftRightLayout Change-Id: I5a7e4f73df75d26a1b7e21460f888f5f1901307b --- .../src/layout/parenthesis_left_layout.cpp | 89 --------------- poincare/src/layout/parenthesis_left_layout.h | 2 - .../layout/parenthesis_left_right_layout.cpp | 103 ++++++++++++++++++ .../layout/parenthesis_left_right_layout.h | 3 +- .../src/layout/parenthesis_right_layout.cpp | 68 ------------ .../src/layout/parenthesis_right_layout.h | 2 - 6 files changed, 105 insertions(+), 162 deletions(-) diff --git a/poincare/src/layout/parenthesis_left_layout.cpp b/poincare/src/layout/parenthesis_left_layout.cpp index e1ac24b97..4e3d241fb 100644 --- a/poincare/src/layout/parenthesis_left_layout.cpp +++ b/poincare/src/layout/parenthesis_left_layout.cpp @@ -1,5 +1,4 @@ #include "parenthesis_left_layout.h" -#include extern "C" { #include #include @@ -62,92 +61,4 @@ void ParenthesisLeftLayout::render(KDContext * ctx, KDPoint p, KDColor expressio expressionColor); } -void ParenthesisLeftLayout::computeOperandHeight() { - assert(m_parent != nullptr); - m_operandHeight = Metric::MinimalBracketAndParenthesisHeight; - KDCoordinate max_under_baseline = 0; - KDCoordinate max_above_baseline = 0; - int indexInParent = m_parent->indexOfChild(this); - int currentNumberOfOpenParentheses = 1; - int numberOfBrothers = m_parent->numberOfChildren(); - if (indexInParent < numberOfBrothers - 1 - && m_parent->child(indexInParent + 1)->isVerticalOffset()) - { - // If the parenthesis is the base of a superscript layout, it should have a - // default height, else it creates an infinite loop because the parenthesis - // needs the superscript height, which needs the parenthesis height. - return; - } - for (int i = indexInParent + 1; i < numberOfBrothers; i++) { - ExpressionLayout * brother = m_parent->editableChild(i); - if (brother->isRightParenthesis()) { - currentNumberOfOpenParentheses--; - if (currentNumberOfOpenParentheses == 0) { - if (max_under_baseline + max_above_baseline > m_operandHeight) { - m_operandHeight = max_under_baseline + max_above_baseline; - } - return; - } - } else if (brother->isLeftParenthesis()) { - currentNumberOfOpenParentheses++; - } - KDCoordinate brotherHeight = brother->size().height(); - KDCoordinate brotherBaseline = brother->baseline(); - if (brotherHeight - brotherBaseline > max_under_baseline) { - max_under_baseline = brotherHeight - brotherBaseline ; - } - if (brotherBaseline > max_above_baseline) { - max_above_baseline = brotherBaseline; - } - } - if (max_under_baseline + max_above_baseline > m_operandHeight) { - m_operandHeight = max_under_baseline + max_above_baseline; - } -} - -void ParenthesisLeftLayout::computeBaseline() { - assert(m_parent != nullptr); - int currentNumberOfOpenParentheses = 1; - int indexInParent = m_parent->indexOfChild(this); - int numberOfBrothers = m_parent->numberOfChildren(); - if (indexInParent == numberOfBrothers - 1) { - // The parenthesis is the rightmost child of its parent. - m_baseline = operandHeight()/2; - m_baselined = true; - return; - } - if (m_parent->child(indexInParent + 1)->isVerticalOffset()) { - // If the parenthesis is the base of a superscript layout, it should have a - // default baseline, else it creates an infinite loop because the - // parenthesis needs the superscript height, which needs the parenthesis - // baseline. - m_baseline = operandHeight()/2; - m_baselined = true; - return; - } - - m_baseline = 0; - for (int i = indexInParent + 1; i < numberOfBrothers; i++) { - ExpressionLayout * brother = m_parent->editableChild(i); - if (brother->isRightParenthesis()) { - if (i == indexInParent + 1) { - // If the parenthesis is immediately closed, we set the baseline to half - // the parenthesis height. - m_baseline = operandHeight()/2; - break; - } - currentNumberOfOpenParentheses--; - if (currentNumberOfOpenParentheses == 0) { - break; - } - } else if (brother->isLeftParenthesis()) { - currentNumberOfOpenParentheses++; - } - if (brother->baseline() > m_baseline) { - m_baseline = brother->baseline(); - } - } - m_baselined = true; -} - } diff --git a/poincare/src/layout/parenthesis_left_layout.h b/poincare/src/layout/parenthesis_left_layout.h index 99c070fe4..565719038 100644 --- a/poincare/src/layout/parenthesis_left_layout.h +++ b/poincare/src/layout/parenthesis_left_layout.h @@ -19,8 +19,6 @@ public: bool isLeftParenthesis() const override { return true; } protected: void render(KDContext * ctx, KDPoint p, KDColor expressionColor, KDColor backgroundColor) override; - void computeOperandHeight() override; - void computeBaseline() override; }; } diff --git a/poincare/src/layout/parenthesis_left_right_layout.cpp b/poincare/src/layout/parenthesis_left_right_layout.cpp index b7d8f819e..9d9fd8bb1 100644 --- a/poincare/src/layout/parenthesis_left_right_layout.cpp +++ b/poincare/src/layout/parenthesis_left_right_layout.cpp @@ -1,4 +1,5 @@ #include "parenthesis_left_right_layout.h" +#include #include extern "C" { #include @@ -56,6 +57,55 @@ KDSize ParenthesisLeftRightLayout::computeSize() { return KDSize(parenthesisWidth(), operandHeight()); } +void ParenthesisLeftRightLayout::computeBaseline() { + assert(m_parent != nullptr); + bool isParenthesisLeft = isLeftParenthesis(); + int indexInParent = m_parent->indexOfChild(this); + int numberOfBrothers = m_parent->numberOfChildren(); + if ((isParenthesisLeft && indexInParent == numberOfBrothers - 1) + || (!isParenthesisLeft && indexInParent == 0) + || (isParenthesisLeft && indexInParent < numberOfBrothers - 1 && m_parent->child(indexInParent + 1)->isVerticalOffset())) + { + /* The parenthesis does not have brothers on its open direction, or it is a + * left parenthesis that is base of a superscript layout. In the latter + * case, it should have a default baseline, else it creates an infinite loop + * because the parenthesis needs the superscript height, which needs the + * parenthesis baseline. */ + m_baseline = operandHeight()/2; + m_baselined = true; + return; + } + + int currentNumberOfOpenParentheses = 1; + m_baseline = 0; + int increment = isParenthesisLeft ? 1 : -1; + for (int i = indexInParent + increment; i >= 0 && i <= numberOfBrothers - 1; i+= increment) { + ExpressionLayout * brother = m_parent->editableChild(i); + if ((isParenthesisLeft && brother->isRightParenthesis()) + || (!isParenthesisLeft && brother->isLeftParenthesis())) + { + if (i == indexInParent + increment) { + /* If the parenthesis is immediately closed, we set the baseline to half + * the parenthesis height. */ + m_baseline = size().height()/2; + break; + } + currentNumberOfOpenParentheses--; + if (currentNumberOfOpenParentheses == 0) { + break; + } + } else if ((isParenthesisLeft && brother->isLeftParenthesis()) + || (!isParenthesisLeft && brother->isRightParenthesis())) + { + currentNumberOfOpenParentheses++; + } + if (brother->baseline() > m_baseline) { + m_baseline = brother->baseline(); + } + } + m_baselined = true; +} + KDCoordinate ParenthesisLeftRightLayout::operandHeight() { if (!m_operandHeightComputed) { computeOperandHeight(); @@ -64,6 +114,59 @@ KDCoordinate ParenthesisLeftRightLayout::operandHeight() { return m_operandHeight; } +void ParenthesisLeftRightLayout::computeOperandHeight() { + assert(m_parent != nullptr); + m_operandHeight = Metric::MinimalBracketAndParenthesisHeight; + bool isParenthesisLeft = isLeftParenthesis(); + int indexInParent = m_parent->indexOfChild(this); + int numberOfBrothers = m_parent->numberOfChildren(); + if (isParenthesisLeft + && indexInParent < numberOfBrothers - 1 + && m_parent->child(indexInParent + 1)->isVerticalOffset()) + { + /* If a left parenthesis is the base of a superscript layout, it should have + * a default height, else it creates an infinite loop because the + * parenthesis needs the superscript height, which needs the parenthesis + * height. */ + return; + } + + KDCoordinate max_under_baseline = 0; + KDCoordinate max_above_baseline = 0; + + int currentNumberOfOpenParentheses = 1; + int increment = isParenthesisLeft ? 1 : -1; + for (int i = indexInParent + increment; i >= 0 && i < numberOfBrothers; i+= increment) { + ExpressionLayout * brother = m_parent->editableChild(i); + if ((!isParenthesisLeft && brother->isLeftParenthesis()) + || (isParenthesisLeft && brother->isRightParenthesis())) + { + currentNumberOfOpenParentheses--; + if (currentNumberOfOpenParentheses == 0) { + if (max_under_baseline + max_above_baseline > m_operandHeight) { + m_operandHeight = max_under_baseline + max_above_baseline; + } + return; + } + } else if ((isParenthesisLeft && brother->isLeftParenthesis()) + || (!isParenthesisLeft && brother->isRightParenthesis())) + { + currentNumberOfOpenParentheses++; + } + KDCoordinate brotherHeight = brother->size().height(); + KDCoordinate brotherBaseline = brother->baseline(); + if (brotherHeight - brotherBaseline > max_under_baseline) { + max_under_baseline = brotherHeight - brotherBaseline ; + } + if (brotherBaseline > max_above_baseline) { + max_above_baseline = brotherBaseline; + } + } + if (max_under_baseline + max_above_baseline > m_operandHeight) { + m_operandHeight = max_under_baseline + max_above_baseline; + } +} + KDPoint ParenthesisLeftRightLayout::positionOfChild(ExpressionLayout * child) { assert(false); return KDPointZero; diff --git a/poincare/src/layout/parenthesis_left_right_layout.h b/poincare/src/layout/parenthesis_left_right_layout.h index b40f2536d..ba6c1a7cd 100644 --- a/poincare/src/layout/parenthesis_left_right_layout.h +++ b/poincare/src/layout/parenthesis_left_right_layout.h @@ -21,8 +21,9 @@ public: protected: KDColor s_parenthesisWorkingBuffer[k_parenthesisCurveHeight*k_parenthesisCurveWidth]; KDSize computeSize() override; + void computeBaseline() override; KDCoordinate operandHeight(); - virtual void computeOperandHeight() = 0; + void computeOperandHeight(); KDPoint positionOfChild(ExpressionLayout * child) override; bool m_operandHeightComputed; uint16_t m_operandHeight; diff --git a/poincare/src/layout/parenthesis_right_layout.cpp b/poincare/src/layout/parenthesis_right_layout.cpp index e0346d42b..08fb8f5cb 100644 --- a/poincare/src/layout/parenthesis_right_layout.cpp +++ b/poincare/src/layout/parenthesis_right_layout.cpp @@ -1,5 +1,4 @@ #include "parenthesis_right_layout.h" -#include extern "C" { #include #include @@ -62,73 +61,6 @@ void ParenthesisRightLayout::render(KDContext * ctx, KDPoint p, KDColor expressi expressionColor); } -void ParenthesisRightLayout::computeOperandHeight() { - assert(m_parent != nullptr); - m_operandHeight = Metric::MinimalBracketAndParenthesisHeight; - KDCoordinate max_under_baseline = 0; - KDCoordinate max_above_baseline = 0; - int currentNumberOfOpenParentheses = 1; - for (int i = m_parent->indexOfChild(this) - 1; i >= 0; i--) { - ExpressionLayout * brother = m_parent->editableChild(i); - if (brother->isLeftParenthesis()) { - currentNumberOfOpenParentheses--; - if (currentNumberOfOpenParentheses == 0) { - if (max_under_baseline + max_above_baseline > m_operandHeight) { - m_operandHeight = max_under_baseline + max_above_baseline; - } - return; - } - } else if (brother->isRightParenthesis()) { - currentNumberOfOpenParentheses++; - } - KDCoordinate brotherHeight = brother->size().height(); - KDCoordinate brotherBaseline = brother->baseline(); - if (brotherHeight - brotherBaseline > max_under_baseline) { - max_under_baseline = brotherHeight - brotherBaseline ; - } - if (brotherBaseline > max_above_baseline) { - max_above_baseline = brotherBaseline; - } - } - if (max_under_baseline + max_above_baseline > m_operandHeight) { - m_operandHeight = max_under_baseline + max_above_baseline; - } -} - -void ParenthesisRightLayout::computeBaseline() { - assert(m_parent != nullptr); - int currentNumberOfOpenParentheses = 1; - int indexInParent = m_parent->indexOfChild(this); - if (indexInParent == 0) { - // The parenthesis is the leftmost child of its parent. - m_baseline = operandHeight()/2; - m_baselined = true; - return; - } - m_baseline = 0; - for (int i = indexInParent - 1; i >= 0; i--) { - ExpressionLayout * brother = m_parent->editableChild(i); - if (brother->isLeftParenthesis()) { - if (i == indexInParent - 1) { - // If the parenthesis is immediately closed, we set the baseline to half - // the parenthesis height. - m_baseline = operandHeight()/2; - break; - } - currentNumberOfOpenParentheses--; - if (currentNumberOfOpenParentheses == 0) { - break; - } - } else if (brother->isRightParenthesis()) { - currentNumberOfOpenParentheses++; - } - if (brother->baseline() > m_baseline) { - m_baseline = brother->baseline(); - } - } - m_baselined = true; -} - } diff --git a/poincare/src/layout/parenthesis_right_layout.h b/poincare/src/layout/parenthesis_right_layout.h index edf361dfb..964bf3d60 100644 --- a/poincare/src/layout/parenthesis_right_layout.h +++ b/poincare/src/layout/parenthesis_right_layout.h @@ -19,8 +19,6 @@ public: bool isRightParenthesis() const override { return true; } protected: void render(KDContext * ctx, KDPoint p, KDColor expressionColor, KDColor backgroundColor) override; - void computeOperandHeight() override; - void computeBaseline() override; }; }