[aquaskk-changes 157] CVS update: AquaSKK

Zurück zum Archiv-Index

Tomotaka SUWA t-suw****@users*****
2006年 3月 6日 (月) 21:03:00 JST


Index: AquaSKK/CandidatesFrame.h
diff -u AquaSKK/CandidatesFrame.h:1.2.2.2 AquaSKK/CandidatesFrame.h:1.2.2.3
--- AquaSKK/CandidatesFrame.h:1.2.2.2	Sun Feb 19 13:50:54 2006
+++ AquaSKK/CandidatesFrame.h	Mon Mar  6 21:03:00 2006
@@ -1,5 +1,5 @@
 /* -*- objc -*-
-  $Id: CandidatesFrame.h,v 1.2.2.2 2006/02/19 04:50:54 t-suwa Exp $
+  $Id: CandidatesFrame.h,v 1.2.2.3 2006/03/06 12:03:00 t-suwa Exp $
 
   MacOS X implementation of the SKK input method.
 
@@ -26,9 +26,11 @@
 // ƒtƒŒ[ƒ€‘®«
 @interface FrameAttribute : NSObject {
     NSString* labels_;		 // ƒAƒNƒZƒX•¶Žš
+    int candidatesCount_;	 // Œó•â”
     NSString* entry_;		 // ’Pˆê‚ÌŒó•â
     NSString* caption_;		 // [Žc‚è nnn]
-    NSDictionary* attributes_;	 // ƒtƒHƒ“ƒg‘®«
+    NSDictionary* normalFontAttributes_;	 // Œó•â•\Ž¦—p‚̃tƒHƒ“ƒg‘®«
+    NSDictionary* indexFontAttributes_;		 // ƒCƒ“ƒfƒbƒNƒX—p‚̃tƒHƒ“ƒg‘®«
 
     NSSize viewSize_;		// ƒrƒ…[‹éŒ`
     NSSize marginSize_;		// ƒ}[ƒWƒ“
@@ -43,7 +45,8 @@
 
 - (NSString*)labels;
 - (NSString*)caption;
-- (NSDictionary*)fontAttributes;
+- (NSDictionary*)normalFontAttributes;
+- (NSDictionary*)indexFontAttributes;
 - (NSSize)viewSize;
 - (NSSize)marginSize;
 - (NSSize)itemSize;
@@ -66,8 +69,7 @@
 }
 
 - (bool)addCandidate:(NSString*)str;
-- (void)setRemain:(int)remains;
 - (unsigned)count;
-- (void)drawRect:(NSRect)rect;
+- (void)drawRect:(NSRect)rect range:(NSRange)range;
 
 @end
Index: AquaSKK/CandidatesFrame.m
diff -u AquaSKK/CandidatesFrame.m:1.4.2.2 AquaSKK/CandidatesFrame.m:1.4.2.3
--- AquaSKK/CandidatesFrame.m:1.4.2.2	Sun Feb 19 13:50:54 2006
+++ AquaSKK/CandidatesFrame.m	Mon Mar  6 21:03:00 2006
@@ -1,5 +1,5 @@
 /*
-  $Id: CandidatesFrame.m,v 1.4.2.2 2006/02/19 04:50:54 t-suwa Exp $
+  $Id: CandidatesFrame.m,v 1.4.2.3 2006/03/06 12:03:00 t-suwa Exp $
 
   MacOS X implementation of the SKK input method.
 
@@ -33,19 +33,17 @@
 	labels_ = @"ASDFJKL";
 
 	// ’Pˆê‚̃Gƒ“ƒgƒŠ
-	char* data = " A  Š¿Žš";
+	char* data = " A  Š¿Žš ";
 	NSData* sjis = [[NSData alloc] initWithBytes:data length:strlen(data)];
 	entry_ = [[NSString alloc] initWithData:sjis encoding:NSShiftJISStringEncoding];
 	[sjis release];
 
-	// [Žc‚è n]
-	data = "Žc‚è";
-	sjis = [[NSData alloc] initWithBytes:data length:strlen(data)];
-	caption_ = [[NSString alloc] initWithData:sjis encoding:NSShiftJISStringEncoding];
-	[sjis release];
+	// ƒCƒ“ƒfƒbƒNƒXƒtƒHƒ“ƒg‘®«
+	indexFontAttributes_ = [NSDictionary dictionaryWithObject:[NSFont toolTipsFontOfSize:0]
+					     forKey:NSFontAttributeName];
 
 	// —]”’‚ðŒˆ‚ß‚é
-	marginSize_ = NSMakeSize(8, 8);
+	marginSize_ = NSMakeSize(8, 6);
 	spaceWidth_ = marginSize_.width * 2;
 
 	[self refresh];
@@ -69,21 +67,24 @@
     NSUserDefaults* defaults = [NSUserDefaults standardUserDefaults];
     NSFont* font = [NSFont fontWithName:[defaults stringForKey:KEY_candidates_font_name]
 			   size:[defaults floatForKey:KEY_candidates_font_size]];
-    attributes_ = [NSDictionary dictionaryWithObject:font forKey:NSFontAttributeName];
+    normalFontAttributes_ = [NSDictionary dictionaryWithObject:font forKey:NSFontAttributeName];
+
+    // Œó•â”‚ðŽæ“¾
+    candidatesCount_ = [defaults integerForKey:KEY_candidates_count];
 
     // €–ڂ̃TƒCƒY‚ðŽæ“¾
-    NSMutableAttributedString* tmp = [[NSMutableAttributedString alloc] initWithString:entry_ attributes:attributes_];
+    NSMutableAttributedString* tmp = [[NSMutableAttributedString alloc] initWithString:entry_
+									attributes:normalFontAttributes_];
     itemSize_ = [tmp size];
     [tmp release];
 
-    // [Žc‚è n] ‚̃TƒCƒY‚ðŽæ“¾
-    NSString* formatedStr = [NSString stringWithFormat:@"[%@ 000]", caption_];
-    tmp = [[NSMutableAttributedString alloc] initWithString:formatedStr attributes:attributes_];
+    // nnn / mmm ‚̃TƒCƒY‚ðŽæ“¾
+    tmp = [[NSMutableAttributedString alloc] initWithString:@"8888 / 8888" attributes:indexFontAttributes_];
     NSSize remainSize = [tmp size];
     [tmp release];
 
     // •ÏŠ·Œó•â‚ð•`‰æ‚·‚éƒGƒŠƒA‚̃TƒCƒY
-    itemAreaSize_ = NSMakeSize([labels_ length] * (itemSize_.width + spaceWidth_), itemSize_.height);
+    itemAreaSize_ = NSMakeSize(candidatesCount_ * (itemSize_.width + spaceWidth_), itemSize_.height);
 
     // ƒrƒ…[‘S‘̂̃TƒCƒY
     viewSize_ = NSMakeSize(marginSize_.width * 2 + itemAreaSize_.width + remainSize.width,
@@ -91,15 +92,19 @@
 }
 
 - (NSString*)labels {
-    return labels_;
+    return [labels_ substringWithRange:NSMakeRange(0, candidatesCount_)];
 }
 
 - (NSString*)caption {
     return caption_;
 }
 
-- (NSDictionary*)fontAttributes {
-    return attributes_;
+- (NSDictionary*)normalFontAttributes {
+    return normalFontAttributes_;
+}
+
+- (NSDictionary*)indexFontAttributes {
+    return indexFontAttributes_;
 }
 
 - (NSSize)viewSize {
@@ -158,7 +163,7 @@
 
     // ‘®«•t‚«•¶Žš—ñ‚ðì‚é
     NSMutableAttributedString* entry = [[NSMutableAttributedString alloc] initWithString:tmpstr
-									  attributes:[attr fontAttributes]];
+									  attributes:[attr normalFontAttributes]];
 
     // ƒ‰ƒxƒ‹‚Ì•¶ŽšF‚Æ”wŒiF‚ðÝ’è
     [entry addAttribute:NSBackgroundColorAttributeName
@@ -201,15 +206,50 @@
     return false;
 }
 
-- (void)setRemain:(int)remains {
-    remainCandidates_ = remains;
-}
-
 - (unsigned)count {
     return [candidates_ count];
 }
 
-- (void)drawRect:(NSRect)rect {
+- (void)drawPage:(NSRange)range {
+    FrameAttribute* attr = [FrameAttribute sharedFrameAttribute];
+
+    // nnn / mmm ‚ð•`‰æ
+    NSString* tmpstr = [NSString stringWithFormat:@"%3d / %-3d", range.location, range.length];
+    NSMutableAttributedString* page = [[NSMutableAttributedString alloc] initWithString:tmpstr
+									 attributes:[attr indexFontAttributes]];
+
+    [[NSColor gridColor] setFill];
+    [page addAttribute:NSBackgroundColorAttributeName
+	  value:[NSColor gridColor] range:NSMakeRange(0, [tmpstr length])];
+    [page addAttribute:NSForegroundColorAttributeName
+	  value:[NSColor whiteColor] range:NSMakeRange(0, [tmpstr length])];
+
+    float radius = 0.5 * [page size].height;
+    NSRect rc = NSMakeRect([attr itemAreaSize].width + [attr marginSize].width + radius,
+			   [attr marginSize].height,
+			   [page size].width,
+			   [page size].height);
+
+    NSPoint topleft = NSMakePoint(NSMinX(rc), NSMaxY(rc));
+    NSPoint bottomleft = NSMakePoint(NSMinX(rc), NSMinY(rc));
+    NSPoint bottomright = NSMakePoint(NSMaxX(rc), NSMinY(rc));
+
+    NSBezierPath* oval = [NSBezierPath bezierPath];
+    [oval moveToPoint:bottomleft];
+    [oval lineToPoint:bottomright];
+    [oval appendBezierPathWithArcWithCenter:NSMakePoint(bottomright.x, bottomright.y + radius)
+	  radius:radius startAngle:270 endAngle:90];
+    [oval lineToPoint:topleft];
+    [oval appendBezierPathWithArcWithCenter:NSMakePoint(topleft.x, topleft.y - radius)
+	  radius:radius startAngle:90 endAngle:270];
+    [oval closePath];
+    [oval fill];
+
+    [page drawAtPoint:bottomleft];
+    [page release];
+}
+
+- (void)drawRect:(NSRect)rect range:(NSRange)range {
     FrameAttribute* attr = [FrameAttribute sharedFrameAttribute];
 
     // ‰Šú‰»‚³‚ê‚Ä‚¢‚È‚¢H
@@ -235,13 +275,8 @@
 	    }
 	}
 
-	// [Žc‚è n] ‚ð•`‰æ
-	NSAttributedString* remain = [[NSAttributedString alloc]
-					 initWithString:[NSString stringWithFormat:@"[%@ %d]",
-								  [attr caption], remainCandidates_]
-					 attributes:[attr fontAttributes]];
-	[remain drawAtPoint:NSMakePoint([attr marginSize].width + [attr itemAreaSize].width, [attr marginSize].height)];
-	[remain release];
+	// nnn / mmm ‚ð•`‰æ
+	[self drawPage:range];
 
 	[view_ unlockFocus];
     }
Index: AquaSKK/CandidatesView.mm
diff -u AquaSKK/CandidatesView.mm:1.2.2.1 AquaSKK/CandidatesView.mm:1.2.2.2
--- AquaSKK/CandidatesView.mm:1.2.2.1	Sun Feb 19 13:50:54 2006
+++ AquaSKK/CandidatesView.mm	Mon Mar  6 21:03:00 2006
@@ -1,5 +1,5 @@
 /*  -*- objc -*-
-  $Id: CandidatesView.mm,v 1.2.2.1 2006/02/19 04:50:54 t-suwa Exp $
+  $Id: CandidatesView.mm,v 1.2.2.2 2006/03/06 12:03:00 t-suwa Exp $
 
   MacOS X implementation of the SKK input method.
 
@@ -44,8 +44,7 @@
     for(i = 0; i < [cands count]; ++ i) {
 	// ‚±‚̃tƒŒ[ƒ€‚É‚±‚êˆÈã‚͒ljÁ‚Å‚«‚È‚¢H
 	if(![tmpFrame addCandidate:[cands objectAtIndex:i]]) {
-	    // uŽc‚èv‚̐”‚ðƒZƒbƒg‚µ‚āA”z—ñ‚ɒljÁ
-	    [tmpFrame setRemain:[cands count] - i];
+	    // ”z—ñ‚ɒljÁ
 	    [frames addObject:tmpFrame];
 	    [tmpFrame release];
 
@@ -76,7 +75,7 @@
 
 - (void)drawRect:(NSRect)rect
 {
-    [[frames objectAtIndex:current_frame] drawRect:rect];
+    [[frames objectAtIndex:current_frame] drawRect:rect range:NSMakeRange(current_frame + 1, [frames count])];
 }
 
 - (void)showNextFrame
Index: AquaSKK/ChangeLog
diff -u AquaSKK/ChangeLog:1.20.2.10 AquaSKK/ChangeLog:1.20.2.11
--- AquaSKK/ChangeLog:1.20.2.10	Sat Feb 25 16:27:32 2006
+++ AquaSKK/ChangeLog	Mon Mar  6 21:03:00 2006
@@ -1,3 +1,25 @@
+2006-03-06  Tomotaka SUWA  <t.suw****@mac*****>
+
+	* skkserv.cpp: I—¹ˆ—‚ð‚æ‚èˆÀ‘S‚ɏC³B
+
+	* UserDefaults.plist: candidates_count Ý’è‚ð’ljÁB
+
+	* SKKDictionary.*: SKKAutoUpdateDictionary ƒNƒ‰ƒX‚ð’ljÁB
+
+	* PreferencesController.mm: KEY_candidates_count ‚ð’ljÁB
+
+	* PreferenceKeys.h: KEY_candidates_count ‚ð’ljÁBŒó•âƒEƒBƒ“ƒhƒE‚É•\
+	Ž¦‚·‚éŒó•â”B
+
+	* DictionarySet.cpp: d•¡‚·‚éŒó•â‚ðí‚鎞‚É’Žß•”•ª‚ðœŠOBSKK Ž©“®
+	XVŽ«‘‚Æ Proxy Ž«‘‚ɑΉžB
+
+	* Dictionary.h: SKKEntryConverter ƒNƒ‰ƒX‚ð’ljÁB
+
+	* ProxyDictionary.*: V‹K’ljÁBŠO•” skkserv Ž«‘B
+
+	* Mutex.h: V‹K’ljÁB
+
 2006-02-25  Tomotaka SUWA  <t.suw****@mac*****>
 
 	* AquaSKK.pbproj/project.pbxproj: Panther —p‚ɏC³B
Index: AquaSKK/Dictionary.h
diff -u AquaSKK/Dictionary.h:1.3.2.3 AquaSKK/Dictionary.h:1.3.2.4
--- AquaSKK/Dictionary.h:1.3.2.3	Sat Feb 18 02:20:38 2006
+++ AquaSKK/Dictionary.h	Mon Mar  6 21:03:00 2006
@@ -1,5 +1,5 @@
 /*
-  $Id: Dictionary.h,v 1.3.2.3 2006/02/17 17:20:38 t-suwa Exp $
+  $Id: Dictionary.h,v 1.3.2.4 2006/03/06 12:03:00 t-suwa Exp $
 
   MacOS X implementation of the SKK input method.
 
@@ -21,7 +21,8 @@
   Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA
 */
 
-#pragma once
+#ifndef	INC__Dictionary__
+#define INC__Dictionary__
 
 #include <vector>
 #include <string>
@@ -72,6 +73,8 @@
     }
 };
 
+#pragma mark -- Utility --
+
 // •”•ª•¶Žš—ñ‚ð•Ô‚µ‚Ä‚¢‚­’Pƒ‚ȃp[ƒT
 class SKKEntryParser {
     const std::string& target_;
@@ -433,3 +436,37 @@
 	return Key() + " " + Candidate();
     }
 };
+
+class SKKEntryConverter {
+public:
+    // SKKEntry ¨ std::vector<OkuriganaEntry> •ÏŠ·
+    static std::vector<OkuriganaEntry> OkuriAri(const SKKEntry& entry) {
+	// ‚Ü‚¸ƒqƒ“ƒgî•ñ‚©‚ç’ljÁ‚·‚é
+	std::vector<OkuriganaEntry> result;
+	for(SKKOkuriHint hint = entry.FirstHint(); !hint.IsEmpty(); hint = entry.NextHint()) {
+	    OkuriganaEntry okuri;
+
+	    okuri.setKana(CppCFString(hint.Kana().c_str(), kCFStringEncodingEUC_JP));
+	    for(SKKCandidate candidate = hint.First(); !candidate.IsEmpty(); candidate = hint.Next()) {
+		okuri.add(CppCFString(candidate.Description().c_str(), kCFStringEncodingEUC_JP));
+	    }
+	    result.push_back(okuri);
+	}
+
+	// ŽŸ‚ɁA•ÏŠ·Œó•â‚ð’ljÁ‚·‚é
+	OkuriganaEntry wild;
+	for(SKKCandidate candidate = entry.First(); !candidate.IsEmpty(); candidate = entry.Next()) {
+	    wild.add(CppCFString(candidate.Description().c_str(), kCFStringEncodingEUC_JP));
+	}
+	result.push_back(wild);
+
+	return result;
+    }
+
+    // SKKEntry ¨ std::vector<CppCFString> •ÏŠ·
+    static std::vector<CppCFString> OkuriNasi(const SKKEntry& entry) {
+	return CppCFString(entry.Candidate().c_str(), kCFStringEncodingEUC_JP).split('/');
+    }
+};
+
+#endif // INC__Dictionary__
Index: AquaSKK/DictionarySet.cpp
diff -u AquaSKK/DictionarySet.cpp:1.1.2.4 AquaSKK/DictionarySet.cpp:1.1.2.5
--- AquaSKK/DictionarySet.cpp:1.1.2.4	Sat Feb 25 16:27:32 2006
+++ AquaSKK/DictionarySet.cpp	Mon Mar  6 21:03:00 2006
@@ -1,5 +1,5 @@
 /*
-  $Id: DictionarySet.cpp,v 1.1.2.4 2006/02/25 07:27:32 t-suwa Exp $
+  $Id: DictionarySet.cpp,v 1.1.2.5 2006/03/06 12:03:00 t-suwa Exp $
 
   MacOS X implementation of the SKK input method.
 
@@ -28,6 +28,7 @@
 #include "Dictionary.h"
 #include "SKKDictionary.h"
 #include "KotoeriDictionary.h"
+#include "ProxyDictionary.h"
 #include "DictionarySet.h"
 #include "SkkConfig.h"
 
@@ -46,9 +47,14 @@
     std::vector<CppCFString> result;
 
     for(std::vector<CppCFString>::iterator iter = candidates.begin(); iter != candidates.end(); ++ iter) {
-	if(check.find(*iter) == check.end()) {
-	    check.insert(check.lower_bound(*iter), *iter);
-	    result.push_back(*iter);
+	// ’Žß•”•ª‚Í”äŠr‚µ‚È‚¢
+	std::string str = iter->toStdString();
+	std::string::size_type pos = str.find_first_of(';');
+	CppCFString target(str.substr(0, pos).c_str(), kCFStringEncodingEUC_JP);
+
+	if(check.find(target) == check.end()) {
+	    check.insert(check.lower_bound(target), target);
+	    result.push_back(target);
 	}
     }
     result.swap(candidates);
@@ -104,14 +110,14 @@
     case SKKDictionaryType:
 	dict = new SKKDictionary();
 	break;
-    case SKKAutoUpdateDictionaryType: // –¢ŽÀ‘•
-	dict = new NullDictionary();
+    case SKKAutoUpdateDictionaryType:
+	dict = new SKKAutoUpdateDictionary();
 	break;
     case KotoeriDictionaryType:
 	dict = new KotoeriDictionary();
 	break;
-    case ProxyDictionaryType:	// –¢ŽÀ‘•
-	dict = new NullDictionary();
+    case ProxyDictionaryType:
+	dict = new ProxyDictionary();
 	break;
     case GroupingDictionaryType:
 	dict = new NullDictionary();
Index: AquaSKK/Mutex.h
diff -u /dev/null AquaSKK/Mutex.h:1.1.2.1
--- /dev/null	Mon Mar  6 21:03:00 2006
+++ AquaSKK/Mutex.h	Mon Mar  6 21:03:00 2006
@@ -0,0 +1,59 @@
+/*
+  $Id: Mutex.h,v 1.1.2.1 2006/03/06 12:03:00 t-suwa Exp $
+
+  MacOS X implementation of the SKK input method.
+
+  Copyright (C) 2006 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__Mutex__
+#define INC__Mutex__
+
+#include <pthread.h>
+
+class Mutex {
+    friend class Guard;
+    pthread_mutex_t mutex_;
+    void lock() {
+	pthread_mutex_lock(&mutex_);
+    }
+    void unlock() {
+	pthread_mutex_unlock(&mutex_);
+    }
+
+public:
+    Mutex() {
+	pthread_mutex_init(&mutex_, NULL);
+    }
+    ~Mutex() {
+	pthread_mutex_destroy(&mutex_);
+    }
+};
+
+class Guard {
+    Mutex& mutex_;
+
+public:
+    Guard(Mutex& ref) : mutex_(ref) {
+	mutex_.lock();
+    }
+    ~Guard() {
+	mutex_.unlock();
+    }
+};
+
+#endif
Index: AquaSKK/PreferenceKeys.h
diff -u AquaSKK/PreferenceKeys.h:1.1.2.3 AquaSKK/PreferenceKeys.h:1.1.2.4
--- AquaSKK/PreferenceKeys.h:1.1.2.3	Sat Feb 25 16:27:32 2006
+++ AquaSKK/PreferenceKeys.h	Mon Mar  6 21:03:00 2006
@@ -1,5 +1,5 @@
 /* -*- objc -*-
-  $Id: PreferenceKeys.h,v 1.1.2.3 2006/02/25 07:27:32 t-suwa Exp $
+  $Id: PreferenceKeys.h,v 1.1.2.4 2006/03/06 12:03:00 t-suwa Exp $
 
   MacOS X implementation of the SKK input method.
 
@@ -30,6 +30,7 @@
 extern NSString* KEY_force_ascii_mode_startup;
 extern NSString* KEY_keyboard_layout_id;
 
+extern NSString* KEY_candidates_count;
 extern NSString* KEY_candidates_font_name;
 extern NSString* KEY_candidates_font_size;
 extern NSString* KEY_candidates_window_color;
Index: AquaSKK/PreferencesController.mm
diff -u AquaSKK/PreferencesController.mm:1.6.2.9 AquaSKK/PreferencesController.mm:1.6.2.10
--- AquaSKK/PreferencesController.mm:1.6.2.9	Sat Feb 25 16:27:32 2006
+++ AquaSKK/PreferencesController.mm	Mon Mar  6 21:03:00 2006
@@ -1,5 +1,5 @@
 /*  -*- objc -*-
-  $Id: PreferencesController.mm,v 1.6.2.9 2006/02/25 07:27:32 t-suwa Exp $
+  $Id: PreferencesController.mm,v 1.6.2.10 2006/03/06 12:03:00 t-suwa Exp $
 
   MacOS X implementation of the SKK input method.
 
@@ -37,6 +37,7 @@
 NSString* KEY_numkeypad_use_halfwidth = @"numkeypad_use_halfwidth";
 NSString* KEY_force_ascii_mode_startup = @"force_ascii_mode_startup";
 
+NSString* KEY_candidates_count = @"candidates_count";
 NSString* KEY_candidates_font_name = @"candidates_font_name";
 NSString* KEY_candidates_font_size = @"candidates_font_size";
 NSString* KEY_candidates_window_color = @"candidates_window_color";
Index: AquaSKK/ProxyDictionary.cpp
diff -u /dev/null AquaSKK/ProxyDictionary.cpp:1.1.2.1
--- /dev/null	Mon Mar  6 21:03:00 2006
+++ AquaSKK/ProxyDictionary.cpp	Mon Mar  6 21:03:00 2006
@@ -0,0 +1,110 @@
+/*
+  $Id: ProxyDictionary.cpp,v 1.1.2.1 2006/03/06 12:03:00 t-suwa Exp $
+
+  MacOS X implementation of the SKK input method.
+
+  Copyright (C) 2006 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 <sstream>
+#include "CppCFString.h"
+#include "OkuriganaEntry.h"
+#include "ProxyDictionary.h"
+
+ProxyDictionary::ProxyDictionary() : host_("localhost"), port_(1178), active_(false) {
+    // empty
+}
+
+ProxyDictionary::~ProxyDictionary() {
+    session_.close();
+}
+
+void ProxyDictionary::load(const std::string& path) {
+    // path ‚́uhost:portvŒ`Ž®
+    std::string::size_type pos = path.find_first_of(":");
+    if(pos != std::string::npos) {
+	host_ = path.substr(0, pos);
+	std::stringstream buf(path.substr(pos + 1));
+	buf >> port_;
+    } else {
+	if(!path.empty()) {
+	    host_ = path;
+	}
+    }
+
+    std::cerr << "Proxy Dictionary(" << host_ << ":" << port_ << ")" << std::endl << std::endl;
+}
+
+int ProxyDictionary::countOkuriAri() {
+    return 0;
+}
+
+int ProxyDictionary::countOkuriNasi() {
+    return 0;
+}
+
+std::vector<OkuriganaEntry> ProxyDictionary::findOkuriAri(const CppCFString& str) {
+    std::string key(str.toStdString());
+    std::string response;
+
+    // ƒqƒbƒg‚µ‚½H
+    if(search(key, response)) {
+	return SKKEntryConverter::OkuriAri(SKKEntry::ParseOkuriAri(key, response));
+    }
+
+    return std::vector<OkuriganaEntry>();
+}
+
+std::vector<CppCFString> ProxyDictionary::findOkuriNasi(const CppCFString& str) {
+    std::string key(str.toStdString());
+    std::string response;
+
+    // ƒqƒbƒg‚µ‚½H
+    if(search(key, response)) {
+	return SKKEntryConverter::OkuriNasi(SKKEntry::ParseOkuriNasi(key, response));
+    }
+
+    return std::vector<CppCFString>();
+}
+
+bool ProxyDictionary::search(const std::string& str, std::string& response) {
+    // Ú‘±‚·‚é
+    if(!session_) {
+	session_.open(host_.c_str(), port_);
+	if(!session_) return false;
+    }
+
+    // Ä“ü‚Ń‹[ƒv‚·‚é‚Ì‚ð–h‚®
+    if(active_) return false;
+    active_ = true;
+
+    // ƒNƒGƒŠ‘—M
+    session_ << "1" << str << " ";
+    session_.flush();
+
+    // Œ‹‰ÊŽóM
+    getline(session_, response);
+
+    active_ = false;
+
+    if(response[0] == '1') {
+	response = response.substr(1);
+	return true;
+    } else {
+	return false;
+    }
+}
Index: AquaSKK/ProxyDictionary.h
diff -u /dev/null AquaSKK/ProxyDictionary.h:1.1.2.1
--- /dev/null	Mon Mar  6 21:03:00 2006
+++ AquaSKK/ProxyDictionary.h	Mon Mar  6 21:03:00 2006
@@ -0,0 +1,54 @@
+/*
+  $Id: ProxyDictionary.h,v 1.1.2.1 2006/03/06 12:03:00 t-suwa Exp $
+
+  MacOS X implementation of the SKK input method.
+
+  Copyright (C) 2006 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__ProxyDictionary__
+#define INC__ProxyDictionary__
+
+#include "Dictionary.h"
+#include "socketstream.h"
+
+class OkuriganaEntry;
+class CppCFString;
+
+// ŠO•” skkserv Ž«‘
+class ProxyDictionary: public Dictionary {
+    socket_stream session_;
+    std::string host_;
+    unsigned short port_;
+    bool active_;
+
+    bool search(const std::string& key, std::string& response);
+
+public:
+    ProxyDictionary();
+    virtual ~ProxyDictionary();
+
+    virtual void load(const std::string& path);
+
+    virtual int countOkuriAri();
+    virtual int countOkuriNasi();
+
+    virtual std::vector<OkuriganaEntry> findOkuriAri(const CppCFString& query);
+    virtual std::vector<CppCFString> findOkuriNasi(const CppCFString& query);
+};
+
+#endif
Index: AquaSKK/SKKDictionary.cpp
diff -u AquaSKK/SKKDictionary.cpp:1.6.2.2 AquaSKK/SKKDictionary.cpp:1.6.2.3
--- AquaSKK/SKKDictionary.cpp:1.6.2.2	Sat Feb 18 02:20:38 2006
+++ AquaSKK/SKKDictionary.cpp	Mon Mar  6 21:03:00 2006
@@ -1,5 +1,5 @@
 /*
-  $Id: SKKDictionary.cpp,v 1.6.2.2 2006/02/17 17:20:38 t-suwa Exp $
+  $Id: SKKDictionary.cpp,v 1.6.2.3 2006/03/06 12:03:00 t-suwa Exp $
 
   MacOS X implementation of the SKK input method.
 
@@ -29,11 +29,13 @@
 #include <sys/types.h>
 #include <sys/stat.h>
 #include <unistd.h>
+#include <pthread.h>
 #include "CppCFString.h"
 #include "OkuriganaEntry.h"
 #include "Dictionary.h"
 #include "SKKDictionary.h"
-#include "SKKConfig.h"
+#include "SkkConfig.h"
+#include "socketstream.h"
 
 #pragma mark --- SKK common functions ---
 
@@ -117,35 +119,6 @@
 	    ofs_ << pair.first << " " << pair.second << std::endl;
 	}
     };
-
-    // SKKEntry ¨ std::vector<OkuriganaEntry> •ÏŠ·
-    std::vector<OkuriganaEntry> ConvertOkuriAri(const SKKEntry& entry) {
-	// ‚Ü‚¸ƒqƒ“ƒgî•ñ‚©‚ç’ljÁ‚·‚é
-	std::vector<OkuriganaEntry> result;
-	for(SKKOkuriHint hint = entry.FirstHint(); !hint.IsEmpty(); hint = entry.NextHint()) {
-	    OkuriganaEntry okuri;
-
-	    okuri.setKana(CppCFString(hint.Kana().c_str(), kCFStringEncodingEUC_JP));
-	    for(SKKCandidate candidate = hint.First(); !candidate.IsEmpty(); candidate = hint.Next()) {
-		okuri.add(CppCFString(candidate.Description().c_str(), kCFStringEncodingEUC_JP));
-	    }
-	    result.push_back(okuri);
-	}
-
-	// ŽŸ‚ɁA•ÏŠ·Œó•â‚ð’ljÁ‚·‚é
-	OkuriganaEntry wild;
-	for(SKKCandidate candidate = entry.First(); !candidate.IsEmpty(); candidate = entry.Next()) {
-	    wild.add(CppCFString(candidate.Description().c_str(), kCFStringEncodingEUC_JP));
-	}
-	result.push_back(wild);
-
-	return result;
-    }
-
-    // SKKEntry ¨ std::vector<CppCFString> •ÏŠ·
-    std::vector<CppCFString> ConvertOkuriNasi(const SKKEntry& entry) {
-	return CppCFString(entry.Candidate().c_str(), kCFStringEncodingEUC_JP).split('/');
-    }
 };
 
 #pragma mark --- SKKDictionary ---
@@ -158,14 +131,12 @@
     // empty
 }
 
-void SKKDictionary::load(const std::string& path) {
+void SKKDictionary::initializeContainer(EntryContainer& okuriAri, EntryContainer& okuriNasi) {
     std::string line;
     std::string index;
     std::string entry;
     std::ifstream dic;
 
-    path_ = path;
-
     if(!skkdic::OpenAndSeek(path_, dic)) {
 	return;
     }
@@ -178,7 +149,7 @@
 	if(skkdic::OkuriNasiMark.find(line) != std::string::npos) break;
 
 	// ‘—‚è‚È‚µƒGƒ“ƒgƒŠ‚͍~‡‚Ń\[ƒg‚³‚ê‚Ä‚¢‚é‚Í‚¸
-	okuriAri_.push_front(SKKPair(index, line));
+	okuriAri.push_front(SKKPair(index, line));
     }
 
     while(1) {
@@ -188,8 +159,15 @@
 	std::getline(dic, line);
 
 	// ‘—‚è‚ ‚èƒGƒ“ƒgƒŠ‚͏¸‡‚Ń\[ƒg‚³‚ê‚Ä‚¢‚é‚Í‚¸
-	okuriNasi_.push_back(SKKPair(index, line));
+	okuriNasi.push_back(SKKPair(index, line));
     }
+}
+
+void SKKDictionary::load(const std::string& path) {
+    path_ = path;
+
+    // Ž«‘‚ðƒ[ƒh
+    initializeContainer(okuriAri_, okuriNasi_);
 
     // ƒGƒ“ƒgƒŠ‚ðƒ\[ƒg‚·‚é
     std::sort(okuriAri_.begin(), okuriAri_.end(), skkdic::EntryCompare());
@@ -218,7 +196,7 @@
 
     EntryIterator i = std::lower_bound(okuriAri_.begin(), okuriAri_.end(), index, skkdic::EntryCompare());
 
-    return skkdic::ConvertOkuriAri(SKKEntry::ParseOkuriAri(i->first, i->second));
+    return SKKEntryConverter::OkuriAri(SKKEntry::ParseOkuriAri(i->first, i->second));
 }
 
 std::vector<CppCFString> SKKDictionary::findOkuriNasi(const CppCFString& query) {
@@ -231,7 +209,121 @@
 
     EntryIterator i = std::lower_bound(okuriNasi_.begin(), okuriNasi_.end(), index, skkdic::EntryCompare());
 
-    return skkdic::ConvertOkuriNasi(SKKEntry::ParseOkuriNasi(i->first, i->second));
+    return SKKEntryConverter::OkuriNasi(SKKEntry::ParseOkuriNasi(i->first, i->second));
+}
+
+#pragma mark --- SKKAutoUpdateDictionary ---
+
+SKKAutoUpdateDictionary::SKKAutoUpdateDictionary() {
+    // empty
+}
+
+SKKAutoUpdateDictionary::~SKKAutoUpdateDictionary() {
+    // empty
+}
+
+void SKKAutoUpdateDictionary::load(const std::string& path) {
+    std::string::size_type pos = path.find_first_of('/');
+    host_ = path.substr(0, pos);
+    url_ = path.substr(pos);
+
+    pos = path.find_last_of('/');
+    path_  = SkkConfig::home() + "/Library/AquaSKK" + path.substr(pos);
+    initializeContainer(okuriAri_, okuriNasi_);
+
+    std::cerr << "SKK AutoUpdate Dictionary(" << path_ << ")" << std::endl
+	      << "  okuri-ari: " << countOkuriAri() << " entries." << std::endl
+	      << "  okuri-nasi: " << countOkuriNasi() << " entries." << std::endl << std::endl;
+
+    // ƒ_ƒEƒ“ƒ[ƒh—p‚̃XƒŒƒbƒh‚𑖂点‚é
+    pthread_t pth = 0;
+    if(pthread_create(&pth, NULL, SKKAutoUpdateDictionary::download, this) == 0) {
+	pthread_detach(pth);
+    } else {
+	std::cerr << "pthread_create() failed: " << errno << std::endl;
+    }
+}
+
+int SKKAutoUpdateDictionary::countOkuriAri() {
+    Guard g(mutex_);
+    return SKKDictionary::countOkuriAri();
+}
+
+int SKKAutoUpdateDictionary::countOkuriNasi() {
+    Guard g(mutex_);
+    return SKKDictionary::countOkuriNasi();
+}
+
+std::vector<OkuriganaEntry> SKKAutoUpdateDictionary::findOkuriAri(const CppCFString& query) {
+    Guard g(mutex_);
+    return SKKDictionary::findOkuriAri(query);
+}
+
+std::vector<CppCFString> SKKAutoUpdateDictionary::findOkuriNasi(const CppCFString& query) {
+    Guard g(mutex_);
+    return SKKDictionary::findOkuriNasi(query);
+}
+
+void* SKKAutoUpdateDictionary::download(void* param) {
+    SKKAutoUpdateDictionary* obj = static_cast<SKKAutoUpdateDictionary*>(param);
+
+    socket_stream session(obj->host_.c_str(), 80);
+    if(!session) {
+	std::cerr << "can't connect to [" << obj->host_ << "]" << std::endl;
+	return NULL;
+    }
+
+    while(true) {
+	// Ž«‘‚̍XV“ú•t‚ðŽæ“¾
+	char timestamp[64];
+	struct stat st;
+	if(stat(obj->path_.c_str(), &st) != 0) {
+	    st.st_mtime = 0;
+	}
+	strftime(timestamp, sizeof(timestamp), "%a, %d %b %Y %T %Z", gmtime(&st.st_mtime));
+
+	// ƒŠƒNƒGƒXƒg
+	session << "GET " << obj->url_ << " HTTP/1.1" << std::endl;
+	session << "Host: " << obj->host_ << std::endl;
+	session << "If-Modified-Since: " << timestamp << std::endl;
+	session << "Connection: close" << std::endl << std::endl;
+
+	// ƒŒƒXƒ|ƒ“ƒX
+	std::string response;
+	bool modified = false;
+	while(true) {
+	    getline(session, response);
+	    if(response.find("200 OK") != std::string::npos) {
+		modified = true;
+	    }
+	    if(response == "\r") break;
+	}
+
+	if(modified) {
+	    // •Û‘¶
+	    std::ofstream ofs(obj->path_.c_str());
+	    while(true) {
+		getline(session, response);
+		if(response.empty()) break;
+		ofs << response << std::endl;
+	    }
+
+	    // ƒŠƒ[ƒh
+	    EntryContainer tmpOkuriAri;
+	    EntryContainer tmpOkuriNasi;
+	    obj->initializeContainer(tmpOkuriAri, tmpOkuriNasi);
+
+	    // ’u‚«Š·‚¦
+	    Guard g(obj->mutex_);
+	    tmpOkuriAri.swap(obj->okuriAri_);
+	    tmpOkuriNasi.swap(obj->okuriNasi_);
+
+	    std::cerr << "SKK AutoUpdate Dictionary(" << obj->path_ << ") updated" << std::endl;
+	}
+
+	// 6 ŽžŠÔ‘Ò‚Â
+	sleep(60 * 60 * 6);
+    }
 }
 
 #pragma mark --- SKKUserDictionary ---
@@ -295,7 +387,7 @@
 	return std::vector<OkuriganaEntry>();
     }
 
-    return skkdic::ConvertOkuriAri(SKKEntry::ParseOkuriAri(i->first, i->second));
+    return SKKEntryConverter::OkuriAri(SKKEntry::ParseOkuriAri(i->first, i->second));
 }
 
 std::vector<CppCFString> SKKUserDictionary::findOkuriNasi(const CppCFString& query) {
@@ -306,7 +398,7 @@
 	return std::vector<CppCFString>();
     }
 
-    return skkdic::ConvertOkuriNasi(SKKEntry::ParseOkuriNasi(i->first, i->second));
+    return SKKEntryConverter::OkuriNasi(SKKEntry::ParseOkuriNasi(i->first, i->second));
 }
 
 std::vector<CppCFString> SKKUserDictionary::findCompletions(const CppCFString& query) {
Index: AquaSKK/SKKDictionary.h
diff -u AquaSKK/SKKDictionary.h:1.5.2.2 AquaSKK/SKKDictionary.h:1.5.2.3
--- AquaSKK/SKKDictionary.h:1.5.2.2	Sat Feb 18 02:20:38 2006
+++ AquaSKK/SKKDictionary.h	Mon Mar  6 21:03:00 2006
@@ -1,5 +1,5 @@
 /*
-  $Id: SKKDictionary.h,v 1.5.2.2 2006/02/17 17:20:38 t-suwa Exp $
+  $Id: SKKDictionary.h,v 1.5.2.3 2006/03/06 12:03:00 t-suwa Exp $
 
   MacOS X implementation of the SKK input method.
 
@@ -25,6 +25,7 @@
 
 #include <deque>
 #include "Dictionary.h"
+#include "Mutex.h"
 
 class OkuriganaEntry;
 class CppCFString;
@@ -38,10 +39,13 @@
 
 // SKK ‹¤—LŽ«‘
 class SKKDictionary: public Dictionary {
+protected:
     std::string path_;
     EntryContainer okuriAri_;
     EntryContainer okuriNasi_;
 
+    void initializeContainer(EntryContainer& okuriAri, EntryContainer& okuriNasi);
+
 public:
     SKKDictionary();
     virtual ~SKKDictionary();
@@ -53,8 +57,27 @@
 
     virtual std::vector<OkuriganaEntry> findOkuriAri(const CppCFString& query);
     virtual std::vector<CppCFString> findOkuriNasi(const CppCFString& query);
+};
+
+// SKK Ž©“®XVŽ«‘
+class SKKAutoUpdateDictionary: public SKKDictionary {
+    std::string host_;
+    std::string url_;
+    Mutex mutex_;
+
+    static void* download(void* param);
 
-    void changeDictionaryFile(const std::string& fpath);
+public:
+    SKKAutoUpdateDictionary();
+    virtual ~SKKAutoUpdateDictionary();
+
+    virtual void load(const std::string& path);
+
+    virtual int countOkuriAri();
+    virtual int countOkuriNasi();
+
+    virtual std::vector<OkuriganaEntry> findOkuriAri(const CppCFString& query);
+    virtual std::vector<CppCFString> findOkuriNasi(const CppCFString& query);
 };
 
 // SKK ƒ†[ƒU[Ž«‘
Index: AquaSKK/UserDefaults.plist
diff -u AquaSKK/UserDefaults.plist:1.1.2.3 AquaSKK/UserDefaults.plist:1.1.2.4
--- AquaSKK/UserDefaults.plist:1.1.2.3	Sat Feb 25 16:27:32 2006
+++ AquaSKK/UserDefaults.plist	Mon Mar  6 21:03:00 2006
@@ -2,6 +2,8 @@
 <!DOCTYPE plist PUBLIC "-//Apple Computer//DTD PLIST 1.0//EN" "http://www.apple.com/DTDs/PropertyList-1.0.dtd">
 <plist version="1.0">
 <dict>
+	<key>candidates_count</key>
+	<integer>7</integer>
 	<key>candidates_font_name</key>
 	<string>LucidaGrande</string>
 	<key>candidates_font_size</key>
Index: AquaSKK/skkserv.cpp
diff -u AquaSKK/skkserv.cpp:1.1.2.5 AquaSKK/skkserv.cpp:1.1.2.6
--- AquaSKK/skkserv.cpp:1.1.2.5	Sat Feb 25 16:27:32 2006
+++ AquaSKK/skkserv.cpp	Mon Mar  6 21:03:00 2006
@@ -1,5 +1,5 @@
 /*  -*- c++ -*-
-  $Id: skkserv.cpp,v 1.1.2.5 2006/02/25 07:27:32 t-suwa Exp $
+  $Id: skkserv.cpp,v 1.1.2.6 2006/03/06 12:03:00 t-suwa Exp $
 
   MacOS X implementation of the SKK input method.
 
@@ -53,12 +53,12 @@
 }
 
 void skkserv::stop() {
+    server_.close();
     if(pth_) {
         pthread_cancel(pth_);
         pthread_join(pth_, NULL);
 	pth_ = 0;
     }
-    server_.close();
 }
 
 void* skkserv::engine(void* param) {
@@ -102,9 +102,8 @@
 
 	    // Œ©‚‚©‚Á‚½H
 	    if(reply.length() > 0) {
-		char* reply_c = reply.toCString(kCFStringEncodingEUC_JP);
-		sock << "1" << reply_c << "\n";
-		delete[] reply_c;
+		std::string candidates = reply.toStdString();
+		sock << "1" << candidates << "\n";
 	    } else {
 		sock << "4" << word << "\n";
 	    }
@@ -116,7 +115,7 @@
             sock.flush();
             break;
         case '3':		// ƒzƒXƒgî•ñ
-	    sock << ip_address::getsockname(sock.socket()) << "::" << std::endl;
+	    sock << ip_address::getsockname(sock.socket()) << ":0.0.0.0:" << std::endl;
             sock.flush();
             break;
         default:		// –³Œø‚ȃRƒ}ƒ“ƒh


aquaskk-changes メーリングリストの案内
Zurück zum Archiv-Index