OpenCPN Partial API docs
Loading...
Searching...
No Matches
RolloverWin.cpp
1/******************************************************************************
2 *
3 * Project: OpenCPN
4 *
5 ***************************************************************************
6 * Copyright (C) 2013 by David S. Register *
7 * *
8 * This program is free software; you can redistribute it and/or modify *
9 * it under the terms of the GNU General Public License as published by *
10 * the Free Software Foundation; either version 2 of the License, or *
11 * (at your option) any later version. *
12 * *
13 * This program is distributed in the hope that it will be useful, *
14 * but WITHOUT ANY WARRANTY; without even the implied warranty of *
15 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the *
16 * GNU General Public License for more details. *
17 * *
18 * You should have received a copy of the GNU General Public License *
19 * along with this program; if not, write to the *
20 * Free Software Foundation, Inc., *
21 * 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. *
22 ***************************************************************************
23 */
24
25#include <wx/wxprec.h>
26
27#include <wx/bitmap.h>
28#include <wx/dcmemory.h>
29#include <wx/dcscreen.h>
30
31#ifdef ocpnUSE_GL
32#if defined(__OCPN__ANDROID__)
33#include <GLES2/gl2.h>
34#elif defined(__WXQT__) || defined(__WXGTK__)
35#include <GL/glew.h>
36#endif
37#endif
38
39#include "ocpndc.h"
40#include "RolloverWin.h"
41#include "timers.h"
42#include "navutil.h"
43#include "FontMgr.h"
44#include "ocpn_plugin.h"
45#include "color_handler.h"
46#include "ocpn_frame.h"
47#include "OCPNPlatform.h"
48
49#ifdef ocpnUSE_GL
50#include "glChartCanvas.h"
51#include "chcanv.h"
52#endif
53
54extern bool g_bopengl;
55#ifdef ocpnUSE_GL
56extern GLenum g_texture_rectangle_format;
57#endif
58extern MyFrame *gFrame;
59extern BasePlatform *g_BasePlatform;
60
61BEGIN_EVENT_TABLE(RolloverWin, wxWindow)
62EVT_PAINT(RolloverWin::OnPaint)
63EVT_TIMER(ROLLOVER_TIMER, RolloverWin::OnTimer)
64EVT_MOUSE_EVENTS(RolloverWin::OnMouseEvent)
65
66END_EVENT_TABLE()
67
68// Define a constructor
69RolloverWin::RolloverWin(wxWindow *parent, int timeout, bool maincanvas)
70 : wxWindow(parent, wxID_ANY, wxPoint(0, 0), wxSize(1, 1), wxNO_BORDER),
71 m_bmaincanvas(maincanvas) {
72 m_pbm = NULL;
73
74 m_timer_timeout.SetOwner(this, ROLLOVER_TIMER);
75 m_timeout_sec = timeout;
76 m_mmouse_propogate = 0;
77 isActive = false;
78 m_plabelFont = NULL;
79 m_texture = 0;
80 Hide();
81}
82
83RolloverWin::~RolloverWin() {
84 delete m_pbm;
85#ifdef ocpnUSE_GL
86 if (g_bopengl) glDeleteTextures(1, &m_texture);
87#endif
88}
89void RolloverWin::OnTimer(wxTimerEvent &event) {
90 if (IsActive()) {
91 Hide();
92 GetParent()->Refresh(true);
93 IsActive(false);
94 }
95}
96
97void RolloverWin::OnMouseEvent(wxMouseEvent &event) {
98 // If directed, send mouse events up the window family tree,
99 // until some parent window does NOT call event.Skip()
100 if (m_mmouse_propogate) {
101 event.ResumePropagation(m_mmouse_propogate);
102 event.Skip();
103 }
104}
105
106void RolloverWin::SetBitmap(int rollover) {
107 wxMemoryDC mdc;
108 delete m_pbm;
109 m_pbm = new wxBitmap(m_size.x, m_size.y);
110 mdc.SelectObject(*m_pbm);
111
112 mdc.SetBackground(wxBrush(GetGlobalColor(_T ( "YELO1" ))));
113 mdc.Clear();
114#ifdef ocpnUSE_GL
115 bool usegl = g_bopengl && g_texture_rectangle_format;
116#else
117 bool usegl = false;
118#endif
119
120 if (!usegl) {
121 if (m_bmaincanvas) {
122 wxDC *cdc = new wxScreenDC();
123 int cpx = 0, cpy = 0;
124 GetParent()->ClientToScreen(&cpx, &cpy);
125 mdc.Blit(0, 0, m_size.x, m_size.y, cdc, m_position.x + cpx,
126 m_position.y + cpy);
127 delete cdc;
128 }
129 }
130
131 ocpnDC dc(mdc);
132
133 wxString text;
134 double radius = 6.0;
135 switch (rollover) {
136 case AIS_ROLLOVER:
137 text = _("AISRollover");
138 break;
139 case TC_ROLLOVER:
140 text = _("TideCurrentGraphRollover"), radius = 0;
141 break;
142 default:
143 case LEG_ROLLOVER:
144 text = _("RouteLegInfoRollover");
145 break;
146 }
147
148 if (m_bmaincanvas)
149 AlphaBlending(dc, 0, 0, m_size.x, m_size.y, radius,
150 GetGlobalColor(_T ( "YELO1" )), 172);
151
152 mdc.SetTextForeground(FontMgr::Get().GetFontColor(text));
153
154#ifdef __WXOSX__
155 mdc.SetTextForeground(wxColour(0, 0, 0));
156#endif
157
158 if (m_plabelFont && m_plabelFont->IsOk()) {
159 // Draw the text
160 mdc.SetFont(*m_plabelFont);
161
162 mdc.DrawLabel(m_string, wxRect(0, 0, m_size.x, m_size.y),
163 wxALIGN_CENTRE_HORIZONTAL | wxALIGN_CENTRE_VERTICAL);
164 }
165
166 mdc.SelectObject(wxNullBitmap);
167
168 SetSize(m_position.x, m_position.y, m_size.x, m_size.y);
169
170#ifdef ocpnUSE_GL
171 if (usegl) {
172 if (!m_texture) {
173 glGenTextures(1, &m_texture);
174
175 glBindTexture(g_texture_rectangle_format, m_texture);
176 glTexParameterf(g_texture_rectangle_format, GL_TEXTURE_MIN_FILTER,
177 GL_NEAREST);
178 glTexParameteri(g_texture_rectangle_format, GL_TEXTURE_MAG_FILTER,
179 GL_NEAREST);
180 glTexParameteri(g_texture_rectangle_format, GL_TEXTURE_WRAP_S,
181 GL_CLAMP_TO_EDGE);
182 glTexParameteri(g_texture_rectangle_format, GL_TEXTURE_WRAP_T,
183 GL_CLAMP_TO_EDGE);
184
185 } else
186 glBindTexture(g_texture_rectangle_format, m_texture);
187
188 // make texture data
189 wxImage image = m_pbm->ConvertToImage();
190
191 unsigned char *d = image.GetData();
192 unsigned char *e = new unsigned char[4 * m_size.x * m_size.y];
193 for (int y = 0; y < m_size.y; y++)
194 for (int x = 0; x < m_size.x; x++) {
195 int i = y * m_size.x + x;
196 memcpy(e + 4 * i, d + 3 * i, 3);
197 e[4 * i + 3] = 255 - d[3 * i + 2];
198 }
199 glTexImage2D(g_texture_rectangle_format, 0, GL_RGBA, m_size.x, m_size.y, 0,
200 GL_RGBA, GL_UNSIGNED_BYTE, e);
201 delete[] e;
202 glDisable(g_texture_rectangle_format);
203 glDisable(GL_BLEND);
204 }
205#endif
206
207 // Retrigger the auto timeout
208 if (m_timeout_sec > 0) {
209 m_timer_timeout.Start(m_timeout_sec * 1000, wxTIMER_ONE_SHOT);
210 }
211}
212
213void RolloverWin::OnPaint(wxPaintEvent &event) {
214 int width, height;
215 GetClientSize(&width, &height);
216 wxPaintDC dc(this);
217
218 if (m_string.Len()) {
219 wxMemoryDC mdc;
220 mdc.SelectObject(*m_pbm);
221 dc.Blit(0, 0, width, height, &mdc, 0, 0);
222 }
223}
224
225void RolloverWin::Draw(ocpnDC &dc) {
226 if (!IsActive()) return;
227#ifdef ocpnUSE_GL
228 if (g_bopengl && m_texture) {
229 glEnable(g_texture_rectangle_format);
230 glBindTexture(g_texture_rectangle_format, m_texture);
231 glEnable(GL_BLEND);
232
233 int x0 = m_position.x, x1 = x0 + m_size.x;
234 int y0 = m_position.y, y1 = y0 + m_size.y;
235 float tx, ty;
236 if (GL_TEXTURE_RECTANGLE_ARB == g_texture_rectangle_format)
237 tx = m_size.x, ty = m_size.y;
238 else
239 tx = ty = 1;
240
241 float coords[8];
242 float uv[8];
243
244 // normal uv
245 uv[0] = 0;
246 uv[1] = 0;
247 uv[2] = tx;
248 uv[3] = 0;
249 uv[4] = tx;
250 uv[5] = ty;
251 uv[6] = 0;
252 uv[7] = ty;
253
254 // pixels
255 coords[0] = x0;
256 coords[1] = y0;
257 coords[2] = x1;
258 coords[3] = y0;
259 coords[4] = x1;
260 coords[5] = y1;
261 coords[6] = x0;
262 coords[7] = y1;
263
264 auto pCanvas = dynamic_cast<ChartCanvas *>(GetParent());
265 if (pCanvas)
266 pCanvas->GetglCanvas()->RenderTextures(dc, coords, uv, 4,
267 pCanvas->GetpVP());
268
269 glDisable(g_texture_rectangle_format);
270 glDisable(GL_BLEND);
271 } else {
272#ifdef __WXOSX__
273 // Support MacBook Retina display
274 if (g_bopengl) {
275 double scale = m_parent->GetContentScaleFactor();
276 if (scale > 1) {
277 wxImage image = m_pbm->ConvertToImage();
278 image.Rescale(image.GetWidth() * scale, image.GetHeight() * scale);
279 wxBitmap bmp(image);
280 dc.DrawBitmap(bmp, m_position.x, m_position.y, false);
281 } else
282 dc.DrawBitmap(*m_pbm, m_position.x, m_position.y, false);
283 } else
284 dc.DrawBitmap(*m_pbm, m_position.x, m_position.y, false);
285#else
286 dc.DrawBitmap(*m_pbm, m_position.x, m_position.y, false);
287#endif
288 }
289
290#else
291 dc.DrawBitmap(*m_pbm, m_position.x, m_position.y, false);
292#endif
293}
294
295void RolloverWin::SetBestPosition(int x, int y, int off_x, int off_y,
296 int rollover, wxSize parent_size) {
297 int h, w;
298
299 wxFont *dFont;
300 switch (rollover) {
301 case AIS_ROLLOVER:
302 dFont = FontMgr::Get().GetFont(_("AISRollover"));
303 break;
304
305 case TC_ROLLOVER:
306 dFont = FontMgr::Get().GetFont(_("TideCurrentGraphRollover"));
307 break;
308
309 default:
310 case LEG_ROLLOVER:
311 dFont = FontMgr::Get().GetFont(_("RouteLegInfoRollover"));
312 break;
313 }
314
315 int font_size =
316 wxMax(8 * g_current_monitor_dip_px_ratio, dFont->GetPointSize());
317 font_size /= OCPN_GetWinDIPScaleFactor();
318
319 m_plabelFont = FontMgr::Get().FindOrCreateFont(
320 font_size, dFont->GetFamily(), dFont->GetStyle(), dFont->GetWeight(),
321 false, dFont->GetFaceName());
322
323 wxSize sizeM;
324 if (m_plabelFont && m_plabelFont->IsOk()) {
325#ifdef __WXMAC__
326 wxScreenDC sdc;
327 sdc.SetFont(*m_plabelFont);
328 sdc.GetMultiLineTextExtent(m_string, &w, &h, NULL, m_plabelFont);
329 sizeM = sdc.GetTextExtent("M");
330#else
331 wxClientDC cdc(GetParent());
332 cdc.SetFont(*m_plabelFont);
333 cdc.GetMultiLineTextExtent(m_string, &w, &h, NULL, m_plabelFont);
334 sizeM = cdc.GetTextExtent("M");
335#endif
336 } else {
337 w = 10;
338 h = 10;
339 }
340
341 m_size.x = w + sizeM.x;
342 m_size.y = h + sizeM.y;
343
344 m_size *=
345 OCPN_GetWinDIPScaleFactor(); // g_BasePlatform->GetDisplayDPIMult(this);
346
347 int xp, yp;
348 if ((x + off_x + m_size.x) > parent_size.x) {
349 xp = x - (off_x / 2) - m_size.x;
350 xp = wxMax(0, xp);
351 } else
352 xp = x + off_x;
353
354 if ((y + off_y + m_size.y) > parent_size.y) {
355 yp = y - (off_y / 2) - m_size.y;
356 } else
357 yp = y + off_y;
358
359 SetPosition(wxPoint(xp, yp));
360}
Chart display canvas.
Definition chcanv.h:135
wxFont * FindOrCreateFont(int point_size, wxFontFamily family, wxFontStyle style, wxFontWeight weight, bool underline=false, const wxString &facename=wxEmptyString, wxFontEncoding encoding=wxFONTENCODING_DEFAULT)
Creates or finds a matching font in the font cache.
Definition FontMgr.cpp:450
wxFont * GetFont(const wxString &TextElement, int requested_font_size=0)
Gets a font object for a UI element.
Definition FontMgr.cpp:186
Main application frame.
Definition ocpn_frame.h:136
Device context class that can use either wxDC or OpenGL for drawing.
Definition ocpndc.h:64
PlugIn Object Definition/API.