1 /**
2  * \file MetricsInfo.cpp
3  * This file is part of LyX, the document processor.
4  * Licence details can be found in the file COPYING.
5  *
6  * \author André Pönitz
7  *
8  * Full author contact details are available in file CREDITS.
9  */
10 
11 #include <config.h>
12 
13 #include "BufferView.h"
14 #include "ColorSet.h"
15 #include "LyXRC.h"
16 #include "MetricsInfo.h"
17 
18 #include "insets/Inset.h"
19 
20 #include "mathed/MathSupport.h"
21 
22 #include "frontends/Painter.h"
23 
24 #include "support/docstring.h"
25 #include "support/lassert.h"
26 #include "support/RefChanger.h"
27 
28 using namespace std;
29 
30 
31 namespace lyx {
32 
33 /////////////////////////////////////////////////////////////////////////
34 //
35 // MetricsBase
36 //
37 /////////////////////////////////////////////////////////////////////////
38 
MetricsBase(BufferView * b,FontInfo f,int w)39 MetricsBase::MetricsBase(BufferView * b, FontInfo f, int w)
40 	: bv(b), font(move(f)), fontname("mathnormal"),
41 	  textwidth(w), macro_nesting(0),
42 	  solid_line_thickness_(1), solid_line_offset_(1), dotted_line_thickness_(1)
43 {
44 	if (lyxrc.currentZoom >= 200) {
45 		// derive the line thickness from zoom factor
46 		// the zoom is given in percent
47 		// (increase thickness at 250%, 450% etc.)
48 		solid_line_thickness_ = (lyxrc.currentZoom + 150) / 200;
49 		// adjust line_offset_ too
50 		solid_line_offset_ = 1 + solid_line_thickness_ / 2;
51 	}
52 	if (lyxrc.currentZoom >= 100) {
53 		// derive the line thickness from zoom factor
54 		// the zoom is given in percent
55 		// (increase thickness at 150%, 250% etc.)
56 		dotted_line_thickness_ = (lyxrc.currentZoom + 50) / 100;
57 	}
58 }
59 
60 
changeFontSet(string const & name)61 Changer MetricsBase::changeFontSet(string const & name)
62 {
63 	RefChanger<MetricsBase> rc = make_save(*this);
64 	ColorCode oldcolor = font.color();
65 	string const oldname = fontname;
66 	fontname = name;
67 	if (isMathFont(name) || isMathFont(oldname))
68 		font = sane_font;
69 	augmentFont(font, name);
70 	font.setSize(rc->old.font.size());
71 	font.setStyle(rc->old.font.style());
72 	if (name != "lyxtex"
73 	    && ((isTextFont(oldname) && oldcolor != Color_foreground)
74 	        || (isMathFont(oldname) && oldcolor != Color_math)))
75 		font.setColor(oldcolor);
76 #if __cplusplus >= 201402L
77 	return rc;
78 #else
79 	return move(rc);
80 #endif
81 }
82 
83 
changeEnsureMath(Inset::mode_type mode)84 Changer MetricsBase::changeEnsureMath(Inset::mode_type mode)
85 {
86 	switch (mode) {
87 	case Inset::UNDECIDED_MODE:
88 		return Changer();
89 	case Inset::TEXT_MODE:
90 		return isMathFont(fontname) ? changeFontSet("textnormal") : Changer();
91 	case Inset::MATH_MODE:
92 		// FIXME:
93 		//   \textit{\ensuremath{\text{a}}}
94 		// should appear in italics
95 		return isTextFont(fontname) ? changeFontSet("mathnormal"): Changer();
96 	}
97 	return Changer();
98 }
99 
100 
101 /////////////////////////////////////////////////////////////////////////
102 //
103 // MetricsInfo
104 //
105 /////////////////////////////////////////////////////////////////////////
106 
MetricsInfo(BufferView * bv,FontInfo font,int textwidth,MacroContext const & mc)107 MetricsInfo::MetricsInfo(BufferView * bv, FontInfo font, int textwidth,
108                          MacroContext const & mc)
109 	: base(bv, font, textwidth), macrocontext(mc)
110 {}
111 
112 
113 /////////////////////////////////////////////////////////////////////////
114 //
115 // PainterInfo
116 //
117 /////////////////////////////////////////////////////////////////////////
118 
PainterInfo(BufferView * bv,lyx::frontend::Painter & painter)119 PainterInfo::PainterInfo(BufferView * bv, lyx::frontend::Painter & painter)
120 	: pain(painter), ltr_pos(false), change_(), selected(false),
121 	do_spellcheck(true), full_repaint(true), background_color(Color_background)
122 {
123 	base.bv = bv;
124 }
125 
126 
draw(int x,int y,char_type c)127 void PainterInfo::draw(int x, int y, char_type c)
128 {
129 	pain.text(x, y, c, base.font);
130 }
131 
132 
draw(int x,int y,docstring const & str)133 void PainterInfo::draw(int x, int y, docstring const & str)
134 {
135 	pain.text(x, y, str, base.font);
136 }
137 
138 
backgroundColor(Inset const * inset,bool sel) const139 ColorCode PainterInfo::backgroundColor(Inset const * inset, bool sel) const
140 {
141 	ColorCode const color_bg = inset->backgroundColor(*this);
142 
143 	if (selected && sel)
144 		// This inset is in a selection
145 		return Color_selection;
146 	else {
147 		if (color_bg != Color_none)
148 			// This inset has its own color
149 			return color_bg;
150 		else {
151 			if (background_color == Color_none)
152 				// This inset has no own color and does not inherit a color
153 				return Color_background;
154 			else
155 				// This inset has no own color, but inherits a color
156 				return background_color;
157 		}
158 	}
159 }
160 
161 
textColor(Color const & color) const162 Color PainterInfo::textColor(Color const & color) const
163 {
164 	if (change_.changed())
165 		return change_.color();
166 	if (selected)
167 		return Color_selectiontext;
168 	return color;
169 }
170 
171 
changeScript()172 Changer MetricsBase::changeScript()
173 {
174 	switch (font.style()) {
175 	case LM_ST_DISPLAY:
176 	case LM_ST_TEXT:
177 		return font.changeStyle(LM_ST_SCRIPT);
178 	case LM_ST_SCRIPT:
179 	case LM_ST_SCRIPTSCRIPT:
180 		return font.changeStyle(LM_ST_SCRIPTSCRIPT);
181 	}
182 	//remove Warning
183 	return Changer();
184 }
185 
186 
changeFrac()187 Changer MetricsBase::changeFrac()
188 {
189 	switch (font.style()) {
190 	case LM_ST_DISPLAY:
191 		return font.changeStyle(LM_ST_TEXT);
192 	case LM_ST_TEXT:
193 		return font.changeStyle(LM_ST_SCRIPT);
194 	case LM_ST_SCRIPT:
195 	case LM_ST_SCRIPTSCRIPT:
196 		return font.changeStyle(LM_ST_SCRIPTSCRIPT);
197 	}
198 	//remove Warning
199 	return Changer();
200 }
201 
202 
changeArray()203 Changer MetricsBase::changeArray()
204 {
205 	return (font.style() == LM_ST_DISPLAY) ? font.changeStyle(LM_ST_TEXT)
206 		: Changer();
207 }
208 
209 
210 } // namespace lyx
211