<div dir="ltr">Hi Bill,<div class="gmail_extra"><br><br><div class="gmail_quote">2013/10/18 Bill Spitzak <span dir="ltr"><<a href="mailto:spitzak@gmail.com" target="_blank">spitzak@gmail.com</a>></span><br><blockquote class="gmail_quote" style="margin:0px 0px 0px 0.8ex;border-left-width:1px;border-left-color:rgb(204,204,204);border-left-style:solid;padding-left:1ex">
<div class="im">Giulio Camuffo wrote:<br>
<blockquote class="gmail_quote" style="margin:0px 0px 0px 0.8ex;border-left-width:1px;border-left-color:rgb(204,204,204);border-left-style:solid;padding-left:1ex">
And what is it that doesn't work? As a wild bet I'd say you probably<br>
want to look at wl_event_queue.<br>
See <a href="http://wayland.freedesktop.org/docs/html/chap-Library.html#sect-Library-Client" target="_blank">http://wayland.freedesktop.<u></u>org/docs/html/chap-Library.<u></u>html#sect-Library-Client</a><br>
</blockquote>
<br></div>
This brings up some questions I have had about making a complete wayland client. The documentation says you should do this:<br>
<br>
while (wl_display_prepare_read(<u></u>display) != 0)<br>
wl_display_dispatch_pending(<u></u>display);<br>
wl_display_flush(display);<br>
poll(fds, nfds, -1);<br>
wl_display_read_events(<u></u>display);<br>
wl_display_dispatch_pending(<u></u>display); <br></blockquote><blockquote class="gmail_quote" style="margin:0px 0px 0px 0.8ex;border-left-width:1px;border-left-color:rgb(204,204,204);border-left-style:solid;padding-left:1ex">
Now a "real" application or toolkit will need to do a few other things:Basicaly<br></blockquote><blockquote class="gmail_quote" style="margin:0px 0px 0px 0.8ex;border-left-width:1px;border-left-color:rgb(204,204,204);border-left-style:solid;padding-left:1ex">
* It has to loop<br>
<br>
* It has to respond to other fds than the wayland one (yes this could be done with threads but I am assuming situations where the overhead and difficulty with threads is greater than just handling it in the main thread).<br>
<br>
* It has to handle timeouts (same comment about threads)<br>
<br>
* Most important: it has to have an "idle" (Qt calls it "aboutToBlock") handling. FLTK and our Qt programs rely on doing perhaps 90% of their work in this, to produce smooth and responsive update with minimal overhead. I think *all* toolkits use this as a "now is the time to draw all the windows" event.</blockquote>
<blockquote class="gmail_quote" style="margin:0px 0px 0px 0.8ex;border-left-width:1px;border-left-color:rgb(204,204,204);border-left-style:solid;padding-left:1ex">
I will add them here in what I think is the proper places, please inform me if this is wrong. The trick is that I have to make sure I don't call poll() when any pending events or the queue unlocked, and that any of the dispatches can cause more pending events:<br>
<br>
while (!quit) { //ADDED<br>
while (wl_display_prepare_read(<u></u>display) != 0) {<br>
wl_display_dispatch_pending(<u></u>display);<br>
dispatch_idle(); // ADDED<br>
}<br>
wl_display_flush(display);<br>
poll(...); // with timeout if necessary<br>
dispatch_other_fds(); // ADDED<br>
dispatch_expired_timeouts(); // ADDED<br>
wl_display_read_events(<u></u>display);<br>
wl_display_dispatch_pending(<u></u>display);<br>
dispatch_idle(); // ADDED<br>
}<br>
<br>
The above code assumes that wl_display_dispatch_pending() will consume events made pending by it's own dispatches (ie it loops until the queue is empty, rather than looping over all events that happen to be in the queue when it is called). If this is not true then dispatch_idle() will be called more than necessary.<br>
<br>
This I believe can be simplified by moving the end of the loop to the start to merge identical code, is this correct: ? This reduces the number of checks that the queue is empty by at least one:<br>
<br>
bool first = true;<br>
while (!quit) {<br>
if (first) first = false;<br>
else wl_display_read_events(<u></u>display);<br>
do {<br>
wl_display_dispatch_pending(<u></u>display);<br>
dispatch_idle();<br>
} while (wl_display_prepare_read(<u></u>display) != 0);<br>
wl_display_flush(display);<br>
poll(...); // with timeout if necessary<br>
dispatch_other_fds();<br>
dispatch_expired_timeouts();<br>
}<br>
<br>
Note: the reason it does the "first" check, rather than putting the wl_display_read_events at the end, is because I don't want to call wl_display_read_events when quit is true. The earlier version does this incorrectly if a timeout or fd turns on quit.<br>
<br>
Assuming this is correct, it looks to me like the client has little choice about rearranging this and must call in a precise order. So I will propose a new function called "wl_i_want_a_pony" so that the main loop looks like this:<br>
<br>
while (!quit) {<br>
wl_i_want_a_pony(display, dispatch_idle);<br>
poll(...);<br>
dispatch_other_fds();<br>
dispatch_expired_timeouts();<br>
}<br>
<br>
The implementation of wl_i_want_a_pony is this:<br>
<br>
wl_i_want_a_pony(display, dispatch_idle) {<br>
static bool did_prepare_read = false;<br>
if (did_prepare_read)<br>
wl_display_read_events(<u></u>display);<br>
do {<br>
wl_display_dispatch_pending(<u></u>display);<br>
dispatch_idle();<br>
} while (wl_display_prepare_read(<u></u>display) != 0);<br>
wl_display_flush(display);<br>
did_prepare_read = true;<br>
}<br>
<br>
Of course in reality the dispatch_idle would be registered with another call, and multiple ones allowed. Still this seems like it would reduce the size of the wayland client api a lot and remove some of these questions, and allow a simpler and more efficient implementation.<br>
</blockquote></div><br></div><div class="gmail_extra">Basically i would like to implement a thread(input thread) that should only dispatch incoming input events from wayland compositor when the rendering thread is idle and the input thread should sleep in wait for events function(i think poll on wl_display fd in the example above) without blocking the rendering thread, because the input events are not the only one trigger for rendering thread to start rendering again.<br>
</div><div class="gmail_extra">in this case the following code should be sufficient right?</div><div class="gmail_extra"><br></div><div class="gmail_extra">while(!quit)//main loop</div><div class="gmail_extra">{</div><div class="gmail_extra">
while (wl_display_prepare_read(<u></u>display) != 0)<br> wl_display_dispatch_pending(<u></u>display);<br> wl_display_flush(display);<br> poll(fds, nfds, -1); //wait until new input event arrives <br> wl_display_read_events(<u></u>display);<br>
wl_display_dispatch_pending(<u></u>display); <br></div><div class="gmail_extra">}</div><div class="gmail_extra"><br></div><div class="gmail_extra">And in this case are there some additional modifications/ wayland calls in the egl (rendering thread) needed?</div>
</div>