Add sj4_ime_length

This commit is contained in:
Nishi 2026-07-05 04:25:55 +09:00
commit 4f5463b884
5 changed files with 125 additions and 19 deletions

View file

@ -9,8 +9,19 @@ extern "C" {
typedef struct sj4ime Sj4Ime;
Sj4Ime* sj4_ime(int charset, const char* dict);
typedef void (*Sj4ImePacket)(Sj4Ime* ime, int type, void* data);
enum SJ4IMEPACKET {
Sj4ImeBeginKanList = 0,
Sj4ImeKanEntry,
Sj4ImeEndKanList
};
Sj4Ime* sj4_ime(int charset, const char* dict, Sj4ImePacket packet);
void sj4_ime_key(Sj4Ime* ime, int key);
int sj4_ime_length(Sj4Ime* ime);
void* sj4_ime_kouho(Sj4Ime* ime);
void* sj4_ime_kanabuf(Sj4Ime* ime);
void* sj4_ime_convbuf(Sj4Ime* ime);
#ifdef __cplusplus

View file

@ -24,6 +24,8 @@ typedef union sj4kouhobuffer {
typedef struct sj4kouho {
Sj4KouhoBuffer buffer;
int take;
unsigned char intbuf[SJ4BUFSZ];
} Sj4Kouho;
@ -32,6 +34,7 @@ typedef struct sj4lib Sj4Lib;
Sj4Lib* sj4_open(int, const char*);
int sj4_getkan(Sj4Lib*, const void*, int len, Sj4Kouho*);
int sj4_nextkan(Sj4Lib*);
int sj4_prevkan(Sj4Lib*);
void sj4_close(Sj4Lib*);
#ifdef __cplusplus

View file

@ -13,10 +13,12 @@ struct sj4ime {
Sj4Lib* lib;
int charset;
Sj4Kouho kouho;
unsigned int last;
Sj4ImePacket packet;
u_char romabuf[7];
Sj4Kouho kouho;
unsigned int length;
char romabuf[7];
u_char kanabuf[SJ4BUFSZ];
u_char convbuf[SJ4BUFSZ];
};
@ -29,7 +31,12 @@ static struct sj4table {
#include "KanaTable"
};
Sj4Ime* sj4_ime(int charset, const char* dict) {
#define DISPATCH(x, y) \
if(ime->packet != NULL) { \
ime->packet(ime, (x), (y)); \
}
Sj4Ime* sj4_ime(int charset, const char* dict, Sj4ImePacket packet) {
Sj4Ime* ime;
if((ime = calloc(1, sizeof(*ime))) == NULL) return NULL;
@ -41,6 +48,8 @@ Sj4Ime* sj4_ime(int charset, const char* dict) {
}
ime->charset = charset;
ime->packet = packet;
}
static int w_len(wchar_t* wc) {
@ -51,11 +60,11 @@ static int w_len(wchar_t* wc) {
return i;
}
static int b_len(int charset, Sj4KouhoBuffer* buffer) {
static int b_len(int charset, u_char* buffer) {
if(charset == SJ4UTF16) {
return w_len(buffer->utf16);
return w_len((wchar_t*)buffer);
} else {
return strlen(buffer->raw);
return strlen(buffer);
}
}
@ -106,27 +115,50 @@ static void concat_nc(int charset, u_char* out, u_char* in) {
#define ZEROBUF memset(&ime->kouho.buffer, 0, sizeof(ime->kouho.buffer))
static void comp(Sj4Ime* ime) {
if(ime->last == 0) {
#if 0
do {
#endif
if(ime->length == 0) {
concat_nc(ime->charset, ime->convbuf, ime->kanabuf);
} else {
concat_nc(ime->charset, ime->convbuf, ime->kouho.buffer.raw);
}
printf("%s\n", ime->convbuf);
#ifdef UCS
memset(ime->kanabuf, 0, sizeof(wchar_t));
#else
ime->kanabuf[0] = 0;
ime->last = 0;
#endif
} else {
int sc = ime->charset == SJ4UTF16 ? sizeof(wchar_t) : 1;
concat_nc(ime->charset, ime->convbuf, ime->kouho.buffer.raw);
memmove(ime->kanabuf, ime->kanabuf + ime->length * sc, SJ4BUFSZ - ime->length * sc);
memset(ime->kanabuf + SJ4BUFSZ - ime->length * sc, 0, ime->length * sc);
}
ime->length = 0;
ZEROBUF;
#if 0
} while(b_len(ime->charset, ime->kanabuf) > 0);
#endif
}
void sj4_ime_key(Sj4Ime* ime, int key) {
if(key == '\n') {
comp(ime);
} else if(key == ' ') {
reconvert:
if(b_len(ime->charset, &ime->kouho.buffer) == 0) {
ime->last = sj4_getkan(ime->lib, ime->kanabuf, strlen(ime->kanabuf), &ime->kouho);
reconvert:;
if(b_len(ime->charset, ime->kouho.buffer.raw) == 0) {
ime->length = sj4_getkan(ime->lib, ime->kanabuf, strlen(ime->kanabuf), &ime->kouho);
DISPATCH(Sj4ImeBeginKanList, NULL);
do {
DISPATCH(Sj4ImeKanEntry, &ime->kouho);
} while(sj4_nextkan(ime->lib) != 0);
DISPATCH(Sj4ImeEndKanList, NULL);
ime->length = sj4_getkan(ime->lib, ime->kanabuf, strlen(ime->kanabuf), &ime->kouho);
} else {
if((ime->last = sj4_nextkan(ime->lib)) == 0) {
if((ime->length = sj4_nextkan(ime->lib)) == 0) {
ZEROBUF;
goto reconvert;
@ -135,7 +167,7 @@ void sj4_ime_key(Sj4Ime* ime, int key) {
} else if(('a' <= tolower(key) && tolower(key) <= 'z') || key == '~' || key == ',' || key == '.' || key == '[' || key == ']') {
int i;
if(ime->last != 0) comp(ime);
if(ime->length != 0) comp(ime);
key = toupper(key);
@ -176,9 +208,28 @@ void sj4_ime_key(Sj4Ime* ime, int key) {
if(strlen(ime->romabuf) >= 4) {
ime->romabuf[0] = 0;
}
} else {
char keys[2];
keys[0] = key;
keys[1] = 0;
concat(ime->charset, ime->kanabuf, keys);
}
}
int sj4_ime_length(Sj4Ime* ime) {
return ime->length;
}
void* sj4_ime_kouho(Sj4Ime* ime) {
return ime->kouho.buffer.raw;
}
void* sj4_ime_kanabuf(Sj4Ime* ime) {
return ime->kanabuf;
}
void* sj4_ime_convbuf(Sj4Ime* ime) {
return ime->convbuf;
}

View file

@ -40,6 +40,7 @@ Sj4Lib* sj4_open(int charset, const char* dic) {
#define RUNME(PROC) \
PROC \
ctx->kouho->take = len; \
\
len2 = sj4_charset_to(ctx->charset, ctx->kouho->buffer.raw, ctx->kouho->intbuf + sizeof(STDYOUT), strlen(ctx->kouho->intbuf + sizeof(STDYOUT))); \
\
@ -81,6 +82,14 @@ int sj4_nextkan(Sj4Lib* ctx) {
});
}
int sj4_prevkan(Sj4Lib* ctx) {
int len, len2;
RUNME({
len = prevcl(ctx->ctx, ctx->kouho->intbuf, 0);
});
}
void sj4_close(Sj4Lib* ctx) {
free_context(ctx->ctx);
free(ctx);

View file

@ -5,18 +5,50 @@
#define CHARSET SJ4SJIS
#else
#define CHARSET SJ4UTF8
#include <termios.h>
#define getch getchar
#endif
static void ime_packet(Sj4Ime* ime, int type, void* data) {
printf("%d %p\n", type, data);
}
int main() {
Sj4Ime* ime = sj4_ime(CHARSET, "sj4main.dic");
Sj4Ime* ime = sj4_ime(CHARSET, "sj4main.dic", ime_packet);
char b;
char* conv = sj4_ime_convbuf(ime);
char* kouho = sj4_ime_kouho(ime);
if(ime == NULL) {
fprintf(stderr, "Failed to create context\n");
return 1;
}
while(fread(&b, 1, sizeof(b), stdin)) {
#ifdef _WIN32
#else
{
struct termios new;
tcgetattr(0, &new);
new.c_lflag &= ~(ICANON | ECHO);
tcsetattr(0, TCSANOW, &new);
}
#endif
while((b = getch()) != EOF) {
sj4_ime_key(ime, b);
if(conv[0]) {
printf("[%s]\n", conv);
conv[0] = 0;
} else if(kouho[0]) {
printf("<%s>", kouho);
}
if(b != '\n' && b != '\n') {
putchar(b);
}
}
}