Wtx ~ Wt Extension Library
WtxLib
Application Tic

If you want to have an external timer run on the application to give the application a 'tic' that can be used to stimulate automatic actions within the web page, there are a few methods.

One method is to install a WTimer somewhere within the application and use it to drive signal events. The difficulty, however, with these timers is that they place a load on both the web-browser and the network connection as the WTimer is actually running within the web-browser, and must send events back to the server through the network. This can generate oddities in the UI experience.

Another method is to fire a separate thread that imposes a simple delay and then calls-back in to the application to stimulate timer 'tic' events.

Difference between thread timer and browser timer
Timer in Thread Timer in Browser Button in Browser
--------------- ---------------- -----------------
thread Browser Browser
Timer (sleep) Timer (sleep) Button (click)
App (wake) Network Network
event() Internet Internet
Network Network
Service Service
App (wake) App (wake)
event() event()
190 std::thread thread( Rtm::AppBase::tic_handler, this );
191 thread.detach();
192
193 } // endvoid Rtm::AppBase::init( )
194
195 void Rtm::AppBase::tic_handler( Rtm::AppBase * app ) // this is a static function
196 {
197 /*
198 ** If there is no app-pointer, then quit.
199 **
200 */
201 if( !app )
202 return;
203
204 /*
205 ** This task just runs forever, sleeping for a bit, and then
206 ** waking the app.
207 **
208 */
209 while( true )
210 {
211 /*
212 ** Sleep this thread for just one second
213 ** before doing anything
214 **
215 */
216 std::this_thread::sleep_for( std::chrono::seconds(1) );
217
218 /*
219 ** If the application has already quit, then there's nothing to do.
220 **
221 */
222 if( app-> hasQuit() )
223 return;
224
225 /*
226 ** Acquire an application lock. If the application is busy handling
227 ** some user interaction, this call will block until that other
228 ** task has completed.
229 **
230 */
231 Wt::WApplication::UpdateLock lock( app );
232
233 /*
234 ** If we could not get a lock, then quit. If we could not get a lock,
235 ** then it sort of implies that the application was being destroyed.
236 ** In that case, we don't want to do anything more anyhow, so we just
237 ** quit.
238 **
239 */
240 if( !lock )
241 return;
242
243 /*
244 ** Make the tic happen
245 **
246 */
247 app-> tic();
248
249 /*
250 ** After everything has fired, trigger an update.
251 **
252 */
253 app-> triggerUpdate();
254
255 } // endwhile( true )
256
257 } // endvoid Rtm::AppBase::tic_handler( Rtm::AppBase * app )
258
2024 void AdminWidget::hold_me()
2025 {
2026 for( int i = 0; i < 10; i++ )
2027 {
2028 std::cout << __FILE__ << ":" << __LINE__ << " holding... " << i << std::endl;
2029
2030 std::this_thread::sleep_for( std::chrono::seconds(1) );
2031 }
2032
2033 std::cout << __FILE__ << ":" << __LINE__ << " held." << std::endl;
2034
2035 }
2036
AppBase.cpp:198 0
[2020-Jul-08 08:45:25.400] AppBase.cpp:298 logs/Admin(1)/2020-07-08.log Admin(1) buildSite logon ip:71.170.246.90 w:1920 h:1080
[2020-Jul-08 13:45:26.471] 26022 [/staff2 tg4JC7kUmbwSwunn] [warning] "WApplication: WApplication::addMetaHeader() with no effect"
AppBase.cpp:198 1
[2020-Jul-08 13:45:27.406] 26022 [/staff2 tg4JC7kUmbwSwunn] [error] "Wt: decodeSignal(): signal 'orp26iu.render' not exposed"
AppBase.cpp:198 2
AppBase.cpp:198 3
AppBase.cpp:198 4
AppBase.cpp:198 5
src/AppStaff.cpp:2028 holding... 0
src/AppStaff.cpp:2028 holding... 1
src/AppStaff.cpp:2028 holding... 2
src/AppStaff.cpp:2028 holding... 3
src/AppStaff.cpp:2028 holding... 4
src/AppStaff.cpp:2028 holding... 5
src/AppStaff.cpp:2028 holding... 6
src/AppStaff.cpp:2028 holding... 7
src/AppStaff.cpp:2028 holding... 8
src/AppStaff.cpp:2028 holding... 9
src/AppStaff.cpp:2033 held.
AppBase.cpp:198 6
AppBase.cpp:198 7
AppBase.cpp:198 8
AppBase.cpp:198 9
^Csleep for 1