4 * Purpose: Math editor definitions
5 * Author: Alejandro Aguilar Sierra <asierra@servidor.unam.mx>
6 * Created: January 1996
7 * Description: Math paragraph and objects for a WYSIWYG math editor.
11 * Copyright: (c) 1996, 1997 Alejandro Aguilar Sierra
13 * Version: 0.8beta, Mathed & Lyx project.
15 * You are free to use and modify this code under the terms of
16 * the GNU General Public Licence version 2 or later.
34 #define MATH_ALIGN_LEFT 1
36 #define MATH_ALIGN_RIGHT 2
38 #define MATH_ALIGN_BOTTOM 4
40 #define MATH_ALIGN_TOP 8
47 /// Standard Math Sizes (Math mode styles)
60 /// Standard LaTeX Math Environments
61 enum MathedEnvironment {
77 /** The restrictions of a standard LaTeX math paragraph
78 allows to get a small number of text codes (<30) */
79 enum MathedTextCodes {
82 /// Open and Close group
92 /// Super and sub scripts
96 /// Editable Math Inset
98 /// Editable Text Inset
102 /// Internal code for constants
104 /// Internal code for variables
120 /// Math mode TeX characters ",;:{}"
122 /// Special characters "{}&#_%"
124 /// Internal code for operators
126 /// Internal code for symbols
135 /// This must be < 32
139 ostream & operator<<(ostream &, MathedTextCodes mtc);
142 #define LM_TC_NORMAL LM_TC_VAR
145 /// Types of lyx-math insets
146 enum MathedInsetTypes {
149 /// A simple paragraph
151 /// A simple numbered paragraph
153 /// A multiline paragraph
155 /// A multiline numbered paragraph
196 enum MathedBinaryTypes {
204 LMB_BOP = (LMB_RELATION | LMB_OPERATOR)
212 /** Abstract base class for all math objects.
213 A math insets is for use of the math editor only, it isn't a
214 general LyX inset. It's used to represent all the math objects.
215 The formulaInset (a LyX inset) encapsulates a math inset.
219 /// A math inset has a name (usually its LaTeX name), type and font-size
220 MathedInset(char const *nm, short ot, short st);
222 MathedInset(MathedInset*);
224 virtual ~MathedInset() { };
227 virtual void Draw(int x, int baseline)=0;
229 /// Write LaTeX and Lyx code
230 virtual void Write(FILE *file)=0;
231 /// Write LaTeX and Lyx code
232 virtual void Write(string & file)=0;
234 /// Reproduces itself
235 virtual MathedInset *Clone()=0;
237 /// Compute the size of the object
238 virtual void Metrics()=0;
240 virtual int Ascent() const { return ascent; }
242 virtual int Descent() const { return descent; }
244 virtual int Width() const { return width; }
246 virtual int Height() const { return ascent + descent; }
249 virtual bool GetLimits() const { return false; }
251 virtual void SetLimits(bool) { }
254 char const *GetName() const { return name; }
256 short GetType() const { return objtype; }
258 short GetStyle() const { return size; }
260 //Man: Avoid to use these functions if it's not strictly necessary
262 virtual void SetType(short t) { objtype = t; }
264 virtual void SetStyle(short st) { size = st; } // Metrics();
266 virtual void SetName(char const* n) { name = n; }
268 void setDrawable(long unsigned int d) { pm = d; }
283 /// This works while only one process can draw unless
284 /// the process have their own data
285 static long unsigned int pm;
287 static int df_asc, df_des, df_width;
289 /// In a near future maybe we use a better fonts renderer than X
290 void drawStr(short, int, int, int, byte*, int);
292 friend class MathedCursor;
294 friend void mathed_init_fonts();
300 /// Paragraph permissions
303 /// If false can use a non-standard size
305 /// If true can insert newlines
307 /// If true can use tabs
309 /// If true can insert new columns
310 LMPF_ALLOW_NEW_COL = 8,
311 /// Smaller than current size (frac)
313 /// Script size (subscript, stackrel)
318 /** The math paragraph base class, base to all editable math objects */
319 class MathParInset: public MathedInset {
322 MathParInset(short st=LM_ST_TEXT, char const *nm=0, short ot=LM_OT_MIN);
324 MathParInset(MathParInset*);
326 virtual ~MathParInset();
328 virtual MathedInset *Clone();
330 /// Draw the object on a drawable
331 virtual void Draw(int x, int baseline);
334 virtual void Write(FILE *file);
336 virtual void Write(string &file);
338 virtual void Metrics();
340 virtual void UserSetSize(short);
342 /// Data is stored in a LyXArray
343 virtual void SetData(LyxArrayBase *);
345 virtual LyxArrayBase * GetData() { return array; }
347 /// Paragraph position
348 virtual void GetXY(int&, int&) const;
350 virtual void setXY(int x, int y) { xo =x; yo = y; }
352 virtual void SetFocus(int,int) { };
354 virtual bool Inside(int, int);
356 // Tab stuff used by Matrix.
358 virtual void SetAlign(char, char const*) { };
360 // virtual int GetTabPos() { return 0; }
362 // virtual int GetTab(int) { return 0; }
364 virtual int GetColumns() { return 1; }
366 virtual int GetRows() { return 1; }
368 virtual bool isMatrix() { return false; }
369 // /// These functions should report an error
370 // virtual char const* GetLabel() { return 0; }
371 // virtual char const* GetLabel(int) { return 0; }
373 // Vertical switching
375 virtual bool setArgumentIdx(int i) { return (i==0); }
377 virtual bool setNextArgIdx() { return false; }
379 virtual int getArgumentIdx() { return 0; }
381 virtual int getMaxArgumentIdx() { return 0; }
383 // virtual void SetLabel(char const*) { }
385 virtual void SetStyle(short);
387 virtual MathedRowSt *getRowSt() const { return 0; }
389 virtual void setRowSt(MathedRowSt*) { }
391 virtual bool Permit(short f) { return (bool)(f & flag); }
394 /// Paragraph data is stored here
396 /// Cursor start position
403 virtual void setFlag(MathedParFlag f) { flag |= f; }
405 friend class InsetFormula;
407 friend class MathedXIter;
409 friend class MathedCursor;
411 friend LyxArrayBase *mathed_parse(unsigned flags = 0, LyxArrayBase*a=0, MathParInset**p=0);
415 /* The physical structure of a row and aditional information is stored here.
416 It allows to manage the extra info independently of the paragraph data.
417 Only used for multiline paragraphs.
422 w = new int[n+1]; // this leaks
430 if (label) delete[] label;
432 /// Should be const but...
433 MathedRowSt* getNext() const { return next; }
434 /// ...we couldn't use this.
435 void setNext(MathedRowSt* n) { next = n; }
437 char const* getLabel() const { return label; }
439 bool isNumbered() const { return numbered; }
441 int getBaseline() const { return y; }
443 int getTab(int i) { return w[i]; }
445 void setLabel(char* l) { label = l; }
447 void setNumbered(bool nf) { numbered = nf; }
449 void setTab(int i, int t) { w[i] = t; }
463 friend class MathMatrixInset;
465 friend class MathedXIter;
469 /** Multiline math paragraph base class.
470 This is the base to all multiline editable math objects
471 like array and eqnarray.
473 class MathMatrixInset: public MathParInset {
476 MathMatrixInset(int m=1, int n=1, short st=LM_ST_TEXT);
478 MathMatrixInset(MathMatrixInset*);
480 MathedInset *Clone();
482 virtual ~MathMatrixInset();
486 void Write(FILE *file);
488 void Write(string &file);
492 void SetData(LyxArrayBase *);
494 void SetAlign(char, char const*);
496 char *GetAlign(char* vv) {
503 int GetColumns() { return nc; }
505 int GetRows() { return nr; }
507 virtual bool isMatrix() { return true; }
509 /// Use this to manage the extra information independently of paragraph
510 MathedRowSt *getRowSt() const { return row; }
512 void setRowSt(MathedRowSt* r) { row = r; }
515 /// Number of columns & rows
520 char v_align; // add approp. signedness
523 /// Vertical structure
530 /************************* Prototypes **********************************/
532 LyxArrayBase *mathed_parse(unsigned flags, LyxArrayBase *data, MathParInset **mt);
534 void mathed_write(MathParInset*, FILE *, int*, char fragile, char const* label=0);
536 void mathed_write(MathParInset*, string&, int*, char fragile, char const* label=0);
538 void mathed_parser_file(FILE*, int);
540 int mathed_parser_lineno();
542 int MathedLookupBOP(short);
544 /************************ Inline functions ********************************/
547 #define MathIsInset(x) (LM_TC_INSET<=(x) && (x)<=LM_TC_ACTIVE_INSET)
549 #define MathIsFont(x) (LM_TC_CONST<=(x) && (x)<=LM_TC_BSYM)
551 #define MathIsAlphaFont(x) (LM_TC_VAR<=(x) && (x)<=LM_TC_TEXTRM)
553 #define MathIsActive(x) (LM_TC_INSET<(x) && (x)<=LM_TC_ACTIVE_INSET)
555 #define MathIsUp(x) ((x)==LM_TC_UP)
557 #define MathIsDown(x) ((x)==LM_TC_DOWN)
559 #define MathIsScript(x) ((x)==LM_TC_DOWN || (x)==LM_TC_UP)
561 #define MathIsBOPS(x) (MathedLookupBOP(x)>LMB_NONE)
565 inline bool MathIsBinary(short x)
567 return (x==LM_TC_BOP || x==LM_TC_BOPS);
571 inline bool MathIsSymbol(short x) {
572 return (LM_TC_SYMB<=x && x<=LM_TC_BSYM);
577 MathedInset::MathedInset(char const *nm, short ot, short st):
578 name(nm), objtype(ot), size(st)
580 width = ascent = descent = 0;
584 bool MathParInset::Inside(int x, int y)
586 return (x>=xo && x<=xo+width && y<=yo+descent && y>=yo-ascent);
591 void MathParInset::GetXY(int& x, int& y) const
598 void MathParInset::UserSetSize(short sz)
602 flag = flag & ~LMPF_FIXED_SIZE;
608 void MathParInset::SetStyle(short sz)
610 if (Permit(LMPF_FIXED_SIZE)) {
611 if (Permit(LMPF_SCRIPT))
612 sz = (sz<LM_ST_SCRIPT) ? LM_ST_SCRIPT: LM_ST_SCRIPTSCRIPT;
613 if (Permit(LMPF_SMALLER) && sz < LM_ST_SCRIPTSCRIPT) {
616 MathedInset::SetStyle(sz);