What does the `window` mean in RxJS? - rxjs

I'v heard about the buffer. Seems like the window is similar to the buffer.
What's the difference between them? and WHY it's called a 'window'??

Buffer is a specialization of Window.
Window notifies you immediately of new windows, along with an observable to observe the values that will be in that window.
In contrast, Buffer does not notify you immediately of new windows. Instead it internally collects the items in the window. When the window is complete, Buffer will send a notification with an array containing all of the items in the window.
Conceptually, you can write buffer by using window like so:
Rx.Observable.prototype.buffer = function () {
return this.window
.apply(this, arguments)
.flatMap(function (w) { return w.toArray(); });
};
As to why it is called "window"...unless the Rx authors come answer, any answers will be purely speculative. Window is a term commonly used to represent a time interval in many disciplines, including software development & signal processing.

Related

How to obtain keyboard layout for Microsoft Edge and other windows hosted in ApplicationFrameHost.exe

As we all know, Windows's keyboard layouts are thread-specific. When a layout changes, a message is dispatched to the foreground thread by the shell. So if one wants to obtain the most recent system-wide keyboard layout, one must do something like this:
const HWND foregroundWindow = ::GetForegroundWindow();
const DWORD foregroundThread = ::GetWindowThreadProcessId(foregroundWindow, NULL);
const HKL layout = ::GetKeyboardLayout(foregroundThread);
This works fine for most native Windows apps.
However, UWP applications, and several system apps including Microsoft Edge host their windows in the ApplicationFrameHost.exe. This causes ::GetForegroundWindow() to return the window of said process, leading to several curious problems, including misdetection of the foreground process and troubles detecting the actual keyboard layout.
The threads of ApplicationFrameHost.exe simply don't react to the system-wide keyboard layout change. It seems that they are not hosting the actual focused UI element. ::GetForegroundWindow() returns only the frame window, but the actual UI element has its own thread and maybe is hosted by its own process. Thus, the foreground framw window is simply not getting the respective layout change messages, and its thread has a stale HKL associated with it.
How can I detect the correct HKL of the foreground process?
The trick was to stop relying on the GetForegroundWindow() method altogether.
Instead, I solved the problem by utilising the quirky and counter-intuitive, but documented specific usecase of GetGUIThreadInfo().
If you pass zero as the first argument to this function, it will return the information for the foreground thread – the one that is receiving the actual user input!
This thread will also receive timely HKL-related messages from the shell, so the keyboard layout will not be stale.
GUITHREADINFO gti = { sizeof(GUITHREADINFO) };
// fetching the foreground thread info
::GetGUIThreadInfo(0, &gti);
// you may also fallback to other window handles in the GUITHREADINFO
// if the `hwndFocus == NULL`
const DWORD thread = ::GetWindowThreadProcessId(gti.hwndFocus, NULL);
const HKL layout = ::GetKeyboardLayout(thread);

Is it OK to delete window from callback window function (Windows OS)?

I want to make Application where you can see only one window at a time in order to save memory. Let's say, we have one window, after pressing a button another window shows, but the previous is deleted. If the button pressing is handled in window callback function, is it safe to delete the window from inside of that window function and recreate it after the new window is closed? Something like that:
void callback(...) {
...
if (msgID == ENTER_KEY) {
deleteMyself();
showWindow2();
createMyself();
}
...
}
Could you suggest better approach if this one is not good?
I think this is generally on a desktop a bad idea. So you would loose everything the userinput. And depending on your application the user maybe confuses why an options dialog closes the main window.
However on a mobile device it is normal only to have just one window (except you use dialogs). But in those cases all inputs should be stored so that the window can be reovered to its old state.
In general if you have trouble with the memory managment better check if you leak somewhere memory in most cases the GUI does not need so much memory.

How modal dialog is implemented?

For a long time I have been wondering how modal dialog is implemented.
Let me take Qt as an example. (Nearly all GUI toolkit has this mechanism)
In the main event loop, a slot is called, and in this slot a modal dialog is opened. Before the dialog is closed, the slot doesn't return control to the main event loop. So I thought that the main event loop is blocked and become unresponsive. Apparently this is not true, since when you open a modal dialog, the background main window is still working, like repainting its UI or keep displaying a curve or some graph. It just becomes not to accept any user input.
I did an experiment. I didn't open a modal dialog in the slot, but start a new thread there, and wait for the thread to finish in that slot. This definitely blocked the main event loop.
How modal dialog is implemented after all? How does it keep main event loop unblocked but at the same time blocked the calling slot?
There is only ever a need for a single event loop, and it does not block when a modal dialog appears. Though, I suppose, different toolkits may handle this differently. You would need to consult the documentation to know for sure. Conceptually, however, it all works in the same way.
Every event has a source where the event occured. When a modal dialog appears, the event loop either ignores or redirects all events that originate outside of the dialog. There's really no magic to it. Generally speaking, it's like an if statement in the event loop code that says "if (modal_is_shown() and !event_is_in_modal_window()) {ignore_and_wait_for_next_event()}". Of course, the logic is a bit more complicated, but that's the gist of it.
If you're looking for examples here's another one:
In Tk, there is only ever one event loop. Modal behavior (doesn't have to be dialog, can also be tooltips, textbox etc) is simply implemented by making the main window ignore mouse and keyboard events. All other events like redraws etc. can still be serviced because the event loop is still running.
Tk implements this via the [grab] function. Calling grab on a UI object makes it the only object able to respond to keyboard and mouse events. Essentially blocking all other objects. This doesn't mess with the event loop. It merely temporarily disables event handlers until the grab is released.
It should be noted that Unix-like operating systems running X also has grab built in to the windowing system. So it's not necessarily implemented merely by UI toolkit libraries but is sometimes also a built in feature of the OS. Again, this is implemented by simple blocking/disabling of events instead of instantiating separate event loops. I believe this also used to be the case for the older MacOS before OSX. Not sure about OSX or Windows though. Even though modality is often implemented by the OS itself, toolkits like Qt and Tk often implement their own mechanisms to standardize behaviors across different platforms.
So the conclusion is, it is not necessary to block the main event loop to implement modality. You just need to block the events and/or event handlers.
The answer by https://stackoverflow.com/users/893/greg-hewgill is correct.
However, reading the follow-up discussion between him and https://stackoverflow.com/users/188326/solotim , I feel that there is room for further clarification, by means of prose and some pseudo-code.
I'll handle the prose part with a fact-list:
The main message loop does not run until the modal activity is finished
However, events are still delivered while the modal activity is running
This is because there is a nested event loop within the modal activity.
So far I just repeated Greg's answer, please bear with me as it is for continuity's sake. Below is where I hope to contribute additional, useful info.
The nested event loop is part of the GUI toolkit, and as such, it knows the callback functions related to every window in existence
When the nested event loop raises an event (such as a repaint event directed to the main window), it invokes the callback function associated with that event. Note that "callback" here may refer to a method of a class representing a window, in object-oriented systems.
the callback function does what is needed (e.g., repaint), and returns right back to the nested message loop (the one within the modal activity)
Last, but not least, here's pseudo-code to hopefully illustrate further, using a fictitious "GuiToolkit":
void GuiToolkit::RunModal( ModalWindow *m )
{
// main event loop
while( !GuiToolkit::IsFinished() && m->IsOpen() )
{
GuiToolkit::ProcessEvent(); // this will call
// MainWindow::OnRepaint
// as needed, via the virtual
// method of the base class
// NonModalWindow::OnRepaint
}
}
class AboutDialog: public ModalWindow
{
}
class MainWindow: public NonModalWindow
{
virtual void OnRepaint()
{
...
}
virtual void OnAboutBox()
{
AboutDialog about;
GuiToolkit::RunModal(&about); // blocks here!!
}
}
main()
{
MainWindow window;
GuiToolkit::Register( &window ) // GuiToolkit knows how to
// invoke methods of window
// main event loop
while( !GuiToolkit::IsFinished() )
{
GuiToolkit::ProcessEvent(); // this will call
// MainWindow::OnAboutBox
// at some point
}
}
In general, a modal dialog box of this type is implemented by running its own message loop instead of your application's message loop. Messages directed to your main window (such as timer or paint messages) will still get delivered, even during the modal operation.
In some situations, you may have to be careful that you don't recursively do the same thing repeatedly. For example, if you trigger a modal dialog box on a timer message combined with some persistent flag, you'll want to make sure you don't keep bringing up the same dialog box repeatedly whenever the timer message fires.

How does a GUI Framework work?

I have been all over the web looking for an answer to this, and my question is this:
How does a GUI framework work? for instance how does Qt work, is there any books or wibsites on the topic of writing a GUI framework from scratch? and also does the framework have to call methods from the operating systems GUI framework?
-- Thank you to any one who takes the time to try to answer this question, and forgive me if i misspelled anything.
In the old days we did a lot of GUI programming from scratch. It is not as hard as it seems, but it requires a few weeks to come with results.
First you need a good drawing library. Minimal functionality for this library is drawing clipped rectangles (using patterns), lines, bitmaps, and fonts. You can cheat by creating fonts as bitmaps, and clipped rectangle is just a bunch of horizontal lines.
Now you need at least drivers for mouse, keyboard, and timer (if not already provided by the operating system). In general, you will need to detect keys, symbol keys (such as shift, etc.), mouse moves and mouse clicks. Basic timer functions will allow you to detect double clicks.
Then you need to create a window data structure. This data structure needs to have coordinates i.e. a rectangle, link to parent window (if not top window), and window function i.e. the function that will be called when this window should handle some events.
Once you can draw on screen you need some rectangle algebra functions. You need at least good function to calculate intersection of rectangles, and a quick resolution of relative to absolute coordinates. For example - if your child window has parent then its' x and y should recursively be added to parent x and y until you reach top window.
At this point you have your:
- primitive graphical functions,
- window structure,
- mouse driver, keyboard driver, and timer,
- rectangle arithmetic.
Now you can write your main event harvesting function. This function will run all the time. It's purpose will be to detect events and send messages to correct windows. What is an event? Well, when you start your program, store mouse x and y coordinates. Then in a loop check if they have changed. If they have changed, find the window at that position ... and send WM_MOUSEMOVE event to it. Your harvesting function should handle:
- mouse moves
- mouse clicks
- mouse double clicks (remember last click and position, measure time and decide if it is a double click or not)
- timer events
- keyboard buffer changes
...
Now you should be able to send events to windows. But you really need a mechanism for it. It is a combination of message queue, and window procedure. It usually works like this: each window has a window procedure which commonly accepts four arguments: message id (i.e. is it mouse move, is it paint message), window handle, parameter 1 and parameter 2. You can call this window procedure directly using something like a send_message functions. Or you can send this window a message via post_message function. This will put message to the queue and window will process messages one by one, eventually receiving this one. So why should you call one messages directly and put others to the queue? Because of priority. You see, a keyboard click can wait some time before being processed. But a window redraw must complete immediately to prevent flicker and wrong data on screen.
So your harvest_events function sends messages to windows using post_message, and send_message. And your window message pump gets them using typical message pump like this:
while (pmsg = get_message() != NULL) send_message(pmsg->id, pmsg->hwnd, pmsg->p1, pmsg->p2);
get_message simply obtains message from the queue, and calls send message. Simple, huh? Well, not quite so. This way you would only receive driver messages to windows, but you also need some functions to redraw windows, move them, etc.. When you create move_window function, resize_window, show_window, and hide_window function, your window coordinates will change. Parts of other windows will be uncovered (if top window is moved or closed).You need to calculate which windows are affected by coordinate changes and send paint message to those windows (to repaint only the parts that were uncovered - remember, you have clipping drawing functions so this will work).
These functions introduces messages msg_paint, msg_move, msg_resize, msg_hide...
Last, you need to maintain hierarchy of windows. Your top window should be the desktop. It should have child windows (application top windows). These windows may have further child windows (buttons, edit boxes, etc.) The obvious structure for holding these is the window tree. When you detect mouse click you have to traverse window tree and do it in a smart way (finding out who has focus, who is modal, etc.) to send message to the right window. And when you draw you also must traverse all children to see who is uncovered and who is not. Last but not least, you need to handle mouse rectangle as top window to prevent flickering the mouse as windows are re-drawn or (using timers and msg_paint events) animated.
That's roughly it.
A GUI framework like Qt generally works by taking the existing OS's primitive objects (windows, fonts, bitmaps, etc), wrapping them in more platform-neutral and less clunky classes/structures/handles, and giving you the functionality you'll need to manipulate them. Yes, that almost always involves using the OS's own functions, but it doesn't HAVE to -- if you're designing an API to draw an OpenGL UI, for example, most of the underlying OS's GUI stuff won't even work, and you'll be doing just about everything on your own.
Either way, it's not for the faint of heart. If you have to ask how a GUI framework works, you're not even close to ready to design one. You're better off sticking with an existing framework and extending it to do the spiffy stuff it doesn't do already.

Win32 call order

I have two windows that I send scripted input to. The procedure goes as this
BringWindowToTop( window1 );
i = Build input structures( window1 );
SendInput(i);
BringWindowToTop( window2 );
i = Build input structures( window2 );
SendInput(i);
I was having trouble with inputs not being sent and the correct time. I put delays after each call and saw that input from the first SendInput() was processed after window2 is brought to top. Same thing at the end of the loop as well.
Are SendInput calls buffered? If so, how can I make sure of a serial execution of this code?
Thanks
Input, like most messages in Win32, goes through two phases. First it is posted into a queue. At this point the destination window is already determined. Then when the receiving program is idle it is processed. Even though the input might not be processed until after the second window is brought forward in the Z-order, the input messages should have been queued to the first window.
Does the behavior rely only on which window the input goes to, or does the program also have to be frontmost when the message is fully processed?
Anyway, since you are trying to send input to specific windows and not whatever the user made active, why not PostMessage the events such as WM_BUTTONDOWN and WM_KEYPRESS directly to their destinations?
From the MSDN page:
The SendInput function inserts the events in the INPUT structures serially into the keyboard or mouse input stream. These events are not interspersed with other keyboard or mouse input events inserted either by the user (with the keyboard or mouse) or by calls to keybd_event, mouse_event, or other calls to SendInput.
So SendInput is inserting into the input stream where, presumably, BringWindowToTop is executing serially, or inserting into an events queue that is processed first. Perhaps you could find an event to call the second SendInput from, which will be executed after the first window is brought to the front.

Resources