Example #1
0
static void FcitxRimeStart(FcitxRime* rime, boolean fullcheck) {

    char* user_path = NULL;
    FILE* fp = FcitxXDGGetFileUserWithPrefix("rime", ".place_holder", "w", NULL);
    if (fp)
        fclose(fp);
    FcitxXDGGetFileUserWithPrefix("rime", "", NULL, &user_path);
    //char* shared_data_dir = fcitx_utils_get_fcitx_path_with_filename("pkgdatadir", "rime");
    const char* shared_data_dir = RIME_DATA_DIR;

    RIME_STRUCT(RimeTraits, fcitx_rime_traits);
    fcitx_rime_traits.shared_data_dir = shared_data_dir;
    fcitx_rime_traits.app_name = "rime.fcitx-rime";
    fcitx_rime_traits.user_data_dir = user_path;
    fcitx_rime_traits.distribution_name = "Rime";
    fcitx_rime_traits.distribution_code_name = "fcitx-rime";
    fcitx_rime_traits.distribution_version = "0.2.3";
    if (rime->firstRun) {
        rime->api->setup(&fcitx_rime_traits);
        rime->firstRun = false;
    }
    rime->api->initialize(&fcitx_rime_traits);
    rime->api->set_notification_handler(FcitxRimeNotificationHandler, rime);
    rime->api->start_maintenance(fullcheck);

    rime->session_id = rime->api->create_session();
    free(user_path);
}
Example #2
0
void FcitxRimeUpdateStatus(FcitxRime* rime)
{
    if (rime->api->is_maintenance_mode()) {
        return;
    }
    if (!rime->api->find_session(rime->session_id)) {
        rime->session_id = rime->api->create_session();
    }
    
    RIME_STRUCT(RimeStatus, status);
    if (rime->api->get_status(rime->session_id, &status)) {
        char* text = "";
        if (status.is_disabled) {
            text = "\xe2\x8c\x9b";
        } else if (status.is_ascii_mode) {
            text = "A";
        } else if (status.schema_name &&
                status.schema_name[0] != '.') {
            text = status.schema_name;
        } else {
            text = "δΈ­";
        }
        FcitxUISetStatusString(rime->owner, "rime-enzh", text, text);
        rime->api->free_status(&status);
    } else {
        FcitxUISetStatusString(rime->owner, "rime-enzh", "\xe2\x8c\x9b", "\xe2\x8c\x9b");
    }
}
Example #3
0
INPUT_RETURN_VALUE FcitxRimeDoInputReal(void* arg, FcitxKeySym sym, unsigned int state)
{
    FcitxRime *rime = (FcitxRime *)arg;

    if (rime->api->is_maintenance_mode()) {
        return IRV_TO_PROCESS;
    }
    if (!rime->api->find_session(rime->session_id)) {
        rime->session_id = rime->api->create_session();
    }
    if (!rime->session_id) { // service disabled
        FcitxRimeUpdateStatus(rime);
        return IRV_TO_PROCESS;
    }
    boolean result = rime->api->process_key(rime->session_id, sym, state);

    RIME_STRUCT(RimeCommit, commit);
    if (rime->api->get_commit(rime->session_id, &commit)) {
        FcitxInputContext* ic = FcitxInstanceGetCurrentIC(rime->owner);
        FcitxInstanceCommitString(rime->owner, ic, commit.text);
        rime->api->free_commit(&commit);
    }

    FcitxRimeUpdateStatus(rime);

    if (!result) {
        FcitxRimeGetCandWords(rime);
        FcitxUIUpdateInputWindow(rime->owner);
        return IRV_TO_PROCESS;
    }
    else
        return IRV_DISPLAY_CANDWORDS;
}
Example #4
0
static jboolean get_status(JNIEnv *env, jobject thiz, jint session_id) {
  RIME_STRUCT(RimeStatus, status);
  Bool r = RimeGetStatus(session_id, &status);
  if (r) {
    jclass jc = env->GetObjectClass(thiz);
    jfieldID fid = env->GetFieldID(jc, "schema_id", "Ljava/lang/String;");
    env->SetObjectField(thiz, fid, newJstring(env, status.schema_id));
    fid = env->GetFieldID(jc, "schema_name", "Ljava/lang/String;");
    env->SetObjectField(thiz, fid, newJstring(env, status.schema_name));
    fid = env->GetFieldID(jc, "is_disabled", "Z");
    env->SetBooleanField(thiz, fid, status.is_disabled);
    fid = env->GetFieldID(jc, "is_composing", "Z");
    env->SetBooleanField(thiz, fid, status.is_composing);
    fid = env->GetFieldID(jc, "is_ascii_mode", "Z");
    env->SetBooleanField(thiz, fid, status.is_ascii_mode);
    fid = env->GetFieldID(jc, "is_full_shape", "Z");
    env->SetBooleanField(thiz, fid, status.is_full_shape);
    fid = env->GetFieldID(jc, "is_simplified", "Z");
    env->SetBooleanField(thiz, fid, status.is_simplified);
    fid = env->GetFieldID(jc, "is_traditional", "Z");
    env->SetBooleanField(thiz, fid, status.is_traditional);
    fid = env->GetFieldID(jc, "is_ascii_punct", "Z");
    env->SetBooleanField(thiz, fid, status.is_ascii_punct);
    RimeFreeStatus(&status);
  }
  return r;
}
Example #5
0
void RimeWithWeaselHandler::_GetContext(weasel::Context & weasel_context, UINT session_id)
{
	RIME_STRUCT(RimeContext, ctx);
	if (RimeGetContext(session_id, &ctx))
	{
		if (ctx.composition.length > 0)
		{
			weasel_context.preedit.str = utf8towcs(ctx.composition.preedit);
			if (ctx.composition.sel_start < ctx.composition.sel_end)
			{
				weasel::TextAttribute attr;
				attr.type = weasel::HIGHLIGHTED;
				attr.range.start = utf8towcslen(ctx.composition.preedit, ctx.composition.sel_start);
				attr.range.end = utf8towcslen(ctx.composition.preedit, ctx.composition.sel_end);

				weasel_context.preedit.attributes.push_back(attr);
			}
		}
		if (ctx.menu.num_candidates)
		{
			weasel::CandidateInfo &cinfo(weasel_context.cinfo);
			_GetCandidateInfo(cinfo, ctx);
		}
		RimeFreeContext(&ctx);
	}
}
Example #6
0
INPUT_RETURN_VALUE FcitxRimeGetCandWord(void* arg, FcitxCandidateWord* candWord)
{
    FcitxRime *rime = (FcitxRime *)arg;
    RIME_STRUCT(RimeContext, context);
    INPUT_RETURN_VALUE retVal = IRV_TO_PROCESS;
    if (rime->api->get_context(rime->session_id, &context)) {
        if (context.menu.num_candidates)
        {
            int i = *(int*) candWord->priv;
            const char* digit = DIGIT_STR_CHOOSE;
            int num_select_keys = context.menu.select_keys ? strlen(context.menu.select_keys) : 0;
            FcitxKeySym sym = FcitxKey_None;
            if (i < 10) {
                if (i < num_select_keys)
                    sym = context.menu.select_keys[i];
                else
                    sym = digit[i];
            }
            if (sym != FcitxKey_None) {
                boolean result = rime->api->process_key(rime->session_id, sym, 0);
                
                RIME_STRUCT(RimeCommit, commit);
                if (rime->api->get_commit(rime->session_id, &commit)) {
                    FcitxInputContext* ic = FcitxInstanceGetCurrentIC(rime->owner);
                    FcitxInstanceCommitString(rime->owner, ic, commit.text);
                    rime->api->free_commit(&commit);
                }
                if (!result) {
                    FcitxRimeGetCandWords(rime);
                    FcitxUIUpdateInputWindow(rime->owner);
                    retVal = IRV_TO_PROCESS;
                }
                else
                    retVal = IRV_DISPLAY_CANDWORDS;
            }
        }
        rime->api->free_context(&context);
    }

    return retVal;
}
Example #7
0
static void start(JNIEnv *env, jobject thiz, jstring shared_data_dir, jstring user_data_dir) {
  RIME_STRUCT(RimeTraits, traits);
  
  const char* str1 = shared_data_dir == NULL ? NULL : env->GetStringUTFChars(shared_data_dir, NULL); 
  const char* str2 = user_data_dir == NULL ? NULL : env->GetStringUTFChars(user_data_dir, NULL); 
  if (str1 != NULL) traits.shared_data_dir = str1;
  if (str2 != NULL) traits.user_data_dir = str2;
  traits.app_name = "rime.jni";
  ALOGE("setup...\n");
  RimeInitialize(&traits);
  env->ReleaseStringUTFChars(shared_data_dir, str1);
  env->ReleaseStringUTFChars(user_data_dir, str2);
}
Example #8
0
// output
static jboolean get_commit(JNIEnv *env, jobject thiz, jint session_id) {
  RIME_STRUCT(RimeCommit, commit);
  Bool r = RimeGetCommit((RimeSessionId)session_id, &commit);
  jclass jc = env->GetObjectClass(thiz);
  jfieldID fid = env->GetFieldID(jc, "commit_text", "Ljava/lang/String;");
  jstring s = NULL;
  if (r) {
    s = newJstring(env, commit.text);
    RimeFreeCommit(&commit);
  }
  env->SetObjectField(thiz, fid, s);
  return r;
}
Example #9
0
void RimeWithWeaselHandler::_Setup()
{
	RIME_STRUCT(RimeTraits, weasel_traits);
	weasel_traits.shared_data_dir = weasel_shared_data_dir();
	weasel_traits.user_data_dir = weasel_user_data_dir();
	const int len = 20;
	char utf8_str[len];
	memset(utf8_str, 0, sizeof(utf8_str));
	WideCharToMultiByte(CP_UTF8, 0, WEASEL_IME_NAME, -1, utf8_str, len - 1, NULL, NULL);
	weasel_traits.distribution_name = utf8_str;
	weasel_traits.distribution_code_name = WEASEL_CODE_NAME;
	weasel_traits.distribution_version = WEASEL_VERSION;
	weasel_traits.app_name = "rime.weasel";
	RimeSetup(&weasel_traits);
	RimeSetNotificationHandler(&RimeWithWeaselHandler::OnNotify, this);
}
Example #10
0
static jboolean get_context(JNIEnv *env, jobject thiz, jint session_id) {
  RIME_STRUCT(RimeContext, context);
  Bool r = RimeGetContext(session_id, &context);
  if (r) {
    jclass jc = env->GetObjectClass(thiz);
    jfieldID fid;
    fid = env->GetFieldID(jc, "commit_text_preview", "Ljava/lang/String;");
    env->SetObjectField(thiz, fid, newJstring(env, context.commit_text_preview));

    fid = env->GetFieldID(jc, "menu_num_candidates", "I");
    env->SetIntField(thiz, fid, context.menu.num_candidates);
    fid = env->GetFieldID(jc, "menu_page_size", "I");
    env->SetIntField(thiz, fid, context.menu.page_size);
    fid = env->GetFieldID(jc, "menu_page_no", "I");
    env->SetIntField(thiz, fid, context.menu.page_no);
    fid = env->GetFieldID(jc, "menu_highlighted_candidate_index", "I");
    env->SetIntField(thiz, fid, context.menu.highlighted_candidate_index);
    fid = env->GetFieldID(jc, "menu_is_last_page", "Z");
    env->SetBooleanField(thiz, fid, context.menu.is_last_page);
    fid = env->GetFieldID(jc, "menu_select_keys", "Ljava/lang/String;");
    env->SetObjectField(thiz, fid, newJstring(env, context.menu.select_keys));

    fid = env->GetFieldID(jc, "composition_length", "I");
    env->SetIntField(thiz, fid, context.composition.length);
    fid = env->GetFieldID(jc, "composition_cursor_pos", "I");
    env->SetIntField(thiz, fid, context.composition.cursor_pos);
    fid = env->GetFieldID(jc, "composition_sel_start", "I");
    env->SetIntField(thiz, fid, context.composition.sel_start);
    fid = env->GetFieldID(jc, "composition_sel_end", "I");
    env->SetIntField(thiz, fid, context.composition.sel_end);
    fid = env->GetFieldID(jc, "composition_preedit", "Ljava/lang/String;");
    env->SetObjectField(thiz, fid, newJstring(env, context.composition.preedit));

    int n = context.menu.num_candidates;
    fid = env->GetFieldID(jc, "candidates_text", "[Ljava/lang/String;");
    jobjectArray texts = (jobjectArray) env->GetObjectField(thiz, fid);
    fid = env->GetFieldID(jc, "candidates_comment", "[Ljava/lang/String;");
    jobjectArray comments = (jobjectArray) env->GetObjectField(thiz, fid);
    for (int i = 0; i < n;  ++i) {
      env->SetObjectArrayElement(texts, i, newJstring(env, context.menu.candidates[i].text));
      env->SetObjectArrayElement(comments, i, newJstring(env, context.menu.candidates[i].comment));
    }
    RimeFreeContext(&context);
  }
  return r;
}
Example #11
0
void Configurator::Initialize()
{
	RIME_STRUCT(RimeTraits, weasel_traits);
	weasel_traits.shared_data_dir = weasel_shared_data_dir();
	weasel_traits.user_data_dir = weasel_user_data_dir();
	const int len = 20;
	char utf8_str[len];
	memset(utf8_str, 0, sizeof(utf8_str));
	WideCharToMultiByte(CP_UTF8, 0, WEASEL_IME_NAME, -1, utf8_str, len - 1, NULL, NULL);
	weasel_traits.distribution_name = utf8_str;
	weasel_traits.distribution_code_name = WEASEL_CODE_NAME;
	weasel_traits.distribution_version = WEASEL_VERSION;
	weasel_traits.app_name = "rime.weasel";
	RimeSetup(&weasel_traits);
	
	LOG(INFO) << "WeaselDeployer reporting.";
	RimeDeployerInitialize(NULL);
}
Example #12
0
void RimeWithWeaselHandler::_GetStatus(weasel::Status & stat, UINT session_id)
{
	RIME_STRUCT(RimeStatus, status);
	if (RimeGetStatus(session_id, &status))
	{
		std::string schema_id = status.schema_id;
		if (schema_id != m_last_schema_id)
		{
			m_last_schema_id = schema_id;
			RimeSetOption(session_id, "__synced", false); // Sync new schema options with front end
			_LoadSchemaSpecificSettings(schema_id);
		}
		stat.schema_name = utf8towcs(status.schema_name);
		stat.ascii_mode = !!status.is_ascii_mode;
		stat.composing = !!status.is_composing;
		stat.disabled = !!status.is_disabled;
		RimeFreeStatus(&status);
	}

}
Example #13
0
INPUT_RETURN_VALUE FcitxRimeGetCandWords(void* arg)
{
    FcitxRime *rime = (FcitxRime *)arg;
    FcitxInputState *input = FcitxInstanceGetInputState(rime->owner);
    FcitxInstanceCleanInputWindow(rime->owner);

    RIME_STRUCT(RimeContext, context);
    if (!rime->api->get_context(rime->session_id, &context)) {
        return IRV_DISPLAY_CANDWORDS;
    }

    if (context.composition.length == 0) {
        rime->api->free_context(&context);
        return IRV_DISPLAY_CANDWORDS;
    }

    FcitxMessages* msgPreedit = FcitxInputStateGetPreedit(input);
    FcitxMessages* msgClientPreedit = FcitxInputStateGetClientPreedit(input);
    FcitxInputStateSetShowCursor(input, true);
    FcitxInputStateSetCursorPos(input, context.composition.cursor_pos);
    if (context.commit_text_preview) {
        FcitxInputStateSetClientCursorPos(input, strlen(context.commit_text_preview));
    }

    /* converted text */
    if (context.composition.sel_start > 0) {
        char* temp = strndup(context.composition.preedit, context.composition.sel_start);
        FcitxMessagesAddMessageAtLast(msgPreedit, MSG_OTHER, "%s", temp);
        free(temp);
        if (context.commit_text_preview) {
            temp = strndup(context.commit_text_preview, context.composition.sel_start);
            FcitxMessagesAddMessageAtLast(msgClientPreedit, MSG_INPUT, "%s", temp);
            free(temp);
        }
    }

    /* converting candidate */
    if (context.composition.sel_start < context.composition.sel_end) {
        char* temp = strndup(&context.composition.preedit[context.composition.sel_start], context.composition.sel_end - context.composition.sel_start);
        FcitxMessagesAddMessageAtLast(msgPreedit, MSG_HIGHLIGHT | MSG_CODE, "%s", temp);
        free(temp);
        if (context.commit_text_preview) {
            FcitxMessagesAddMessageAtLast(msgClientPreedit, MSG_HIGHLIGHT, "%s", &context.commit_text_preview[context.composition.sel_start]);
        }
    }

    /* remaining input to convert */
    if (context.composition.sel_end < strlen(context.composition.preedit)) {
        FcitxMessagesAddMessageAtLast(msgPreedit, MSG_CODE, "%s", &context.composition.preedit[context.composition.sel_end]);
    }

    if (context.menu.num_candidates)
    {
        FcitxCandidateWordList* candList = FcitxInputStateGetCandidateList(input);
        const char* digit = DIGIT_STR_CHOOSE;
        char strChoose[11];
        strChoose[10] = '\0';
        FcitxCandidateWordSetPageSize(candList, 10);
        int num_select_keys = context.menu.select_keys ? strlen(context.menu.select_keys) : 0;
        int i;
        for (i = 0; i < context.menu.num_candidates; ++i) {
            FcitxCandidateWord candWord;
            candWord.strWord = strdup (context.menu.candidates[i].text);
            if (i == context.menu.highlighted_candidate_index)
                candWord.wordType = MSG_CANDIATE_CURSOR;
            else
                candWord.wordType = MSG_OTHER;
            candWord.strExtra = context.menu.candidates[i].comment ? strdup (context.menu.candidates[i].comment) : NULL;
            candWord.extraType = MSG_CODE;
            candWord.callback = FcitxRimeGetCandWord;
            candWord.owner = rime;
            int* priv = fcitx_utils_new(int);
            *priv = i;
            candWord.priv = priv;

            FcitxCandidateWordAppend(candList, &candWord);
            if (i < 10) {
                if (i < num_select_keys) {
                    strChoose[i] = context.menu.select_keys[i];
                }
                else {
                    strChoose[i] = digit[i];
                }
            }
        }
        FcitxCandidateWordSetChoose(candList, strChoose);

        FcitxCandidateWordSetOverridePaging(candList, context.menu.page_no != 0, !context.menu.is_last_page, FcitxRimePaging, rime, NULL);
    }
Example #14
0
bool RimeWithWeaselHandler::_Respond(UINT session_id, EatLine eat)
{
	std::set<std::string> actions;
	std::list<std::string> messages;

	// extract information

	RIME_STRUCT(RimeCommit, commit);
	if (RimeGetCommit(session_id, &commit))
	{
		actions.insert("commit");
		messages.push_back(std::string("commit=") + commit.text + '\n');
		RimeFreeCommit(&commit);
	}
	
	bool is_composing = false;
	RIME_STRUCT(RimeStatus, status);
	if (RimeGetStatus(session_id, &status))
	{
		is_composing = !!status.is_composing;
		actions.insert("status");
		messages.push_back(std::string("status.ascii_mode=") + std::to_string(status.is_ascii_mode) + '\n');
		messages.push_back(std::string("status.composing=") + std::to_string(status.is_composing) + '\n');
		messages.push_back(std::string("status.disabled=") + std::to_string(status.is_disabled) + '\n');
		RimeFreeStatus(&status);
	}
	
	RIME_STRUCT(RimeContext, ctx);
	if (RimeGetContext(session_id, &ctx))
	{
		if (is_composing)
		{
			actions.insert("ctx");
			switch (m_ui->style().preedit_type)
			{
			case weasel::UIStyle::PREVIEW:
				if (ctx.commit_text_preview != NULL)
				{
					std::string first = ctx.commit_text_preview;
					messages.push_back(std::string("ctx.preedit=") + first + '\n');
					messages.push_back(std::string("ctx.preedit.cursor=") +
						std::to_string(utf8towcslen(first.c_str(), 0)) + ',' +
						std::to_string(utf8towcslen(first.c_str(), first.size())) + '\n');
					break;
				}
				// no preview, fall back to composition
			case weasel::UIStyle::COMPOSITION:
				messages.push_back(std::string("ctx.preedit=") + ctx.composition.preedit + '\n');
				if (ctx.composition.sel_start <= ctx.composition.sel_end)
				{
					messages.push_back(std::string("ctx.preedit.cursor=") +
						std::to_string(utf8towcslen(ctx.composition.preedit, ctx.composition.sel_start)) + ',' +
						std::to_string(utf8towcslen(ctx.composition.preedit, ctx.composition.sel_end)) + '\n');
				}
				break;
			}
		}
		if (ctx.menu.num_candidates)
		{
			weasel::CandidateInfo cinfo;
			std::wstringstream ss;
			boost::archive::text_woarchive oa(ss);
			_GetCandidateInfo(cinfo, ctx);

			oa << cinfo;

			messages.push_back(std::string("ctx.cand=") + wcstoutf8(ss.str().c_str()) + '\n');
		}
		RimeFreeContext(&ctx);
	}

	// configuration information
	actions.insert("config");
	messages.push_back(std::string("config.inline_preedit=") + std::to_string((int)m_ui->style().inline_preedit) + '\n');

	// style
	bool has_synced = RimeGetOption(session_id, "__synced");
	if (!has_synced) {
		std::wstringstream ss;
		boost::archive::text_woarchive oa(ss);
		oa << m_ui->style();

		actions.insert("style");
		messages.push_back(std::string("style=") + wcstoutf8(ss.str().c_str()) + '\n');
		RimeSetOption(session_id, "__synced", true);
	}

	// summarize

	if (actions.empty())
	{
		messages.insert(messages.begin(), std::string("action=noop\n"));
	}
	else
	{
		std::string actionList(join(actions, ","));
		messages.insert(messages.begin(), std::string("action=") + actionList + '\n');
	}

	messages.push_back(std::string(".\n"));

	return std::all_of(messages.begin(), messages.end(), [&eat](std::string &msg)
	{
		return eat(std::wstring(utf8towcs(msg.c_str())));
	});
}