diff --git a/apps/math_toolbox.cpp b/apps/math_toolbox.cpp index 192c2180c..cdf4e14b4 100644 --- a/apps/math_toolbox.cpp +++ b/apps/math_toolbox.cpp @@ -13,14 +13,18 @@ const ToolboxNode probabilityChildren[2] = {ToolboxNode(I18n::Message::BinomialC const ToolboxNode arithmeticChildren[4] = {ToolboxNode(I18n::Message::GcdCommandWithArg, I18n::Message::GreatCommonDivisor, I18n::Message::GcdCommand),ToolboxNode(I18n::Message::LcmCommandWithArg, I18n::Message::LeastCommonMultiple, I18n::Message::LcmCommand), ToolboxNode(I18n::Message::RemCommandWithArg, I18n::Message::Remainder, I18n::Message::RemCommand), ToolboxNode(I18n::Message::QuoCommandWithArg, I18n::Message::Quotient, I18n::Message::QuoCommand)}; #if MATRICES_ARE_DEFINED const ToolboxNode matricesChildren[5] = {ToolboxNode(I18n::Message::InverseCommandWithArg, I18n::Message::Inverse, I18n::Message::InverseCommand), ToolboxNode(I18n::Message::DeterminantCommandWithArg, I18n::Message::Determinant, I18n::Message::DeterminantCommand), ToolboxNode(I18n::Message::TransposeCommandWithArg, I18n::Message::Transpose, I18n::Message::TransposeCommand), ToolboxNode(I18n::Message::TraceCommandWithArg, I18n::Message::Trace, I18n::Message::TraceCommand), ToolboxNode(I18n::Message::DimensionCommandWithArg, I18n::Message::Dimension, I18n::Message::DimensionCommand)}; +#endif +#if LIST_ARE_DEFINED const ToolboxNode listesChildren[5] = {ToolboxNode(I18n::Message::SortCommandWithArg, I18n::Message::Sort, I18n::Message::SortCommand), ToolboxNode(I18n::Message::InvSortCommandWithArg, I18n::Message::InvSort, I18n::Message::InvSortCommand), ToolboxNode(I18n::Message::MaxCommandWithArg, I18n::Message::Maximum, I18n::Message::MaxCommand), ToolboxNode(I18n::Message::MinCommandWithArg, I18n::Message::Minimum, I18n::Message::MinCommand), ToolboxNode(I18n::Message::DimensionCommandWithArg, I18n::Message::Dimension, I18n::Message::DimensionCommand)}; #endif const ToolboxNode approximationChildren[4] = {ToolboxNode(I18n::Message::FloorCommandWithArg, I18n::Message::Floor, I18n::Message::FloorCommand), ToolboxNode(I18n::Message::FracCommandWithArg, I18n::Message::FracPart, I18n::Message::FracCommand), ToolboxNode(I18n::Message::CeilCommandWithArg, I18n::Message::Ceiling, I18n::Message::CeilCommand), ToolboxNode(I18n::Message::RoundCommandWithArg, I18n::Message::Rounding, I18n::Message::RoundCommand)}; const ToolboxNode trigonometryChildren[6] = {ToolboxNode(I18n::Message::CoshCommandWithArg, I18n::Message::Cosh, I18n::Message::CoshCommand), ToolboxNode(I18n::Message::SinhCommandWithArg, I18n::Message::Sinh, I18n::Message::SinhCommand), ToolboxNode(I18n::Message::TanhCommandWithArg, I18n::Message::Tanh, I18n::Message::TanhCommand), ToolboxNode(I18n::Message::AcoshCommandWithArg, I18n::Message::Acosh, I18n::Message::AcoshCommand), ToolboxNode(I18n::Message::AsinhCommandWithArg, I18n::Message::Asinh, I18n::Message::AsinhCommand), ToolboxNode(I18n::Message::AtanhCommandWithArg, I18n::Message::Atanh, I18n::Message::AtanhCommand)}; const ToolboxNode predictionChildren[3] = {ToolboxNode(I18n::Message::Prediction95CommandWithArg, I18n::Message::Prediction95, I18n::Message::Prediction95Command), ToolboxNode(I18n::Message::PredictionCommandWithArg, I18n::Message::Prediction, I18n::Message::PredictionCommand), ToolboxNode(I18n::Message::ConfidenceCommandWithArg, I18n::Message::Confidence, I18n::Message::ConfidenceCommand)}; -#if MATRICES_ARE_DEFINED +#if LIST_ARE_DEFINED const ToolboxNode menu[12] = {ToolboxNode(I18n::Message::AbsCommandWithArg, I18n::Message::AbsoluteValue, I18n::Message::AbsCommand), +#elif MATRICES_ARE_DEFINED +const ToolboxNode menu[11] = {ToolboxNode(I18n::Message::AbsCommandWithArg, I18n::Message::AbsoluteValue, I18n::Message::AbsCommand), #else const ToolboxNode menu[10] = {ToolboxNode(I18n::Message::AbsCommandWithArg, I18n::Message::AbsoluteValue, I18n::Message::AbsCommand), #endif @@ -32,13 +36,17 @@ const ToolboxNode menu[10] = {ToolboxNode(I18n::Message::AbsCommandWithArg, I18n ToolboxNode(I18n::Message::Arithmetic, I18n::Message::Default, I18n::Message::Default, arithmeticChildren, 4), #if MATRICES_ARE_DEFINED ToolboxNode(I18n::Message::Matrices, I18n::Message::Default, I18n::Message::Default, matricesChildren, 5), +#endif +#if LIST_ARE_DEFINED ToolboxNode(I18n::Message::Lists, I18n::Message::Default, I18n::Message::Default, listesChildren, 5), #endif ToolboxNode(I18n::Message::Approximation, I18n::Message::Default, I18n::Message::Default, approximationChildren, 4), ToolboxNode(I18n::Message::HyperbolicTrigonometry, I18n::Message::Default, I18n::Message::Default, trigonometryChildren, 6), ToolboxNode(I18n::Message::Fluctuation, I18n::Message::Default, I18n::Message::Default, predictionChildren, 3)}; -#if MATRICES_ARE_DEFINED +#if LIST_ARE_DEFINED const ToolboxNode toolboxModel = ToolboxNode(I18n::Message::Toolbox, I18n::Message::Default, I18n::Message::Default, menu, 12); +#elif MATRICES_ARE_DEFINED +const ToolboxNode toolboxModel = ToolboxNode(I18n::Message::Toolbox, I18n::Message::Default, I18n::Message::Default, menu, 11); #else const ToolboxNode toolboxModel = ToolboxNode(I18n::Message::Toolbox, I18n::Message::Default, I18n::Message::Default, menu, 10); #endif diff --git a/apps/math_toolbox.h b/apps/math_toolbox.h index 65d94129b..95b30de74 100644 --- a/apps/math_toolbox.h +++ b/apps/math_toolbox.h @@ -1,6 +1,7 @@ #ifndef APPS_MATH_TOOLBOX_H #define APPS_MATH_TOOLBOX_H +#define MATRICES_ARE_DEFINED 1 #include #include "toolbox_node.h" diff --git a/apps/variable_box_controller.cpp b/apps/variable_box_controller.cpp index e748117cc..bd60dcc19 100644 --- a/apps/variable_box_controller.cpp +++ b/apps/variable_box_controller.cpp @@ -32,7 +32,7 @@ void VariableBoxController::ContentViewController::didBecomeFirstResponder() { } bool VariableBoxController::ContentViewController::handleEvent(Ion::Events::Event event) { -#if MATRIX_LIST_VARIABLES +#if MATRIX_VARIABLES if (event == Ion::Events::Back && m_currentPage == Page::RootMenu) { #else if (event == Ion::Events::Back && m_currentPage == Page::Scalar) { @@ -43,17 +43,19 @@ bool VariableBoxController::ContentViewController::handleEvent(Ion::Events::Even } if (event == Ion::Events::Back || event == Ion::Events::Left) { m_firstSelectedRow = m_previousSelectedRow; -#if MATRIX_LIST_VARIABLES +#if MATRIX_VARIABLES + m_selectableTableView.deselectTable(); m_currentPage = Page::RootMenu; #endif app()->setFirstResponder(this); return true; } if (event == Ion::Events::OK || event == Ion::Events::EXE || (event == Ion::Events::Right && m_currentPage == Page::RootMenu)) { - if (m_currentPage == Page::RootMenu) { + if (m_currentPage == Page::RootMenu) { m_previousSelectedRow = selectedRow(); m_firstSelectedRow = 0; - m_currentPage = pageAtIndex(selectedRow()); + m_selectableTableView.deselectTable(); + m_currentPage = pageAtIndex(m_previousSelectedRow); app()->setFirstResponder(this); return true; } @@ -66,7 +68,8 @@ bool VariableBoxController::ContentViewController::handleEvent(Ion::Events::Even } m_textFieldCaller->insertTextAtLocation(editedText, m_textFieldCaller->cursorLocation()); m_textFieldCaller->setCursorLocation(m_textFieldCaller->cursorLocation() + strlen(editedText)); -#if MATRIX_LIST_VARIABLES +#if MATRIX_VARIABLES + m_selectableTableView.deselectTable(); m_currentPage = Page::RootMenu; #endif app()->dismissModalViewController(); @@ -78,11 +81,13 @@ bool VariableBoxController::ContentViewController::handleEvent(Ion::Events::Even int VariableBoxController::ContentViewController::numberOfRows() { switch (m_currentPage) { case Page::RootMenu: - return 3; + return k_numberOfMenuRows; case Page::Scalar: return GlobalContext::k_maxNumberOfScalarExpressions; +#if LIST_VARIABLES case Page::List: return GlobalContext::k_maxNumberOfListExpressions; +#endif case Page::Matrix: return GlobalContext::k_maxNumberOfMatrixExpressions; default: @@ -130,16 +135,17 @@ void VariableBoxController::ContentViewController::willDisplayCellForIndex(Highl } myCell->displayExpression(true); if (expression) { - /* TODO: implement matrix and list contexts */ - //myCell->setExpression(expression->createLayout()); - // TODO: display the dimensgion of the list/matrice as subtitle - /* char buffer[4]; - * buffer[0] = (Matrice *)expression->dim(0); - * buffer[1] = 'x'; - * buffer[2] = (Matrice *)expression->dim(1) - * buffer[3] = 0; - * myCell->setSubtitle(buffer);*/ + assert(expression->type() == Expression::Type::Matrix); + Matrix * m = (Matrix *)expression; + /* TODO: implement list contexts */ + myCell->setExpression((Expression *)expression); + char buffer[2*Complex::bufferSizeForFloatsWithPrecision(2)+1]; + int numberOfChars = Complex::convertFloatToText(m->numberOfRows(), buffer, Complex::bufferSizeForFloatsWithPrecision(2), 2, Expression::FloatDisplayMode::Decimal); + buffer[numberOfChars++] = 'x'; + Complex::convertFloatToText(m->numberOfColumns(), buffer+numberOfChars, Complex::bufferSizeForFloatsWithPrecision(2), 2, Expression::FloatDisplayMode::Decimal); + myCell->setSubtitle(buffer); } else { + myCell->setExpression(nullptr); myCell->setSubtitle("Vide"); } } @@ -153,8 +159,10 @@ KDCoordinate VariableBoxController::ContentViewController::rowHeight(int index) } const Expression * expression = expressionForIndex(index); if (expression) { - KDCoordinate expressionHeight = expression->createLayout()->size().height(); - return expressionHeight; + ExpressionLayout * layout = expression->createLayout(); + KDCoordinate expressionHeight = layout->size().height(); + delete layout; + return expressionHeight+k_leafMargin; } return k_leafRowHeight; } @@ -189,16 +197,23 @@ const Expression * VariableBoxController::ContentViewController::expressionForIn return m_context->expressionForSymbol(&symbol); } if (m_currentPage == Page::Matrix) { - return nullptr; + const Symbol symbol = Symbol::matrixSymbol('0'+(char)index); + return m_context->expressionForSymbol(&symbol); } +#if LIST_VARIABLES if (m_currentPage == Page::List) { return nullptr; } +#endif return nullptr; } VariableBoxController::ContentViewController::Page VariableBoxController::ContentViewController::pageAtIndex(int index) { +#if LIST_VARIABLES Page pages[3] = {Page::Scalar, Page::List, Page::Matrix}; +#else + Page pages[2] = {Page::Scalar, Page::Matrix}; +#endif return pages[index]; } @@ -207,11 +222,13 @@ void VariableBoxController::ContentViewController::putLabelAtIndexInBuffer(int i buffer[0] = 'A' + index; buffer[1] = 0; } +#if LIST_VARIABLES if (m_currentPage == Page::List) { buffer[0] = 'L'; buffer[1] = '0' + index; buffer[2] = 0; } +#endif if (m_currentPage == Page::Matrix) { buffer[0] = 'M'; buffer[1] = '0' + index; @@ -221,7 +238,11 @@ void VariableBoxController::ContentViewController::putLabelAtIndexInBuffer(int i I18n::Message VariableBoxController::ContentViewController::nodeLabelAtIndex(int index) { assert(m_currentPage == Page::RootMenu); +#if LIST_VARIABLES I18n::Message labels[3] = {I18n::Message::Number, I18n::Message::List, I18n::Message::Matrix}; +#else + I18n::Message labels[2] = {I18n::Message::Number, I18n::Message::Matrix}; +#endif return labels[index]; } @@ -234,13 +255,18 @@ void VariableBoxController::ContentViewController::reloadData() { } void VariableBoxController::ContentViewController::resetPage() { -#if MATRIX_LIST_VARIABLES +#if MATRIX_VARIABLES m_currentPage = Page::RootMenu; #else m_currentPage = Page::Scalar; #endif } +void VariableBoxController::ContentViewController::viewDidDisappear() { + m_selectableTableView.deselectTable(); + ViewController::viewDidDisappear(); +} + VariableBoxController::VariableBoxController(Context * context) : StackViewController(nullptr, &m_contentViewController, true, KDColorWhite, Palette::PurpleBright, Palette::PurpleDark), m_contentViewController(this, context) diff --git a/apps/variable_box_controller.h b/apps/variable_box_controller.h index cdb00d496..96583be0f 100644 --- a/apps/variable_box_controller.h +++ b/apps/variable_box_controller.h @@ -1,6 +1,8 @@ #ifndef APPS_VARIABLE_BOX_CONTROLLER_H #define APPS_VARIABLE_BOX_CONTROLLER_H +#define MATRIX_VARIABLES 1 + #include #include #include "variable_box_leaf_cell.h" @@ -32,16 +34,24 @@ private: void setTextFieldCaller(TextField * textField); void reloadData(); void resetPage(); + void viewDidDisappear() override; private: enum class Page { RootMenu, Scalar, +#if LIST_VARIABLES List, +#endif Matrix }; constexpr static int k_maxNumberOfDisplayedRows = 6; //240/40 - constexpr static int k_numberOfMenuRows = 3; //240/40 +#if LIST_VARIABLES + constexpr static int k_numberOfMenuRows = 3; +#else + constexpr static int k_numberOfMenuRows = 2; +#endif constexpr static KDCoordinate k_leafRowHeight = 40; + constexpr static KDCoordinate k_leafMargin = 10; constexpr static KDCoordinate k_nodeRowHeight = 40; Page pageAtIndex(int index); void putLabelAtIndexInBuffer(int index, char * buffer); diff --git a/apps/variable_box_leaf_cell.cpp b/apps/variable_box_leaf_cell.cpp index 32cdbfe21..aec45eeb8 100644 --- a/apps/variable_box_leaf_cell.cpp +++ b/apps/variable_box_leaf_cell.cpp @@ -5,12 +5,20 @@ using namespace Poincare; VariableBoxLeafCell::VariableBoxLeafCell() : HighlightCell(), + m_expressionLayout(nullptr), m_labelView(KDText::FontSize::Small, 0, 0.5, KDColorBlack, KDColorWhite), m_subtitleView(KDText::FontSize::Small, 0, 0.5, Palette::GreyDark, KDColorWhite), + m_expressionView(1.0f, 0.5f), m_displayExpression(false) { } +VariableBoxLeafCell::~VariableBoxLeafCell() { + if (m_expressionLayout != nullptr) { + delete m_expressionLayout; + m_expressionLayout = nullptr; + } +} void VariableBoxLeafCell::displayExpression(bool displayExpression) { m_displayExpression = displayExpression; } @@ -37,10 +45,19 @@ void VariableBoxLeafCell::layoutSubviews() { KDCoordinate width = bounds().width(); KDCoordinate height = bounds().height(); if (numberOfSubviews() == 3) { - m_labelView.setFrame(KDRect(k_separatorThickness+k_widthMargin, k_separatorThickness, width/2-k_separatorThickness-k_widthMargin, height/2 - k_separatorThickness)); - m_subtitleView.setFrame(KDRect(k_separatorThickness+k_widthMargin, height/2, width/2-k_widthMargin-k_separatorThickness, height/2-k_separatorThickness)); + KDSize labelSize = m_labelView.minimalSizeForOptimalDisplay(); + KDSize subtitleSize = m_subtitleView.minimalSizeForOptimalDisplay(); + m_labelView.setFrame(KDRect(k_separatorThickness+k_widthMargin, k_separatorThickness, labelSize.width(), height/2 - k_separatorThickness)); + m_subtitleView.setFrame(KDRect(k_separatorThickness+k_widthMargin, height/2, subtitleSize.width(), height/2-k_separatorThickness)); m_subtitleView.setAlignment(0.0f, 0.5f); - m_expressionView.setFrame(KDRect(width/2, k_separatorThickness, width/2-k_separatorThickness-k_widthMargin, height-2*k_separatorThickness)); + KDCoordinate maxTextSize = subtitleSize.width() > labelSize.width() ? subtitleSize.width() : labelSize.width(); + KDCoordinate expressionAvailableSize = width-k_separatorThickness-3*k_widthMargin-maxTextSize; + m_expressionView.setFrame(KDRect(width - expressionAvailableSize - k_widthMargin, k_separatorThickness, expressionAvailableSize, height-2*k_separatorThickness)); + if (m_expressionView.minimalSizeForOptimalDisplay().width() > expressionAvailableSize) { + m_expressionView.setAlignment(0.0f, 0.5f); + } else { + m_expressionView.setAlignment(1.0f, 0.5f); + } return; } m_labelView.setFrame(KDRect(k_separatorThickness+k_widthMargin, k_separatorThickness, width/2-k_separatorThickness-k_widthMargin, height-2*k_separatorThickness)); @@ -66,8 +83,15 @@ void VariableBoxLeafCell::setSubtitle(const char * text) { layoutSubviews(); } -void VariableBoxLeafCell::setExpression(ExpressionLayout * expressionLayout) { - m_expressionView.setExpression(expressionLayout); +void VariableBoxLeafCell::setExpression(Expression * expression) { + if(m_expressionLayout != nullptr) { + delete m_expressionLayout; + m_expressionLayout = nullptr; + } + if (expression) { + m_expressionLayout = expression->createLayout(); + } + m_expressionView.setExpression(m_expressionLayout); } void VariableBoxLeafCell::drawRect(KDContext * ctx, KDRect rect) const { diff --git a/apps/variable_box_leaf_cell.h b/apps/variable_box_leaf_cell.h index 2133f9e23..83b7e0147 100644 --- a/apps/variable_box_leaf_cell.h +++ b/apps/variable_box_leaf_cell.h @@ -2,15 +2,17 @@ #define APPS_VARIABLE_BOX_LEAF_CELL_H #include +#include class VariableBoxLeafCell : public HighlightCell { public: VariableBoxLeafCell(); + ~VariableBoxLeafCell(); void displayExpression(bool displayExpression); void reloadCell() override; void setLabel(const char * text); void setSubtitle(const char * text); - void setExpression(Poincare::ExpressionLayout * expressionLayout); + void setExpression(Poincare::Expression * expression); void drawRect(KDContext * ctx, KDRect rect) const override; private: constexpr static KDCoordinate k_separatorThickness = 1; @@ -18,6 +20,9 @@ private: int numberOfSubviews() const override; View * subviewAtIndex(int index) override; void layoutSubviews() override; + /* The cell is responsible to delete the layout that may be created by its + * dynamic method 'setExpression'.*/ + Poincare::ExpressionLayout * m_expressionLayout; BufferTextView m_labelView; BufferTextView m_subtitleView; ExpressionView m_expressionView; diff --git a/poincare/include/poincare/global_context.h b/poincare/include/poincare/global_context.h index fd160aed8..d443ed371 100644 --- a/poincare/include/poincare/global_context.h +++ b/poincare/include/poincare/global_context.h @@ -29,6 +29,7 @@ public: private: int symbolIndex(const Symbol * symbol) const; Expression * m_expressions[k_maxNumberOfScalarExpressions]; + Expression * m_matrixExpressions[k_maxNumberOfMatrixExpressions]; Complex m_pi; Complex m_e; }; diff --git a/poincare/include/poincare/symbol.h b/poincare/include/poincare/symbol.h index c78b518f2..06cde83a2 100644 --- a/poincare/include/poincare/symbol.h +++ b/poincare/include/poincare/symbol.h @@ -8,19 +8,33 @@ namespace Poincare { class Symbol : public LeafExpression { public: enum SpecialSymbols : char { - Ans = '^', - un = 1, - un1 = 2, - vn = 3, - vn1 = 4, - wn = 5, - wn1 = 6 + /* We can use characters from 1 to 31 as they do not correspond to usual + * characters but events as 'end of text', 'backspace'... */ + Ans = 1, + un = 2, + un1 = 3, + vn = 4, + vn1 = 5, + wn = 6, + wn1 = 7, + M0 = 8, + M1 = 9, + M2, + M3, + M4, + M5, + M6, + M7, + M8, + M9 = 17 }; + static SpecialSymbols matrixSymbol(char index); Symbol(char name); Type type() const override; const char name() const; Expression * clone() const override; bool valueEquals(const Expression * e) const override; + bool isMatrixSymbol() const; private: float privateApproximate(Context& context, AngleUnit angleUnit) const override; Expression * privateEvaluate(Context& context, AngleUnit angleUnit) const override; diff --git a/poincare/src/expression_lexer.l b/poincare/src/expression_lexer.l index 1fdda7668..70b6e19de 100644 --- a/poincare/src/expression_lexer.l +++ b/poincare/src/expression_lexer.l @@ -84,6 +84,7 @@ using namespace Poincare; [0-9]+ { poincare_expression_yylval.string.address = yytext; poincare_expression_yylval.string.length = yyleng; return DIGITS; } [A-Zxn] { poincare_expression_yylval.character = yytext[0]; return SYMBOL; } [a-z;:"_=<>] { return UNDEFINED_SYMBOL; } +M[0-9] { poincare_expression_yylval.character = Symbol::matrixSymbol(yytext[1]); return SYMBOL; } u\(n\) { poincare_expression_yylval.character = Symbol::SpecialSymbols::un; return SYMBOL; } u\(n\+1\) { poincare_expression_yylval.character = Symbol::SpecialSymbols::un1; return SYMBOL; } v\(n\) { poincare_expression_yylval.character = Symbol::SpecialSymbols::vn; return SYMBOL; } diff --git a/poincare/src/global_context.cpp b/poincare/src/global_context.cpp index 71dab552f..06256a00c 100644 --- a/poincare/src/global_context.cpp +++ b/poincare/src/global_context.cpp @@ -1,4 +1,5 @@ #include +#include #include #include #include @@ -12,6 +13,9 @@ GlobalContext::GlobalContext() : for (int i = 0; i < k_maxNumberOfScalarExpressions; i++) { m_expressions[i] = nullptr; } + for (int i = 0; i < k_maxNumberOfMatrixExpressions ; i++) { + m_matrixExpressions[i] = nullptr; + } } GlobalContext::~GlobalContext() { @@ -21,6 +25,12 @@ GlobalContext::~GlobalContext() { } m_expressions[i] = nullptr; } + for (int i = 0; i < k_maxNumberOfMatrixExpressions; i++) { + if (m_matrixExpressions[i] != nullptr) { + delete m_matrixExpressions[i]; + } + m_matrixExpressions[i] = nullptr; + } } Complex * GlobalContext::defaultExpression() { @@ -40,6 +50,10 @@ const Expression * GlobalContext::expressionForSymbol(const Symbol * symbol) { if (symbol->name() == Ion::Charset::Exponential) { return &m_e; } + if (symbol->isMatrixSymbol()) { + int indexMatrix = symbol->name() - (char)Symbol::SpecialSymbols::M0; + return m_matrixExpressions[indexMatrix]; + } int index = symbolIndex(symbol); if (index < 0 || index >= k_maxNumberOfScalarExpressions) { return nullptr; @@ -51,6 +65,18 @@ const Expression * GlobalContext::expressionForSymbol(const Symbol * symbol) { } void GlobalContext::setExpressionForSymbolName(Expression * expression, const Symbol * symbol) { + if (symbol->isMatrixSymbol()) { + int indexMatrix = symbol->name() - (char)Symbol::SpecialSymbols::M0; + assert(indexMatrix >= 0 && indexMatrix < k_maxNumberOfMatrixExpressions); + if (m_expressions[indexMatrix] != nullptr) { + delete m_matrixExpressions[indexMatrix]; + m_matrixExpressions[indexMatrix] = nullptr; + } + if (expression->type() == Expression::Type::Matrix) { + m_matrixExpressions[indexMatrix] = expression->clone(); + } + return; + } int index = symbolIndex(symbol); if (index < 0 || index >= k_maxNumberOfScalarExpressions) { return; diff --git a/poincare/src/symbol.cpp b/poincare/src/symbol.cpp index ea4be7894..52867567c 100644 --- a/poincare/src/symbol.cpp +++ b/poincare/src/symbol.cpp @@ -10,6 +10,34 @@ extern "C" { namespace Poincare { +Symbol::SpecialSymbols Symbol::matrixSymbol(char index) { + switch (index - '0') { + case 0: + return SpecialSymbols::M0; + case 1: + return SpecialSymbols::M1; + case 2: + return SpecialSymbols::M2; + case 3: + return SpecialSymbols::M3; + case 4: + return SpecialSymbols::M4; + case 5: + return SpecialSymbols::M5; + case 6: + return SpecialSymbols::M6; + case 7: + return SpecialSymbols::M7; + case 8: + return SpecialSymbols::M8; + case 9: + return SpecialSymbols::M9; + default: + assert(false); + return SpecialSymbols::M0; + } +} + Symbol::Symbol(char name) : m_name(name) { @@ -64,6 +92,11 @@ ExpressionLayout * Symbol::privateCreateLayout(FloatDisplayMode floatDisplayMode if (m_name == SpecialSymbols::wn1) { return new BaselineRelativeLayout(new StringLayout("w", 1), new StringLayout("n+1",3, KDText::FontSize::Small), BaselineRelativeLayout::Type::Subscript); } + if (isMatrixSymbol()) { + char mi[3] = "M0"; + mi[1] = m_name-(char)SpecialSymbols::M0+'0'; + return new StringLayout(mi, 2); + } return new StringLayout(&m_name, 1); } @@ -76,4 +109,11 @@ bool Symbol::valueEquals(const Expression * e) const { return (m_name == ((Symbol *)e)->m_name); } +bool Symbol::isMatrixSymbol() const { + if (m_name >= (char)SpecialSymbols::M0 && m_name <= (char)SpecialSymbols::M9) { + return true; + } + return false; +} + }