History of Orfo Switcher
Good day, dear habrozhitel!
Once upon a time, in August 2006, as a student, I got the idea to write a program that would transfer the cursor keys (arrows) on the keyboard from a familiar place directly to the alphabetic keyboard. The idea of the fix was to navigate through the editor in which I programmed without taking my hands off the usual position of FYVA-OLDJ. It was enough to hold Caps-Lock and the keys I, J, K, L turned into the cursor keys. That was great! I had to deal with Windows hooks, with the feature of intercepting and falsifying messages from the keyboard, and despite the fact that the idea of simplified navigation did not even take hold of myself (it was difficult to force myself to use the new keys), I was happy with the work done, because I already had everything necessary to create my keyboard switch,
Around the same time, I got acquainted with the D programming language and fell in love with it for the ability to write in C ++ and at the same time enjoy automatic garbage collection, interfaces, closures, and other fashionable features. It was cool! I decided to rewrite the keyboard interceptor to D, supplementing it so that it would switch the keyboard layout if I started typing, forgetting to switch the language. Not just switched, but erased the gibberish I had already typed and inserted the corrected text. Well, you all know how Punto does it.
And after a while everything was ready. I had a file in which combinations of characters were listed through a line break character, upon meeting which, the program automatically switched the layout. After listening to Sergei Moskalev (author of Punto) on the radio, I decided that the secret to the success of the correct switch lies in the “impossibilities” of the language, which, he said, had accumulated in him while he worked with “combing” the result of recognizing scanned pages of text. Well, you all know the story .
I tried to figure out the impossibility dictionary from the Punto distribution, but nothing worked out for me. I couldn’t figure out the ps.dat file format, and collecting statistics of impossible combinations of characters, processing volumes of text, seemed to me an unfinished method that would always strive for excellence, but never reach it. And I decided to go the other way - to include absolutely all the words of the language in the program. It seemed like a solution to all the problems! At that moment, I decided that the program would still be checking spelling, as long as it already contained all the words in the correct form.
Having downloaded from some site a list of all Russian words with all possible endings and prefixes, I found that there are much more of them than I expected - about 800,000 words! The Russian language file weighed about 15 megabytes, and the search in it took tens of milliseconds! This was no good, because in order to find a similar word, you need to do more than a hundred search operations and these milliseconds would turn into seconds, and no one would want to wait a second until a menu appears with the correct word variant. It was close to failure.
A little later, I discovered that I was lucky, because most of the words in the Russian language are a continuation of some other, already existing word. That was great news!
If we arrange all the words in the form of a special tree in which the root nodes are the letters of the alphabet on which the words can begin, the nodes of the second level of the letter, which can be in the second position in the words and so on up to the very last letter of the longest word, can be not only reduce the file size of the dictionary by several times, but also create ideal conditions for the search, because each node contains the size of the entire branch, and if the letter of the node does not match the search word, we can step over the entire branch without having to ebora all its contents. So I did. It turned out a great dictionary! As many as iterations of the search took 0 milliseconds of time, and my hands were finally completely untied. The size of the Russian dictionary was only 5 mb, and the English 1.4 mb. In the archive, both dictionaries together with the executable file orfoswitcher.exe occupied only 1.1 megabytes. Great size for such a program. I was very pleased with the work!
With this, coming up with a layout switching algorithm turned out to be very simple. It was enough to look if the dialed combination exists in one dictionary and whether it exists in another. If this is the case and the layout does not match the found word, then the switch is performed. This worked fine, and all the wrong switching was solved by adding some new word to the dictionary. It immediately became clear, for example, that the word "schA" constantly switched to the English "of", and, despite a dictionary of eight hundred thousand words, it had to be manually supplemented with such various popular words.
The next curious task was to create a menu that could work in any application. Variants of correct spelling of words, and possibly something else, were supposedly to appear in this menu. I already knew how to integrate into running applications using Windows hooks, but there were problems with the menu. The first attempts were unsuccessful. Creating a standard Windows menu from the space of an active application did not always work - some applications hung up and behaved unpredictably, because each application had its own working principle, and there were no guarantees that the menu would be correctly processed and messages from it would successfully fall into the program message loop. Creating a menu from the orfoswitcher process led to a loss of focus of the current application, which was also ugly. After all, even return the focus after the menu is displayed back to the active application, there are no guarantees that the application will not do any work to remove or set the focus. Any solution was either unstable or did not work everywhere.
Once again, I was lucky. Having looked at using Spy ++ how the On-Screen Keyboard application (osk.exe) works, I found that the creators of Windows provided a special window style called WS_EX_NOACTIVATE, thanks to which the created window never becomes active, even if you click on it. This was wonderful, because on the basis of this window I was able to create a menu that could be walked with both a mouse and a keyboard, while the input cursor remained in the current application. This menu was ideally suited for displaying the correct words when checking spelling, but I realized that it could have other useful uses.
The first application that came to mind was to save the history of everything that was copied and display it in the form of menu items. One point for each text fragment that got to the clipboard. So the history of the clipboard appeared in the program. It turned out to be convenient to always have at hand the last fragments of the text, especially when you had to copy the login from somewhere, then the password, and then paste them into the input fields. There was no need to worry that the clipboard would be overwritten with the new copied text, because everything was saved in the history, even after turning off the computer. A friend told me that the history of the clipboard is the only function of the ortho switcher that stops it before uninstalling the program. I always appreciated his frankness.
Then notes appeared in the program, the auto-replace function, all kinds of exceptions for working in applications, and the orphoswicher gradually came to the form in which it can be seen now. Such is the story. I hope someone also came in handy this program.
Program website: virtassist.eu
Once upon a time, in August 2006, as a student, I got the idea to write a program that would transfer the cursor keys (arrows) on the keyboard from a familiar place directly to the alphabetic keyboard. The idea of the fix was to navigate through the editor in which I programmed without taking my hands off the usual position of FYVA-OLDJ. It was enough to hold Caps-Lock and the keys I, J, K, L turned into the cursor keys. That was great! I had to deal with Windows hooks, with the feature of intercepting and falsifying messages from the keyboard, and despite the fact that the idea of simplified navigation did not even take hold of myself (it was difficult to force myself to use the new keys), I was happy with the work done, because I already had everything necessary to create my keyboard switch,
Around the same time, I got acquainted with the D programming language and fell in love with it for the ability to write in C ++ and at the same time enjoy automatic garbage collection, interfaces, closures, and other fashionable features. It was cool! I decided to rewrite the keyboard interceptor to D, supplementing it so that it would switch the keyboard layout if I started typing, forgetting to switch the language. Not just switched, but erased the gibberish I had already typed and inserted the corrected text. Well, you all know how Punto does it.
And after a while everything was ready. I had a file in which combinations of characters were listed through a line break character, upon meeting which, the program automatically switched the layout. After listening to Sergei Moskalev (author of Punto) on the radio, I decided that the secret to the success of the correct switch lies in the “impossibilities” of the language, which, he said, had accumulated in him while he worked with “combing” the result of recognizing scanned pages of text. Well, you all know the story .
I tried to figure out the impossibility dictionary from the Punto distribution, but nothing worked out for me. I couldn’t figure out the ps.dat file format, and collecting statistics of impossible combinations of characters, processing volumes of text, seemed to me an unfinished method that would always strive for excellence, but never reach it. And I decided to go the other way - to include absolutely all the words of the language in the program. It seemed like a solution to all the problems! At that moment, I decided that the program would still be checking spelling, as long as it already contained all the words in the correct form.
Having downloaded from some site a list of all Russian words with all possible endings and prefixes, I found that there are much more of them than I expected - about 800,000 words! The Russian language file weighed about 15 megabytes, and the search in it took tens of milliseconds! This was no good, because in order to find a similar word, you need to do more than a hundred search operations and these milliseconds would turn into seconds, and no one would want to wait a second until a menu appears with the correct word variant. It was close to failure.
A little later, I discovered that I was lucky, because most of the words in the Russian language are a continuation of some other, already existing word. That was great news!
If we arrange all the words in the form of a special tree in which the root nodes are the letters of the alphabet on which the words can begin, the nodes of the second level of the letter, which can be in the second position in the words and so on up to the very last letter of the longest word, can be not only reduce the file size of the dictionary by several times, but also create ideal conditions for the search, because each node contains the size of the entire branch, and if the letter of the node does not match the search word, we can step over the entire branch without having to ebora all its contents. So I did. It turned out a great dictionary! As many as iterations of the search took 0 milliseconds of time, and my hands were finally completely untied. The size of the Russian dictionary was only 5 mb, and the English 1.4 mb. In the archive, both dictionaries together with the executable file orfoswitcher.exe occupied only 1.1 megabytes. Great size for such a program. I was very pleased with the work!
With this, coming up with a layout switching algorithm turned out to be very simple. It was enough to look if the dialed combination exists in one dictionary and whether it exists in another. If this is the case and the layout does not match the found word, then the switch is performed. This worked fine, and all the wrong switching was solved by adding some new word to the dictionary. It immediately became clear, for example, that the word "schA" constantly switched to the English "of", and, despite a dictionary of eight hundred thousand words, it had to be manually supplemented with such various popular words.
The next curious task was to create a menu that could work in any application. Variants of correct spelling of words, and possibly something else, were supposedly to appear in this menu. I already knew how to integrate into running applications using Windows hooks, but there were problems with the menu. The first attempts were unsuccessful. Creating a standard Windows menu from the space of an active application did not always work - some applications hung up and behaved unpredictably, because each application had its own working principle, and there were no guarantees that the menu would be correctly processed and messages from it would successfully fall into the program message loop. Creating a menu from the orfoswitcher process led to a loss of focus of the current application, which was also ugly. After all, even return the focus after the menu is displayed back to the active application, there are no guarantees that the application will not do any work to remove or set the focus. Any solution was either unstable or did not work everywhere.
Once again, I was lucky. Having looked at using Spy ++ how the On-Screen Keyboard application (osk.exe) works, I found that the creators of Windows provided a special window style called WS_EX_NOACTIVATE, thanks to which the created window never becomes active, even if you click on it. This was wonderful, because on the basis of this window I was able to create a menu that could be walked with both a mouse and a keyboard, while the input cursor remained in the current application. This menu was ideally suited for displaying the correct words when checking spelling, but I realized that it could have other useful uses.
The first application that came to mind was to save the history of everything that was copied and display it in the form of menu items. One point for each text fragment that got to the clipboard. So the history of the clipboard appeared in the program. It turned out to be convenient to always have at hand the last fragments of the text, especially when you had to copy the login from somewhere, then the password, and then paste them into the input fields. There was no need to worry that the clipboard would be overwritten with the new copied text, because everything was saved in the history, even after turning off the computer. A friend told me that the history of the clipboard is the only function of the ortho switcher that stops it before uninstalling the program. I always appreciated his frankness.
Then notes appeared in the program, the auto-replace function, all kinds of exceptions for working in applications, and the orphoswicher gradually came to the form in which it can be seen now. Such is the story. I hope someone also came in handy this program.
Program website: virtassist.eu