Signaling a menu entry from a method

In method routines, a twilight zone exists from the moment you use %M_SIGNAL to signal a menu entry to the moment control returns from the method routine. An %M_SIGNAL (D_SIGNAL) call in a method routine simultaneously sets g_select and g_entnam and instructs the Synergy runtime to signal the menu entry when control returns from the method routine. So if you clear g_select or g_entnam or set them to something different during this time, your changes will be ignored. As soon as control returns from the method routine, they will be reset to the values set by the %M_SIGNAL call because the Synergy runtime has already received its instructions. We recommend, however, that you return immediately after the %M_SIGNAL call, and we recommend that you avoid modifying g_select or g_entnam after the %M_SIGNAL call. (%M_SIGNAL can also be used to cancel a signaled menu entry.)

Note the following:

Combinations of these subtleties can create order-of-magnitude subtleties. For instance, if a method routine signals a menu entry with %M_SIGNAL and then calls a Toolkit input routine such as I_INPUT, I_INPUT clears g_select and g_entnam and may signal another menu entry. But unless %M_SIGNAL is called again before returning from the method, the lost menu entry will be resurrected when the method returns. In general, it is a good idea to avoid these situations, and it’s best to avoid nesting methods. You can do this by signaling the menu entry and then returning and letting the outer-level routine dispatch the signaled menu entry. This approach results in a somewhat flatter application design, which more closely matches Toolkit’s event paradigm, where there is no event stack or queue.

There is one subtle effect of %M_SIGNAL that makes things easier: %M_SIGNAL helps you to synchronize events. On Windows platforms, there are two different types of event processing: the UI Toolkit processing of the menu entry and Windows messaging. Because Windows messages occur quickly—you can get hundreds of them by simply moving the mouse across a window—the Synergy runtime dispatches these messages between lines of Synergy code. And because asynchronous methods are invoked immediately by their associated Windows events, a toolbar method, for example, can be called between statements of another Synergy routine. If the toolbar method and the routine it interrupts access shared data, the result can be extremely confusing. If, however, you limit the toolbar routine to calling %M_SIGNAL with an event that will be dispatched later, you have ensured that the associated code will not be executed asynchronously.