NumeRe v1.1.4
NumeRe: Framework für Numerische Rechnungen
history.cpp
Go to the documentation of this file.
1/*****************************************************************************
2 NumeRe: Framework fuer Numerische Rechnungen
3 Copyright (C) 2017 Erik Haenel et al.
4
5 This program is free software: you can redistribute it and/or modify
6 it under the terms of the GNU General Public License as published by
7 the Free Software Foundation, either version 3 of the License, or
8 (at your option) any later version.
9
10 This program is distributed in the hope that it will be useful,
11 but WITHOUT ANY WARRANTY; without even the implied warranty of
12 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
13 GNU General Public License for more details.
14
15 You should have received a copy of the GNU General Public License
16 along with this program. If not, see <http://www.gnu.org/licenses/>.
17******************************************************************************/
18
19
20
21#include "../../common/CommonHeaders.h"
22#include "../../kernel/core/ui/language.hpp"
23#include "../../kernel/core/utils/tools.hpp"
24
25#include <wx/datetime.h>
26#include <wx/stdpaths.h>
27#include <vector>
28#include <string>
29
30#include "history.hpp"
31#define HISTORYHEADERSTART "## --- "
32
33#define MARGIN_FOLD 3
34
35BEGIN_EVENT_TABLE(NumeReHistory, wxStyledTextCtrl)
36 EVT_LEFT_DOWN (NumeReHistory::OnMouseDn)
37 EVT_RIGHT_DOWN (NumeReHistory::OnRightClick)
38 EVT_LEFT_DCLICK (NumeReHistory::OnMouseDblClk)
39 EVT_MOUSE_CAPTURE_LOST(NumeReHistory::OnMouseCaptureLost)
40 EVT_STC_MARGINCLICK (-1, NumeReHistory::OnMarginClick)
44
45
46extern Language _guilang;
47using namespace std;
48
64NumeReHistory::NumeReHistory(NumeReWindow* mframe, Options* options, wxWindow* parent, wxWindowID id, NumeReSyntax* __syntax,
65 NumeReTerminal* __terminal, const wxPoint& pos, const wxSize& size, long style, const wxString& name) :
66 NumeReEditor(mframe, options, parent, id, __syntax, __terminal, pos, size, style, name)
67{
68 _syntax = __syntax;
69 m_mainframe = mframe;
70 m_terminal = __terminal;
71 m_clickedLine = 0;
72
73 this->SetTabWidth(4);
74 this->SetIndent(4);
75 this->SetUseTabs(true);
76 this->SetReadOnly(true);
77
78 //this->SetMarginWidth(0, 22);
79 this->SetMarginWidth(0, 0);
80 this->SetMarginType(0, wxSTC_MARGIN_NUMBER);
81 this->SetMarginWidth(1,0);
82
83 wxFont font = options->toFont(options->getSetting(SETTING_S_HISTORYFONT).stringval());
84 this->StyleSetFont(wxSTC_STYLE_DEFAULT, font);
85
86 this->StyleClearAll();
87
88 this->SetMouseDwellTime(250);
89
90 UpdateSyntaxHighlighting();
91 loadHistory();
92
93 SetEdgeMode(wxSTC_EDGE_NONE);
94 this->SetCaretLineVisible(false);
95
96 this->SetWrapMode(wxSTC_WRAP_WORD);
97 this->SetWrapIndentMode(wxSTC_WRAPINDENT_INDENT);
98 this->SetWrapStartIndent(1);
99 this->SetWrapVisualFlags(wxSTC_WRAPVISUALFLAG_END);
100 this->SetWrapVisualFlagsLocation(wxSTC_WRAPVISUALFLAGLOC_END_BY_TEXT);
101
102 this->GotoPos(this->GetLastPosition());
103}
104
105
110{
111}
112
113
123{
125 this->StyleSetFont(wxSTC_STYLE_DEFAULT, font);
126 this->StyleClearAll();
127
128 this->StyleSetBackground(wxSTC_STYLE_DEFAULT, m_options->GetSyntaxStyle(Options::STANDARD).background);
129
130 this->SetLexer(wxSTC_LEX_NSCR);
131
132 this->SetProperty("fold", "0");
133 this->SetFoldFlags(wxSTC_FOLDFLAG_LINEAFTER_CONTRACTED | wxSTC_FOLDFLAG_LINEAFTER_EXPANDED);
134
135 this->SetMarginType(MARGIN_FOLD, wxSTC_MARGIN_SYMBOL);
136 this->SetMarginWidth(MARGIN_FOLD, 10);
137 this->SetMarginMask(MARGIN_FOLD, wxSTC_MASK_FOLDERS);
138 this->SetMarginSensitive(MARGIN_FOLD, true);
139 this->StyleSetBackground(MARGIN_FOLD, wxColor(200, 200, 200) );
140 this->SetMarginSensitive(MARGIN_FOLD, true);
141
142 wxColor grey( 100, 100, 100 );
143 this->MarkerDefine (wxSTC_MARKNUM_FOLDER, wxSTC_MARK_BOXPLUS);
144 this->MarkerSetForeground (wxSTC_MARKNUM_FOLDER, "WHITE");
145 this->MarkerSetBackground (wxSTC_MARKNUM_FOLDER, grey);
146
147 this->MarkerDefine (wxSTC_MARKNUM_FOLDEROPEN, wxSTC_MARK_BOXMINUS);
148 this->MarkerSetForeground (wxSTC_MARKNUM_FOLDEROPEN, "WHITE");
149 this->MarkerSetBackground (wxSTC_MARKNUM_FOLDEROPEN, grey);
150
151 this->MarkerDefine (wxSTC_MARKNUM_FOLDERSUB, wxSTC_MARK_VLINE);
152 this->MarkerSetForeground (wxSTC_MARKNUM_FOLDERSUB, grey);
153 this->MarkerSetBackground (wxSTC_MARKNUM_FOLDERSUB, grey);
154
155 this->MarkerDefine (wxSTC_MARKNUM_FOLDEREND, wxSTC_MARK_BOXPLUSCONNECTED);
156 this->MarkerSetForeground (wxSTC_MARKNUM_FOLDEREND, "WHITE");
157 this->MarkerSetBackground (wxSTC_MARKNUM_FOLDEREND, grey);
158
159 this->MarkerDefine (wxSTC_MARKNUM_FOLDEROPENMID, wxSTC_MARK_BOXMINUSCONNECTED);
160 this->MarkerSetForeground (wxSTC_MARKNUM_FOLDEROPENMID, "WHITE");
161 this->MarkerSetBackground (wxSTC_MARKNUM_FOLDEROPENMID, grey);
162
163 this->MarkerDefine (wxSTC_MARKNUM_FOLDERMIDTAIL, wxSTC_MARK_TCORNER);
164 this->MarkerSetForeground (wxSTC_MARKNUM_FOLDERMIDTAIL, grey);
165 this->MarkerSetBackground (wxSTC_MARKNUM_FOLDERMIDTAIL, grey);
166
167 this->MarkerDefine (wxSTC_MARKNUM_FOLDERTAIL, wxSTC_MARK_LCORNER);
168 this->MarkerSetForeground (wxSTC_MARKNUM_FOLDERTAIL, grey);
169 this->MarkerSetBackground (wxSTC_MARKNUM_FOLDERTAIL, grey);
170
171 if (_syntax)
172 {
173 this->SetKeyWords(0, _syntax->getCommands());
174 this->SetKeyWords(1, _syntax->getOptions());
175 this->SetKeyWords(2, _syntax->getFunctions());
176 this->SetKeyWords(3, _syntax->getMethods());
177 this->SetKeyWords(4, "x y z t");
178 this->SetKeyWords(5, _syntax->getConstants());
179 this->SetKeyWords(6, _syntax->getSpecial());
180 this->SetKeyWords(7, _syntax->getOperators());
181 this->SetKeyWords(8, _syntax->getNPRCCommands());
182 }
183
184 for (int i = 0; i <= wxSTC_NSCR_PROCEDURE_COMMANDS; i++)
185 {
186 SyntaxStyles _style;
187 switch (i)
188 {
189 case wxSTC_NSCR_DEFAULT:
190 case wxSTC_NSCR_IDENTIFIER:
192 break;
193 case wxSTC_NSCR_NUMBERS:
195 break;
196 case wxSTC_NSCR_COMMENT_BLOCK:
197 case wxSTC_NSCR_COMMENT_LINE:
199 break;
200 case wxSTC_NSCR_COMMAND:
202 break;
203 case wxSTC_NSCR_OPTION:
205 break;
206 case wxSTC_NSCR_CONSTANTS:
208 break;
209 case wxSTC_NSCR_FUNCTION:
211 break;
212 case wxSTC_NSCR_METHOD:
214 break;
215 case wxSTC_NSCR_PREDEFS:
217 break;
218 case wxSTC_NSCR_STRING:
220 break;
221 case wxSTC_NSCR_STRING_PARSER:
223 break;
224 case wxSTC_NSCR_INCLUDES:
226 break;
227 case wxSTC_NSCR_PROCEDURES:
229 break;
230 case wxSTC_NSCR_PROCEDURE_COMMANDS:
232 break;
233 case wxSTC_NSCR_INSTALL:
235 break;
236 case wxSTC_NSCR_DEFAULT_VARS:
238 break;
239 case wxSTC_NSCR_CUSTOM_FUNCTION:
241 break;
242 case wxSTC_NSCR_CLUSTER:
244 break;
245 case wxSTC_NSCR_OPERATORS:
246 case wxSTC_NSCR_OPERATOR_KEYWORDS:
248 break;
249 }
250
251 this->StyleSetForeground(i, _style.foreground);
252 if (!_style.defaultbackground)
253 this->StyleSetBackground(i, _style.background);
254 else
255 this->StyleSetBackground(i, this->StyleGetBackground(wxSTC_STYLE_DEFAULT));
256 this->StyleSetBold(i, _style.bold);
257 this->StyleSetItalic(i, _style.italics);
258 this->StyleSetUnderline(i, _style.underline);
259 }
260 //updateDefaultHighlightSettings();
261 this->Colourise(0,-1);
262}
263
264
272void NumeReHistory::OnMenuEvent(wxCommandEvent& event)
273{
274 switch (event.GetId())
275 {
277 deleteLine();
278 break;
280 copyLine();
281 break;
282 }
283}
284
285
294void NumeReHistory::OnMouseCaptureLost(wxMouseCaptureLostEvent& event)
295{
296 if (GetCapture() == this)
297 {
298 ReleaseMouse();
299 Refresh();
300 }
301}
302
303
311{
312 this->SetReadOnly(false);
313 this->GotoLine(m_clickedLine);
314 this->LineDelete();
316 this->SetReadOnly(true);
317}
318
319
328{
329 this->SetReadOnly(false);
330 this->SetSelection(PositionFromLine(m_clickedLine), GetLineEndPosition(m_clickedLine));
331 this->Copy();
332 this->GotoPos(PositionFromLine(m_clickedLine));
333 this->SetReadOnly(true);
334}
335
336
345{
346 wxString sFileName = m_mainframe->getProgramFolder() + "\\numere.history";
347
348 SetReadOnly(false);
349
350 if (fileExists(sFileName.ToStdString()))
351 {
352 LoadFile(sFileName);
353 Colourise(0, -1);
354
355 // Clean history by deleting repeated history header lines
356 for (int i = 1; i < GetLineCount(); i++)
357 {
358 while (GetLine(i-1).substr(0, 7) == HISTORYHEADERSTART && GetLine(i).substr(0, 7) == HISTORYHEADERSTART)
359 {
360 DeleteRange(PositionFromLine(i-1), PositionFromLine(i)-PositionFromLine(i-1));
361 }
362
363 // Resolve missing quotation marks
364 if (GetStyleAt(GetLineEndPosition(i)) == wxSTC_NSCR_STRING)
365 {
366 InsertText(GetLineEndPosition(i), "\"");
367 Colourise(PositionFromLine(i), -1);
368 }
369 }
370
371 if (GetLineCount() > 10000)
372 DeleteRange(0, PositionFromLine(GetLineCount()-99999));
373
374 GotoPos(GetLastPosition());
375 }
376
377 addHeader();
379 SetReadOnly(true);
380}
381
382
391{
392 wxString sFileName = m_mainframe->getProgramFolder() + "\\numere.history";
393
394 // only save the history, if it is necessary
395 if (getLastLine().substr(0, 7) == HISTORYHEADERSTART)
396 return;
397
398 this->SaveFile(sFileName);
399}
400
401
410{
411 this->AddText(HISTORYHEADERSTART + getTimeStamp(false) + " ---\n");
412}
413
414
423{
424 int zerolevel = wxSTC_FOLDLEVELBASE;
425 for (int i = 0; i < this->GetLineCount(); i++)
426 {
427 if (this->GetLine(i).substr(0, 7) == HISTORYHEADERSTART)
428 {
429 if (!i)
430 {
431 this->SetFoldLevel(i, zerolevel | wxSTC_FOLDLEVELHEADERFLAG);
432 }
433 else
434 {
435 //this->SetFoldLevel(i-1, zerolevel | wxSTC_FOLDLEVELWHITEFLAG);
436 this->SetFoldLevel(i, zerolevel | wxSTC_FOLDLEVELHEADERFLAG);
437 }
438 }
439 else
440 this->SetFoldLevel(i, zerolevel+1);
441 }
442}
443
444
453void NumeReHistory::AddToHistory(const wxString& commandstring)
454{
455 if (!commandstring.length())
456 return;
457
458 this->SetReadOnly(false);
459 this->GotoPos(this->GetLastPosition());
460
461 wxString cleaned = commandstring.substr(0, commandstring.find_last_not_of(' ')+1);
462
463 // Get last line
464 wxString lastline = getLastLine();
465
466 // return, if last line is equal to the current one
467 if (lastline == cleaned)
468 {
469 this->SetReadOnly(true);
470 return;
471 }
472
473 // add the new line to the history
474 this->AddText(cleaned);
475
476 if (commandstring[commandstring.find_last_not_of(' ')] != '\n')
477 this->AddText("\n");
478
479 Colourise(PositionFromLine(GetCurrentLine()-2), -1);
480
481 if (GetStyleAt(GetLastPosition()-1) == wxSTC_NSCR_STRING)
482 this->InsertText(GetLastPosition()-1, "\"");
483
485 this->SetReadOnly(true);
486}
487
488
497{
498 wxString lastline = GetLine(LineFromPosition(GetLastPosition()-1));
499 lastline.erase(lastline.find_first_of("\n\r"));
500
501 return lastline;
502}
503
504
512void NumeReHistory::OnMarginClick( wxStyledTextEvent &event )
513{
514 int position = event.GetPosition();
515
516 int linenum = this->LineFromPosition(position);
517
518 if (event.GetMargin() == MARGIN_FOLD)
519 {
520 int levelClick = this->GetFoldLevel(linenum);
521 if ((levelClick & wxSTC_FOLDLEVELHEADERFLAG) > 0)
522 this->ToggleFold(linenum);
523 }
524}
525
526
536void NumeReHistory::OnMouseDblClk(wxMouseEvent& event)
537{
538 int clickedLine = LineFromPosition(PositionFromPoint(event.GetPosition()));
539 wxString line = this->GetLine(clickedLine);
540 if (line.substr(0,6) == "## ---")
541 {
542 int levelClick = this->GetFoldLevel(clickedLine);
543 if ((levelClick & wxSTC_FOLDLEVELHEADERFLAG) > 0)
544 this->ToggleFold(clickedLine);
545 return;
546 }
547 while (line[line.length()-1] == '\r' || line[line.length()-1] == '\n')
548 line.erase(line.length()-1);
549 if (line.length())
550 m_terminal->pass_command(line.ToStdString(), false);
551}
552
553
562void NumeReHistory::OnMouseDn(wxMouseEvent& event)
563{
564 int clickedLine = LineFromPosition(PositionFromPoint(event.GetPosition()));
565 if (this->GetLine(clickedLine).substr(0,6) == "## ---")
566 return;
567 this->SetSelection(PositionFromLine(clickedLine), GetLineEndPosition(clickedLine));
568 event.Skip();
569}
570
571
580void NumeReHistory::OnRightClick(wxMouseEvent& event)
581{
582 int clickedLine = LineFromPosition(PositionFromPoint(event.GetPosition()));
583 if (this->GetLine(clickedLine).substr(0,6) == "## ---")
584 return;
585 m_clickedLine = clickedLine;
586 wxMenu popupMenu;
587 popupMenu.Append(ID_COPY_FROM_HISTORY, _guilang.get("GUI_HISTORY_COPYLINE"));
588 popupMenu.Append(ID_DELETE_FROM_HISTORY, _guilang.get("GUI_HISTORY_DELETELINE"));
589 wxPoint p = event.GetPosition();
590 this->PopupMenu(&popupMenu, p);
591}
592
593
This class handles the internal language system and returns the language strings of the selected lang...
Definition: language.hpp:38
std::string get(const std::string &sMessage, const std::vector< std::string > &vTokens) const
This member function returns the language string for the passed language identifier and replaces all ...
Definition: language.cpp:292
The class of the editor window.
Definition: editor.h:53
bool SaveFile(const wxString &filename)
Definition: editor.cpp:396
Options * m_options
Definition: editor.h:313
NumeReTerminal * m_terminal
Definition: history.hpp:64
NumeReWindow * m_mainframe
Definition: history.hpp:65
NumeReSyntax * _syntax
Definition: history.hpp:63
void OnMenuEvent(wxCommandEvent &event)
Event handler for the context menu.
Definition: history.cpp:272
void OnMouseDblClk(wxMouseEvent &event)
Double clicking event handler. Will re-execute the selected line or fold the session,...
Definition: history.cpp:536
wxString getLastLine()
Return the last line of the input history.
Definition: history.cpp:496
void applyFoldPoints()
Add fold points to hide previous sessions.
Definition: history.cpp:422
~NumeReHistory()
Empty destructor.
Definition: history.cpp:109
void UpdateSyntaxHighlighting(bool forceUpdate=false)
Update the syntax highlighting to represent the selected syntax colors.
Definition: history.cpp:122
void OnMouseDn(wxMouseEvent &event)
Select the whole line, if the user clicks on a line.
Definition: history.cpp:562
void AddToHistory(const wxString &commandstring)
Add the passed string at the end of the input history.
Definition: history.cpp:453
void saveHistory()
Save the history to the corresponding file.
Definition: history.cpp:390
void addHeader()
Add the history header presenting the current date and time.
Definition: history.cpp:409
void OnMarginClick(wxStyledTextEvent &event)
Event handler for folding.
Definition: history.cpp:512
void copyLine()
Copy the selected line to the clipboard.
Definition: history.cpp:327
void OnRightClick(wxMouseEvent &event)
Event handler to display the context menu, if the user clicks right on a line.
Definition: history.cpp:580
void loadHistory()
Load the history from the corresponding file.
Definition: history.cpp:344
void OnMouseCaptureLost(wxMouseCaptureLostEvent &event)
Ensure that the drag'n drop is handled consistently.
Definition: history.cpp:294
void deleteLine()
Delete the previously selected line.
Definition: history.cpp:310
int m_clickedLine
Definition: history.hpp:66
This class contains all needed keywords to highlight their occurences correspondingly....
Definition: syntax.hpp:55
std::string getNPRCCommands() const
Definition: syntax.hpp:117
std::string getConstants() const
Definition: syntax.hpp:125
std::string getOperators() const
Definition: syntax.hpp:129
std::string getMethods() const
Definition: syntax.hpp:123
std::string getCommands() const
Definition: syntax.hpp:115
std::string getSpecial() const
Definition: syntax.hpp:127
std::string getFunctions() const
Definition: syntax.hpp:121
std::string getOptions() const
Definition: syntax.hpp:119
The terminal class for the GUI. It's a specialisation of the GenericTerminal.
Definition: terminal.hpp:46
void pass_command(const std::string &command, bool isEvent)
Pass the external command to the kernel without printing it to the console.
Definition: terminal.cpp:925
This class is the actual NumeRe main frame. The application's logic is implemented here.
Definition: NumeReWindow.h:177
wxString getProgramFolder()
This member function returns the application's root path.
This class implements an interface of the internal Settings object adapted to be usable from the GUI.
Definition: Options.h:178
static wxFont toFont(const std::string &sFontDescr)
Definition: Options.h:348
@ INCLUDES
Definition: Options.h:292
@ FUNCTION
Definition: Options.h:285
@ OPERATOR
Definition: Options.h:293
@ STRING
Definition: Options.h:290
@ COMMAND
Definition: Options.h:280
@ SPECIALVAL
Definition: Options.h:289
@ CLUSTER
Definition: Options.h:287
@ NUMBER
Definition: Options.h:295
@ INSTALL
Definition: Options.h:298
@ DEFAULT_VARS
Definition: Options.h:299
@ COMMENT
Definition: Options.h:281
@ STANDARD
Definition: Options.h:278
@ PROCEDURE
Definition: Options.h:294
@ STRINGPARSER
Definition: Options.h:291
@ OPTION
Definition: Options.h:284
@ CUSTOM_FUNCTION
Definition: Options.h:286
@ CONSTANT
Definition: Options.h:288
@ PROCEDURE_COMMAND
Definition: Options.h:296
@ METHODS
Definition: Options.h:297
SyntaxStyles GetSyntaxStyle(size_t i) const
Return the selected syntax style by constructing it from the style string.
Definition: options.cpp:112
SettingsValue & getSetting(const std::string &value)
Returns a reference to the setting value, which corresponds to the passed string. Throws an exception...
Definition: settings.hpp:711
std::string & stringval()
Returns a reference to a std::string value type setting.
Definition: settings.hpp:590
@ ID_DELETE_FROM_HISTORY
@ ID_COPY_FROM_HISTORY
Language _guilang
#define MARGIN_FOLD
Definition: history.cpp:33
#define HISTORYHEADERSTART
Definition: history.cpp:31
bool fileExists(const string &)
This function checks, whether the file with the passed file name exists.
Definition: tools.cpp:2500
char name[32]
Definition: resampler.cpp:371
#define SETTING_S_HISTORYFONT
Definition: settings.hpp:56
std::string getTimeStamp(bool bGetStamp)
This function simple returns the current time as a default timestamp.
This structure contains the necessary data to completely define a style for a distinctive syntax elem...
Definition: Options.h:27
bool bold
Definition: Options.h:30
wxColour background
Definition: Options.h:29
bool italics
Definition: Options.h:31
bool defaultbackground
Definition: Options.h:33
wxColour foreground
Definition: Options.h:28
bool underline
Definition: Options.h:32
END_EVENT_TABLE()