mirror of
https://github.com/UpsilonNumworks/Upsilon.git
synced 2026-01-19 00:37:25 +01:00
GraphApp: Use a FunctionStore
Change-Id: Ib75947c40167489726fafc493ccb0ebf2862142b
This commit is contained in:
@@ -1,5 +1,7 @@
|
||||
app_objs += $(addprefix apps/graph/,\
|
||||
graph_app.o\
|
||||
function.o\
|
||||
function_store.o\
|
||||
graph/cursor_view.o\
|
||||
graph/graph_controller.o\
|
||||
graph/graph_view.o\
|
||||
|
||||
43
apps/graph/function.cpp
Normal file
43
apps/graph/function.cpp
Normal file
@@ -0,0 +1,43 @@
|
||||
#include "function.h"
|
||||
|
||||
Graph::Function::Function() :
|
||||
m_text(nullptr),
|
||||
m_expression(nullptr),
|
||||
m_layout(nullptr)
|
||||
{
|
||||
}
|
||||
|
||||
Graph::Function::Function(const char * text) :
|
||||
m_text(text), // FIXME: Copy !!
|
||||
m_expression(nullptr),
|
||||
m_layout(nullptr)
|
||||
{
|
||||
}
|
||||
|
||||
Graph::Function::~Function() {
|
||||
//FIXME: Free m_text!
|
||||
if (m_layout != nullptr) {
|
||||
delete m_layout;
|
||||
}
|
||||
if (m_expression != nullptr) {
|
||||
delete m_expression;
|
||||
}
|
||||
}
|
||||
|
||||
const char * Graph::Function::text() {
|
||||
return m_text;
|
||||
}
|
||||
|
||||
Expression * Graph::Function::expression() {
|
||||
if (m_expression == nullptr) {
|
||||
m_expression = Expression::parse(m_text);
|
||||
}
|
||||
return m_expression;
|
||||
}
|
||||
|
||||
ExpressionLayout * Graph::Function::layout() {
|
||||
if (m_layout == nullptr) {
|
||||
m_layout = expression()->createLayout();
|
||||
}
|
||||
return m_layout;
|
||||
}
|
||||
24
apps/graph/function.h
Normal file
24
apps/graph/function.h
Normal file
@@ -0,0 +1,24 @@
|
||||
#ifndef GRAPH_FUNCTION_H
|
||||
#define GRAPH_FUNCTION_H
|
||||
|
||||
#include <poincare.h>
|
||||
|
||||
namespace Graph {
|
||||
|
||||
class Function {
|
||||
public:
|
||||
Function();
|
||||
Function(const char * text);
|
||||
~Function(); // Delete expression and layout, if needed
|
||||
const char * text();
|
||||
Expression * expression();
|
||||
ExpressionLayout * layout();
|
||||
private:
|
||||
const char * m_text;
|
||||
Expression * m_expression;
|
||||
ExpressionLayout * m_layout;
|
||||
};
|
||||
|
||||
}
|
||||
|
||||
#endif
|
||||
23
apps/graph/function_store.cpp
Normal file
23
apps/graph/function_store.cpp
Normal file
@@ -0,0 +1,23 @@
|
||||
#include "function_store.h"
|
||||
extern "C" {
|
||||
#include <assert.h>
|
||||
}
|
||||
|
||||
Graph::FunctionStore::FunctionStore() :
|
||||
m_numberOfFunctions(0)
|
||||
{
|
||||
}
|
||||
|
||||
Graph::Function * Graph::FunctionStore::functionAtIndex(int i) {
|
||||
assert(i>=0 && i<m_numberOfFunctions);
|
||||
return &m_functions[i];
|
||||
}
|
||||
|
||||
void Graph::FunctionStore::pushFunction(const char * functionText) {
|
||||
assert(m_numberOfFunctions < k_maxNumberOfFunctions);
|
||||
m_functions[m_numberOfFunctions++] = Function(functionText);
|
||||
}
|
||||
|
||||
int Graph::FunctionStore::numberOfFunctions() {
|
||||
return m_numberOfFunctions;
|
||||
}
|
||||
22
apps/graph/function_store.h
Normal file
22
apps/graph/function_store.h
Normal file
@@ -0,0 +1,22 @@
|
||||
#ifndef GRAPH_FUNCTION_STORE_H
|
||||
#define GRAPH_FUNCTION_STORE_H
|
||||
|
||||
#include "function.h"
|
||||
|
||||
namespace Graph {
|
||||
|
||||
class FunctionStore {
|
||||
public:
|
||||
FunctionStore();
|
||||
Function * functionAtIndex(int i);
|
||||
void pushFunction(const char * functionText);
|
||||
int numberOfFunctions();
|
||||
private:
|
||||
int m_numberOfFunctions;
|
||||
static constexpr int k_maxNumberOfFunctions = 8;
|
||||
Function m_functions[k_maxNumberOfFunctions];
|
||||
};
|
||||
|
||||
}
|
||||
|
||||
#endif
|
||||
@@ -1,8 +1,8 @@
|
||||
#include "graph_controller.h"
|
||||
|
||||
GraphController::GraphController(Responder * parentResponder) :
|
||||
GraphController::GraphController(Responder * parentResponder, Graph::FunctionStore * functionStore) :
|
||||
ViewController(parentResponder),
|
||||
m_view(GraphView())
|
||||
m_view(GraphView(functionStore))
|
||||
{
|
||||
}
|
||||
|
||||
|
||||
@@ -3,10 +3,11 @@
|
||||
|
||||
#include <escher.h>
|
||||
#include "graph_view.h"
|
||||
#include "../function_store.h"
|
||||
|
||||
class GraphController : public ViewController {
|
||||
public:
|
||||
GraphController(Responder * parentResponder);
|
||||
GraphController(Responder * parentResponder, Graph::FunctionStore * functionStore);
|
||||
View * view() override;
|
||||
const char * title() const override;
|
||||
void setFocused(bool focused) override;
|
||||
|
||||
@@ -7,7 +7,7 @@ constexpr KDColor kSecondaryGridColor = KDColor(0xEEEEEE);
|
||||
constexpr int kNumberOfMainGridLines = 5;
|
||||
constexpr int kNumberOfSecondaryGridLines = 4;
|
||||
|
||||
GraphView::GraphView() :
|
||||
GraphView::GraphView(Graph::FunctionStore * functionStore) :
|
||||
#if GRAPH_VIEW_IS_TILED
|
||||
TiledView(),
|
||||
#else
|
||||
@@ -18,7 +18,8 @@ GraphView::GraphView() :
|
||||
m_xMin(-2.0f),
|
||||
m_xMax(2.0f),
|
||||
m_yMin(-2.0f),
|
||||
m_yMax(2.0f)
|
||||
m_yMax(2.0f),
|
||||
m_functionStore(functionStore)
|
||||
{
|
||||
}
|
||||
|
||||
@@ -157,14 +158,18 @@ void GraphView::drawFunction(KDContext * ctx, KDRect rect) const {
|
||||
|
||||
KDColor workingBuffer[stampSize*stampSize];
|
||||
|
||||
Context plotContext;
|
||||
for (KDCoordinate px = rect.x()-stampSize; px<rect.right(); px++) {
|
||||
float x = pixelToFloat(Axis::Horizontal, px);
|
||||
float y = (x-1)*(x+1)*x;
|
||||
KDCoordinate py = floatToPixel(Axis::Vertical, y);
|
||||
KDRect stampRect(px, py, stampSize, stampSize);
|
||||
//KDColor red = KDColorRed;
|
||||
ctx->fillRectWithMask(stampRect, KDColorRed, mask, workingBuffer);
|
||||
//KDBlitRect(stampRect, &red, {1,1}, mask, {stampSize,stampSize});
|
||||
for (int i=0; i<m_functionStore->numberOfFunctions(); i++) {
|
||||
Float xExp = Float(x);
|
||||
plotContext.setExpressionForSymbolName(&xExp, "x");
|
||||
Graph::Function * f = m_functionStore->functionAtIndex(i);
|
||||
float y = f->expression()->approximate(plotContext);
|
||||
KDCoordinate py = floatToPixel(Axis::Vertical, y);
|
||||
KDRect stampRect(px, py, stampSize, stampSize);
|
||||
ctx->fillRectWithMask(stampRect, KDColorRed, mask, workingBuffer);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
@@ -3,6 +3,7 @@
|
||||
|
||||
#include <escher.h>
|
||||
#include "cursor_view.h"
|
||||
#include "../function_store.h"
|
||||
|
||||
#define GRAPH_VIEW_IS_TILED 1
|
||||
|
||||
@@ -14,7 +15,7 @@ class GraphView : public
|
||||
#endif
|
||||
{
|
||||
public:
|
||||
GraphView();
|
||||
GraphView(Graph::FunctionStore * functionStore);
|
||||
|
||||
#if GRAPH_VIEW_IS_TILED
|
||||
KDColor * tile() const override;
|
||||
@@ -64,6 +65,8 @@ private:
|
||||
float m_xMax;
|
||||
float m_yMin;
|
||||
float m_yMax;
|
||||
|
||||
Graph::FunctionStore * m_functionStore;
|
||||
};
|
||||
|
||||
#endif
|
||||
|
||||
@@ -2,10 +2,13 @@
|
||||
|
||||
GraphApp::GraphApp() :
|
||||
App(),
|
||||
m_listController(ListController(nullptr)),
|
||||
m_graphController(GraphController(nullptr)),
|
||||
m_functionStore(Graph::FunctionStore()),
|
||||
m_listController(ListController(nullptr, &m_functionStore)),
|
||||
m_graphController(GraphController(nullptr, &m_functionStore)),
|
||||
m_tabViewController(this, &m_listController, &m_graphController)
|
||||
{
|
||||
m_functionStore.pushFunction("(x-1)*(x+1)*x");
|
||||
m_functionStore.pushFunction("x*x");
|
||||
}
|
||||
|
||||
ViewController * GraphApp::rootViewController() {
|
||||
|
||||
@@ -2,15 +2,17 @@
|
||||
#define GRAPH_GRAPH_APP_H
|
||||
|
||||
#include <escher.h>
|
||||
#include "function_store.h"
|
||||
#include "graph/graph_controller.h"
|
||||
#include "list/list_controller.h"
|
||||
|
||||
class GraphApp : public App {
|
||||
class GraphApp : public ::App {
|
||||
public:
|
||||
GraphApp();
|
||||
protected:
|
||||
ViewController * rootViewController() override;
|
||||
private:
|
||||
Graph::FunctionStore m_functionStore;
|
||||
ListController m_listController;
|
||||
GraphController m_graphController;
|
||||
TabViewController m_tabViewController;
|
||||
|
||||
@@ -1,22 +1,29 @@
|
||||
#include "function_cell.h"
|
||||
#include <poincare.h>
|
||||
|
||||
FunctionCell::FunctionCell() :
|
||||
ChildlessView(),
|
||||
Responder(nullptr),
|
||||
m_function(nullptr),
|
||||
m_focused(false),
|
||||
m_even(false)
|
||||
{
|
||||
m_message = "NULL";
|
||||
}
|
||||
|
||||
void FunctionCell::drawRect(KDContext * ctx, KDRect rect) const {
|
||||
KDColor background = m_even ? KDColor(0xEEEEEE) : KDColor(0x777777);
|
||||
ctx->fillRect(rect, background);
|
||||
ctx->drawString(m_message, KDPointZero, m_focused);
|
||||
ctx->drawString(m_function->text(), KDPointZero, m_focused);
|
||||
m_function->layout()->draw(ctx, KDPointZero);
|
||||
//Expression * foo = Expression::parse("1+2/3");
|
||||
//ExpressionLayout * fooLayout = foo->createLayout();
|
||||
//fooLayout->draw(ctx, KDPointZero);
|
||||
//delete fooLayout;
|
||||
//delete foo;
|
||||
}
|
||||
|
||||
void FunctionCell::setMessage(const char * message) {
|
||||
m_message = message;
|
||||
void FunctionCell::setFunction(Graph::Function * f) {
|
||||
m_function = f;
|
||||
}
|
||||
|
||||
void FunctionCell::setFocused(bool focused) {
|
||||
|
||||
@@ -2,17 +2,18 @@
|
||||
#define GRAPH_FUNCTION_CELL_H
|
||||
|
||||
#include <escher.h>
|
||||
#include "../function.h"
|
||||
|
||||
class FunctionCell : public ChildlessView, public Responder {
|
||||
public:
|
||||
FunctionCell();
|
||||
void setMessage(const char * message);
|
||||
void setFunction(Graph::Function * f);
|
||||
void setEven(bool even);
|
||||
|
||||
void drawRect(KDContext * ctx, KDRect rect) const override;
|
||||
void setFocused(bool focused) override;
|
||||
private:
|
||||
const char * m_message;
|
||||
Graph::Function * m_function;
|
||||
bool m_focused;
|
||||
bool m_even;
|
||||
};
|
||||
|
||||
@@ -1,20 +1,13 @@
|
||||
#include "list_controller.h"
|
||||
#include <assert.h>
|
||||
|
||||
static const char * sMessages[] = {
|
||||
"AAA 0", "BBB 1", "CCC 2", "DDD 3", "EEE 4",
|
||||
"FFF 5", "GGG 6", "HHH 7", "III 8", "JJJ 9",
|
||||
"KKK10", "LLL11", "MMM12", "NNN13", "OOO14",
|
||||
"PPP15", "QQQ16", "RRR17", "SSS18", "TTT19"
|
||||
};
|
||||
|
||||
ListController::ListController(Responder * parentResponder) :
|
||||
ListController::ListController(Responder * parentResponder, Graph::FunctionStore * functionStore) :
|
||||
ViewController(parentResponder),
|
||||
m_tableView(TableView(this)),
|
||||
m_activeCell(0),
|
||||
m_manualScrolling(0)
|
||||
m_manualScrolling(0),
|
||||
m_functionStore(functionStore)
|
||||
{
|
||||
m_messages = sMessages;
|
||||
}
|
||||
|
||||
View * ListController::view() {
|
||||
@@ -26,7 +19,7 @@ const char * ListController::title() const {
|
||||
}
|
||||
|
||||
void ListController::setActiveCell(int index) {
|
||||
if (index < 0 || index >= k_totalNumberOfModels) {
|
||||
if (index < 0 || index >= m_functionStore->numberOfFunctions()) {
|
||||
return;
|
||||
}
|
||||
|
||||
@@ -55,7 +48,7 @@ bool ListController::handleEvent(ion_event_t event) {
|
||||
}
|
||||
|
||||
int ListController::numberOfCells() {
|
||||
return k_totalNumberOfModels;
|
||||
return m_functionStore->numberOfFunctions();
|
||||
};
|
||||
|
||||
View * ListController::reusableCell(int index) {
|
||||
@@ -70,7 +63,7 @@ int ListController::reusableCellCount() {
|
||||
|
||||
void ListController::willDisplayCellForIndex(View * cell, int index) {
|
||||
FunctionCell * myCell = (FunctionCell *)cell;
|
||||
myCell->setMessage(m_messages[index]);
|
||||
myCell->setFunction(m_functionStore->functionAtIndex(index));
|
||||
myCell->setEven(index%2 == 0);
|
||||
}
|
||||
|
||||
|
||||
@@ -2,11 +2,12 @@
|
||||
#define GRAPH_LIST_CONTROLLER_H
|
||||
|
||||
#include <escher.h>
|
||||
#include "../function_store.h"
|
||||
#include "function_cell.h"
|
||||
|
||||
class ListController : public ViewController, public TableViewDataSource {
|
||||
public:
|
||||
ListController(Responder * parentResponder);
|
||||
ListController(Responder * parentResponder, Graph::FunctionStore * functionStore);
|
||||
|
||||
void setActiveCell(int index);
|
||||
|
||||
@@ -26,9 +27,9 @@ private:
|
||||
// The cells should be initialized *before* the tableview!
|
||||
FunctionCell m_cells[k_maxNumberOfCells];
|
||||
TableView m_tableView;
|
||||
const char ** m_messages;
|
||||
int m_activeCell;
|
||||
KDCoordinate m_manualScrolling;
|
||||
Graph::FunctionStore * m_functionStore;
|
||||
};
|
||||
|
||||
#endif
|
||||
|
||||
Reference in New Issue
Block a user