hanja: add one-shot Korean search

This commit is contained in:
2026-08-12 19:19:26 +09:00
parent e69883d0ad
commit 0216cc3c8a
4 changed files with 288 additions and 59 deletions

View File

@@ -16,12 +16,20 @@ static int maplookup(Trie*, Str*, Str*);
typedef struct Search Search;
struct Search
{
int on;
int kind;
Str raw;
Str text;
};
static Search search;
enum
{
SearchOff,
SearchEmoji,
SearchHanja,
Hanjakey = 0x08,
};
uvlong
ownernew(void)
{
@@ -115,12 +123,12 @@ show(void)
int i, first, n;
sclear(&dc.pre);
if(search.on)
if(search.kind)
pre = search.text;
else
impre(&pre);
if(popup){
if(search.on || isjp(&im) || im.l->map == nil ||
if(search.kind || isjp(&im) || im.l->map == nil ||
!mapget(im.l->map, &pre, &dc.pre))
dc.pre = pre;
}
@@ -146,7 +154,7 @@ reset(void)
{
sclear(&im.pre);
sclear(&im.raw);
search.on = 0;
search.kind = SearchOff;
sclear(&search.raw);
sclear(&search.text);
memset(&caret, 0, sizeof caret);
@@ -460,13 +468,13 @@ addkouho(Str *s)
}
static void
emojilookup(Str *key, Dictres *res)
searchlookup(int lang, Str *key, Dictres *res)
{
Dictreq req;
req.key = *key;
req.pre = req.key;
req.lang = LangEMOJI;
req.lang = lang;
dictlookup(&req, res);
}
@@ -482,13 +490,13 @@ emojiquery(void)
transstr(im.l, &search.raw, &local);
foldascii(&local);
clearkouho();
emojilookup(&raw, &res);
searchlookup(LangEMOJI, &raw, &res);
rawhit = res.nkouho != 0;
for(i = 0; i < res.nkouho; i++)
addkouho(&res.kouho[i]);
localhit = 0;
if(scmp(&raw, &local) != 0){
emojilookup(&local, &res);
searchlookup(LangEMOJI, &local, &res);
localhit = res.nkouho != 0;
for(i = 0; i < res.nkouho; i++)
addkouho(&res.kouho[i]);
@@ -497,10 +505,44 @@ emojiquery(void)
show();
}
static void
hanjaquery(void)
{
static Dictres res;
Str key;
transstr(getlang(LangKO), &search.raw, &key);
search.text = key;
searchlookup(LangKO, &key, &res);
setkouho(&res);
show();
}
static void
searchquery(void)
{
if(search.kind == SearchEmoji)
emojiquery();
else if(search.kind == SearchHanja)
hanjaquery();
}
static int
searchkind(Rune c, u32int mod)
{
if(c == LangEMOJI)
return SearchEmoji;
if(mod & (Malt|Msuper))
return SearchOff;
if(c == Hanjakey && im.l->lang == LangKO)
return SearchHanja;
return SearchOff;
}
static void
endsearch(void)
{
search.on = 0;
search.kind = SearchOff;
sclear(&search.raw);
sclear(&search.text);
clearkouho();
@@ -508,14 +550,14 @@ endsearch(void)
}
static void
startsearch(Str *com)
startsearch(int kind, Str *com)
{
if(haspre(&im))
commit(com);
sclear(&im.pre);
sclear(&im.raw);
clearkouho();
search.on = 1;
search.kind = kind;
sclear(&search.raw);
sclear(&search.text);
show();
@@ -529,7 +571,7 @@ commitsearch(Str *com)
}
static int
pickemoji(int n, Str *com)
picksearch(int n, Str *com)
{
if(n < 0 || n >= im.nkouho)
return 0;
@@ -559,7 +601,7 @@ searchkey(u32int ks, u32int mod, Str *com)
n = ks - '1';
off = im.sel >= Maxdisp ? im.sel - Maxdisp + 1 : 0;
if(n >= 0 && n < Maxdisp && off + n < im.nkouho && mod == 0){
pickemoji(off + n, com);
picksearch(off + n, com);
return 1;
}
if(ks == Ktab){
@@ -579,7 +621,7 @@ searchkey(u32int ks, u32int mod, Str *com)
}
if(ks == Kret){
if(im.nkouho > 0)
return pickemoji(im.sel >= 0 ? im.sel : 0, com);
return picksearch(im.sel >= 0 ? im.sel : 0, com);
commitsearch(com);
return 1;
}
@@ -587,7 +629,7 @@ searchkey(u32int ks, u32int mod, Str *com)
if(search.raw.n == 0)
return 1;
spopr(&search.raw);
emojiquery();
searchquery();
return 1;
}
if(ks == Kesc){
@@ -596,8 +638,12 @@ searchkey(u32int ks, u32int mod, Str *com)
}
if(mod & Mctrl){
c = ctrlkey(ks);
if(c == LangEMOJI){
endsearch();
n = searchkind(c, mod);
if(n != SearchOff){
if(n == search.kind)
endsearch();
else
startsearch(n, com);
return 1;
}
if(c == 0x10){
@@ -618,8 +664,10 @@ searchkey(u32int ks, u32int mod, Str *com)
commitsearch(com);
return 0;
}
if(search.kind == SearchHanja)
ks = kokey(ks, mod);
sputr(&search.raw, ks);
emojiquery();
searchquery();
return 1;
}
@@ -631,7 +679,7 @@ keystroke(u32int ks, u32int mod, Str *com)
if(ismodkey(ks))
return 0;
if(search.on)
if(search.kind)
return searchkey(ks, mod, com);
if(ks == Kdown || ks == Kup){
if(im.nkouho == 0)
@@ -690,8 +738,9 @@ keystroke(u32int ks, u32int mod, Str *com)
}
if(mod & Mctrl){
c = ctrlkey(ks);
if(c == LangEMOJI){
startsearch(com);
n = searchkind(c, mod);
if(n != SearchOff){
startsearch(n, com);
return 1;
}
if(c == 0x10){
@@ -795,7 +844,7 @@ imhandlekey(Keyreq *kr)
break;
}
if(kr->want && kr->owner == activeowner){
if(search.on)
if(search.kind)
res.preedit = search.text;
else
impre(&res.preedit);
@@ -809,7 +858,7 @@ dictresult(Dictres *res)
Str pre;
impre(&pre);
if(search.on || res->lang != im.l->lang ||
if(search.kind || res->lang != im.l->lang ||
scmp(&res->key, &pre) != 0)
return;
setkouho(res);