1 /* 2 * This file is part of gtkD. 3 * 4 * gtkD is free software; you can redistribute it and/or modify 5 * it under the terms of the GNU Lesser General Public License 6 * as published by the Free Software Foundation; either version 3 7 * of the License, or (at your option) any later version, with 8 * some exceptions, please read the COPYING file. 9 * 10 * gtkD is distributed in the hope that it will be useful, 11 * but WITHOUT ANY WARRANTY; without even the implied warranty of 12 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 13 * GNU Lesser General Public License for more details. 14 * 15 * You should have received a copy of the GNU Lesser General Public License 16 * along with gtkD; if not, write to the Free Software 17 * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110, USA 18 */ 19 20 // generated automatically - do not change 21 // find conversion definition on APILookup.txt 22 // implement new conversion functionalities on the wrap.utils pakage 23 24 25 module gdk.FrameClock; 26 27 private import gdk.FrameTimings; 28 private import gobject.ObjectG; 29 private import gobject.Signals; 30 private import gtkc.gdk; 31 public import gtkc.gdktypes; 32 33 34 /** 35 * A #GdkFrameClock tells the application when to update and repaint a 36 * window. This may be synced to the vertical refresh rate of the 37 * monitor, for example. Even when the frame clock uses a simple timer 38 * rather than a hardware-based vertical sync, the frame clock helps 39 * because it ensures everything paints at the same time (reducing the 40 * total number of frames). The frame clock can also automatically 41 * stop painting when it knows the frames will not be visible, or 42 * scale back animation framerates. 43 * 44 * #GdkFrameClock is designed to be compatible with an OpenGL-based 45 * implementation or with mozRequestAnimationFrame in Firefox, 46 * for example. 47 * 48 * A frame clock is idle until someone requests a frame with 49 * gdk_frame_clock_request_phase(). At some later point that makes 50 * sense for the synchronization being implemented, the clock will 51 * process a frame and emit signals for each phase that has been 52 * requested. (See the signals of the #GdkFrameClock class for 53 * documentation of the phases. %GDK_FRAME_CLOCK_PHASE_UPDATE and the 54 * #GdkFrameClock::update signal are most interesting for application 55 * writers, and are used to update the animations, using the frame time 56 * given by gdk_frame_clock_get_frame_time(). 57 * 58 * The frame time is reported in microseconds and generally in the same 59 * timescale as g_get_monotonic_time(), however, it is not the same 60 * as g_get_monotonic_time(). The frame time does not advance during 61 * the time a frame is being painted, and outside of a frame, an attempt 62 * is made so that all calls to gdk_frame_clock_get_frame_time() that 63 * are called at a “similar” time get the same value. This means that 64 * if different animations are timed by looking at the difference in 65 * time between an initial value from gdk_frame_clock_get_frame_time() 66 * and the value inside the #GdkFrameClock::update signal of the clock, 67 * they will stay exactly synchronized. 68 */ 69 public class FrameClock : ObjectG 70 { 71 /** the main Gtk struct */ 72 protected GdkFrameClock* gdkFrameClock; 73 74 /** Get the main Gtk struct */ 75 public GdkFrameClock* getFrameClockStruct() 76 { 77 return gdkFrameClock; 78 } 79 80 /** the main Gtk struct as a void* */ 81 protected override void* getStruct() 82 { 83 return cast(void*)gdkFrameClock; 84 } 85 86 protected override void setStruct(GObject* obj) 87 { 88 gdkFrameClock = cast(GdkFrameClock*)obj; 89 super.setStruct(obj); 90 } 91 92 /** 93 * Sets our main struct and passes it to the parent class. 94 */ 95 public this (GdkFrameClock* gdkFrameClock, bool ownedRef = false) 96 { 97 this.gdkFrameClock = gdkFrameClock; 98 super(cast(GObject*)gdkFrameClock, ownedRef); 99 } 100 101 102 /** */ 103 public static GType getType() 104 { 105 return gdk_frame_clock_get_type(); 106 } 107 108 /** 109 * Starts updates for an animation. Until a matching call to 110 * gdk_frame_clock_end_updating() is made, the frame clock will continually 111 * request a new frame with the %GDK_FRAME_CLOCK_PHASE_UPDATE phase. 112 * This function may be called multiple times and frames will be 113 * requested until gdk_frame_clock_end_updating() is called the same 114 * number of times. 115 * 116 * Since: 3.8 117 */ 118 public void beginUpdating() 119 { 120 gdk_frame_clock_begin_updating(gdkFrameClock); 121 } 122 123 /** 124 * Stops updates for an animation. See the documentation for 125 * gdk_frame_clock_begin_updating(). 126 * 127 * Since: 3.8 128 */ 129 public void endUpdating() 130 { 131 gdk_frame_clock_end_updating(gdkFrameClock); 132 } 133 134 /** 135 * Gets the frame timings for the current frame. 136 * 137 * Return: the #GdkFrameTimings for the frame currently 138 * being processed, or even no frame is being processed, for the 139 * previous frame. Before any frames have been procesed, returns 140 * %NULL. 141 * 142 * Since: 3.8 143 */ 144 public FrameTimings getCurrentTimings() 145 { 146 auto p = gdk_frame_clock_get_current_timings(gdkFrameClock); 147 148 if(p is null) 149 { 150 return null; 151 } 152 153 return ObjectG.getDObject!(FrameTimings)(cast(GdkFrameTimings*) p, true); 154 } 155 156 /** 157 * A #GdkFrameClock maintains a 64-bit counter that increments for 158 * each frame drawn. 159 * 160 * Return: inside frame processing, the value of the frame counter 161 * for the current frame. Outside of frame processing, the frame 162 * counter for the last frame. 163 * 164 * Since: 3.8 165 */ 166 public long getFrameCounter() 167 { 168 return gdk_frame_clock_get_frame_counter(gdkFrameClock); 169 } 170 171 /** 172 * Gets the time that should currently be used for animations. Inside 173 * the processing of a frame, it’s the time used to compute the 174 * animation position of everything in a frame. Outside of a frame, it's 175 * the time of the conceptual “previous frame,” which may be either 176 * the actual previous frame time, or if that’s too old, an updated 177 * time. 178 * 179 * Return: a timestamp in microseconds, in the timescale of 180 * of g_get_monotonic_time(). 181 * 182 * Since: 3.8 183 */ 184 public long getFrameTime() 185 { 186 return gdk_frame_clock_get_frame_time(gdkFrameClock); 187 } 188 189 /** 190 * #GdkFrameClock internally keeps a history of #GdkFrameTimings 191 * objects for recent frames that can be retrieved with 192 * gdk_frame_clock_get_timings(). The set of stored frames 193 * is the set from the counter values given by 194 * gdk_frame_clock_get_history_start() and 195 * gdk_frame_clock_get_frame_counter(), inclusive. 196 * 197 * Return: the frame counter value for the oldest frame 198 * that is available in the internal frame history of the 199 * #GdkFrameClock. 200 * 201 * Since: 3.8 202 */ 203 public long getHistoryStart() 204 { 205 return gdk_frame_clock_get_history_start(gdkFrameClock); 206 } 207 208 /** 209 * Using the frame history stored in the frame clock, finds the last 210 * known presentation time and refresh interval, and assuming that 211 * presentation times are separated by the refresh interval, 212 * predicts a presentation time that is a multiple of the refresh 213 * interval after the last presentation time, and later than @base_time. 214 * 215 * Params: 216 * baseTime = base time for determining a presentaton time 217 * refreshIntervalReturn = a location to store the determined refresh 218 * interval, or %NULL. A default refresh interval of 1/60th of 219 * a second will be stored if no history is present. 220 * presentationTimeReturn = a location to store the next 221 * candidate presentation time after the given base time. 222 * 0 will be will be stored if no history is present. 223 * 224 * Since: 3.8 225 */ 226 public void getRefreshInfo(long baseTime, long* refreshIntervalReturn, long* presentationTimeReturn) 227 { 228 gdk_frame_clock_get_refresh_info(gdkFrameClock, baseTime, refreshIntervalReturn, presentationTimeReturn); 229 } 230 231 /** 232 * Retrieves a #GdkFrameTimings object holding timing information 233 * for the current frame or a recent frame. The #GdkFrameTimings 234 * object may not yet be complete: see gdk_frame_timings_get_complete(). 235 * 236 * Params: 237 * frameCounter = the frame counter value identifying the frame to 238 * be received. 239 * 240 * Return: the #GdkFrameTimings object for the specified 241 * frame, or %NULL if it is not available. See 242 * gdk_frame_clock_get_history_start(). 243 * 244 * Since: 3.8 245 */ 246 public FrameTimings getTimings(long frameCounter) 247 { 248 auto p = gdk_frame_clock_get_timings(gdkFrameClock, frameCounter); 249 250 if(p is null) 251 { 252 return null; 253 } 254 255 return ObjectG.getDObject!(FrameTimings)(cast(GdkFrameTimings*) p, true); 256 } 257 258 /** 259 * Asks the frame clock to run a particular phase. The signal 260 * corresponding the requested phase will be emitted the next 261 * time the frame clock processes. Multiple calls to 262 * gdk_frame_clock_request_phase() will be combined together 263 * and only one frame processed. If you are displaying animated 264 * content and want to continually request the 265 * %GDK_FRAME_CLOCK_PHASE_UPDATE phase for a period of time, 266 * you should use gdk_frame_clock_begin_updating() instead, since 267 * this allows GTK+ to adjust system parameters to get maximally 268 * smooth animations. 269 * 270 * Params: 271 * phase = the phase that is requested 272 * 273 * Since: 3.8 274 */ 275 public void requestPhase(GdkFrameClockPhase phase) 276 { 277 gdk_frame_clock_request_phase(gdkFrameClock, phase); 278 } 279 280 int[string] connectedSignals; 281 282 void delegate(FrameClock)[] onAfterPaintListeners; 283 /** 284 * This signal ends processing of the frame. Applications 285 * should generally not handle this signal. 286 */ 287 void addOnAfterPaint(void delegate(FrameClock) dlg, ConnectFlags connectFlags=cast(ConnectFlags)0) 288 { 289 if ( "after-paint" !in connectedSignals ) 290 { 291 Signals.connectData( 292 this, 293 "after-paint", 294 cast(GCallback)&callBackAfterPaint, 295 cast(void*)this, 296 null, 297 connectFlags); 298 connectedSignals["after-paint"] = 1; 299 } 300 onAfterPaintListeners ~= dlg; 301 } 302 extern(C) static void callBackAfterPaint(GdkFrameClock* frameclockStruct, FrameClock _frameclock) 303 { 304 foreach ( void delegate(FrameClock) dlg; _frameclock.onAfterPaintListeners ) 305 { 306 dlg(_frameclock); 307 } 308 } 309 310 void delegate(FrameClock)[] onBeforePaintListeners; 311 /** 312 * This signal begins processing of the frame. Applications 313 * should generally not handle this signal. 314 */ 315 void addOnBeforePaint(void delegate(FrameClock) dlg, ConnectFlags connectFlags=cast(ConnectFlags)0) 316 { 317 if ( "before-paint" !in connectedSignals ) 318 { 319 Signals.connectData( 320 this, 321 "before-paint", 322 cast(GCallback)&callBackBeforePaint, 323 cast(void*)this, 324 null, 325 connectFlags); 326 connectedSignals["before-paint"] = 1; 327 } 328 onBeforePaintListeners ~= dlg; 329 } 330 extern(C) static void callBackBeforePaint(GdkFrameClock* frameclockStruct, FrameClock _frameclock) 331 { 332 foreach ( void delegate(FrameClock) dlg; _frameclock.onBeforePaintListeners ) 333 { 334 dlg(_frameclock); 335 } 336 } 337 338 void delegate(FrameClock)[] onFlushEventsListeners; 339 /** 340 * This signal is used to flush pending motion events that 341 * are being batched up and compressed together. Applications 342 * should not handle this signal. 343 */ 344 void addOnFlushEvents(void delegate(FrameClock) dlg, ConnectFlags connectFlags=cast(ConnectFlags)0) 345 { 346 if ( "flush-events" !in connectedSignals ) 347 { 348 Signals.connectData( 349 this, 350 "flush-events", 351 cast(GCallback)&callBackFlushEvents, 352 cast(void*)this, 353 null, 354 connectFlags); 355 connectedSignals["flush-events"] = 1; 356 } 357 onFlushEventsListeners ~= dlg; 358 } 359 extern(C) static void callBackFlushEvents(GdkFrameClock* frameclockStruct, FrameClock _frameclock) 360 { 361 foreach ( void delegate(FrameClock) dlg; _frameclock.onFlushEventsListeners ) 362 { 363 dlg(_frameclock); 364 } 365 } 366 367 void delegate(FrameClock)[] onLayoutListeners; 368 /** 369 * This signal is emitted as the second step of toolkit and 370 * application processing of the frame. Any work to update 371 * sizes and positions of application elements should be 372 * performed. GTK+ normally handles this internally. 373 */ 374 void addOnLayout(void delegate(FrameClock) dlg, ConnectFlags connectFlags=cast(ConnectFlags)0) 375 { 376 if ( "layout" !in connectedSignals ) 377 { 378 Signals.connectData( 379 this, 380 "layout", 381 cast(GCallback)&callBackLayout, 382 cast(void*)this, 383 null, 384 connectFlags); 385 connectedSignals["layout"] = 1; 386 } 387 onLayoutListeners ~= dlg; 388 } 389 extern(C) static void callBackLayout(GdkFrameClock* frameclockStruct, FrameClock _frameclock) 390 { 391 foreach ( void delegate(FrameClock) dlg; _frameclock.onLayoutListeners ) 392 { 393 dlg(_frameclock); 394 } 395 } 396 397 void delegate(FrameClock)[] onPaintListeners; 398 /** 399 * This signal is emitted as the third step of toolkit and 400 * application processing of the frame. The frame is 401 * repainted. GDK normally handles this internally and 402 * produces expose events, which are turned into GTK+ 403 * #GtkWidget::draw signals. 404 */ 405 void addOnPaint(void delegate(FrameClock) dlg, ConnectFlags connectFlags=cast(ConnectFlags)0) 406 { 407 if ( "paint" !in connectedSignals ) 408 { 409 Signals.connectData( 410 this, 411 "paint", 412 cast(GCallback)&callBackPaint, 413 cast(void*)this, 414 null, 415 connectFlags); 416 connectedSignals["paint"] = 1; 417 } 418 onPaintListeners ~= dlg; 419 } 420 extern(C) static void callBackPaint(GdkFrameClock* frameclockStruct, FrameClock _frameclock) 421 { 422 foreach ( void delegate(FrameClock) dlg; _frameclock.onPaintListeners ) 423 { 424 dlg(_frameclock); 425 } 426 } 427 428 void delegate(FrameClock)[] onResumeEventsListeners; 429 /** 430 * This signal is emitted after processing of the frame is 431 * finished, and is handled internally by GTK+ to resume normal 432 * event processing. Applications should not handle this signal. 433 */ 434 void addOnResumeEvents(void delegate(FrameClock) dlg, ConnectFlags connectFlags=cast(ConnectFlags)0) 435 { 436 if ( "resume-events" !in connectedSignals ) 437 { 438 Signals.connectData( 439 this, 440 "resume-events", 441 cast(GCallback)&callBackResumeEvents, 442 cast(void*)this, 443 null, 444 connectFlags); 445 connectedSignals["resume-events"] = 1; 446 } 447 onResumeEventsListeners ~= dlg; 448 } 449 extern(C) static void callBackResumeEvents(GdkFrameClock* frameclockStruct, FrameClock _frameclock) 450 { 451 foreach ( void delegate(FrameClock) dlg; _frameclock.onResumeEventsListeners ) 452 { 453 dlg(_frameclock); 454 } 455 } 456 457 void delegate(FrameClock)[] onUpdateListeners; 458 /** 459 * This signal is emitted as the first step of toolkit and 460 * application processing of the frame. Animations should 461 * be updated using gdk_frame_clock_get_frame_time(). 462 * Applications can connect directly to this signal, or 463 * use gtk_widget_add_tick_callback() as a more convenient 464 * interface. 465 */ 466 void addOnUpdate(void delegate(FrameClock) dlg, ConnectFlags connectFlags=cast(ConnectFlags)0) 467 { 468 if ( "update" !in connectedSignals ) 469 { 470 Signals.connectData( 471 this, 472 "update", 473 cast(GCallback)&callBackUpdate, 474 cast(void*)this, 475 null, 476 connectFlags); 477 connectedSignals["update"] = 1; 478 } 479 onUpdateListeners ~= dlg; 480 } 481 extern(C) static void callBackUpdate(GdkFrameClock* frameclockStruct, FrameClock _frameclock) 482 { 483 foreach ( void delegate(FrameClock) dlg; _frameclock.onUpdateListeners ) 484 { 485 dlg(_frameclock); 486 } 487 } 488 }