Skip to content

Commit

Permalink
Integrate static language switching
Browse files Browse the repository at this point in the history
  • Loading branch information
mufeedvh committed Dec 18, 2023
1 parent 35618e0 commit 78bf4ec
Show file tree
Hide file tree
Showing 347 changed files with 872 additions and 79 deletions.
139 changes: 66 additions & 73 deletions rust/composition_processor/src/engine.rs
Original file line number Diff line number Diff line change
Expand Up @@ -4,6 +4,7 @@ use itf_components::compartment::Compartment;
use crate::test_virtual_key::{
test_virtual_key, CandidateMode, KeystrokeCategory, KeystrokeFunction,
};

use windows::{
core::{AsImpl, GUID},
Win32::{
Expand All @@ -12,25 +13,28 @@ use windows::{
UI::{
Input::KeyboardAndMouse::VK_SHIFT,
TextServices::{ITfThreadMgr, TF_LBI_STATUS_DISABLED, TF_LBI_STATUS_HIDDEN},
},
// System::SystemServices::{
// LANG_MALAYALAM,
// LANG_ASSAMESE,
// LANG_MARATHI,
// LANG_BENGALI,
// LANG_NEPALI,
// LANG_GUJARATI,
// LANG_ODIA,
// LANG_HINDI,
// LANG_PUNJABI,
// LANG_KANNADA,
// LANG_SANSKRIT,
// LANG_TAMIL,
// LANG_TELUGU,
// },
}
},
};

use windows::Win32::System::Com::{CoInitializeEx, COINIT_APARTMENTTHREADED};

use windows::Win32::System::SystemServices::{
LANG_MALAYALAM, SUBLANG_MALAYALAM_INDIA,
LANG_ASSAMESE, SUBLANG_ASSAMESE_INDIA,
LANG_MARATHI, SUBLANG_MARATHI_INDIA,
LANG_BENGALI, SUBLANG_BENGALI_INDIA,
LANG_NEPALI, SUBLANG_NEPALI_INDIA,
LANG_GUJARATI, SUBLANG_GUJARATI_INDIA,
LANG_ODIA, SUBLANG_ODIA_INDIA,
LANG_HINDI, SUBLANG_HINDI_INDIA,
LANG_PUNJABI, SUBLANG_PUNJABI_INDIA,
LANG_KANNADA, SUBLANG_KANNADA_INDIA,
LANG_SANSKRIT, SUBLANG_SANSKRIT_INDIA,
LANG_TAMIL, SUBLANG_TAMIL_INDIA,
LANG_TELUGU, SUBLANG_TELUGU_INDIA,
};

pub mod keystroke_buffer;
use keystroke_buffer::KeystrokeBuffer;

Expand All @@ -53,6 +57,26 @@ use once_cell::sync::Lazy;

use govarnam::Varnam;

use std::collections::HashMap;

static LANG_MAP: Lazy<HashMap<u16, u32>> = Lazy::new(|| {
let mut m = HashMap::new();
m.insert((SUBLANG_MALAYALAM_INDIA << 10 | LANG_MALAYALAM) as u16, LANG_MALAYALAM);
m.insert((SUBLANG_ASSAMESE_INDIA << 10 | LANG_ASSAMESE) as u16, LANG_ASSAMESE);
m.insert((SUBLANG_MARATHI_INDIA << 10 | LANG_MARATHI) as u16, LANG_MARATHI);
m.insert((SUBLANG_BENGALI_INDIA << 10 | LANG_BENGALI) as u16, LANG_BENGALI);
m.insert((SUBLANG_NEPALI_INDIA << 10 | LANG_NEPALI) as u16, LANG_NEPALI);
m.insert((SUBLANG_GUJARATI_INDIA << 10 | LANG_GUJARATI) as u16, LANG_GUJARATI);
m.insert((SUBLANG_ODIA_INDIA << 10 | LANG_ODIA) as u16, LANG_ODIA);
m.insert((SUBLANG_HINDI_INDIA << 10 | LANG_HINDI) as u16, LANG_HINDI);
m.insert((SUBLANG_PUNJABI_INDIA << 10 | LANG_PUNJABI) as u16, LANG_PUNJABI);
m.insert((SUBLANG_KANNADA_INDIA << 10 | LANG_KANNADA) as u16, LANG_KANNADA);
m.insert((SUBLANG_SANSKRIT_INDIA << 10 | LANG_SANSKRIT) as u16, LANG_SANSKRIT);
m.insert((SUBLANG_TAMIL_INDIA << 10 | LANG_TAMIL) as u16, LANG_TAMIL);
m.insert((SUBLANG_TELUGU_INDIA << 10 | LANG_TELUGU) as u16, LANG_TELUGU);
m
});

static VARNAM: Lazy<Varnam> = Lazy::new(|| {
let dll_instance_handle = unsafe { ime::dll::DLL_INSTANCE };

Expand All @@ -64,25 +88,32 @@ static VARNAM: Lazy<Varnam> = Lazy::new(|| {

let dir = std::path::Path::new(&file_name[..]).parent().unwrap();

// let (scheme_path, learning_path) = match active_langid as u32 {
// LANG_MALAYALAM => (dir.join("schemes/ml/ml.vst"), dir.join("schemes/learnings/ml.vst.learnings")), // Malayalam
// LANG_ASSAMESE => (dir.join("schemes/as/as.vst"), dir.join("schemes/learnings/as.vst.learnings")), // Assamese
// LANG_MARATHI => (dir.join("schemes/mr/mr.vst"), dir.join("schemes/learnings/mr.vst.learnings")), // Marathi
// LANG_BENGALI => (dir.join("schemes/bn/bn.vst"), dir.join("schemes/learnings/bn.vst.learnings")), // Bengali
// LANG_NEPALI => (dir.join("schemes/ne/ne.vst"), dir.join("schemes/learnings/ne.vst.learnings")), // Nepali
// LANG_GUJARATI => (dir.join("schemes/gu/gu.vst"), dir.join("schemes/learnings/gu.vst.learnings")), // Gujarati
// LANG_ODIA => (dir.join("schemes/or/or.vst"), dir.join("schemes/learnings/or.vst.learnings")), // Odia
// LANG_HINDI => (dir.join("schemes/hi/hi.vst"), dir.join("schemes/learnings/hi.vst.learnings")), // Hindi
// LANG_PUNJABI => (dir.join("schemes/pa/pa.vst"), dir.join("schemes/learnings/pa.vst.learnings")), // Punjabi
// LANG_KANNADA => (dir.join("schemes/kn/kn.vst"), dir.join("schemes/learnings/kn.vst.learnings")), // Kannada
// LANG_SANSKRIT => (dir.join("schemes/sa/sa.vst"), dir.join("schemes/learnings/sa.vst.learnings")), // Sanskrit
// LANG_TAMIL => (dir.join("schemes/ta/ta.vst"), dir.join("schemes/learnings/ta.vst.learnings")), // Tamil
// LANG_TELUGU => (dir.join("schemes/te/te.vst"), dir.join("schemes/learnings/te.vst.learnings")), // Telugu
// _ => panic!("Unsupported language ID: {}", active_langid), // Panic for unsupported languages
// };

let scheme_path = dir.join("schemes/ml/ml.vst");
let learning_path = dir.join("schemes/learnings/ml.vst.learnings");
unsafe {
CoInitializeEx(None, COINIT_APARTMENTTHREADED).expect("Failed to initialize COM");
}

let active_lang_profile = LanguageBar::get_active_langid().unwrap();
let active_langid = LANG_MAP.get(&active_lang_profile).unwrap();

let (scheme_path, learning_path) = match active_langid {
&LANG_MALAYALAM => (dir.join("schemes/ml/ml.vst"), dir.join("schemes/learnings/ml.vst.learnings")), // Malayalam
&LANG_ASSAMESE => (dir.join("schemes/as/as.vst"), dir.join("schemes/learnings/as.vst.learnings")), // Assamese
&LANG_MARATHI => (dir.join("schemes/mr/mr.vst"), dir.join("schemes/learnings/mr.vst.learnings")), // Marathi
&LANG_BENGALI => (dir.join("schemes/bn/bn.vst"), dir.join("schemes/learnings/bn.vst.learnings")), // Bengali
&LANG_NEPALI => (dir.join("schemes/ne/ne.vst"), dir.join("schemes/learnings/ne.vst.learnings")), // Nepali
&LANG_GUJARATI => (dir.join("schemes/gu/gu.vst"), dir.join("schemes/learnings/gu.vst.learnings")), // Gujarati
&LANG_ODIA => (dir.join("schemes/or/or.vst"), dir.join("schemes/learnings/or.vst.learnings")), // Odia
&LANG_HINDI => (dir.join("schemes/hi/hi.vst"), dir.join("schemes/learnings/hi.vst.learnings")), // Hindi
&LANG_PUNJABI => (dir.join("schemes/pa/pa.vst"), dir.join("schemes/learnings/pa.vst.learnings")), // Punjabi
&LANG_KANNADA => (dir.join("schemes/kn/kn.vst"), dir.join("schemes/learnings/kn.vst.learnings")), // Kannada
&LANG_SANSKRIT => (dir.join("schemes/sa/sa.vst"), dir.join("schemes/learnings/sa.vst.learnings")), // Sanskrit
&LANG_TAMIL => (dir.join("schemes/ta/ta.vst"), dir.join("schemes/learnings/ta.vst.learnings")), // Tamil
&LANG_TELUGU => (dir.join("schemes/te/te.vst"), dir.join("schemes/learnings/te.vst.learnings")), // Telugu
_ => panic!("Unsupported language ID: {}", active_langid), // Panic for unsupported languages
};

// let scheme_path = dir.join("schemes/ml/ml.vst");
// let learning_path = dir.join("schemes/learnings/ml.vst.learnings");

match Varnam::init(
scheme_path,
Expand Down Expand Up @@ -162,44 +193,6 @@ impl CompositionProcessorEngine {

let results = VARNAM.transliterate(keystroke_buffer.to_owned());

// let results: Vec<&str> = Vec::from(["stuff", "stuff", "stuff", "stuff"]);

// let current_language = self.language_bar.get_active_langid();

// if let Ok(lang_id) = current_language {
// use std::io::prelude::*;

// let mut file = std::fs::OpenOptions::new()
// .write(true)
// .append(true)
// .open("C:\\Users\\doxop\\Documents\\debug.txt")
// .unwrap();

// if let Err(e) = writeln!(file, "Language ID: {}", lang_id) {
// eprintln!("Couldn't write to file: {}", e);
// let mut error_file = std::fs::OpenOptions::new()
// .write(true)
// .append(true)
// .open("C:\\Users\\doxop\\Documents\\debug.txt")
// .unwrap();
// if let Err(e) = writeln!(error_file, "Error: {}", e) {
// eprintln!("Couldn't write error to file: {}", e);
// }
// }
// } else {
// use std::io::prelude::*;

// let mut file = std::fs::OpenOptions::new()
// .write(true)
// .append(true)
// .open("C:\\Users\\doxop\\Documents\\debug.txt")
// .unwrap();

// if let Err(e) = writeln!(file, "Error: Failed to get active language ID") {
// eprintln!("Couldn't write error to file: {}", e);
// }
// }

for result in results {
matches.push((keystroke_buffer.clone(), result.to_string()))
}
Expand Down
12 changes: 6 additions & 6 deletions rust/composition_processor/src/engine/language_bar.rs
Original file line number Diff line number Diff line change
@@ -1,7 +1,7 @@
use std::ffi::c_void;

use globals::{
SAMPLEIME_GUID_PROFILE, SAMPLEIME_GUID_COMPARTMENT_DOUBLE_SINGLE_BYTE, SAMPLEIME_GUID_COMPARTMENT_PUNCTUATION,
SAMPLEIME_GUID_COMPARTMENT_DOUBLE_SINGLE_BYTE, SAMPLEIME_GUID_COMPARTMENT_PUNCTUATION,
};
use ime::resources::{
IME_MODE_DESCRIPTION, IME_MODE_OFF_ICO_INDEX, IME_MODE_ON_ICO_INDEX,
Expand All @@ -15,7 +15,7 @@ use windows::{
Win32::UI::TextServices::{
ITfCompartmentEventSink, ITfLangBarItemButton, ITfThreadMgr, ITfInputProcessorProfileMgr, TF_INPUTPROCESSORPROFILE,
GUID_COMPARTMENT_KEYBOARD_INPUTMODE_CONVERSION, GUID_COMPARTMENT_KEYBOARD_OPENCLOSE,
GUID_LBI_INPUTMODE, CLSID_TF_InputProcessorProfiles
GUID_LBI_INPUTMODE, GUID_TFCAT_TIP_KEYBOARD, CLSID_TF_InputProcessorProfiles
},
};
use ime::com::create_instance_inproc;
Expand Down Expand Up @@ -105,15 +105,15 @@ impl LanguageBar {
Ok(())
}

pub fn get_active_langid(&self) -> windows::core::Result<u16> {
pub fn get_active_langid() -> windows::core::Result<u16> {
let profile_manager: ITfInputProcessorProfileMgr =
create_instance_inproc(&CLSID_TF_InputProcessorProfiles)?;

let mut profile: TF_INPUTPROCESSORPROFILE = Default::default();
unsafe {
profile_manager.GetActiveProfile(&SAMPLEIME_GUID_PROFILE, &mut profile)?;
profile_manager.GetActiveProfile(&GUID_TFCAT_TIP_KEYBOARD, &mut profile)?;
}

Ok(profile.langid)
}
}
Expand Down
84 changes: 84 additions & 0 deletions windows-langinput/Cargo.lock

Some generated files are not rendered by default. Learn more about how customized files appear on GitHub.

18 changes: 18 additions & 0 deletions windows-langinput/Cargo.toml
Original file line number Diff line number Diff line change
@@ -0,0 +1,18 @@
[package]
name = "windows-langinput"
version = "0.1.0"
edition = "2021"

[dependencies]
globals = { path = "../rust/globals" }

[dependencies.windows]
version = "0.48.0"
features = [
"Win32_Foundation",
"Win32_System_LibraryLoader",
"Win32_UI_Input_KeyboardAndMouse",
"Win32_System_Com",
"Win32_System_SystemServices",
"Win32_UI_TextServices",
]
53 changes: 53 additions & 0 deletions windows-langinput/src/main.rs
Original file line number Diff line number Diff line change
@@ -0,0 +1,53 @@
use windows::Win32::UI::TextServices::{
ITfInputProcessorProfileMgr, TF_INPUTPROCESSORPROFILE, GUID_TFCAT_TIP_KEYBOARD,
CLSID_TF_InputProcessorProfiles
};

use windows::core::{Interface, Result, GUID};

use windows::Win32::System::Com::{CoCreateInstance, CoInitializeEx, CLSCTX_INPROC_SERVER, COINIT_APARTMENTTHREADED};

use windows::Win32::System::SystemServices::{
LANG_MALAYALAM, SUBLANG_MALAYALAM_INDIA,
LANG_ASSAMESE, SUBLANG_ASSAMESE_INDIA,
LANG_MARATHI, SUBLANG_MARATHI_INDIA,
LANG_BENGALI, SUBLANG_BENGALI_INDIA,
LANG_NEPALI, SUBLANG_NEPALI_INDIA,
LANG_GUJARATI, SUBLANG_GUJARATI_INDIA,
LANG_ODIA, SUBLANG_ODIA_INDIA,
LANG_HINDI, SUBLANG_HINDI_INDIA,
LANG_PUNJABI, SUBLANG_PUNJABI_INDIA,
LANG_KANNADA, SUBLANG_KANNADA_INDIA,
LANG_SANSKRIT, SUBLANG_SANSKRIT_INDIA,
LANG_TAMIL, SUBLANG_TAMIL_INDIA,
LANG_TELUGU, SUBLANG_TELUGU_INDIA,
};

pub fn create_instance_inproc<T: Interface + windows::core::ComInterface>(
clsid: &GUID,
) -> Result<T> {
unsafe { CoCreateInstance(clsid, None, CLSCTX_INPROC_SERVER) }
}

pub fn get_active_langid() -> windows::core::Result<u16> {
let profile_manager: ITfInputProcessorProfileMgr =
create_instance_inproc(&CLSID_TF_InputProcessorProfiles)?;

let mut profile: TF_INPUTPROCESSORPROFILE = Default::default();
unsafe {
profile_manager.GetActiveProfile(&GUID_TFCAT_TIP_KEYBOARD, &mut profile)?;
}

Ok(profile.langid)
}

fn main() {
unsafe {
CoInitializeEx(None, COINIT_APARTMENTTHREADED).expect("Failed to initialize COM");
}

let langid = get_active_langid().unwrap() as u32;
println!("{} - {}", LANG_MALAYALAM, SUBLANG_MALAYALAM_INDIA);
println!("{}", (SUBLANG_MALAYALAM_INDIA << 10 | LANG_MALAYALAM) as u16);
println!("Active langid: {}", langid);
}
1 change: 1 addition & 0 deletions windows-langinput/target/.rustc_info.json
Original file line number Diff line number Diff line change
@@ -0,0 +1 @@
{"rustc_fingerprint":13664666599156650873,"outputs":{"4614504638168534921":{"success":true,"status":"","code":0,"stdout":"rustc 1.73.0 (cc66ad468 2023-10-03)\nbinary: rustc\ncommit-hash: cc66ad468955717ab92600c770da8c1601a4ff33\ncommit-date: 2023-10-03\nhost: x86_64-pc-windows-gnu\nrelease: 1.73.0\nLLVM version: 17.0.2\n","stderr":""},"15729799797837862367":{"success":true,"status":"","code":0,"stdout":"___.exe\nlib___.rlib\n___.dll\n___.dll\nlib___.a\n___.dll\nC:\\Users\\doxop\\.rustup\\toolchains\\stable-x86_64-pc-windows-gnu\noff\n___\ndebug_assertions\npanic=\"unwind\"\nproc_macro\ntarget_arch=\"x86_64\"\ntarget_endian=\"little\"\ntarget_env=\"gnu\"\ntarget_family=\"windows\"\ntarget_feature=\"fxsr\"\ntarget_feature=\"sse\"\ntarget_feature=\"sse2\"\ntarget_has_atomic=\"16\"\ntarget_has_atomic=\"32\"\ntarget_has_atomic=\"64\"\ntarget_has_atomic=\"8\"\ntarget_has_atomic=\"ptr\"\ntarget_os=\"windows\"\ntarget_pointer_width=\"64\"\ntarget_vendor=\"pc\"\nwindows\n","stderr":""},"14799887915714938425":{"success":true,"status":"","code":0,"stdout":"___.exe\nlib___.rlib\n___.dll\n___.dll\nlib___.a\n___.dll\nC:\\Users\\doxop\\.rustup\\toolchains\\stable-x86_64-pc-windows-gnu\noff\n___\ndebug_assertions\npanic=\"unwind\"\nproc_macro\ntarget_arch=\"x86_64\"\ntarget_endian=\"little\"\ntarget_env=\"gnu\"\ntarget_family=\"windows\"\ntarget_feature=\"fxsr\"\ntarget_feature=\"sse\"\ntarget_feature=\"sse2\"\ntarget_has_atomic=\"16\"\ntarget_has_atomic=\"32\"\ntarget_has_atomic=\"64\"\ntarget_has_atomic=\"8\"\ntarget_has_atomic=\"ptr\"\ntarget_os=\"windows\"\ntarget_pointer_width=\"64\"\ntarget_vendor=\"pc\"\nwindows\n","stderr":""}},"successes":{}}
3 changes: 3 additions & 0 deletions windows-langinput/target/CACHEDIR.TAG
Original file line number Diff line number Diff line change
@@ -0,0 +1,3 @@
Signature: 8a477f597d28d172789f06886806bc55
# This file is a cache directory tag created by cargo.
# For information about cache directory tags see https://bford.info/cachedir/
Empty file.
Binary file not shown.
Original file line number Diff line number Diff line change
@@ -0,0 +1 @@
This file has an mtime of when this was started.
Original file line number Diff line number Diff line change
@@ -0,0 +1 @@
84018162c8646049
Original file line number Diff line number Diff line change
@@ -0,0 +1 @@
{"rustc":8246398906084555539,"features":"[]","target":13942762244805310453,"profile":13126374248311259211,"path":4401910561198685777,"deps":[[4069948179348390201,"windows",false,10713239733314860667]],"local":[{"CheckDepInfo":{"dep_info":"debug\\.fingerprint\\globals-5a4a9210e21fe9bf\\dep-lib-globals"}}],"rustflags":[],"metadata":8270665798335384255,"config":2202906307356721367,"compile_kind":0}
Binary file not shown.
Original file line number Diff line number Diff line change
@@ -0,0 +1 @@
This file has an mtime of when this was started.
Original file line number Diff line number Diff line change
@@ -0,0 +1 @@
41a52dff7d80ee8b
Original file line number Diff line number Diff line change
@@ -0,0 +1 @@
{"rustc":8246398906084555539,"features":"[]","target":13942762244805310453,"profile":13126374248311259211,"path":4401910561198685777,"deps":[[4069948179348390201,"windows",false,8914311598249581259]],"local":[{"CheckDepInfo":{"dep_info":"debug\\.fingerprint\\globals-956644818b420a56\\dep-lib-globals"}}],"rustflags":[],"metadata":8270665798335384255,"config":2202906307356721367,"compile_kind":0}
Binary file not shown.
Loading

0 comments on commit 78bf4ec

Please sign in to comment.