]> git.lyx.org Git - lyx.git/blob - src/Paragraph.h
Make the fake sequence for braces highly unlikely (addressing #6478).
[lyx.git] / src / Paragraph.h
1 // -*- C++ -*-
2 /**
3  * \file Paragraph.h
4  * This file is part of LyX, the document processor.
5  * Licence details can be found in the file COPYING.
6  *
7  * \author Asger Alstrup
8  * \author Lars Gullik Bjønnes
9  * \author John Levon
10  * \author André Pönitz
11  * \author Jürgen Vigna
12  *
13  * Full author contact details are available in file CREDITS.
14  */
15
16 #ifndef PARAGRAPH_H
17 #define PARAGRAPH_H
18
19 #include "FontEnums.h"
20
21 #include "insets/InsetCode.h"
22
23 #include "support/strfwd.h"
24 #include "support/types.h"
25
26 namespace lyx {
27
28 class AuthorList;
29 class Buffer;
30 class BufferParams;
31 class Change;
32 class Counters;
33 class Cursor;
34 class CursorSlice;
35 class DocIterator;
36 class docstring_list;
37 class DocumentClass;
38 class Inset;
39 class InsetBibitem;
40 class LaTeXFeatures;
41 class Inset_code;
42 class InsetList;
43 class Language;
44 class Layout;
45 class Font;
46 class Font_size;
47 class MetricsInfo;
48 class OutputParams;
49 class PainterInfo;
50 class ParagraphParameters;
51 class TexRow;
52 class Toc;
53 class WordLangTuple;
54 class XHTMLStream;
55
56 class FontSpan {
57 public:
58         /// Invalid font span containing no character
59         FontSpan() : first(0), last(-1) {}
60         /// Span including first and last
61         FontSpan(pos_type f, pos_type l) : first(f), last(l) {}
62
63 public:
64         /// Range including first and last.
65         pos_type first, last;
66 };
67
68 ///
69 enum TextCase {
70         ///
71         text_lowercase = 0,
72         ///
73         text_capitalization = 1,
74         ///
75         text_uppercase = 2
76 };
77
78
79 ///
80 enum AsStringParameter
81 {
82         AS_STR_NONE = 0, ///< No option, only printable characters.
83         AS_STR_LABEL = 1, ///< Prefix with paragraph label.
84         AS_STR_INSETS = 2, ///< Go into insets.
85         AS_STR_NEWLINES = 4 ///< Get also newline characters.
86 };
87
88
89 /// A Paragraph holds all text, attributes and insets in a text paragraph
90 class Paragraph
91 {
92 public:
93         ///
94         Paragraph();
95         /// Copy constructor.
96         Paragraph(Paragraph const &);
97         /// Partial copy constructor.
98         /// Copy the Paragraph contents from \p beg to \p end (without end).
99         Paragraph(Paragraph const & par, pos_type beg, pos_type end);
100         ///
101         Paragraph & operator=(Paragraph const &);
102         ///
103         ~Paragraph();
104         ///
105         int id() const;
106         ///
107         void setId(int id);
108
109         ///
110         void addChangesToToc(DocIterator const & cdit, Buffer const & buf) const;
111         ///
112         Language const * getParLanguage(BufferParams const &) const;
113         ///
114         bool isRTL(BufferParams const &) const;
115         ///
116         void changeLanguage(BufferParams const & bparams,
117                             Language const * from, Language const * to);
118         ///
119         bool isMultiLingual(BufferParams const &) const;
120
121         /// Convert the paragraph to a string.
122         /// \param AsStringParameter options. This can contain any combination of
123         /// asStringParameter values. Valid examples:
124         ///             asString(AS_STR_LABEL)
125         ///             asString(AS_STR_LABEL | AS_STR_INSETS)
126         ///             asString(AS_STR_INSETS)
127         docstring asString(int options = AS_STR_NONE) const;
128         ///
129         docstring asString(pos_type beg, pos_type end,
130                 int options = AS_STR_NONE) const;
131
132         /// Extract only the explicitly visible text (without any formatting),
133         /// descending into insets
134         docstring stringify(pos_type beg, pos_type end, int options, OutputParams & runparams) const;
135
136         ///
137         void write(std::ostream &, BufferParams const &,
138                    depth_type & depth) const;
139         ///
140         void validate(LaTeXFeatures &) const;
141
142         ///
143         bool latex(BufferParams const &, Font const & outerfont, odocstream &,
144                    TexRow & texrow, OutputParams const &,
145                    int start_pos = 0, int end_pos = -1) const;
146
147         /// Can we drop the standard paragraph wrapper?
148         bool emptyTag() const;
149
150         /// Get the id of the paragraph, usefull for docbook
151         std::string getID(Buffer const & buf, OutputParams const & runparams) const;
152
153         /// Output the first word of a paragraph, return the position where it left.
154         pos_type firstWordDocBook(odocstream & os, OutputParams const & runparams) const;
155
156         /// Output the first word of a paragraph, return the position where it left.
157         pos_type firstWordLyXHTML(XHTMLStream & xs, OutputParams const & runparams) const;
158
159         /// Writes to stream the docbook representation
160         void simpleDocBookOnePar(Buffer const & buf,
161                                  odocstream &,
162                                  OutputParams const & runparams,
163                                  Font const & outerfont,
164                                  pos_type initial = 0) const;
165         /// \return any material that has had to be deferred until after the
166         /// paragraph has closed.
167         docstring simpleLyXHTMLOnePar(Buffer const & buf,
168                                  XHTMLStream & xs,
169                                  OutputParams const & runparams,
170                                  Font const & outerfont,
171                                  pos_type initial = 0) const;
172
173         ///
174         bool hasSameLayout(Paragraph const & par) const;
175
176         ///
177         void makeSameLayout(Paragraph const & par);
178
179         ///
180         void setInsetOwner(Inset const * inset);
181         ///
182         Inset const & inInset() const;
183         ///
184         bool allowParagraphCustomization() const;
185         ///
186         bool usePlainLayout() const;
187         ///
188         pos_type size() const;
189         ///
190         bool empty() const;
191
192         ///
193         Layout const & layout() const;
194         /// Do not pass a temporary to this!
195         void setLayout(Layout const & layout);
196         ///
197         void setPlainOrDefaultLayout(DocumentClass const & tc);
198         ///
199         void setDefaultLayout(DocumentClass const & tc);
200         ///
201         void setPlainLayout(DocumentClass const & tc);
202
203         /// This is the item depth, only used by enumerate and itemize
204         signed char itemdepth;
205
206         /// look up change at given pos
207         Change const & lookupChange(pos_type pos) const;
208
209         /// is there a change within the given range ?
210         bool isChanged(pos_type start, pos_type end) const;
211         /// is there an unchanged char at the given pos ?
212         bool isChanged(pos_type pos) const;
213         /// is there an insertion at the given pos ?
214         bool isInserted(pos_type pos) const;
215         /// is there a deletion at the given pos ?
216         bool isDeleted(pos_type pos) const;
217         /// is the whole paragraph deleted ?
218         bool isDeleted(pos_type start, pos_type end) const;
219
220         /// will the paragraph be physically merged with the next
221         /// one if the imaginary end-of-par character is logically deleted?
222         bool isMergedOnEndOfParDeletion(bool trackChanges) const;
223
224         /// set change for the entire par
225         void setChange(Change const & change);
226
227         /// set change at given pos
228         void setChange(pos_type pos, Change const & change);
229
230         /// accept changes within the given range
231         void acceptChanges(pos_type start, pos_type end);
232
233         /// reject changes within the given range
234         void rejectChanges(pos_type start, pos_type end);
235
236         /// Paragraphs can contain "manual labels", for example, Description
237         /// environment. The text for this user-editable label is stored in
238         /// the paragraph alongside the text of the rest of the paragraph
239         /// (the body). This function returns the starting position of the
240         /// body of the text in the paragraph.
241         pos_type beginOfBody() const;
242         /// recompute this value
243         void setBeginOfBody();
244
245         ///
246         docstring expandLabel(Layout const &, BufferParams const &) const;
247         ///
248         docstring expandDocBookLabel(Layout const &, BufferParams const &) const;
249         ///
250         docstring const & labelString() const;
251         /// the next two functions are for the manual labels
252         docstring const getLabelWidthString() const;
253         /// Set label width string.
254         void setLabelWidthString(docstring const & s);
255         /// Actual paragraph alignment used
256         char getAlign() const;
257         /// The nesting depth of a paragraph
258         depth_type getDepth() const;
259         /// The maximal possible depth of a paragraph after this one
260         depth_type getMaxDepthAfter() const;
261         ///
262         void applyLayout(Layout const & new_layout);
263
264         /// (logically) erase the char at pos; return true if it was actually erased
265         bool eraseChar(pos_type pos, bool trackChanges);
266         /// (logically) erase the given range; return the number of chars actually erased
267         int eraseChars(pos_type start, pos_type end, bool trackChanges);
268
269         ///
270         void resetFonts(Font const & font);
271
272         /** Get uninstantiated font setting. Returns the difference
273             between the characters font and the layoutfont.
274             This is what is stored in the fonttable
275         */
276         Font const &
277         getFontSettings(BufferParams const &, pos_type pos) const;
278         ///
279         Font const & getFirstFontSettings(BufferParams const &) const;
280
281         /** Get fully instantiated font. If pos == -1, use the layout
282             font attached to this paragraph.
283             If pos == -2, use the label font of the layout attached here.
284             In all cases, the font is instantiated, i.e. does not have any
285             attributes with values FONT_INHERIT, FONT_IGNORE or
286             FONT_TOGGLE.
287         */
288         Font const getFont(BufferParams const &, pos_type pos,
289                               Font const & outerfont) const;
290         Font const getLayoutFont(BufferParams const &,
291                                     Font const & outerfont) const;
292         Font const getLabelFont(BufferParams const &,
293                                    Font const & outerfont) const;
294         /**
295          * The font returned by the above functions is the same in a
296          * span of characters. This method will return the first and
297          * the last positions in the paragraph for which that font is
298          * the same. This can be used to avoid unnecessary calls to getFont.
299          */
300         FontSpan fontSpan(pos_type pos) const;
301         ///
302         char_type getChar(pos_type pos) const;
303         /// Get the char, but mirror all bracket characters if it is right-to-left
304         char_type getUChar(BufferParams const &, pos_type pos) const;
305         /// pos <= size() (there is a dummy font change at the end of each par)
306         void setFont(pos_type pos, Font const & font);
307         /// Returns the height of the highest font in range
308         FontSize highestFontInRange(pos_type startpos,
309                                         pos_type endpos, FontSize def_size) const;
310         ///
311         void insert(pos_type pos, docstring const & str,
312                     Font const & font, Change const & change);
313
314         ///
315         void appendString(docstring const & s, Font const & font,
316                 Change const & change);
317         ///
318         void appendChar(char_type c, Font const & font, Change const & change);
319         ///
320         void insertChar(pos_type pos, char_type c, bool trackChanges);
321         ///
322         void insertChar(pos_type pos, char_type c,
323                         Font const &, bool trackChanges);
324         ///
325         void insertChar(pos_type pos, char_type c,
326                         Font const &, Change const & change);
327         /// Insert \p inset at position \p pos with \p change traking status.
328         /// \return true if successful.
329         bool insertInset(pos_type pos, Inset * inset,
330                          Change const & change);
331         /// Insert \p inset at position \p pos with \p change traking status and
332         /// \p font.
333         /// \return true if successful.
334         bool insertInset(pos_type pos, Inset * inset,
335                          Font const & font, Change const & change);
336         ///
337         Inset * getInset(pos_type pos);
338         ///
339         Inset const * getInset(pos_type pos) const;
340
341         /// Release inset at given position.
342         /// \warning does not honour change tracking!
343         /// Therefore, it should only be used for breaking and merging
344         /// paragraphs
345         Inset * releaseInset(pos_type pos);
346
347         ///
348         InsetList const & insetList() const;
349         ///
350         void setBuffer(Buffer &);
351
352         ///
353         bool isHfill(pos_type pos) const;
354
355         /// hinted by profiler
356         bool isInset(pos_type pos) const;
357         ///
358         bool isNewline(pos_type pos) const;
359         /// return true if the char is a word separator
360         bool isSeparator(pos_type pos) const;
361         ///
362         bool isLineSeparator(pos_type pos) const;
363         /// True if the character/inset at this point is a word separator.
364         /// Note that digits in particular are not considered as word separator.
365         bool isWordSeparator(pos_type pos) const;
366         /// True if the element at this point is a character that is not a letter.
367         bool isChar(pos_type pos) const;
368         /// True if the element at this point is a space
369         bool isSpace(pos_type pos) const;
370
371         /// returns true if at least one line break or line separator has been deleted
372         /// at the beginning of the paragraph (either physically or logically)
373         bool stripLeadingSpaces(bool trackChanges);
374
375         /// return true if we allow multiple spaces
376         bool isFreeSpacing() const;
377
378         /// return true if we allow this par to stay empty
379         bool allowEmpty() const;
380         ///
381         char_type transformChar(char_type c, pos_type pos) const;
382         ///
383         ParagraphParameters & params();
384         ///
385         ParagraphParameters const & params() const;
386
387         /// Check if we are in a Biblio environment and insert or
388         /// delete InsetBibitems as necessary.
389         /// \retval int 1, if we had to add an inset, in which case
390         /// the cursor will need to move cursor forward; -pos, if we deleted
391         /// an inset, in which case pos is the position from which the inset
392         /// was deleted, and the cursor will need to be moved back one if it
393         /// was previously past that position. Return 0 otherwise.
394         int checkBiblio(Buffer const & buffer);
395
396         /// For each author, set 'used' to true if there is a change
397         /// by this author in the paragraph.
398         void checkAuthors(AuthorList const & authorList);
399
400         ///
401         void changeCase(BufferParams const & bparams, pos_type pos,
402                 pos_type & right, TextCase action);
403
404         /// find \param str string inside Paragraph.
405         /// \return true if the specified string is at the specified position
406         /// \param del specifies whether deleted strings in ct mode will be considered
407         bool find(
408                 docstring const & str, ///< string to search
409                 bool cs, ///<
410                 bool mw, ///<
411                 pos_type pos, ///< start from here.
412                 bool del = true) const;
413         
414         void locateWord(pos_type & from, pos_type & to,
415                 word_location const loc) const;
416         ///
417         void updateWords();
418
419         /// Spellcheck word at position \p from and fill in found misspelled word
420         /// and \p suggestions if \p do_suggestion is true.
421         /// \return true if pointed word is misspelled.
422         bool spellCheck(pos_type & from, pos_type & to, WordLangTuple & wl,
423                 docstring_list & suggestions, bool do_suggestion =  true) const;
424
425         /// Spellcheck word at position \p pos.
426         /// \return true if pointed word is misspelled.
427         bool isMisspelled(pos_type pos) const;
428         /// an automatically generated identifying label for this paragraph.
429         /// presently used only in the XHTML output routines.
430         std::string magicLabel() const;
431
432 private:
433         /// Expand the counters for the labelstring of \c layout
434         docstring expandParagraphLabel(Layout const &, BufferParams const &,
435                 bool process_appendix) const;
436         ///
437         void deregisterWords();
438         ///
439         void collectWords();
440         ///
441         void registerWords();
442
443         /// Pimpl away stuff
444         class Private;
445         ///
446         friend class Paragraph::Private;
447         ///
448         Private * d;
449 };
450
451 } // namespace lyx
452
453 #endif // PARAGRAPH_H