2 Copyright © 1995-2001, The AROS Development Team. All rights reserved.
9 /*********************************************************************************************/
11 #define SHOWFLAGS 1 /* Set to 1 to show Flags in the keylist */
13 #include <proto/keymap.h>
16 #include <aros/debug.h>
20 /*********************************************************************************************/
23 BOOL inputdev_changed
= FALSE
;
24 struct List keymap_list
;
25 struct InputPrefs inputprefs
;
26 struct InputPrefs restore_prefs
;
27 struct MsgPort
*InputMP
;
28 struct timerequest
*InputIO
;
29 BPTR testkeymap_seg
= NULL
;
31 /*********************************************************************************************/
33 struct nameexp layout_expansion_table
[] =
35 {"al" , "Albanian" , NULL
},
36 {"usa" , "American (Sun 5c)" , "United_States" },
37 {"us" , "American (PC 104)" , "United_States" },
38 {"usx" , "American (PC 105)" , "United_States" },
39 {"d" , "Deutsch" , "Deutschland" },
40 {"be" , "Belge" , "Belgique" },
41 {"br" , "Brasileiro" , "Brasil" },
42 {"gb" , "British" , "United_Kingdom" },
43 {"gbx" , "British Extended" , "United_Kingdom" },
44 {"cdn" , "Canadien Français" , "Canada" },
45 {"ca" , "Canadien Français" , "Canada_Français" },
46 {"cz" , "Czech" , "Cesko" },
47 {"dk" , "Dansk" , "Danmark" },
48 {"ne" , "Dutch" , "Nederland" },
49 {"dvx" , "Dvorak" , "Espana" },
50 {"usa2" , "Dvorak" , NULL
},
51 {"dvl" , "Dvorak Left-handed" , NULL
},
52 {"dvr" , "Dvorak Right-handed" , NULL
},
53 {"ir" , "English Ireland" , "Ireland" },
54 {"e" , "Español" , "España" },
55 {"sp" , "Español no deadkeys" , "España" },
56 {"et" , "Estonian" , NULL
},
57 {"fi" , "Finnish" , "Suomi" },
58 {"f" , "Français" , "France" },
59 {"ic" , "Icelandic" , "Island" },
60 {"i" , "Italiana" , "Italia" },
61 {"la" , "Latin American" , NULL
},
62 {"lv" , "Latvian" , NULL
},
63 {"lt" , "Lithuanian" , NULL
},
64 {"hu" , "Magyar" , NULL
},
65 {"n" , "Norsk" , "Norge" },
66 {"pl" , "Polski" , "Polska" },
67 {"po" , "Português" , "Portugal" },
68 {"ru" , "Russian" , "Rossija" },
69 {"sg" , "Schweiz" , "Suisse" },
70 {"ch2" , "Schweiz" , "Suisse" },
71 {"sl" , "Slovak" , "Slovakia" },
72 {"sf" , "Suisse" , "Suisse" },
73 {"ch1" , "Suisse" , "Suisse" },
74 {"s" , "Svenskt" , "Sverige" },
75 {"ur" , "Ucranian" , "Ukrajina" },
79 /*********************************************************************************************/
81 static void ExpandName(STRPTR name
, STRPTR flag
, struct nameexp
*exp
)
83 for(; exp
->shortname
; exp
++)
85 if (stricmp(exp
->shortname
, name
) == 0)
87 strcpy(name
, exp
->longname
);
88 if (exp
->flag
!= NULL
) strcpy(flag
, exp
->flag
);
94 /*********************************************************************************************/
97 void SortInNode(struct List
*list
, struct Node
*node
)
99 struct Node
*sort
, *prev
= NULL
;
101 ForeachNode(list
, sort
)
103 if (Stricmp(node
->ln_Name
, sort
->ln_Name
) < 0) break;
107 Insert(list
, node
, prev
);
110 void ScanDirectory(STRPTR pattern
, struct List
*list
, LONG entrysize
)
112 struct AnchorPath ap
;
113 struct ListviewEntry
*entry
, *entry2
;
114 struct List templist
;
118 memset(&ap
, 0, sizeof(ap
));
121 error
= MatchFirst(pattern
, &ap
);
124 if (ap
.ap_Info
.fib_DirEntryType
< 0)
126 entry
= (struct ListviewEntry
*)AllocPooled(mempool
, entrysize
);
129 entry
->node
.ln_Name
= entry
->layoutname
;
130 strncpy(entry
->realname
, ap
.ap_Info
.fib_FileName
, sizeof(entry
->realname
));
132 sp
= strchr(entry
->realname
, '_');
136 strcpy(entry
->layoutname
, sp
+ 1);
140 strcpy(entry
->layoutname
, entry
->realname
);
142 ExpandName(entry
->layoutname
, entry
->flagname
, layout_expansion_table
);
143 AddTail(&templist
, &entry
->node
);
146 error
= MatchNext(&ap
);
150 /* Sort by Layout Name */
152 ForeachNodeSafe(&templist
, entry
, entry2
)
154 Remove(&entry
->node
);
155 SortInNode(list
, &entry
->node
);
158 ForeachNode(list
, entry
)
161 sprintf(entry
->displayname
, "\033I[5:Locale:Flags/Countries/%s]%s", entry
->flagname
, entry
->node
.ln_Name
);
163 sprintf(entry
->displayname
, "%s", entry
->node
.ln_Name
);
165 D(bug("IPrefs: kbd entry flag: %s\n", entry
->flagname
));
169 /*********************************************************************************************/
171 BOOL
LoadPrefs(BPTR fh
)
173 static struct FileInputPrefs loadprefs
;
174 struct IFFHandle
*iff
;
177 if ((iff
= AllocIFF()))
179 iff
->iff_Stream
= fh
;
182 D(bug("LoadPrefs: stream opened.\n"));
186 if (!OpenIFF(iff
, IFFF_READ
))
188 D(bug("LoadPrefs: OpenIFF okay.\n"));
190 if (!StopChunk(iff
, ID_PREF
, ID_INPT
))
192 D(bug("LoadPrefs: StopChunk okay.\n"));
194 if (!ParseIFF(iff
, IFFPARSE_SCAN
))
196 struct ContextNode
*cn
;
198 D(bug("LoadPrefs: ParseIFF okay.\n"));
200 cn
= CurrentChunk(iff
);
202 if (cn
->cn_Size
== sizeof(struct FileInputPrefs
))
204 D(bug("LoadPrefs: ID_INPT chunk size okay.\n"));
206 if (ReadChunkBytes(iff
, &loadprefs
, sizeof(struct FileInputPrefs
)) == sizeof(struct FileInputPrefs
))
208 D(bug("LoadPrefs: Reading chunk successful.\n"));
210 CopyMem(loadprefs
.ip_Keymap
, inputprefs
.ip_Keymap
, sizeof(loadprefs
.ip_Keymap
));
211 inputprefs
.ip_PointerTicks
= ARRAY_TO_WORD(loadprefs
.ip_PointerTicks
);
212 inputprefs
.ip_DoubleClick
.tv_secs
= ARRAY_TO_LONG(loadprefs
.ip_DoubleClick_secs
);
213 inputprefs
.ip_DoubleClick
.tv_micro
= ARRAY_TO_LONG(loadprefs
.ip_DoubleClick_micro
);
214 inputprefs
.ip_KeyRptDelay
.tv_secs
= ARRAY_TO_LONG(loadprefs
.ip_KeyRptDelay_secs
);
215 inputprefs
.ip_KeyRptDelay
.tv_micro
= ARRAY_TO_LONG(loadprefs
.ip_KeyRptDelay_micro
);
216 inputprefs
.ip_KeyRptSpeed
.tv_secs
= ARRAY_TO_LONG(loadprefs
.ip_KeyRptSpeed_secs
);
217 inputprefs
.ip_KeyRptSpeed
.tv_micro
= ARRAY_TO_LONG(loadprefs
.ip_KeyRptSpeed_micro
);
218 inputprefs
.ip_MouseAccel
= ARRAY_TO_WORD(loadprefs
.ip_MouseAccel
);
220 D(bug("LoadPrefs: Everything okay :-)\n"));
226 } /* if (!ParseIFF(iff, IFFPARSE_SCAN)) */
228 } /* if (!StopChunk(iff, ID_PREF, ID_INPT)) */
232 } /* if (!OpenIFF(iff, IFFF_READ)) */
234 } /* if (fh != NULL) */
238 } /* if ((iff = AllocIFF())) */
243 /*********************************************************************************************/
245 BOOL
SavePrefs(BPTR fh
)
247 static struct FileInputPrefs saveprefs
;
248 struct IFFHandle
*iff
;
249 BOOL retval
= FALSE
, delete_if_error
= FALSE
;
251 CopyMem(inputprefs
.ip_Keymap
, saveprefs
.ip_Keymap
, sizeof(saveprefs
.ip_Keymap
));
252 WORD_TO_ARRAY(inputprefs
.ip_PointerTicks
, saveprefs
.ip_PointerTicks
);
253 LONG_TO_ARRAY(inputprefs
.ip_DoubleClick
.tv_secs
, saveprefs
.ip_DoubleClick_secs
);
254 LONG_TO_ARRAY(inputprefs
.ip_DoubleClick
.tv_micro
, saveprefs
.ip_DoubleClick_micro
);
255 LONG_TO_ARRAY(inputprefs
.ip_KeyRptDelay
.tv_secs
, saveprefs
.ip_KeyRptDelay_secs
);
256 LONG_TO_ARRAY(inputprefs
.ip_KeyRptDelay
.tv_micro
, saveprefs
.ip_KeyRptDelay_micro
);
257 LONG_TO_ARRAY(inputprefs
.ip_KeyRptSpeed
.tv_secs
, saveprefs
.ip_KeyRptSpeed_secs
);
258 LONG_TO_ARRAY(inputprefs
.ip_KeyRptSpeed
.tv_micro
, saveprefs
.ip_KeyRptSpeed_micro
);
259 WORD_TO_ARRAY(inputprefs
.ip_MouseAccel
, saveprefs
.ip_MouseAccel
);
261 if ((iff
= AllocIFF()))
263 iff
->iff_Stream
= fh
;
266 D(bug("SavePrefs: stream opened.\n"));
268 delete_if_error
= TRUE
;
272 if (!OpenIFF(iff
, IFFF_WRITE
))
274 D(bug("SavePrefs: OpenIFF okay.\n"));
276 if (!PushChunk(iff
, ID_PREF
, ID_FORM
, IFFSIZE_UNKNOWN
))
278 D(bug("SavePrefs: PushChunk(FORM) okay.\n"));
280 if (!PushChunk(iff
, ID_PREF
, ID_PRHD
, sizeof(struct FilePrefHeader
)))
282 struct FilePrefHeader head
;
284 D(bug("SavePrefs: PushChunk(PRHD) okay.\n"));
286 head
.ph_Version
= 0; // FIXME: shouold be PHV_CURRENT, but see <prefs/prefhdr.h>
291 head
.ph_Flags
[3] = 0;
293 if (WriteChunkBytes(iff
, &head
, sizeof(head
)) == sizeof(head
))
295 D(bug("SavePrefs: WriteChunkBytes(PRHD) okay.\n"));
299 if (!PushChunk(iff
, ID_PREF
, ID_INPT
, sizeof(saveprefs
)))
301 D(bug("SavePrefs: PushChunk(INPT) okay.\n"));
303 if (WriteChunkBytes(iff
, &saveprefs
, sizeof(saveprefs
)) == sizeof(saveprefs
))
305 D(bug("SavePrefs: WriteChunkBytes(INPT) okay.\n"));
306 D(bug("SavePrefs: Everything okay :-)\n"));
313 } /* if (!PushChunk(iff, ID_PREF, ID_INPT, sizeof(saveprefs))) */
315 } /* if (WriteChunkBytes(iff, &head, sizeof(head)) == sizeof(head)) */
321 } /* if (!PushChunk(iff, ID_PREF, ID_PRHD, sizeof(struct PrefHeader))) */
325 } /* if (!PushChunk(iff, ID_PREF, ID_FORM, IFFSIZE_UNKNOWN)) */
329 } /* if (!OpenIFF(iff, IFFFWRITE)) */
332 } /* if (iff->iff_Stream)) */
336 } /* if ((iff = AllocIFF())) */
338 // if (!retval && delete_if_error)
340 // DeleteFile(filename);
346 /*********************************************************************************************/
348 BOOL
DefaultPrefs(void)
350 strcpy(inputprefs
.ip_Keymap
, "amiga_usa0");
351 inputprefs
.ip_PointerTicks
= 1;
352 inputprefs
.ip_DoubleClick
.tv_secs
= 0;
353 inputprefs
.ip_DoubleClick
.tv_micro
= 500000;
354 inputprefs
.ip_KeyRptDelay
.tv_secs
= 0;
355 inputprefs
.ip_KeyRptDelay
.tv_micro
= 500000;
356 inputprefs
.ip_KeyRptSpeed
.tv_secs
= 0;
357 inputprefs
.ip_KeyRptSpeed
.tv_micro
= 40000;
358 inputprefs
.ip_MouseAccel
= 1;
363 /*********************************************************************************************/
365 void CopyPrefs(struct InputPrefs
*s
, struct InputPrefs
*d
)
367 CopyMem(s
, d
, sizeof(struct InputPrefs
));
370 void RestorePrefs(void)
372 CopyPrefs(&restore_prefs
, &inputprefs
);
375 /*********************************************************************************************/
377 void update_inputdev(void)
381 if (InputIO
->tr_node
.io_Device
)
383 InputIO
->tr_node
.io_Command
= IND_SETPERIOD
;
384 InputIO
->tr_time
= inputprefs
.ip_KeyRptSpeed
;
385 DoIO(&InputIO
->tr_node
);
387 InputIO
->tr_node
.io_Command
= IND_SETTHRESH
;
388 InputIO
->tr_time
= inputprefs
.ip_KeyRptDelay
;
389 DoIO(&InputIO
->tr_node
);
391 inputdev_changed
= TRUE
;
397 void try_setting_mousespeed(void)
399 struct Preferences p
;
401 GetPrefs(&p
, sizeof(p
));
402 p
.PointerTicks
= inputprefs
.ip_PointerTicks
;
403 p
.DoubleClick
= inputprefs
.ip_DoubleClick
;
404 p
.KeyRptDelay
= inputprefs
.ip_KeyRptDelay
;
405 p
.KeyRptSpeed
= inputprefs
.ip_KeyRptSpeed
;
406 if (inputprefs
.ip_MouseAccel
)
408 p
.EnableCLI
|= MOUSE_ACCEL
;
412 p
.EnableCLI
&= ~MOUSE_ACCEL
;
415 SetPrefs(&p
, sizeof(p
), FALSE
);
418 void try_setting_test_keymap(void)
420 struct KeyMapResource
*KeyMapResource
;
421 struct Library
*KeymapBase
;
422 struct KeyMapNode
*kmn
= NULL
;
424 BPTR lock
, seg
, olddir
, oldseg
= 0;
426 if ((KeyMapResource
= OpenResource("keymap.resource")))
430 ForeachNode(&KeyMapResource
->kr_List
, node
)
432 if (!stricmp(inputprefs
.ip_Keymap
, node
->ln_Name
))
434 kmn
= (struct KeyMapNode
*)node
;
445 lock
= Lock("DEVS:Keymaps", SHARED_LOCK
);
449 olddir
= CurrentDir(lock
);
451 if ((seg
= LoadSeg(inputprefs
.ip_Keymap
)))
453 kmn
= (struct KeyMapNode
*) (((UBYTE
*)BADDR(seg
)) + sizeof(APTR
));
454 oldseg
= testkeymap_seg
;
455 testkeymap_seg
= seg
;
466 KeymapBase
= OpenLibrary("keymap.library", 0);
469 SetKeyMapDefault((IPTR
)&kmn
->kn_KeyMap
);
470 CloseLibrary(KeymapBase
);
473 if (oldseg
) UnLoadSeg(oldseg
);
477 void kbd_cleanup(void)
479 if (inputdev_changed
)
481 InputIO
->tr_node
.io_Command
= IND_SETPERIOD
;
482 InputIO
->tr_time
= restore_prefs
.ip_KeyRptSpeed
;
483 DoIO(&InputIO
->tr_node
);
485 InputIO
->tr_node
.io_Command
= IND_SETTHRESH
;
486 InputIO
->tr_time
= restore_prefs
.ip_KeyRptDelay
;
487 DoIO(&InputIO
->tr_node
);
488 inputdev_changed
= FALSE
;
493 UnLoadSeg(testkeymap_seg
);