t-suw****@users*****
t-suw****@users*****
2007年 9月 2日 (日) 12:36:26 JST
Index: AquaSKK/src/statemachine/SKKEngine.h diff -u /dev/null AquaSKK/src/statemachine/SKKEngine.h:1.1.2.1 --- /dev/null Sun Sep 2 12:36:26 2007 +++ AquaSKK/src/statemachine/SKKEngine.h Sun Sep 2 12:36:25 2007 @@ -0,0 +1,78 @@ +/* -*- C++ -*- + $Id: SKKEngine.h,v 1.1.2.1 2007/09/02 03:36:25 t-suwa Exp $ + + MacOS X implementation of the SKK input method. + + Copyright (C) 2007 Tomotaka SUWA <t.suw****@mac*****> + + This program is free software; you can redistribute it and/or modify + it under the terms of the GNU General Public License as published by + the Free Software Foundation; either version 2 of the License, or + any later version. + + This program is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + GNU General Public License for more details. + + You should have received a copy of the GNU General Public License + along with this program; if not, write to the Free Software + Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA +*/ + +#ifndef INC__SKKEngine__ +#define INC__SKKEngine__ + +#include <iostream> +#include "SKKEnvironment.h" + +template <typename Handler, typename Event> +struct DebugInspector { +public: + void operator()(const Handler handler, const Event& event) { +#define DEFINE_State(arg) { &SKKEnvironment::arg, #arg } + const static struct { + Handler handler; + const char* name; + } states[] = { + DEFINE_State(KanaInput), + DEFINE_State(Hirakana), + DEFINE_State(Katakana), + DEFINE_State(Jisx0201Kana), + DEFINE_State(LatinInput), + DEFINE_State(Ascii), + DEFINE_State(Jisx0208Latin), + DEFINE_State(PreConversion), + DEFINE_State(EntryInput), + DEFINE_State(Japanese), + DEFINE_State(Abbreviation), + DEFINE_State(EntryCompletion), + DEFINE_State(SelectCandidate), + DEFINE_State(Inline), + DEFINE_State(Window), + DEFINE_State(EntryRemove), + { 0, 0x00 } + }; +#undef DEFINE_State(arg) + + static char* system_event[] = { "<<EXIT>>", "<<INIT>>", "<<ENTRY>>" }; + + if(event != 0) { + for(int i = 0; states[i].handler != 0; ++ i) { + if(handler == states[i].handler) { + std::cerr << "SKKEnvironment::" << states[i].name << ": "; + if(event < 0) { + std::cerr << system_event[event + 3] << std::endl; + } else { + std::cerr << event.Param().dump() << std::endl; + } + break; + } + } + } + } +}; + +typedef GenericStateMachine<SKKEnvironment, DebugInspector> SKKEngine; + +#endif Index: AquaSKK/src/statemachine/SKKEnvironment.cpp diff -u /dev/null AquaSKK/src/statemachine/SKKEnvironment.cpp:1.1.2.1 --- /dev/null Sun Sep 2 12:36:26 2007 +++ AquaSKK/src/statemachine/SKKEnvironment.cpp Sun Sep 2 12:36:25 2007 @@ -0,0 +1,443 @@ +/* -*- C++ -*- + MacOS X implementation of the SKK input method. + + Copyright (C) 2007 Tomotaka SUWA <t.suw****@mac*****> + + This program is free software; you can redistribute it and/or modify + it under the terms of the GNU General Public License as published by + the Free Software Foundation; either version 2 of the License, or + any later version. + + This program is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + GNU General Public License for more details. + + You should have received a copy of the GNU General Public License + along with this program; if not, write to the Free Software + Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA +*/ + +#include "SKKEnvironment.h" +#include "SKKController.h" + +typedef SKKEnvironment::Event Event; +typedef SKKEnvironment::State State; +typedef SKKEnvironment::Output Output; + +SKKEnvironment::SKKEnvironment() { + controller_ = new SKKController(); +} + +SKKEnvironment::~SKKEnvironment() { + delete controller_; +} + +const Output& SKKEnvironment::Result() const { + return controller_->Result(); +} + +// ====================================================================== +// level 1ï¼ããªå ¥å +// ====================================================================== +State SKKEnvironment::KanaInput(const Event& event) { + const SKKEventParam& param = event.Param(); + + switch(event) { + case ENTRY_EVENT: + controller_->ChangeState(SKK::DirectInput); + return 0; + + case INIT_EVENT: + return State::ShallowHistory(&SKKEnvironment::Hirakana); + + case EXIT_EVENT: + return State::SaveHistory(); + + case SKK_JMODE: + return controller_->HandleJmode(); + + case SKK_ENTER: + return controller_->HandleEnter(); + + case SKK_BACKSPACE: + return controller_->HandleBackSpace(); + + case SKK_DELETE: + return controller_->HandleDelete(); + + case SKK_CANCEL: + return controller_->HandleCancel(); + + case SKK_PASTE: + return controller_->HandlePaste(); + + case SKK_LEFT: + return controller_->HandleCursorLeft(); + + case SKK_RIGHT: + return controller_->HandleCursorRight(); + + case SKK_UP: + return controller_->HandleCursorUp(); + + case SKK_DOWN: + return controller_->HandleCursorDown(); + + case SKK_ASCII: + return State::Transition(&SKKEnvironment::Ascii); + + case SKK_JISX0208LATIN: + return State::Transition(&SKKEnvironment::Jisx0208Latin); + + case SKK_CHAR: + return controller_->HandleInput(param); + } + + return &SKKEnvironment::TopState; +} + +// ====================================================================== +// level 2 (sub of KanaInput)ï¼ã²ãã㪠+// ====================================================================== +State SKKEnvironment::Hirakana(const Event& event) { + const SKKEventParam& param = event.Param(); + + switch(event) { + case ENTRY_EVENT: + controller_->SelectInputMode(SKK::Hirakana); + return 0; + + case SKK_KATAKANA: + return State::Transition(&SKKEnvironment::Katakana); + + case SKK_JISX0201KANA: + return State::Transition(&SKKEnvironment::Jisx0201Kana); + + case SKK_CHAR: + if(param.IsToggleKana()) { + return State::Transition(&SKKEnvironment::Katakana); + } + + if(param.IsToggleJisx0201Kana()) { + return State::Transition(&SKKEnvironment::Jisx0201Kana); + } + } + + return &SKKEnvironment::KanaInput; +} + +// ====================================================================== +// level 2 (sub of KanaInput)ï¼ã«ã¿ã«ã +// ====================================================================== +State SKKEnvironment::Katakana(const Event& event) { + const SKKEventParam& param = event.Param(); + + switch(event) { + case ENTRY_EVENT: + controller_->SelectInputMode(SKK::Katakana); + return 0; + + case SKK_HIRAKANA: + return State::Transition(&SKKEnvironment::Hirakana); + + case SKK_JISX0201KANA: + return State::Transition(&SKKEnvironment::Jisx0201Kana); + + case SKK_CHAR: + if(param.IsToggleKana()) { + return State::Transition(&SKKEnvironment::Hirakana); + } + + if(param.IsToggleJisx0201Kana()) { + return State::Transition(&SKKEnvironment::Jisx0201Kana); + } + } + + return &SKKEnvironment::KanaInput; +} + +// ====================================================================== +// level 2 (sub of KanaInput)ï¼åè§ã«ã¿ã«ã +// ====================================================================== +State SKKEnvironment::Jisx0201Kana(const Event& event) { + const SKKEventParam& param = event.Param(); + + switch(event) { + case ENTRY_EVENT: + controller_->SelectInputMode(SKK::Jisx0201Kana); + return 0; + + case SKK_HIRAKANA: + return State::Transition(&SKKEnvironment::Hirakana); + + case SKK_CHAR: + if(param.IsToggleKana() || param.IsToggleJisx0201Kana()) { + return State::Transition(&SKKEnvironment::Hirakana); + } + } + + return &SKKEnvironment::KanaInput; +} + +// ====================================================================== +// level 1ï¼Latin å ¥å +// ====================================================================== +State SKKEnvironment::LatinInput(const Event& event) { + const SKKEventParam& param = event.Param(); + + switch(event) { + case ENTRY_EVENT: + controller_->ChangeState(SKK::DirectInput); + return 0; + + case SKK_JMODE: + case SKK_HIRAKANA: + return State::Transition(&SKKEnvironment::Hirakana); + + case SKK_CHAR: + return controller_->HandleInput(param); + } + + return &SKKEnvironment::TopState; +} + +// ====================================================================== +// level 2 (sub of LatinInput)ï¼ASCII +// ====================================================================== +State SKKEnvironment::Ascii(const Event& event) { + switch(event) { + case ENTRY_EVENT: + controller_->SelectInputMode(SKK::Ascii); + return 0; + } + + return &SKKEnvironment::LatinInput; +} + +// ====================================================================== +// level 2 (sub of LatinInput)ï¼å ¨è§è±æ° +// ====================================================================== +State SKKEnvironment::Jisx0208Latin(const Event& event) { + switch(event) { + case ENTRY_EVENT: + controller_->SelectInputMode(SKK::Jisx0208Latin); + return 0; + } + + return &SKKEnvironment::LatinInput; +} + +// ====================================================================== +// level 1ï¼å¤æå +// ====================================================================== +State SKKEnvironment::PreConversion(const Event& event) { + switch(event) { + case SKK_ENTER: + return controller_->HandleEnter(); + + case SKK_JMODE: + return controller_->HandleJmode(); + + case SKK_TAB: + return controller_->HandleTab(); + + case SKK_BACKSPACE: + return controller_->HandleBackSpace(); + + case SKK_DELETE: + return controller_->HandleDelete(); + + case SKK_LEFT: + return controller_->HandleCursorLeft(); + + case SKK_RIGHT: + return controller_->HandleCursorRight(); + + case SKK_UP: + return controller_->HandleCursorUp(); + + case SKK_DOWN: + return controller_->HandleCursorDown(); + + case SKK_CANCEL: + return State::Transition(&SKKEnvironment::KanaInput); + } + + return &SKKEnvironment::TopState; +} + +// ====================================================================== +// level 2 (sub of PreConversion)ï¼è¦åºãèªå ¥å +// ====================================================================== +State SKKEnvironment::EntryInput(const Event& event) { + const SKKEventParam& param = event.Param(); + + switch(event) { + case EXIT_EVENT: + return State::SaveHistory(); + + case SKK_PASTE: + return controller_->HandlePaste(); + + case SKK_CHAR: + return controller_->HandleInput(param); + } + + return &SKKEnvironment::PreConversion; +} + +// ====================================================================== +// level 3 (sub of EntryInput)ï¼æ¥æ¬èª +// ====================================================================== +State SKKEnvironment::Japanese(const Event& event) { + switch(event) { + case ENTRY_EVENT: + controller_->ChangeState(SKK::EntryInput); + return 0; + } + + return &SKKEnvironment::EntryInput; +} + +// ====================================================================== +// level 3 (sub of EntryInput)ï¼çç¥è¡¨è¨ +// ====================================================================== +State SKKEnvironment::Abbreviation(const Event& event) { + switch(event) { + case ENTRY_EVENT: + controller_->SelectInputMode(SKK::Ascii); + controller_->ChangeState(SKK::AbbrevInput); + return 0; + } + + return &SKKEnvironment::EntryInput; +} + +// ====================================================================== +// level 2 (sub of PreConversion)ï¼è¦åºãèªè£å® +// ====================================================================== +State SKKEnvironment::EntryCompletion(const Event& event) { + const SKKEventParam& param = event.Param(); + + switch(event) { + case ENTRY_EVENT: + controller_->ChangeState(SKK::Completion); + return 0; + } + + // ã·ã¹ãã ã¤ãã³ãã¨å¤æã¯ç¡è¦ãã + if(event.IsSystem() || + event == SKK_TAB || + (event == SKK_CHAR && (param.IsNextCandidate() || + param.IsNextCompletion() || + param.IsPrevCompletion()))) { + return &SKKEnvironment::PreConversion; + } + + // è£å®ãã¼ä»¥å¤ãªãå±¥æ´ã«è»¢éãã + return State::DeepForward(&SKKEnvironment::EntryInput); +} + +// ====================================================================== +// level 1ï¼åè£é¸æ +// ====================================================================== +State SKKEnvironment::SelectCandidate(const Event& event) { + switch(event) { + case INIT_EVENT: + return State::ShallowHistory(&SKKEnvironment::Inline); + + case EXIT_EVENT: + return State::SaveHistory(); + + case SKK_ENTER: + return controller_->HandleEnter(); + + case SKK_JMODE: + return controller_->HandleJmode(); + + case SKK_CANCEL: + return State::DeepHistory(&SKKEnvironment::EntryInput); + + case SKK_CHAR: + return State::Forward(&SKKEnvironment::KanaInput); + } + + return &SKKEnvironment::TopState; +} + +// ====================================================================== +// level 2 (sub of SelectCandidate)ï¼ã¤ã³ã©ã¤ã³è¡¨ç¤º +// ====================================================================== +State SKKEnvironment::Inline(const Event& event) { + const SKKEventParam& param = event.Param(); + + switch(event) { + case ENTRY_EVENT: + controller_->ChangeState(SKK::SingleCandidate); + return 0; + + case SKK_BACKSPACE: + return controller_->HandleBackSpace(); + + case SKK_CHAR: + return controller_->HandleInput(param); + } + + return &SKKEnvironment::SelectCandidate; +} + +// ====================================================================== +// level 2 (sub of SelectCandidate)ï¼ã¦ã£ã³ãã¦è¡¨ç¤º +// ====================================================================== +State SKKEnvironment::Window(const Event& event) { + const SKKEventParam& param = event.Param(); + + switch(event) { + case ENTRY_EVENT: + controller_->ChangeState(SKK::MultipleCandidate); + return 0; + + case EXIT_EVENT: + return 0; + + case SKK_BACKSPACE: + return controller_->HandleBackSpace();; + + case SKK_CHAR: + return controller_->HandleInput(param); + } + + return &SKKEnvironment::SelectCandidate; +} + +// ====================================================================== +// level 1ï¼åèªåé¤ +// ====================================================================== +State SKKEnvironment::EntryRemove(const Event& event) { + const SKKEventParam& param = event.Param(); + + switch(event) { + case ENTRY_EVENT: + controller_->ChangeState(SKK::EntryRemove); + return 0; + + case SKK_YES: + return State::Transition(&SKKEnvironment::KanaInput); + + case SKK_CANCEL: + case SKK_NO: + return State::Transition(&SKKEnvironment::Inline); + + case SKK_ENTER: + return controller_->HandleEnter(); + + case SKK_BACKSPACE: + return controller_->HandleBackSpace(); + + case SKK_CHAR: + return controller_->HandleInput(param); + } + + return &SKKEnvironment::TopState; +} Index: AquaSKK/src/statemachine/SKKEnvironment.h diff -u /dev/null AquaSKK/src/statemachine/SKKEnvironment.h:1.1.2.1 --- /dev/null Sun Sep 2 12:36:26 2007 +++ AquaSKK/src/statemachine/SKKEnvironment.h Sun Sep 2 12:36:25 2007 @@ -0,0 +1,83 @@ +/* -*- C++ -*- + MacOS X implementation of the SKK input method. + + Copyright (C) 2007 Tomotaka SUWA <t.suw****@mac*****> + + This program is free software; you can redistribute it and/or modify + it under the terms of the GNU General Public License as published by + the Free Software Foundation; either version 2 of the License, or + any later version. + + This program is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + GNU General Public License for more details. + + You should have received a copy of the GNU General Public License + along with this program; if not, write to the Free Software + Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA +*/ + +#ifndef INC__SKKEnvironment__ +#define INC__SKKEnvironment__ + +#include "GenericStateMachine.h" +#include "SKKEventParam.h" +#include "SKKEventResult.h" + +using namespace statemachinecxx_sourceforge_jp; + +class SKKController; + +// å®è¡ç°å¢ +class SKKEnvironment { + SKKController* controller_; + +public: + DECLARE_StateContainer(SKKEnvironment, SKKEventParam, SKKEventResult, KanaInput); + + SKKEnvironment(); + ~SKKEnvironment(); + + const Output& Result() const; + + // level 1 (initial state) + State KanaInput(const Event& event); + + // level 2 (sub of KanaInput) + State Hirakana(const Event& event); + State Katakana(const Event& event); + State Jisx0201Kana(const Event& event); + + // level 1 + State LatinInput(const Event& event); + + // level2 (sub of LatinInput) + State Ascii(const Event& event); + State Jisx0208Latin(const Event& event); + + // level 1 + State PreConversion(const Event& event); + + // level 2 (sub of PreConversion) + State EntryInput(const Event& event); + + // lelvel 3 (sub of EntryInput) + State Japanese(const Event& event); + State Abbreviation(const Event& event); + + // level 2 (sub of PreConversion) + State EntryCompletion(const Event& event); + + // level 1 + State SelectCandidate(const Event& event); + + // level 2 (sub of SelectCandidate) + State Inline(const Event& event); + State Window(const Event& event); + + // level 1 + State EntryRemove(const Event& event); +}; + +#endif Index: AquaSKK/src/statemachine/SKKEventResult.cpp diff -u /dev/null AquaSKK/src/statemachine/SKKEventResult.cpp:1.1.2.1 --- /dev/null Sun Sep 2 12:36:26 2007 +++ AquaSKK/src/statemachine/SKKEventResult.cpp Sun Sep 2 12:36:25 2007 @@ -0,0 +1,35 @@ +/* -*- C++ -*- + MacOS X implementation of the SKK input method. + + Copyright (C) 2007 Tomotaka SUWA <t.suw****@mac*****> + + This program is free software; you can redistribute it and/or modify + it under the terms of the GNU General Public License as published by + the Free Software Foundation; either version 2 of the License, or + any later version. + + This program is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + GNU General Public License for more details. + + You should have received a copy of the GNU General Public License + along with this program; if not, write to the Free Software + Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA +*/ + +#include "SKKEventResult.h" + +SKKEventResult::SKKEventResult() : impl_(new SKKEventResultImpl()) {} + +SKKEventResult::SKKEventResult(const SKKEventResult&) : impl_(new SKKEventResultImpl()) {} + +void SKKEventResult::Update() { + impl_->Update(); +} + +bool SKKEventResult::EventIsHandled() const { + // const ã¡ã½ãããªã®ã§ããã¤ã³ã¿çµç±ã§å é¨å®è£ ã®ç¶æ ãæ´æ° + return impl_->TestAndReset(); + // ãã®å®è£ ã¯ãããããã®ã§ã代æ¿æ¡ãæ¤è¨ããã㨠+} Index: AquaSKK/src/statemachine/SKKEventResult.h diff -u /dev/null AquaSKK/src/statemachine/SKKEventResult.h:1.1.2.1 --- /dev/null Sun Sep 2 12:36:26 2007 +++ AquaSKK/src/statemachine/SKKEventResult.h Sun Sep 2 12:36:25 2007 @@ -0,0 +1,64 @@ +/* -*- C++ -*- + MacOS X implementation of the SKK input method. + + Copyright (C) 2007 Tomotaka SUWA <t.suw****@mac*****> + + This program is free software; you can redistribute it and/or modify + it under the terms of the GNU General Public License as published by + the Free Software Foundation; either version 2 of the License, or + any later version. + + This program is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + GNU General Public License for more details. + + You should have received a copy of the GNU General Public License + along with this program; if not, write to the Free Software + Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA +*/ + +#ifndef INC__SKKEventResult__ +#define INC__SKKEventResult__ + +#include <memory> + +// å é¨å®è£ +class SKKEventResultImpl { + bool handled_; + bool backup_; + +public: + SKKEventResultImpl() : handled_(false), backup_(false) {} + ~SKKEventResultImpl() {} + + void Update() { + handled_ = !backup_; + } + + // separate query from modifier ã®ååããã¶ã + bool TestAndReset() { + bool ret = handled_ == backup_; + + backup_ = handled_; + + return ret; + } +}; + +// å¦ççµæ +class SKKEventResult { + std::auto_ptr<SKKEventResultImpl> impl_; + +public: + SKKEventResult(); + SKKEventResult(const SKKEventResult& src); + + // ã¤ãã³ããå¦çããå ´åã¯å¼ã³åºã + void Update(); + + // ã¤ãã³ãã¯å¦çããããï¼ + bool EventIsHandled() const; +}; + +#endif