engine: trim the key dispatch
mapget and maplookup were one trie probe with two predicates; mapmatch returns the match kind and mapget is its exact case. movedelta is a switch. searchkey's modifier test was unreachable behind transition's, searchlang's Alt/Super test behind both callers' earlier returns, and picksearch's range check behind numberedkouho. Korean key folding runs once at the top of transition. commit() on an empty preedit is a no-op, so the Ctrl branch and startsearch lose their haspre guards and repeated commit/reset pairs. Ctrl+language inside a search now commits the shown query as it does elsewhere instead of dropping it. Language ids are documented as the Ctrl codes they are; Im parameters no longer shadow the file's Im.
This commit is contained in:
172
strans.c
172
strans.c
@@ -9,7 +9,6 @@ static int candidatechosen;
|
||||
static Drawcmd lastdraw;
|
||||
static Emit transjp(Im*, Rune);
|
||||
static void backjp(Im*);
|
||||
static int maplookup(Trie*, Str*, Str*);
|
||||
|
||||
typedef struct Search Search;
|
||||
struct Search
|
||||
@@ -31,6 +30,28 @@ Lang langs[] = {
|
||||
};
|
||||
int nlang = nelem(langs);
|
||||
|
||||
/* Trie match kind for key; on an exact match out holds the value. */
|
||||
static int
|
||||
mapmatch(Trie *t, Str *key, Str *out)
|
||||
{
|
||||
char *v;
|
||||
int match, vlen;
|
||||
|
||||
sclear(out);
|
||||
if(key->n == 0)
|
||||
return TrieMiss;
|
||||
match = trielookup(t, key, &v, &vlen);
|
||||
if(match == TrieExact && !sinit(out, v, vlen))
|
||||
return TrieMiss;
|
||||
return match;
|
||||
}
|
||||
|
||||
int
|
||||
mapget(Trie *t, Str *key, Str *out)
|
||||
{
|
||||
return mapmatch(t, key, out) == TrieExact;
|
||||
}
|
||||
|
||||
static void
|
||||
clearkouho(void)
|
||||
{
|
||||
@@ -56,18 +77,12 @@ pagefirst(void)
|
||||
static int
|
||||
movedelta(u32int ks)
|
||||
{
|
||||
static struct {
|
||||
u32int key;
|
||||
int delta;
|
||||
} move[] = {
|
||||
{Kup, -1}, {Kdown, 1},
|
||||
{Kpgup, -Maxdisp}, {Kpgdown, Maxdisp},
|
||||
};
|
||||
int i;
|
||||
|
||||
for(i = 0; i < nelem(move); i++)
|
||||
if(move[i].key == ks)
|
||||
return move[i].delta;
|
||||
switch(ks){
|
||||
case Kup: return -1;
|
||||
case Kdown: return 1;
|
||||
case Kpgup: return -Maxdisp;
|
||||
case Kpgdown: return Maxdisp;
|
||||
}
|
||||
return 0;
|
||||
}
|
||||
|
||||
@@ -271,12 +286,12 @@ commit(Str *com)
|
||||
}
|
||||
|
||||
static void
|
||||
backjp(Im *im)
|
||||
backjp(Im *p)
|
||||
{
|
||||
if(im->raw.n != 0)
|
||||
spopr(&im->raw);
|
||||
if(p->raw.n != 0)
|
||||
spopr(&p->raw);
|
||||
else
|
||||
spopr(&im->pre);
|
||||
spopr(&p->pre);
|
||||
}
|
||||
|
||||
static int
|
||||
@@ -314,7 +329,7 @@ transjp(Im *p, Rune c)
|
||||
}
|
||||
key = e.raw;
|
||||
sputr(&key, c);
|
||||
if(maplookup(p->l->map, &key, &mapped)){
|
||||
if(mapmatch(p->l->map, &key, &mapped) != TrieMiss){
|
||||
e.raw = key;
|
||||
if(issmalltsu(&mapped)){
|
||||
sappend(&e.next, &mapped);
|
||||
@@ -327,7 +342,7 @@ transjp(Im *p, Rune c)
|
||||
sclear(&e.raw);
|
||||
sclear(&key);
|
||||
sputr(&key, c);
|
||||
if(maplookup(p->l->map, &key, &mapped)){
|
||||
if(mapmatch(p->l->map, &key, &mapped) != TrieMiss){
|
||||
e.raw = key;
|
||||
return e;
|
||||
}
|
||||
@@ -367,43 +382,30 @@ getlang(int lang)
|
||||
return nil;
|
||||
}
|
||||
|
||||
static int
|
||||
maplookup(Trie *t, Str *key, Str *out)
|
||||
{
|
||||
char *v;
|
||||
int match, vlen;
|
||||
|
||||
sclear(out);
|
||||
if(key->n == 0)
|
||||
return 0;
|
||||
match = trielookup(t, key, &v, &vlen);
|
||||
if(match == TrieMiss)
|
||||
return 0;
|
||||
if(match == TrieExact && !sinit(out, v, vlen))
|
||||
return 0;
|
||||
return 1;
|
||||
}
|
||||
|
||||
/*
|
||||
* The pending text is the key sequence itself while it is a prefix of some
|
||||
* map entry; the map value is what gets shown and committed.
|
||||
*/
|
||||
Emit
|
||||
transmap(Im *im, Rune c)
|
||||
transmap(Im *p, Rune c)
|
||||
{
|
||||
Emit e = {0};
|
||||
Str key, mapped;
|
||||
Trie *t;
|
||||
|
||||
t = im->l->map;
|
||||
key = im->pre;
|
||||
t = p->l->map;
|
||||
key = p->pre;
|
||||
sputr(&key, c);
|
||||
if(maplookup(t, &key, &mapped)){
|
||||
if(mapmatch(t, &key, &mapped) != TrieMiss){
|
||||
e.eat = 1;
|
||||
e.next = key;
|
||||
return e;
|
||||
}
|
||||
if(!mapget(t, &im->pre, &e.s))
|
||||
e.s = im->pre;
|
||||
if(!mapget(t, &p->pre, &e.s))
|
||||
e.s = p->pre;
|
||||
sclear(&key);
|
||||
sputr(&key, c);
|
||||
if(!maplookup(t, &key, &mapped))
|
||||
if(mapmatch(t, &key, &mapped) == TrieMiss)
|
||||
return e;
|
||||
e.eat = 1;
|
||||
sputr(&e.next, c);
|
||||
@@ -533,13 +535,9 @@ searchquery(void)
|
||||
}
|
||||
|
||||
static int
|
||||
searchlang(Rune c, u32int mod)
|
||||
searchlang(Rune c)
|
||||
{
|
||||
if(mod & (Malt|Msuper))
|
||||
return 0;
|
||||
if(c == LangEMOJI || c == LangHANJA)
|
||||
return c;
|
||||
return 0;
|
||||
return c == LangEMOJI || c == LangHANJA ? c : 0;
|
||||
}
|
||||
|
||||
static void
|
||||
@@ -551,17 +549,13 @@ endsearch(void)
|
||||
clearkouho();
|
||||
}
|
||||
|
||||
/* A search commits any pending composition and takes over the keys. */
|
||||
static void
|
||||
startsearch(int lang, Str *com)
|
||||
{
|
||||
if(haspre(&im))
|
||||
commit(com);
|
||||
sclear(&im.pre);
|
||||
sclear(&im.raw);
|
||||
clearkouho();
|
||||
commit(com);
|
||||
endsearch();
|
||||
search.lang = lang;
|
||||
sclear(&search.raw);
|
||||
sclear(&search.text);
|
||||
}
|
||||
|
||||
static void
|
||||
@@ -571,14 +565,11 @@ commitsearch(Str *com)
|
||||
endsearch();
|
||||
}
|
||||
|
||||
static int
|
||||
static void
|
||||
picksearch(int n, Str *com)
|
||||
{
|
||||
if(n < 0 || n >= im.nkouho)
|
||||
return 0;
|
||||
sappend(com, &im.kouho[n]);
|
||||
endsearch();
|
||||
return 1;
|
||||
}
|
||||
|
||||
static int
|
||||
@@ -587,8 +578,6 @@ searchkey(u32int ks, u32int mod, Str *com)
|
||||
int n;
|
||||
Rune c;
|
||||
|
||||
if(ismodkey(ks))
|
||||
return 0;
|
||||
n = movedelta(ks);
|
||||
if(n != 0){
|
||||
if(im.nkouho == 0)
|
||||
@@ -617,8 +606,9 @@ searchkey(u32int ks, u32int mod, Str *com)
|
||||
}
|
||||
if(ks == Kret){
|
||||
if(im.nkouho > 0)
|
||||
return picksearch(im.sel >= 0 ? im.sel : 0, com);
|
||||
commitsearch(com);
|
||||
picksearch(max(im.sel, 0), com);
|
||||
else
|
||||
commitsearch(com);
|
||||
return 1;
|
||||
}
|
||||
if(ks == Kback){
|
||||
@@ -641,25 +631,21 @@ searchkey(u32int ks, u32int mod, Str *com)
|
||||
}
|
||||
if(mod & Mctrl){
|
||||
c = ctrlkey(ks);
|
||||
n = searchlang(c, mod);
|
||||
if(n != 0){
|
||||
if(n == search.lang)
|
||||
endsearch();
|
||||
else
|
||||
startsearch(n, com);
|
||||
return 1;
|
||||
n = searchlang(c);
|
||||
if(n == search.lang)
|
||||
endsearch();
|
||||
else if(n != 0)
|
||||
startsearch(n, com);
|
||||
else{
|
||||
commitsearch(com);
|
||||
return setlang(c);
|
||||
}
|
||||
endsearch();
|
||||
if(setlang(c))
|
||||
return 1;
|
||||
return 0;
|
||||
return 1;
|
||||
}
|
||||
if(search.raw.n >= Maxrunes){
|
||||
commitsearch(com);
|
||||
return 0;
|
||||
}
|
||||
if(im.l->lang == LangKO)
|
||||
ks = kokey(ks, mod);
|
||||
sputr(&search.raw, ks);
|
||||
searchquery();
|
||||
return 1;
|
||||
@@ -673,6 +659,8 @@ transition(u32int ks, u32int mod, Str *com)
|
||||
|
||||
if(ismodkey(ks))
|
||||
return 0;
|
||||
if(im.l->lang == LangKO)
|
||||
ks = kokey(ks, mod);
|
||||
if(search.lang)
|
||||
return searchkey(ks, mod, com);
|
||||
n = movedelta(ks);
|
||||
@@ -728,22 +716,14 @@ transition(u32int ks, u32int mod, Str *com)
|
||||
}
|
||||
if(mod & Mctrl){
|
||||
c = ctrlkey(ks);
|
||||
n = searchlang(c, mod);
|
||||
n = searchlang(c);
|
||||
if(n != 0){
|
||||
startsearch(n, com);
|
||||
return 1;
|
||||
}
|
||||
if(getlang(c) != nil){
|
||||
if(haspre(&im))
|
||||
commit(com);
|
||||
reset();
|
||||
setlang(c);
|
||||
return 1;
|
||||
}
|
||||
if(haspre(&im))
|
||||
commit(com);
|
||||
commit(com);
|
||||
reset();
|
||||
return 0;
|
||||
return setlang(c);
|
||||
}
|
||||
if(ks == '0' && im.nkouho > 0){
|
||||
commit(com);
|
||||
@@ -768,10 +748,7 @@ transition(u32int ks, u32int mod, Str *com)
|
||||
reset();
|
||||
return 0;
|
||||
}
|
||||
if(im.l->lang == LangKO)
|
||||
ks = kokey(ks, mod);
|
||||
n = dotrans(ks, com);
|
||||
return n;
|
||||
return dotrans(ks, com);
|
||||
}
|
||||
|
||||
static void
|
||||
@@ -871,14 +848,3 @@ imthread(void*)
|
||||
}
|
||||
}
|
||||
|
||||
int
|
||||
mapget(Trie *t, Str *key, Str *out)
|
||||
{
|
||||
char *v;
|
||||
int vlen;
|
||||
|
||||
sclear(out);
|
||||
if(key->n == 0 || trielookup(t, key, &v, &vlen) != TrieExact)
|
||||
return 0;
|
||||
return sinit(out, v, vlen);
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user