2
* This file is a part of the Cairo-Dock project
4
* Copyright : (C) see the 'copyright' file.
5
* E-mail : see the 'copyright' file.
7
* This program is free software; you can redistribute it and/or
8
* modify it under the terms of the GNU General Public License
9
* as published by the Free Software Foundation; either version 3
10
* of the License, or (at your option) any later version.
12
* This program is distributed in the hope that it will be useful,
13
* but WITHOUT ANY WARRANTY; without even the implied warranty of
14
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
15
* GNU General Public License for more details.
16
* You should have received a copy of the GNU General Public License
17
* along with this program. If not, see <http://www.gnu.org/licenses/>.
29
#include "rendering-diapo-simple.h"
31
extern gint my_diapo_simple_iconGapX;
32
extern gint my_diapo_simple_iconGapY;
33
extern gdouble my_diapo_simple_fScaleMax;
34
extern gint my_diapo_simple_sinW;
35
extern gboolean my_diapo_simple_lineaire;
36
extern gboolean my_diapo_simple_wide_grid;
38
extern gdouble my_diapo_simple_color_frame_start[4];
39
extern gdouble my_diapo_simple_color_frame_stop[4];
40
extern gboolean my_diapo_simple_fade2bottom;
41
extern gboolean my_diapo_simple_fade2right;
42
extern gint my_diapo_simple_arrowWidth;
43
extern gint my_diapo_simple_arrowHeight;
44
//extern gdouble my_diapo_simple_arrowShift;
45
extern gint my_diapo_simple_lineWidth;
46
extern gint my_diapo_simple_radius;
47
extern gdouble my_diapo_simple_color_border_line[4];
48
extern gboolean my_diapo_simple_draw_background;
49
extern gboolean my_diapo_simple_display_all_labels;
51
extern gdouble my_diapo_simple_color_scrollbar_line[4];
52
extern gdouble my_diapo_simple_color_scrollbar_inside[4];
53
extern gdouble my_diapo_simple_color_grip[4];
55
const gint X_BORDER_SPACE = 40; // espace laisse de chaque cote pour eviter de sortir trop facilement (et pour laisser de la place pour les etiquettes).
56
const gint ARROW_TIP = 5; // pour gerer la pointe de la fleche.
57
const double fArrowHeight = 14, fScrollbarWidth = 10, fScrollbarArrowGap = 4;
58
const double fScrollbarIconGap = 10;
59
/// On considere qu'on a my_diapo_simple_iconGapX entre chaque icone horizontalement, et my_diapo_simple_iconGapX/2 entre les icones et les bords (pour aerer un peu plus le dessin). Idem verticalement. X_BORDER_SPACE est la pour empecher que les icones debordent de la fenetre au zoom.
64
gint iDeltaHeight; // hauteur scrollable, en pixels
65
gint iScrollOffset; // hauteur scrollee, en pixels, positive.
66
gboolean bDraggingScrollbar; // si le clic est couramment enfonce sur la scrollbar.
67
guint iSidPressEvent; // sid du clic
68
guint iSidReleaseEvent; // sid du relachement du clic
69
gint iClickY; // hauteur ou on a clique, en coordonnees container.
70
gint iClickOffset; // hauteur scrollee au moment du clic
75
static void cd_rendering_render_diapo_simple (cairo_t *pCairoContext, CairoDock *pDock);
77
// Fonctions utiles pour transformer l'index de la liste en couple (x,y) sur la grille et inversement.
78
static inline void _get_gridXY_from_index (guint nRowsX, guint index, guint* gridX, guint* gridY)
80
*gridX = index % nRowsX;
81
*gridY = index / nRowsX;
83
static inline guint _get_index_from_gridXY (guint nRowsX, guint gridX, guint gridY)
85
return gridX + gridY * nRowsX;
88
static guint _cd_rendering_diapo_simple_guess_grid (GList *pIconList, guint *nRowX, guint *nRowY)
90
// Calcul du nombre de lignes (nY) / colonnes (nX) :
91
guint count = 0; // g_list_length (pIconList)
94
for (ic = pIconList; ic != NULL; ic = ic->next)
97
if (! CAIRO_DOCK_ICON_TYPE_IS_SEPARATOR (icon))
106
else if (my_diapo_simple_wide_grid)
108
*nRowX = ceil(sqrt(count));
109
*nRowY = ceil(((double) count) / *nRowX);
113
*nRowY = ceil(sqrt(count));
114
*nRowX = ceil(((double) count) / *nRowY);
119
static void _set_scroll (CairoDock *pDock, int iOffsetY)
121
//g_print ("%s (%d)\n", __func__, iOffsetY);
122
CDSlideData *pData = pDock->pRendererData;
123
g_return_if_fail (pData != NULL);
125
pData->iScrollOffset = MAX (0, MIN (iOffsetY, pData->iDeltaHeight));
126
cairo_dock_calculate_dock_icons (pDock);
127
gtk_widget_queue_draw (pDock->container.pWidget);
129
static gboolean _add_scroll (CairoDock *pDock, int iDeltaOffsetY)
131
//g_print ("%s (%d)\n", __func__, iDeltaOffsetY);
132
CDSlideData *pData = pDock->pRendererData;
133
g_return_val_if_fail (pData != NULL, FALSE);
135
if (iDeltaOffsetY < 0)
137
if (pData->iScrollOffset <= 0)
142
if (pData->iScrollOffset >= pData->iDeltaHeight)
145
_set_scroll (pDock, pData->iScrollOffset + iDeltaOffsetY);
149
static gboolean _cd_slide_on_scroll (gpointer data, Icon *pClickedIcon, CairoDock *pDock, int iDirection)
151
CDSlideData *pData = pDock->pRendererData;
152
g_return_val_if_fail (pData != NULL, CAIRO_DOCK_LET_PASS_NOTIFICATION);
153
if (pData->iDeltaHeight == 0)
154
return CAIRO_DOCK_LET_PASS_NOTIFICATION;
156
gboolean bScrolled = _add_scroll (pDock, iDirection == 1 ? pDock->iMaxIconHeight : - pDock->iMaxIconHeight);
157
return (bScrolled ? CAIRO_DOCK_INTERCEPT_NOTIFICATION : CAIRO_DOCK_LET_PASS_NOTIFICATION);
159
static gboolean _cd_slide_on_click (gpointer data, Icon *pClickedIcon, CairoDock *pDock, guint iButtonState)
161
CDSlideData *pData = pDock->pRendererData;
162
g_return_val_if_fail (pData != NULL, CAIRO_DOCK_LET_PASS_NOTIFICATION);
163
if (pData->iDeltaHeight == 0)
164
return CAIRO_DOCK_LET_PASS_NOTIFICATION;
165
if (pData->bDraggingScrollbar)
166
return CAIRO_DOCK_INTERCEPT_NOTIFICATION;
168
return CAIRO_DOCK_LET_PASS_NOTIFICATION;
170
gboolean _cd_slide_on_press_button (GtkWidget* pWidget, GdkEventButton* pButton, CairoDock *pDock)
172
CDSlideData *pData = pDock->pRendererData;
173
g_return_val_if_fail (pData != NULL, FALSE);
174
if (pData->iDeltaHeight == 0)
177
if (pButton->type == GDK_BUTTON_PRESS && pButton->button == 1)
179
double x_arrow = pDock->iMaxDockWidth - X_BORDER_SPACE - fScrollbarWidth;
181
if (pDock->container.bIsHorizontal)
191
if (x > x_arrow) // on a clique dans la zone de scroll.
193
//g_print ("click (y=%d, scroll=%d)\n", (int) y, pData->iScrollOffset);
195
// on regarde sur quoi on clic.
196
double y_arrow_top, y_arrow_bottom;
197
if (pDock->container.bDirectionUp)
199
y_arrow_bottom = pDock->iMaxDockHeight - (my_diapo_simple_arrowHeight + ARROW_TIP + my_diapo_simple_lineWidth);
200
y_arrow_top = my_diapo_simple_lineWidth;
204
y_arrow_bottom = pDock->iMaxDockHeight - my_diapo_simple_lineWidth;
205
y_arrow_top = my_diapo_simple_arrowHeight + ARROW_TIP + my_diapo_simple_lineWidth;
207
if (y > y_arrow_top - fScrollbarArrowGap/2 && y < y_arrow_top + fArrowHeight + fScrollbarArrowGap/2) // bouton haut
209
_set_scroll (pDock, 0);
211
else if (y < y_arrow_bottom + fScrollbarArrowGap/2 && y > y_arrow_bottom - fArrowHeight - fScrollbarArrowGap/2) // bouton bas
213
_set_scroll (pDock, pData->iDeltaHeight);
217
pData->bDraggingScrollbar = TRUE;
219
pData->iClickOffset = pData->iScrollOffset;
223
else if (GDK_BUTTON_RELEASE)
225
//g_print ("release\n");
226
pData->bDraggingScrollbar = FALSE;
230
static gboolean _cd_slide_on_mouse_moved (gpointer data, CairoDock *pDock, gboolean *bStartAnimation)
232
CDSlideData *pData = pDock->pRendererData;
233
g_return_val_if_fail (pData != NULL, CAIRO_DOCK_LET_PASS_NOTIFICATION);
234
if (pData->iDeltaHeight == 0)
235
return CAIRO_DOCK_LET_PASS_NOTIFICATION;
237
if (pData->bDraggingScrollbar)
239
//g_print ("scroll on motion (y=%d)\n", pDock->container.iMouseY);
241
double y_arrow_top, y_arrow_bottom;
242
if (pDock->container.bDirectionUp)
244
y_arrow_bottom = my_diapo_simple_arrowHeight + ARROW_TIP + my_diapo_simple_lineWidth;
245
y_arrow_top = pDock->iMaxDockHeight - my_diapo_simple_lineWidth;
249
y_arrow_top = pDock->iMaxDockHeight - (my_diapo_simple_arrowHeight + ARROW_TIP + my_diapo_simple_lineWidth);
250
y_arrow_bottom = my_diapo_simple_lineWidth;
252
double fFrameHeight = pDock->iMaxDockHeight- (my_diapo_simple_arrowHeight + ARROW_TIP + my_diapo_simple_lineWidth); // hauteur du cadre avec les rayons et sans la pointe.
253
double fGripHeight = fFrameHeight / (fFrameHeight + pData->iDeltaHeight) * (y_arrow_top - y_arrow_bottom - 2*(fArrowHeight+fScrollbarArrowGap));
254
double ygrip = (double) pData->iScrollOffset / pData->iDeltaHeight * (y_arrow_top - y_arrow_bottom - 2*(fArrowHeight+fScrollbarArrowGap) - fGripHeight);
256
int delta = pDock->container.iMouseY - pData->iClickY;
257
_set_scroll (pDock, (pData->iClickOffset + (double)delta / (y_arrow_top - y_arrow_bottom - 2*(fArrowHeight+fScrollbarArrowGap) - fGripHeight) * pData->iDeltaHeight));
258
return CAIRO_DOCK_INTERCEPT_NOTIFICATION;
260
return CAIRO_DOCK_LET_PASS_NOTIFICATION;
262
gboolean cd_slide_on_leave (gpointer data, CairoDock *pDock, gboolean *bStartAnimation)
264
CDSlideData *pData = pDock->pRendererData;
265
//g_return_val_if_fail (pData != NULL, CAIRO_DOCK_LET_PASS_NOTIFICATION);
266
if (pData == NULL || ! pDock->pRenderer || pDock->pRenderer->render != cd_rendering_render_diapo_simple) // pas nous
267
return CAIRO_DOCK_LET_PASS_NOTIFICATION;
269
//g_print (" LEAVE (%d)\n", pData->bDraggingScrollbar);
271
return (pData->bDraggingScrollbar ? CAIRO_DOCK_INTERCEPT_NOTIFICATION : CAIRO_DOCK_LET_PASS_NOTIFICATION);
273
const double srx = .5; // screen ratio hori
274
const double sry = .6; // screen ratio verti
275
static void cd_rendering_calculate_max_dock_size_diapo_simple (CairoDock *pDock)
277
// On calcule la configuration de la grille sans contrainte.
278
guint nRowsX = 0; // nb colonnes.
279
guint nRowsY = 0; // nb lignes.
280
guint nIcones = 0; // nb icones.
281
int iDeltaHeight = 0; // hauteur ne pouvant rentrer dans le dock.
282
int iMaxIconWidth = 0;
283
int iDockWidth, iDockHeight; // dimension dock.
284
int Ws = g_desktopGeometry.iXScreenWidth[CAIRO_DOCK_HORIZONTAL]; // dimensions ecran.
285
int Hs = g_desktopGeometry.iXScreenHeight[CAIRO_DOCK_HORIZONTAL];
286
nIcones = _cd_rendering_diapo_simple_guess_grid(pDock->icons, &nRowsX, &nRowsY);
287
//g_print ("nIcones : %d\n", nIcones);
289
// On calcule la taille de l'affichage avec contrainte taille ecran.
292
// on calcule la largeur avec contrainte, ce qui donne aussi le nombre de lignes.
293
iMaxIconWidth = ((Icon*)pDock->icons->data)->fWidth; // approximation un peu bof.
294
iDockWidth = nRowsX * (iMaxIconWidth + my_diapo_simple_iconGapX) + 2*X_BORDER_SPACE;
295
int iMaxWidth = Ws * (Ws > Hs ? srx : sry);
296
if (iDockWidth > iMaxWidth)
298
nRowsX = (iMaxWidth - 2*X_BORDER_SPACE) / (iMaxIconWidth + my_diapo_simple_iconGapX);
299
nRowsY = ceil((double) nIcones / nRowsX);
300
iDockWidth = nRowsX * (iMaxIconWidth + my_diapo_simple_iconGapX) + 2*X_BORDER_SPACE;
301
//g_print ("%d -> %d\n", iMaxWidth, iDockWidth);
304
// on calcule la hauteur avec contrainte, ce qui donne aussi la marge de defilement.
305
int iSingleLineHeight = pDock->iMaxIconHeight * pDock->container.fRatio * my_diapo_simple_fScaleMax + // les icones des bords zooment
306
myLabels.iLabelSize + // le texte des icones de la 1ere ligne
307
my_diapo_simple_lineWidth + // les demi-lignes du haut et du bas
308
my_diapo_simple_arrowHeight + ARROW_TIP; // la fleche etendue
309
int iOneLineHeight = pDock->iMaxIconHeight * pDock->container.fRatio + my_diapo_simple_iconGapY;
311
iDockHeight = (nRowsY - 1) * iOneLineHeight + iSingleLineHeight;
312
int iMaxHeight = Hs * (Ws > Hs ? sry : srx);
313
if (iDockHeight > iMaxHeight)
315
nRowsY = (iMaxHeight - iSingleLineHeight) / iOneLineHeight + 1;
316
if (Ws > Hs && nRowsY > nRowsX) // on evite d'avoir un sous-dock plus haut que large si l'ecran est ausi comme ca, ca rend mieux.
318
int iMaxDockHeight0 = iDockHeight;
319
iDockHeight = (nRowsY - 1) * iOneLineHeight + iSingleLineHeight;
320
iDeltaHeight = iMaxDockHeight0 - iDockHeight;
321
//g_print ("%d -> %d\n", iMaxHeight, iDockHeight);
326
iDockWidth = X_BORDER_SPACE * 2 + 1;
327
iDockHeight = my_diapo_simple_lineWidth + my_diapo_simple_arrowHeight + ARROW_TIP + 1;
330
CDSlideData *pData = pDock->pRendererData;
333
pData = g_new0 (CDSlideData, 1);
334
pDock->pRendererData = pData;
335
cairo_dock_register_notification_on_object (CAIRO_CONTAINER (pDock), CAIRO_DOCK_SCROLL_ICON, (CairoDockNotificationFunc) _cd_slide_on_scroll, CAIRO_DOCK_RUN_AFTER, NULL);
336
cairo_dock_register_notification_on_object (CAIRO_CONTAINER (pDock), CAIRO_DOCK_CLICK_ICON, (CairoDockNotificationFunc) _cd_slide_on_click, CAIRO_DOCK_RUN_FIRST, NULL);
337
cairo_dock_register_notification_on_object (CAIRO_CONTAINER (pDock), CAIRO_DOCK_MOUSE_MOVED, (CairoDockNotificationFunc) _cd_slide_on_mouse_moved, CAIRO_DOCK_RUN_AFTER, NULL);
338
pData->iSidPressEvent = g_signal_connect (G_OBJECT (pDock->container.pWidget),
339
"button-press-event",
340
G_CALLBACK (_cd_slide_on_press_button),
341
pDock); // car les notification de clic en provenance du dock sont emises lors du relachement du bouton.
342
pData->iSidReleaseEvent = g_signal_connect (G_OBJECT (pDock->container.pWidget),
343
"button-release-event",
344
G_CALLBACK (_cd_slide_on_press_button),
347
pData->nRowsX = nRowsX;
348
pData->nRowsY = nRowsY;
349
pData->iDeltaHeight = iDeltaHeight;
350
if (iDeltaHeight != 0)
352
int iScrollMargin = iMaxIconWidth * (my_diapo_simple_fScaleMax - 1) / 2
354
+ fScrollbarWidth; // donc a droite on a : derniere icone en taille max + demi-gapx + gap + scrollbar + X_BORDER_SPACE
355
iDockWidth += iScrollMargin;
359
//if (pDock->container.bIsHorizontal)
361
pDock->iMaxDockWidth = iDockWidth;
362
pDock->iMaxDockHeight = iDockHeight;
364
/*else // pareil, sauf la fleche qui sera sur les cotes.
366
pDock->iMaxDockWidth = iDockHeight - (my_diapo_simple_arrowHeight + ARROW_TIP);
367
pDock->iMaxDockHeight = iDockWidth + my_diapo_simple_arrowHeight + ARROW_TIP;
369
pDock->iMinDockWidth = pDock->iMaxDockWidth - 2*X_BORDER_SPACE;
370
pDock->iMinDockHeight = pDock->iMaxDockHeight;
371
// pas de decorations.
372
pDock->iDecorationsHeight = 0;
373
pDock->iDecorationsWidth = 0;
374
// On affecte ca aussi au cas ou.
375
pDock->fFlatDockWidth = pDock->iMaxDockWidth;
376
pDock->fMagnitudeMax = my_diapo_simple_fScaleMax / (1+g_fAmplitude);
381
//////////////////////////////////////////////////////////////////////////////////////// Methodes de dessin :
383
static void _cairo_dock_draw_frame_horizontal_for_diapo_simple (cairo_t *pCairoContext, CairoDock *pDock)
385
CDSlideData *pData = pDock->pRendererData; // non nul
386
int iArrowShift = pData->iArrowShift;
387
int iDeltaIconX = pData->iDeltaIconX;
389
gdouble fFrameWidth = pDock->iMaxDockWidth - 2 * X_BORDER_SPACE;
390
gdouble fFrameHeight = pDock->iMaxDockHeight - (my_diapo_simple_arrowHeight + ARROW_TIP + my_diapo_simple_lineWidth);
391
gdouble fDockOffsetX = X_BORDER_SPACE;
392
gdouble fDockOffsetY = (pDock->container.bDirectionUp ? .5*my_diapo_simple_lineWidth : my_diapo_simple_arrowHeight + ARROW_TIP);
394
cairo_move_to (pCairoContext, fDockOffsetX, fDockOffsetY);
396
//HautGauche -> HautDroit
397
if(pDock->container.bDirectionUp)
399
cairo_rel_line_to (pCairoContext, fFrameWidth, 0);
404
cairo_rel_line_to (pCairoContext, fFrameWidth/2 - my_diapo_simple_arrowWidth/2 + iArrowShift, 0); // _
405
cairo_rel_line_to (pCairoContext, + my_diapo_simple_arrowWidth/2 - iArrowShift + iDeltaIconX, -my_diapo_simple_arrowHeight); // \.
406
cairo_rel_line_to (pCairoContext, + my_diapo_simple_arrowWidth/2 + iArrowShift - iDeltaIconX, +my_diapo_simple_arrowHeight); // /
407
cairo_rel_line_to (pCairoContext, (fFrameWidth/2 - my_diapo_simple_arrowWidth/2 - iArrowShift) , 0); // _
409
//\_________________ Coin haut droit.
410
cairo_rel_curve_to (pCairoContext,
412
my_diapo_simple_radius, 0,
413
my_diapo_simple_radius, my_diapo_simple_radius );
415
//HautDroit -> BasDroit
416
cairo_rel_line_to (pCairoContext, 0, fFrameHeight + my_diapo_simple_lineWidth - my_diapo_simple_radius * 2 );
417
//\_________________ Coin bas droit.
418
cairo_rel_curve_to (pCairoContext,
420
0 , my_diapo_simple_radius,
421
-my_diapo_simple_radius , my_diapo_simple_radius);
423
//BasDroit -> BasGauche
424
if(!pDock->container.bDirectionUp)
426
cairo_rel_line_to (pCairoContext, - fFrameWidth , 0);
431
cairo_rel_line_to (pCairoContext, - fFrameWidth/2 + my_diapo_simple_arrowWidth/2 + iArrowShift, 0); // _
432
cairo_rel_line_to (pCairoContext, - my_diapo_simple_arrowWidth/2 - iArrowShift + iDeltaIconX, +my_diapo_simple_arrowHeight); // \.
433
cairo_rel_line_to (pCairoContext, - my_diapo_simple_arrowWidth/2 + iArrowShift - iDeltaIconX, -my_diapo_simple_arrowHeight); // /
434
cairo_rel_line_to (pCairoContext, - fFrameWidth/2 + my_diapo_simple_arrowWidth/2 - iArrowShift , 0); // _
436
//\_________________ Coin bas gauche.
437
cairo_rel_curve_to (pCairoContext,
439
-my_diapo_simple_radius, 0,
440
-my_diapo_simple_radius, -my_diapo_simple_radius);
442
//BasGauche -> HautGauche
443
cairo_rel_line_to (pCairoContext, 0, - fFrameHeight - my_diapo_simple_lineWidth + my_diapo_simple_radius * 2);
444
//\_________________ Coin haut gauche.
445
cairo_rel_curve_to (pCairoContext,
447
0 , -my_diapo_simple_radius ,
448
my_diapo_simple_radius, -my_diapo_simple_radius);
451
static void _cairo_dock_draw_frame_vertical_for_diapo_simple (cairo_t *pCairoContext, CairoDock *pDock)
453
CDSlideData *pData = pDock->pRendererData; // non nul
454
int iArrowShift = pData->iArrowShift;
455
int iDeltaIconX = pData->iDeltaIconX;
457
gdouble fFrameWidth = pDock->iMaxDockWidth - 2 * X_BORDER_SPACE;
458
gdouble fFrameHeight = pDock->iMaxDockHeight - (my_diapo_simple_arrowHeight + ARROW_TIP + my_diapo_simple_lineWidth);
459
gdouble fDockOffsetX = X_BORDER_SPACE;
460
gdouble fDockOffsetY = (pDock->container.bDirectionUp ? .5*my_diapo_simple_lineWidth : my_diapo_simple_arrowHeight + ARROW_TIP);
462
cairo_move_to (pCairoContext, fDockOffsetY, fDockOffsetX);
464
if(pDock->container.bDirectionUp)
466
cairo_rel_line_to (pCairoContext, 0, fFrameWidth);
470
cairo_rel_line_to (pCairoContext, 0, fFrameWidth/2 - my_diapo_simple_arrowWidth/2 + iArrowShift); // _
471
cairo_rel_line_to (pCairoContext, -my_diapo_simple_arrowHeight, + my_diapo_simple_arrowWidth/2 - iArrowShift + iDeltaIconX); // \.
472
cairo_rel_line_to (pCairoContext, +my_diapo_simple_arrowHeight, + my_diapo_simple_arrowWidth/2 + iArrowShift - iDeltaIconX); // /
473
cairo_rel_line_to (pCairoContext, 0, (fFrameWidth/2 - my_diapo_simple_arrowWidth/2 - iArrowShift)); // _
475
//\_________________ Coin haut droit.
476
cairo_rel_curve_to (pCairoContext,
478
0, my_diapo_simple_radius,
479
my_diapo_simple_radius, my_diapo_simple_radius);
480
cairo_rel_line_to (pCairoContext, fFrameHeight + my_diapo_simple_lineWidth - my_diapo_simple_radius * 2, 0);
481
//\_________________ Coin bas droit.
482
cairo_rel_curve_to (pCairoContext,
484
my_diapo_simple_radius, 0,
485
my_diapo_simple_radius, -my_diapo_simple_radius);
486
if(!pDock->container.bDirectionUp)
488
cairo_rel_line_to (pCairoContext, 0, - fFrameWidth);
493
cairo_rel_line_to (pCairoContext, 0, - fFrameWidth/2 + my_diapo_simple_arrowWidth/2 + iArrowShift); // _
494
cairo_rel_line_to (pCairoContext, +my_diapo_simple_arrowHeight, - my_diapo_simple_arrowWidth/2 - iArrowShift + iDeltaIconX); // \.
495
cairo_rel_line_to (pCairoContext, -my_diapo_simple_arrowHeight, - my_diapo_simple_arrowWidth/2 + iArrowShift - iDeltaIconX); // /
496
cairo_rel_line_to (pCairoContext, 0, - fFrameWidth/2 + my_diapo_simple_arrowWidth/2 - iArrowShift); // _
499
//\_________________ Coin bas gauche.
500
cairo_rel_curve_to (pCairoContext,
502
0, -my_diapo_simple_radius,
503
-my_diapo_simple_radius, -my_diapo_simple_radius);
504
cairo_rel_line_to (pCairoContext, - fFrameHeight - my_diapo_simple_lineWidth + my_diapo_simple_radius * 2, 0);
505
//\_________________ Coin haut gauche.
506
cairo_rel_curve_to (pCairoContext,
508
-my_diapo_simple_radius, 0,
509
-my_diapo_simple_radius, my_diapo_simple_radius);
511
static void _cairo_dock_draw_frame_for_diapo_simple (cairo_t *pCairoContext, CairoDock *pDock)
513
if (pDock->container.bIsHorizontal)
514
_cairo_dock_draw_frame_horizontal_for_diapo_simple (pCairoContext, pDock);
516
_cairo_dock_draw_frame_vertical_for_diapo_simple (pCairoContext, pDock);
519
static void cairo_dock_render_decorations_in_frame_for_diapo_simple (cairo_t *pCairoContext, CairoDock *pDock, double fAlpha)
521
// On se fait un beau pattern degrade :
522
cairo_pattern_t *mon_super_pattern;
523
mon_super_pattern = cairo_pattern_create_linear (0.0,
525
my_diapo_simple_fade2right ? pDock->iMaxDockWidth : 0.0, // Y'aurait surement des calculs complexes à faire mais
526
my_diapo_simple_fade2bottom ? pDock->iMaxDockHeight : 0.0); // a quelques pixels près pour un dégradé : OSEF !
528
cairo_pattern_add_color_stop_rgba (mon_super_pattern, 0,
529
my_diapo_simple_color_frame_start[0],
530
my_diapo_simple_color_frame_start[1],
531
my_diapo_simple_color_frame_start[2],
532
my_diapo_simple_color_frame_start[3] * fAlpha); // transparent -> opaque au depliage.
534
cairo_pattern_add_color_stop_rgba (mon_super_pattern, 1,
535
my_diapo_simple_color_frame_stop[0],
536
my_diapo_simple_color_frame_stop[1],
537
my_diapo_simple_color_frame_stop[2],
538
my_diapo_simple_color_frame_stop[3] * fAlpha);
539
cairo_set_source (pCairoContext, mon_super_pattern);
541
//On remplit le contexte en le préservant -> pourquoi ? ----> parce qu'on va tracer le contour plus tard ;-)
542
cairo_fill_preserve (pCairoContext);
543
cairo_pattern_destroy (mon_super_pattern);
546
static void cd_rendering_render_diapo_simple (cairo_t *pCairoContext, CairoDock *pDock)
548
CDSlideData *pData = pDock->pRendererData;
549
g_return_if_fail (pData != NULL);
551
double fAlpha = (pDock->fFoldingFactor < .3 ? (.3 - pDock->fFoldingFactor) / .3 : 0.); // apparition du cadre de 0.3 a 0
553
double fDeltaIconX = 0.;
555
if (my_diapo_simple_draw_background)
557
//\____________________ On trace le cadre.
558
cairo_save (pCairoContext);
559
_cairo_dock_draw_frame_for_diapo_simple (pCairoContext, pDock);
561
//\____________________ On dessine les decorations dedans.
562
cairo_dock_render_decorations_in_frame_for_diapo_simple (pCairoContext, pDock, fAlpha);
564
//\____________________ On dessine le cadre.
565
if (my_diapo_simple_lineWidth != 0 && my_diapo_simple_color_border_line[3] != 0 && fAlpha != 0)
567
cairo_set_line_width (pCairoContext, my_diapo_simple_lineWidth);
568
cairo_set_source_rgba (pCairoContext,
569
my_diapo_simple_color_border_line[0],
570
my_diapo_simple_color_border_line[1],
571
my_diapo_simple_color_border_line[2],
572
my_diapo_simple_color_border_line[3] * fAlpha);
573
cairo_stroke (pCairoContext);
576
cairo_new_path (pCairoContext);
577
cairo_restore (pCairoContext);
580
if (pDock->icons == NULL)
583
//\____________________ On dessine la ficelle qui les joint.
585
if (myIcons.iStringLineWidth > 0)
586
cairo_dock_draw_string (pCairoContext, pDock, myIcons.iStringLineWidth, TRUE, TRUE);
588
//\____________________ On dessine les barres de defilement.
589
if (pData->iDeltaHeight != 0)
591
cairo_save (pCairoContext);
592
cairo_set_line_width (pCairoContext, 2.);
594
if (! pDock->container.bIsHorizontal)
596
cairo_translate (pCairoContext, pDock->container.iHeight/2, pDock->container.iWidth/2);
597
cairo_rotate (pCairoContext, G_PI/2);
598
cairo_scale (pCairoContext, 1., -1.);
599
cairo_translate (pCairoContext, -pDock->container.iWidth/2, -pDock->container.iHeight/2);
602
double x_arrow = pDock->iMaxDockWidth - X_BORDER_SPACE - fScrollbarWidth/2; // pointe de la fleche.
603
double y_arrow_top, y_arrow_bottom;
604
if (pDock->container.bDirectionUp)
606
y_arrow_bottom = pDock->iMaxDockHeight - (my_diapo_simple_arrowHeight + ARROW_TIP + my_diapo_simple_lineWidth);
607
y_arrow_top = my_diapo_simple_lineWidth;
611
y_arrow_top = my_diapo_simple_arrowHeight + ARROW_TIP + my_diapo_simple_lineWidth;
612
y_arrow_bottom = pDock->iMaxDockHeight - my_diapo_simple_lineWidth;
614
if (pData->iScrollOffset != 0) // fleche vers le haut.
616
cairo_move_to (pCairoContext, x_arrow, y_arrow_top);
617
cairo_rel_line_to (pCairoContext, fScrollbarWidth/2, fArrowHeight);
618
cairo_rel_line_to (pCairoContext, -fScrollbarWidth, 0.);
619
cairo_close_path (pCairoContext);
621
cairo_set_source_rgba (pCairoContext, my_diapo_simple_color_scrollbar_inside[0], my_diapo_simple_color_scrollbar_inside[1], my_diapo_simple_color_scrollbar_inside[2], my_diapo_simple_color_scrollbar_inside[3] * fAlpha);
622
cairo_fill_preserve (pCairoContext);
624
cairo_set_source_rgba (pCairoContext, my_diapo_simple_color_scrollbar_line[0], my_diapo_simple_color_scrollbar_line[1], my_diapo_simple_color_scrollbar_line[2], my_diapo_simple_color_scrollbar_line[3] * fAlpha);
625
cairo_stroke (pCairoContext);
627
if (pData->iScrollOffset != pData->iDeltaHeight) // fleche vers le bas.
629
cairo_move_to (pCairoContext, x_arrow, y_arrow_bottom);
630
cairo_rel_line_to (pCairoContext, fScrollbarWidth/2, - fArrowHeight);
631
cairo_rel_line_to (pCairoContext, -fScrollbarWidth, 0.);
632
cairo_close_path (pCairoContext);
634
cairo_set_source_rgba (pCairoContext, my_diapo_simple_color_scrollbar_inside[0], my_diapo_simple_color_scrollbar_inside[1], my_diapo_simple_color_scrollbar_inside[2], my_diapo_simple_color_scrollbar_inside[3] * fAlpha);
635
cairo_fill_preserve (pCairoContext);
637
cairo_set_source_rgba (pCairoContext, my_diapo_simple_color_scrollbar_line[0], my_diapo_simple_color_scrollbar_line[1], my_diapo_simple_color_scrollbar_line[2], my_diapo_simple_color_scrollbar_line[3] * fAlpha);
638
cairo_stroke (pCairoContext);
641
cairo_move_to (pCairoContext, x_arrow - fScrollbarWidth/2, y_arrow_top + fArrowHeight + fScrollbarArrowGap);
642
cairo_rel_line_to (pCairoContext, fScrollbarWidth, 0.);
643
cairo_rel_line_to (pCairoContext, 0., y_arrow_bottom - y_arrow_top - 2*(fArrowHeight+fScrollbarArrowGap));
644
cairo_rel_line_to (pCairoContext, -fScrollbarWidth, 0.);
645
cairo_close_path (pCairoContext);
647
cairo_set_source_rgba (pCairoContext, my_diapo_simple_color_scrollbar_inside[0], my_diapo_simple_color_scrollbar_inside[1], my_diapo_simple_color_scrollbar_inside[2], my_diapo_simple_color_scrollbar_inside[3] * fAlpha);
648
cairo_fill_preserve (pCairoContext);
650
cairo_set_source_rgba (pCairoContext, my_diapo_simple_color_scrollbar_line[0], my_diapo_simple_color_scrollbar_line[1], my_diapo_simple_color_scrollbar_line[2], my_diapo_simple_color_scrollbar_line[3] * fAlpha);
651
cairo_stroke (pCairoContext);
653
double fFrameHeight = pDock->iMaxDockHeight - (my_diapo_simple_arrowHeight + ARROW_TIP + my_diapo_simple_lineWidth); // hauteur du cadre avec les rayons et sans la pointe.
654
double fGripHeight = fFrameHeight / (fFrameHeight + pData->iDeltaHeight) * (y_arrow_bottom - y_arrow_top - 2*(fArrowHeight+fScrollbarArrowGap));
655
double ygrip = (double) pData->iScrollOffset / pData->iDeltaHeight * (y_arrow_bottom - y_arrow_top - 2*(fArrowHeight+fScrollbarArrowGap) - fGripHeight);
656
cairo_set_source_rgba (pCairoContext, my_diapo_simple_color_grip[0], my_diapo_simple_color_grip[1], my_diapo_simple_color_grip[2], my_diapo_simple_color_grip[3] * fAlpha);
657
cairo_move_to (pCairoContext, x_arrow - fScrollbarWidth/2 + 1, y_arrow_top + fArrowHeight + fScrollbarArrowGap + ygrip);
658
cairo_rel_line_to (pCairoContext, fScrollbarWidth - 2, 0.);
659
cairo_rel_line_to (pCairoContext, 0., fGripHeight);
660
cairo_rel_line_to (pCairoContext, - (fScrollbarWidth - 2), 0.);
661
cairo_fill (pCairoContext);
663
cairo_restore (pCairoContext);
666
//\____________________ On dessine les icones avec leurs etiquettes.
667
// on determine la 1ere icone a tracer : l'icone suivant l'icone pointee.
668
GList *pFirstDrawnElement = cairo_dock_get_first_drawn_element_linear (pDock->icons);
669
if (pFirstDrawnElement == NULL)
672
//clip pour le scroll
673
if (pData->iDeltaHeight != 0) // on fait un clip pour les icones qui debordent.
675
int h = my_diapo_simple_arrowHeight + ARROW_TIP + my_diapo_simple_lineWidth;
676
if (pDock->container.bIsHorizontal)
678
cairo_rectangle (pCairoContext,
680
(pDock->container.bDirectionUp ? my_diapo_simple_lineWidth : h), // top left corner.
681
pDock->container.iWidth,
682
pDock->container.iHeight - h - my_diapo_simple_lineWidth);
686
cairo_rectangle (pCairoContext,
687
(pDock->container.bDirectionUp ? my_diapo_simple_lineWidth : h), // top left corner.
689
pDock->container.iHeight - h - my_diapo_simple_lineWidth,
690
pDock->container.iWidth);
692
cairo_clip (pCairoContext);
695
// on dessine les icones, l'icone pointee en dernier.
697
GList *ic = pFirstDrawnElement;
701
if (CAIRO_DOCK_ICON_TYPE_IS_SEPARATOR (icon))
703
ic = cairo_dock_get_next_element (ic, pDock->icons);
707
cairo_save (pCairoContext);
708
cairo_dock_render_one_icon (icon, pDock, pCairoContext, 1., FALSE);
709
cairo_restore (pCairoContext);
711
//////////////////////////////////////////////////////////////////////////////////////// On affiche le texte !
713
if(icon->pTextBuffer != NULL && (my_diapo_simple_display_all_labels || icon->bPointed))
715
double fAlpha = (pDock->fFoldingFactor > .5 ? (1 - pDock->fFoldingFactor) / .5 : 1.);
716
cairo_save (pCairoContext);
718
double fOffsetX = -icon->iTextWidth/2 + icon->fWidthFactor * icon->fWidth * icon->fScale / 2;
721
else if (0 + fOffsetX + icon->iTextWidth > pDock->container.iWidth)
722
fOffsetX = pDock->container.iWidth - icon->iTextWidth - 0;
724
if (icon->iTextWidth > icon->fWidth * icon->fScale + my_diapo_simple_iconGapX && ! icon->bPointed)
726
if (pDock->container.bIsHorizontal)
728
cairo_translate (pCairoContext,
729
floor (icon->fDrawX - my_diapo_simple_iconGapX/2),
730
floor (icon->fDrawY - icon->iTextHeight));
734
cairo_translate (pCairoContext,
735
floor (icon->fDrawY - my_diapo_simple_iconGapX/2),
736
floor (icon->fDrawX - icon->iTextHeight));
738
cairo_set_source_surface (pCairoContext,
743
cairo_pattern_t *pGradationPattern = cairo_pattern_create_linear (0.,
745
icon->fWidth * icon->fScale + my_diapo_simple_iconGapX,
747
cairo_pattern_set_extend (pGradationPattern, icon->bPointed ? CAIRO_EXTEND_PAD : CAIRO_EXTEND_NONE);
748
cairo_pattern_add_color_stop_rgba (pGradationPattern,
754
cairo_pattern_add_color_stop_rgba (pGradationPattern,
760
cairo_pattern_add_color_stop_rgba (pGradationPattern,
765
MIN (0.2, fAlpha/2));
766
cairo_mask (pCairoContext, pGradationPattern);
767
cairo_pattern_destroy (pGradationPattern);
769
else // le texte tient dans l'icone.
771
if (pDock->container.bIsHorizontal)
773
fOffsetX = icon->fDrawX + (icon->fWidth * icon->fScale - icon->iTextWidth) / 2;
776
else if (fOffsetX + icon->iTextWidth > pDock->container.iWidth)
777
fOffsetX = pDock->container.iWidth - icon->iTextWidth;
778
cairo_translate (pCairoContext,
780
floor (icon->fDrawY - icon->iTextHeight));
784
fOffsetX = icon->fDrawY + (icon->fWidth * icon->fScale - icon->iTextWidth) / 2;
787
else if (fOffsetX + icon->iTextWidth > pDock->container.iHeight)
788
fOffsetX = pDock->container.iHeight - icon->iTextWidth;
789
cairo_translate (pCairoContext,
791
floor (icon->fDrawX - icon->iTextHeight));
793
cairo_set_source_surface (pCairoContext,
797
cairo_paint_with_alpha (pCairoContext, fAlpha);
799
cairo_restore (pCairoContext);
802
ic = cairo_dock_get_next_element (ic, pDock->icons);
804
while (ic != pFirstDrawnElement);
809
static Icon* _cd_rendering_calculate_icons_for_diapo_simple (CairoDock *pDock, gint nRowsX, gint nRowsY, gint Mx, gint My)
811
CDSlideData *pData = pDock->pRendererData; // non nul
812
double fScrollOffset = (pDock->container.bDirectionUp ? - pData->iScrollOffset : pData->iScrollOffset);
814
// On calcule la position de base pour toutes les icones
816
if (pDock->container.bDirectionUp)
817
iOffsetY = .5 * pDock->iMaxIconHeight * pDock->container.fRatio * (my_diapo_simple_fScaleMax - 1) + // les icones de la 1ere ligne zooment
818
myLabels.iLabelSize + // le texte des icones de la 1ere ligne
819
.5 * my_diapo_simple_lineWidth + // demi-ligne du haut;
822
iOffsetY = .5 * pDock->iMaxIconHeight * pDock->container.fRatio * (my_diapo_simple_fScaleMax - 1) + // les icones de la 1ere ligne zooment
823
.5 * my_diapo_simple_lineWidth + // demi-ligne du bas;
825
double fFoldingX = (pDock->fFoldingFactor > .2 ? (pDock->fFoldingFactor - .2) / .8 : 0.); // placement de 1 a 0.2
826
double fFoldingY = (pDock->fFoldingFactor > .5 ? (pDock->fFoldingFactor - .5) / .5 : 0.); // placement de 1 a 0.5
828
GList* ic, *pointed_ic=NULL;
830
for (ic = pDock->icons; ic != NULL; ic = ic->next)
833
if (CAIRO_DOCK_ICON_TYPE_IS_SEPARATOR (icon))
836
// position sur la grille.
837
_get_gridXY_from_index(nRowsX, i, &x, &y);
839
// on en deduit la position au repos.
840
icon->fX = X_BORDER_SPACE + .5*my_diapo_simple_iconGapX + (icon->fWidth + my_diapo_simple_iconGapX) * x;
841
if (pDock->container.bDirectionUp)
842
icon->fY = iOffsetY + (icon->fHeight + my_diapo_simple_iconGapY) * y;
845
icon->fY = pDock->container.iHeight - iOffsetY - icon->fHeight - (nRowsY - 1 - y) * (icon->fHeight + my_diapo_simple_iconGapY);
848
// on en deduit le zoom par rapport a la position de la souris.
849
gdouble distanceE = sqrt ((icon->fX + icon->fWidth/2 - Mx) * (icon->fX + icon->fWidth/2 - Mx) + (icon->fY + icon->fHeight/2 - My) * (icon->fY + icon->fHeight/2 - My));
850
if (my_diapo_simple_lineaire)
852
gdouble eloignementMax = my_diapo_simple_sinW; // 3. * (icon->fWidth + icon->fHeight) / 2
853
icon->fScale = MAX (1., my_diapo_simple_fScaleMax + (1. - my_diapo_simple_fScaleMax) * distanceE / eloignementMax);
858
icon->fPhase = distanceE * G_PI / my_diapo_simple_sinW + G_PI / 2.;
859
if (icon->fPhase < 0)
861
else if (icon->fPhase > G_PI)
863
icon->fScale = 1. + (my_diapo_simple_fScaleMax - 1.) * sin (icon->fPhase);
866
// on tient compte du zoom (zoom centre).
867
icon->fXMin = icon->fXMax = icon->fXAtRest = // Ca on s'en sert pas encore
868
icon->fDrawX = icon->fX + icon->fWidth * (1. - icon->fScale) / 2;
869
icon->fDrawY = icon->fY + icon->fHeight * (1. - icon->fScale) / 2;
871
// on tient compte du depliage.
872
icon->fDrawX -= (icon->fDrawX - pDock->container.iWidth/2) * fFoldingX;
873
icon->fDrawY = icon->fDrawY + (pDock->container.bDirectionUp ?
874
pDock->container.iHeight - (my_diapo_simple_arrowHeight + ARROW_TIP + icon->fDrawY) :
875
- icon->fDrawY) * fFoldingY;
876
icon->fAlpha = (pDock->fFoldingFactor > .7 ? (1 - pDock->fFoldingFactor) / (1 - .7) : 1.); // apparition de 1 a 0.7
878
// On regarde si l'icone est pointee, si oui elle est un peu plus visible que les autres.
879
if((Mx > icon->fX - .5*my_diapo_simple_iconGapX) &&
880
(My > icon->fY - .5*my_diapo_simple_iconGapY) &&
881
(Mx < icon->fX + icon->fWidth + .5*my_diapo_simple_iconGapX) &&
882
(My < icon->fY + icon->fHeight + .5*my_diapo_simple_iconGapY))
884
icon->bPointed = TRUE;
889
icon->bPointed = FALSE;
892
// On affecte tous les parametres qui n'ont pas été défini précédement
894
icon->fOrientation = 0.; // 2. * G_PI * pDock->fFoldingFactor;
895
icon->fWidthFactor = icon->fHeightFactor = (pDock->fFoldingFactor > .7 ? (1 - pDock->fFoldingFactor) / .3 : 1.);
899
return (pointed_ic == NULL ? NULL : pointed_ic->data);
901
static void _cd_rendering_check_if_mouse_inside_diapo_simple (CairoDock *pDock)
903
if ((pDock->container.iMouseX < 0) || (pDock->container.iMouseX > pDock->iMaxDockWidth - 1) || (pDock->container.iMouseY < 0) || (pDock->container.iMouseY > pDock->iMaxDockHeight - 0))
905
pDock->iMousePositionType = CAIRO_DOCK_MOUSE_OUTSIDE;
907
else // on fait simple.
909
pDock->iMousePositionType = CAIRO_DOCK_MOUSE_INSIDE;
912
static void _cd_rendering_check_can_drop_linear (CairoDock *pDock)
914
pDock->bCanDrop = pDock->bIsDragging; /// calculer bCanDrop ...
916
Icon *cd_rendering_calculate_icons_diapo_simple (CairoDock *pDock)
918
if (pDock->icons == NULL)
920
CDSlideData *pData = pDock->pRendererData;
921
g_return_val_if_fail (pData != NULL, NULL);
923
// On recupere la configuration de la grille
924
gint nRowsX = pData->nRowsX;
925
gint nRowsY = pData->nRowsY;
927
// On calcule les parametres des icones
928
Icon *pPointedIcon = _cd_rendering_calculate_icons_for_diapo_simple (pDock, nRowsX, nRowsY, pDock->container.iMouseX, pDock->container.iMouseY);
930
_cd_rendering_check_if_mouse_inside_diapo_simple (pDock);
932
_cd_rendering_check_can_drop_linear (pDock);
938
#define DELTA_ROUND_DEGREE 5
939
#define _recopy_prev_color(pColorTab, i) memcpy (&pColorTab[4*i], &pColorTab[4*(i-1)], 4*sizeof (GLfloat));
940
#define _copy_color(pColorTab, i, fAlpha, c) do { \
941
pColorTab[4*i] = c[0];\
942
pColorTab[4*i+1] = c[1];\
943
pColorTab[4*i+2] = c[2];\
944
pColorTab[4*i+3] = c[3] * fAlpha; } while (0)
945
/*#define _copy_mean_color(pColorTab, i, fAlpha, c1, c2, f) do { \
946
pColorTab[4*i] = c1[0]*f + c2[0]*(1-f);\
947
pColorTab[4*i+1] = c1[1]*f + c2[1]*(1-f);\
948
pColorTab[4*i+2] = c1[2]*f + c2[2]*(1-f);\
949
pColorTab[4*i+3] = (c1[3]*f + c2[3]*(1-f)) * fAlpha; } while (0)*/
950
static void cd_add_arrow_to_path (CairoDockGLPath *pPath, double fFrameWidth, CDSlideData *pData)
952
int iArrowShift = pData->iArrowShift;
953
int iDeltaIconX = pData->iDeltaIconX;
954
double w = fFrameWidth / 2;
955
double aw = my_diapo_simple_arrowWidth/2;
956
double ah = my_diapo_simple_arrowHeight;
957
/**double xa = my_diapo_simple_arrowShift * (w - aw); // abscisse de l'extremite de la pointe.
958
cairo_dock_gl_path_rel_line_to (pPath, w + xa - aw, 0.); // pointe.
959
cairo_dock_gl_path_rel_line_to (pPath, aw, -ah);
960
cairo_dock_gl_path_rel_line_to (pPath, aw, ah);*/
961
cairo_dock_gl_path_rel_line_to (pPath, w - aw + iArrowShift, 0.); // pointe.
962
cairo_dock_gl_path_rel_line_to (pPath, aw - iArrowShift + iDeltaIconX, -ah);
963
cairo_dock_gl_path_rel_line_to (pPath, aw + iArrowShift - iDeltaIconX, ah);
965
static CairoDockGLPath *cd_generate_frame_path_without_arrow (double fFrameWidth, double fTotalHeight, double fRadius)
967
static CairoDockGLPath *pPath = NULL;
968
double fTotalWidth = fFrameWidth + 2 * fRadius;
969
double fFrameHeight = MAX (0, fTotalHeight - 2 * fRadius);
970
double w = fFrameWidth / 2;
971
double h = fFrameHeight / 2;
974
int iNbPoins1Round = 90/DELTA_ROUND_DEGREE;
976
pPath = cairo_dock_new_gl_path ((iNbPoins1Round+1)*4+1+3, w, -h-r, fTotalWidth, fTotalHeight); // on commence au coin haut droit pour avoir une bonne triangulation du polygone, et en raisonnant par rapport au centre du rectangle.
978
cairo_dock_gl_path_move_to (pPath, w, -h-r);
980
cairo_dock_gl_path_arc (pPath, iNbPoins1Round, w, -h, r, -G_PI/2, +G_PI/2); // coin bas droit.
982
cairo_dock_gl_path_arc (pPath, iNbPoins1Round, w, h, r, 0., +G_PI/2); // coin haut droit.
984
cairo_dock_gl_path_arc (pPath, iNbPoins1Round, -w, h, r, G_PI/2, +G_PI/2); // coin haut gauche.
986
cairo_dock_gl_path_arc (pPath, iNbPoins1Round, -w, -h, r, G_PI, +G_PI/2); // coin bas gauche.
991
static CairoDockGLPath *cd_generate_arrow_path (double fFrameWidth, double fTotalHeight, CDSlideData *pData)
993
static CairoDockGLPath *pPath = NULL;
994
int iArrowShift = pData->iArrowShift;
995
int iDeltaIconX = pData->iDeltaIconX;
996
double w = fFrameWidth / 2;
997
double aw = my_diapo_simple_arrowWidth/2;
998
double ah = my_diapo_simple_arrowHeight;
999
/**double xa = my_diapo_simple_arrowShift * (w - aw); // abscisse de l'extremite de la pointe.
1001
pPath = cairo_dock_new_gl_path (3, xa - aw, -fTotalHeight/2, 0., 0.);
1003
cairo_dock_gl_path_move_to (pPath, xa - aw, -fTotalHeight/2);
1004
cairo_dock_gl_path_rel_line_to (pPath, aw, -ah);
1005
cairo_dock_gl_path_rel_line_to (pPath, aw, ah);*/
1008
pPath = cairo_dock_new_gl_path (3, iArrowShift - aw, -fTotalHeight/2, 0., 0.);
1010
cairo_dock_gl_path_move_to (pPath, iArrowShift - aw, -fTotalHeight/2);
1012
cairo_dock_gl_path_rel_line_to (pPath, aw - iArrowShift + iDeltaIconX, -ah);
1013
cairo_dock_gl_path_rel_line_to (pPath, aw + iArrowShift - iDeltaIconX, ah);
1018
static const GLfloat *cd_generate_color_tab (double fAlpha, GLfloat *pMiddleBottomColor)
1020
static GLfloat *pColorTab = NULL;
1021
int iNbPoins1Round = 90/DELTA_ROUND_DEGREE;
1022
if (pColorTab == NULL)
1023
pColorTab = g_new (GLfloat, ((iNbPoins1Round+1)*4+1) * 4);
1025
double *pTopRightColor, *pTopLeftColor, *pBottomLeftColor, *pBottomRightColor;
1026
double pMeanColor[4] = {(my_diapo_simple_color_frame_start[0] + my_diapo_simple_color_frame_stop[0])/2,
1027
(my_diapo_simple_color_frame_start[1] + my_diapo_simple_color_frame_stop[1])/2,
1028
(my_diapo_simple_color_frame_start[2] + my_diapo_simple_color_frame_stop[2])/2,
1029
(my_diapo_simple_color_frame_start[3] + my_diapo_simple_color_frame_stop[3])/2};
1030
pTopLeftColor = my_diapo_simple_color_frame_start;
1031
if (my_diapo_simple_fade2bottom || my_diapo_simple_fade2right)
1033
pBottomRightColor = my_diapo_simple_color_frame_stop;
1034
if (my_diapo_simple_fade2bottom && my_diapo_simple_fade2right)
1036
pBottomLeftColor = pMeanColor;
1037
pTopRightColor = pMeanColor;
1039
else if (my_diapo_simple_fade2bottom)
1041
pBottomLeftColor = my_diapo_simple_color_frame_stop;
1042
pTopRightColor = my_diapo_simple_color_frame_start;
1046
pBottomLeftColor = my_diapo_simple_color_frame_start;
1047
pTopRightColor = my_diapo_simple_color_frame_stop;
1052
pBottomRightColor = my_diapo_simple_color_frame_start;
1053
pBottomLeftColor = my_diapo_simple_color_frame_start;
1054
pTopRightColor = my_diapo_simple_color_frame_start;
1057
pMiddleBottomColor[0] = (pBottomRightColor[0] + pBottomLeftColor[0])/2;
1058
pMiddleBottomColor[1] = (pBottomRightColor[1] + pBottomLeftColor[1])/2;
1059
pMiddleBottomColor[2] = (pBottomRightColor[2] + pBottomLeftColor[2])/2;
1060
pMiddleBottomColor[3] = (pBottomRightColor[3] + pBottomLeftColor[3])/2;
1063
_copy_color (pColorTab, i, fAlpha, pBottomRightColor);
1066
for (j = 0; j < iNbPoins1Round; j ++, i ++) // coin bas droit.
1068
_copy_color (pColorTab, i, fAlpha, pBottomRightColor);
1071
for (j = 0; j < iNbPoins1Round; j ++, i ++) // coin haut droit.
1073
_copy_color (pColorTab, i, fAlpha, pTopRightColor);
1076
for (j = 0; j < iNbPoins1Round; j ++, i ++) // coin haut gauche.
1078
_copy_color (pColorTab, i, fAlpha, pTopLeftColor);
1081
for (j = 0; j < iNbPoins1Round; j ++, i ++) // coin bas gauche.
1083
_copy_color (pColorTab, i, fAlpha, pBottomLeftColor);
1089
static void cd_rendering_render_diapo_simple_opengl (CairoDock *pDock)
1091
static CairoDockGLPath *pScrollPath = NULL;
1093
//\____________________ On initialise le cadre.
1094
CDSlideData *pData = pDock->pRendererData;
1095
g_return_if_fail (pData != NULL);
1098
GLfloat *pColorTab, *pVertexTab;
1100
double fRadius = my_diapo_simple_radius;
1101
double fFrameWidth = pDock->iMaxDockWidth - 2*X_BORDER_SPACE; // longueur du trait horizontal.
1102
double fFrameHeight = pDock->iMaxDockHeight - (my_diapo_simple_arrowHeight + ARROW_TIP + my_diapo_simple_lineWidth); // hauteur du cadre avec les rayons et sans la pointe.
1103
double fDockOffsetX, fDockOffsetY;
1104
fDockOffsetX = X_BORDER_SPACE;
1105
fDockOffsetY = my_diapo_simple_arrowHeight+ARROW_TIP;
1107
//\_____________ On genere les coordonnees du contour.
1108
CairoDockGLPath *pFramePath = cd_generate_frame_path_without_arrow (fFrameWidth, fFrameHeight, fRadius);
1110
//\_____________ On remplit avec le fond.
1112
double fAlpha = (pDock->fFoldingFactor < .3 ? (.3 - pDock->fFoldingFactor) / .3 : 0.); // apparition du cadre de 0.3 a 0
1113
cairo_dock_set_container_orientation_opengl (CAIRO_CONTAINER (pDock));
1114
glTranslatef (fDockOffsetX + (fFrameWidth)/2,
1115
fDockOffsetY + fFrameHeight/2,
1117
_cairo_dock_set_blend_alpha ();
1119
if (my_diapo_simple_draw_background)
1121
// le cadre sans la pointe.
1122
GLfloat pBottomMiddleColor[4];
1123
const GLfloat *pColorTab = cd_generate_color_tab (fAlpha, pBottomMiddleColor);
1124
glEnableClientState (GL_COLOR_ARRAY);
1125
glColorPointer (4, GL_FLOAT, 0, pColorTab);
1126
cairo_dock_fill_gl_path (pFramePath, 0);
1127
glDisableClientState (GL_COLOR_ARRAY);
1130
CairoDockGLPath *pArrowPath = cd_generate_arrow_path (fFrameWidth, fFrameHeight, pData);
1131
glColor4f (pBottomMiddleColor[0], pBottomMiddleColor[1], pBottomMiddleColor[2], pBottomMiddleColor[3] * fAlpha);
1132
cairo_dock_fill_gl_path (pArrowPath, 0);
1135
//\_____________ On trace le contour.
1136
if (my_diapo_simple_lineWidth != 0 && my_diapo_simple_color_border_line[3] != 0 && fAlpha != 0)
1138
cd_add_arrow_to_path (pFramePath, fFrameWidth, pData);
1139
glLineWidth (my_diapo_simple_lineWidth);
1140
glColor4f (my_diapo_simple_color_border_line[0], my_diapo_simple_color_border_line[1], my_diapo_simple_color_border_line[2], my_diapo_simple_color_border_line[3] * fAlpha);
1141
cairo_dock_stroke_gl_path (pFramePath, TRUE);
1144
_cairo_dock_set_blend_over ();
1146
//\____________________ On dessine les barres de defilement.
1147
if (pData->iDeltaHeight != 0)
1149
if (pScrollPath == NULL)
1150
pScrollPath = cairo_dock_new_gl_path (4, 0., 0., 0, 0); // des triangles ou des rectangles => 4 points max.
1153
if (!pDock->container.bIsHorizontal)
1155
glTranslatef (pDock->container.iHeight/2, pDock->container.iWidth/2, 0.);
1156
glRotatef (-90., 0., 0., 1.);
1157
glScalef (1., -1., 1.); // comme si bDirectionUp
1158
glTranslatef (-pDock->container.iWidth/2, -pDock->container.iHeight/2, 0.);
1160
double x_arrow = pDock->iMaxDockWidth - X_BORDER_SPACE - fScrollbarWidth/2; // pointe de la fleche.
1161
double y_arrow_top, y_arrow_bottom;
1162
if (pDock->container.bDirectionUp)
1164
y_arrow_bottom = my_diapo_simple_arrowHeight + ARROW_TIP + my_diapo_simple_lineWidth;
1165
y_arrow_top = pDock->iMaxDockHeight - my_diapo_simple_lineWidth;
1169
y_arrow_top = pDock->iMaxDockHeight - (my_diapo_simple_arrowHeight + ARROW_TIP + my_diapo_simple_lineWidth);
1170
y_arrow_bottom = my_diapo_simple_lineWidth;
1172
if (pData->iScrollOffset != 0) // fleche vers le haut.
1174
cairo_dock_gl_path_move_to (pScrollPath, x_arrow, y_arrow_top);
1175
cairo_dock_gl_path_rel_line_to (pScrollPath, fScrollbarWidth/2, -fArrowHeight);
1176
cairo_dock_gl_path_rel_line_to (pScrollPath, -fScrollbarWidth, 0.);
1178
glColor4f (my_diapo_simple_color_scrollbar_inside[0], my_diapo_simple_color_scrollbar_inside[1], my_diapo_simple_color_scrollbar_inside[2], my_diapo_simple_color_scrollbar_inside[3] * fAlpha);
1179
cairo_dock_fill_gl_path (pScrollPath, 0);
1181
glColor4f (my_diapo_simple_color_scrollbar_line[0], my_diapo_simple_color_scrollbar_line[1], my_diapo_simple_color_scrollbar_line[2], my_diapo_simple_color_scrollbar_line[3] * fAlpha);
1182
cairo_dock_stroke_gl_path (pScrollPath, TRUE); // TRUE <=> close
1184
if (pData->iScrollOffset != pData->iDeltaHeight) // fleche vers le bas.
1186
cairo_dock_gl_path_move_to (pScrollPath, x_arrow, y_arrow_bottom);
1187
cairo_dock_gl_path_rel_line_to (pScrollPath, fScrollbarWidth/2, fArrowHeight);
1188
cairo_dock_gl_path_rel_line_to (pScrollPath, -fScrollbarWidth, 0.);
1190
glColor4f (my_diapo_simple_color_scrollbar_inside[0], my_diapo_simple_color_scrollbar_inside[1], my_diapo_simple_color_scrollbar_inside[2], my_diapo_simple_color_scrollbar_inside[3] * fAlpha);
1191
cairo_dock_fill_gl_path (pScrollPath, 0);
1193
glColor4f (my_diapo_simple_color_scrollbar_line[0], my_diapo_simple_color_scrollbar_line[1], my_diapo_simple_color_scrollbar_line[2], my_diapo_simple_color_scrollbar_line[3] * fAlpha);
1194
cairo_dock_stroke_gl_path (pScrollPath, TRUE); // TRUE <=> close
1197
// scrollbar outline
1198
cairo_dock_gl_path_move_to (pScrollPath, x_arrow - fScrollbarWidth/2, y_arrow_bottom + fArrowHeight + fScrollbarArrowGap);
1199
cairo_dock_gl_path_rel_line_to (pScrollPath, fScrollbarWidth, 0.);
1200
cairo_dock_gl_path_rel_line_to (pScrollPath, 0., y_arrow_top - y_arrow_bottom - 2*(fArrowHeight+fScrollbarArrowGap));
1201
cairo_dock_gl_path_rel_line_to (pScrollPath, -fScrollbarWidth, 0.);
1203
glColor4f (my_diapo_simple_color_scrollbar_inside[0], my_diapo_simple_color_scrollbar_inside[1], my_diapo_simple_color_scrollbar_inside[2], my_diapo_simple_color_scrollbar_inside[3] * fAlpha);
1204
cairo_dock_fill_gl_path (pScrollPath, 0);
1206
glColor4f (my_diapo_simple_color_scrollbar_line[0], my_diapo_simple_color_scrollbar_line[1], my_diapo_simple_color_scrollbar_line[2], my_diapo_simple_color_scrollbar_line[3] * fAlpha);
1207
cairo_dock_stroke_gl_path (pScrollPath, TRUE);
1210
double fGripHeight = fFrameHeight / (fFrameHeight + pData->iDeltaHeight) * (y_arrow_top - y_arrow_bottom - 2*(fArrowHeight+fScrollbarArrowGap));
1211
double ygrip = (double) pData->iScrollOffset / pData->iDeltaHeight * (y_arrow_top - y_arrow_bottom - 2*(fArrowHeight+fScrollbarArrowGap) - fGripHeight);
1212
glColor4f (my_diapo_simple_color_grip[0], my_diapo_simple_color_grip[1], my_diapo_simple_color_grip[2], my_diapo_simple_color_grip[3] * fAlpha);
1213
cairo_dock_gl_path_move_to (pScrollPath, x_arrow - fScrollbarWidth/2, y_arrow_top - (fArrowHeight+fScrollbarArrowGap) - ygrip);
1214
cairo_dock_gl_path_rel_line_to (pScrollPath, fScrollbarWidth, 0.);
1215
cairo_dock_gl_path_rel_line_to (pScrollPath, 0., - fGripHeight);
1216
cairo_dock_gl_path_rel_line_to (pScrollPath, -fScrollbarWidth, 0.);
1217
cairo_dock_fill_gl_path (pScrollPath, 0);
1221
if (pDock->icons == NULL)
1224
//\____________________ On dessine la ficelle.
1225
if (myIcons.iStringLineWidth > 0)
1226
cairo_dock_draw_string_opengl (pDock, myIcons.iStringLineWidth, FALSE, FALSE);
1228
//\____________________ On dessine les icones.
1229
// on determine la 1ere icone a tracer : l'icone suivant l'icone pointee.
1230
GList *pFirstDrawnElement = cairo_dock_get_first_drawn_element_linear (pDock->icons);
1231
if (pFirstDrawnElement == NULL)
1234
// on dessine les icones, l'icone pointee en dernier.
1235
if (pData->iDeltaHeight != 0) // on fait un clip pour les icones qui debordent.
1237
int h = my_diapo_simple_arrowHeight + ARROW_TIP + my_diapo_simple_lineWidth;
1238
glEnable (GL_SCISSOR_TEST);
1239
if (pDock->container.bIsHorizontal)
1242
(pDock->container.bDirectionUp ? h : my_diapo_simple_lineWidth), // lower left corner of the scissor box.
1243
pDock->container.iWidth,
1244
pDock->container.iHeight - h - my_diapo_simple_lineWidth);
1248
glScissor ((!pDock->container.bDirectionUp ? h : my_diapo_simple_lineWidth), // lower left corner of the scissor box.
1249
my_diapo_simple_lineWidth,
1250
pDock->container.iHeight - h - my_diapo_simple_lineWidth,
1251
pDock->container.iWidth);
1256
GList *ic = pFirstDrawnElement;
1260
if (CAIRO_DOCK_ICON_TYPE_IS_SEPARATOR (icon))
1262
ic = cairo_dock_get_next_element (ic, pDock->icons);
1266
cairo_dock_render_one_icon_opengl (icon, pDock, 1., FALSE);
1268
if (icon->iLabelTexture != 0 && (my_diapo_simple_display_all_labels || icon->bPointed))
1272
double fAlpha = (pDock->fFoldingFactor > .5 ? (1 - pDock->fFoldingFactor) / .5 : 1.); // apparition du texte de 1 a 0.5
1274
double dx = .5 * (icon->iTextWidth & 1); // on decale la texture pour la coller sur la grille des coordonnees entieres.
1275
double dy = .5 * (icon->iTextHeight & 1);
1276
double u0 = 0., u1 = 1.;
1277
double fOffsetX = 0.;
1278
if (pDock->container.bIsHorizontal)
1282
_cairo_dock_set_alpha (fAlpha);
1283
if (icon->fDrawX + icon->fWidth/2 + icon->iTextWidth/2 > pDock->container.iWidth)
1284
fOffsetX = pDock->container.iWidth - (icon->fDrawX + icon->fWidth/2 + icon->iTextWidth/2);
1285
if (icon->fDrawX + icon->fWidth/2 - icon->iTextWidth/2 < 0)
1286
fOffsetX = icon->iTextWidth/2 - (icon->fDrawX + icon->fWidth/2);
1290
_cairo_dock_set_alpha (fAlpha * icon->fScale / my_diapo_simple_fScaleMax);
1291
if (icon->iTextWidth > icon->fWidth + 2 * myLabels.iLabelSize)
1294
u1 = (double) (icon->fWidth + 2 * myLabels.iLabelSize) / icon->iTextWidth;
1298
glTranslatef (ceil (icon->fDrawX + icon->fScale * icon->fWidth/2 + fOffsetX) + dx,
1299
ceil (pDock->container.iHeight - icon->fDrawY + icon->iTextHeight / 2) + dy,
1306
_cairo_dock_set_alpha (fAlpha);
1307
if (icon->fDrawY + icon->fHeight/2 + icon->iTextWidth/2 > pDock->container.iHeight)
1308
fOffsetX = pDock->container.iHeight - (icon->fDrawY + icon->fHeight/2 + icon->iTextWidth/2);
1309
if (icon->fDrawY + icon->fHeight/2 - icon->iTextWidth/2 < 0)
1310
fOffsetX = icon->iTextWidth/2 - (icon->fDrawY + icon->fHeight/2);
1314
_cairo_dock_set_alpha (fAlpha * icon->fScale / my_diapo_simple_fScaleMax);
1315
if (icon->iTextWidth > icon->fWidth + 2 * myLabels.iLabelSize)
1318
u1 = (double) (icon->fWidth + 2 * myLabels.iLabelSize) / icon->iTextWidth;
1322
glTranslatef (ceil (icon->fDrawY + icon->fScale * icon->fHeight/2 + fOffsetX / 2) + dx,
1323
ceil (pDock->container.iWidth - icon->fDrawX + icon->iTextHeight / 2) + dy,
1326
_cairo_dock_enable_texture ();
1327
_cairo_dock_set_blend_alpha ();
1328
glBindTexture (GL_TEXTURE_2D, icon->iLabelTexture);
1329
_cairo_dock_apply_current_texture_portion_at_size_with_offset (u0, 0.,
1331
icon->iTextWidth * (u1 - u0), icon->iTextHeight,
1333
_cairo_dock_disable_texture ();
1334
_cairo_dock_set_alpha (1.);
1339
ic = cairo_dock_get_next_element (ic, pDock->icons);
1341
while (ic != pFirstDrawnElement);
1342
glDisable (GL_SCISSOR_TEST);
1346
void cd_rendering_free_slide_data (CairoDock *pDock)
1348
CDSlideData *pData = pDock->pRendererData;
1351
cairo_dock_remove_notification_func_on_object (CAIRO_CONTAINER (pDock), CAIRO_DOCK_SCROLL_ICON, (CairoDockNotificationFunc) _cd_slide_on_scroll, NULL);
1352
cairo_dock_remove_notification_func_on_object (CAIRO_CONTAINER (pDock), CAIRO_DOCK_CLICK_ICON, (CairoDockNotificationFunc) _cd_slide_on_click, NULL);
1353
cairo_dock_remove_notification_func_on_object (CAIRO_CONTAINER (pDock), CAIRO_DOCK_MOUSE_MOVED, (CairoDockNotificationFunc) _cd_slide_on_mouse_moved, NULL);
1354
g_signal_handler_disconnect (pDock->container.pWidget, pData->iSidPressEvent);
1355
g_signal_handler_disconnect (pDock->container.pWidget, pData->iSidReleaseEvent);
1358
pDock->pRendererData = NULL;
1362
void cd_rendering_set_subdock_position_slide (Icon *pPointedIcon, CairoDock *pDock)
1364
CairoDock *pSubDock = pPointedIcon->pSubDock;
1366
CDSlideData *pData = pSubDock->pRendererData;
1367
g_return_if_fail (pData != NULL);
1369
int iX = pPointedIcon->fXAtRest - (pDock->fFlatDockWidth - pDock->iMaxDockWidth) / 2 + pPointedIcon->fWidth / 2 + (pDock->iOffsetForExtend * (pDock->fAlign - .5) * 2);
1370
if (pSubDock->container.bIsHorizontal == pDock->container.bIsHorizontal)
1372
pSubDock->fAlign = 0.5;
1373
pSubDock->iGapX = iX + pDock->container.iWindowPositionX - (pDock->container.bIsHorizontal ? pDock->iScreenOffsetX : pDock->iScreenOffsetY) - g_desktopGeometry.iScreenWidth[pDock->container.bIsHorizontal] / 2; // ici les sous-dock ont un alignement egal a 0.5
1374
pSubDock->iGapY = pDock->iGapY + pDock->iMaxDockHeight;
1378
pSubDock->fAlign = (pDock->container.bDirectionUp ? 1 : 0);
1379
pSubDock->iGapX = (pDock->iGapY + pDock->iMaxDockHeight) * (pDock->container.bDirectionUp ? -1 : 1);
1380
if (pDock->container.bDirectionUp)
1381
pSubDock->iGapY = g_desktopGeometry.iScreenWidth[pDock->container.bIsHorizontal] - (iX + pDock->container.iWindowPositionX - (pDock->container.bIsHorizontal ? pDock->iScreenOffsetX : pDock->iScreenOffsetY)) - pSubDock->iMaxDockHeight / 2; // les sous-dock ont un alignement egal a 1.
1383
pSubDock->iGapY = iX + pDock->container.iWindowPositionX - pSubDock->iMaxDockHeight / 2; // les sous-dock ont un alignement egal a 0.
1386
pData->iDeltaIconX = MIN (0, iX + pDock->container.iWindowPositionX - pSubDock->iMaxDockWidth/2);
1387
if (pData->iDeltaIconX == 0)
1388
pData->iDeltaIconX = MAX (0, iX + pDock->container.iWindowPositionX + pSubDock->iMaxDockWidth/2 - g_desktopGeometry.iScreenWidth[pDock->container.bIsHorizontal]);
1389
//g_print ("iDeltaIconX: %d\n", pData->iDeltaIconX);
1391
if (pData->iDeltaIconX != 0) // il y'a un decalage, on va limiter la pente du cote le plus court de la pointe a 30 degres.
1393
pData->iArrowShift = MAX (0, fabs (pData->iDeltaIconX) - my_diapo_simple_arrowHeight * .577 - my_diapo_simple_arrowWidth/2); // tan(30)
1394
if (pData->iDeltaIconX < 0)
1395
pData->iArrowShift = - pData->iArrowShift;
1396
//g_print ("iArrowShift: %d\n", pData->iArrowShift);
1399
pData->iArrowShift = 0;
1402
void cd_rendering_register_diapo_simple_renderer (const gchar *cRendererName)
1404
CairoDockRenderer *pRenderer = g_new0 (CairoDockRenderer, 1);
1406
pRenderer->compute_size = cd_rendering_calculate_max_dock_size_diapo_simple;
1407
pRenderer->calculate_icons = cd_rendering_calculate_icons_diapo_simple;
1408
pRenderer->render = cd_rendering_render_diapo_simple;
1409
pRenderer->render_optimized = NULL;
1410
pRenderer->render_opengl = cd_rendering_render_diapo_simple_opengl;
1411
pRenderer->free_data = cd_rendering_free_slide_data;
1412
pRenderer->set_subdock_position = cd_rendering_set_subdock_position_slide;
1414
pRenderer->cReadmeFilePath = g_strdup (MY_APPLET_SHARE_DATA_DIR"/readme-diapo-simple-view");
1415
pRenderer->cPreviewFilePath = g_strdup (MY_APPLET_SHARE_DATA_DIR"/preview-diapo-simple.jpg");
1416
pRenderer->bUseReflect = FALSE; // pas de reflections
1417
pRenderer->cDisplayedName = D_(cRendererName);
1419
cairo_dock_register_renderer (cRendererName, pRenderer);