Writing Multiuser applications for single-byte languages other than English
Accented characters (as well as other non-English characters) have varying ASCII codes depending on whether or not the local environment is Macintosh or ANSI. The differing codes may cause problems when messaging between these different platforms. Therefore, when writing Multiuser applications for single-byte environments other than English, it is essential to map upper ASCII (128-255) so that accented characters can be correctly passed between the client, the server, and other clients.
This TechNote includes the Lingo required to convert between Macintosh and ANSI (Windows) character sets.
Upper ASCII translation
The first thing the application should do is test the Lingo property "the romanLingo". This returns whether Lingo uses a single-byte (TRUE) or double-byte (FALSE) interpreter. Normally, "the romanLingo" is set when Director is first started and is determined by the local version of the system software. In the sample code below, this test occurs in a handler called, "SetupCharConverter()"
If"the romanLingo" is FALSE, meaning that the system software is using a double-byte language interpreter, then do not perform any ASCII mapping. The routines described in this TechNote should not be used in a double-byte environment.
If"the romanLingo" is TRUE then choose from the two options below:
Option one
Make surethat high ASCII characters are never used in any text message (including user names, group names, movieIDs, message contents, database object names, and so forth).
Option two
When a movie is running on a platform that is different from the server, perform high ASCII translation into the server machine's character set for every string sent to the server. If the server is running on an ANSI compliant system, convert all strings to ANSI. If the server is running on a Macintosh, convert all strings to Mac ASCII. In the same fashion, every message sent from the server to the client will need to be converted from the server's character set to the client's local set.
Sample code
In the sample code below, the actual character conversion occurs in either"MacToAnsiStr()" or "AnsiToMacStr()". These functions are called by"ConvertLocalToServer()" and "ConvertServerToLocal()".
Note:For peer to peer connections, all data should be converted to the character set of the host.
-- To use this code, change the server platform in the startMovie -- handler below to match your server. Alternatively, you can query -- the server for its version with the System.Server.GetVersion command -- and pass the platform result to the SetupCharConverter() function. -- Use the routine ConvertLocalToServer() to convert text before calling -- multiuser xtra functions, and ConvertServerToLocal() to convert text -- received from the server. -- These flags are set during SetupCharConverter() global pNeedTranslation global pLocalIsWindows -- Tables generated to convert characters global pMacToAnsiTable global pAnsiToMacTable ----------------------------------------------------------------- -- Startup code. Change -----------------------------------------------------------------
on startMovie -- Change this to either "Windows" or "Macintosh" to match -- your server platform. SetupCharConverter( "Windows" ) pass end startMovie ----------------------------------------------------------------- -- Startup code ----------------------------------------------------------------- on SetupCharConverter platformStr if ( the platform contains "Windows" ) then pLocalIsWindows = true else pLocalIsWindows = false end if if ( the romanlingo = false ) or ( the platform contains platformStr ) then pNeedTranslation = false else pNeedTranslation = true SetupMacToAnsiTable() SetupAnsiToMacTable() end if end SetupCharConverter ----------------------------------------------------------------- -- Convert a string from the local format to the server format. -- This is only done if we're on a different platform. ----------------------------------------------------------------- on ConvertLocalToServer str newStr = "" if ( pNeedTranslation ) then if ( pLocalIsWindows ) then newStr = AnsiToMacStr( str ) else newStr = MacToAnsiStr( str ) end if else newStr = str end if return newStr end ConvertLocalToServer ----------------------------------------------------------------- -- Convert a string from the server format to the local format. -- This is only done if we're on a different platform. ----------------------------------------------------------------- on ConvertServerToLocal str newStr = "" if ( pNeedTranslation ) then if ( pLocalIsWindows ) then newStr = MacToAnsiStr( str ) else newStr = AnsiToMacStr( str ) end if else newStr = str end if return newStr end ConvertLocalToServer ----------------------------------------------------------------- -- Convert a string from Mac text to Ansi text ----------------------------------------------------------------- on MacToAnsiStr str ansiStr = "" numChars = str.chars.count repeat with x = 1 to numChars ansiStr = ansiStr & pMacToAnsiTable[ CharToNum( str.char[x] ) + 1 ] end repeat return ansiStr end MacToAnsiStr ----------------------------------------------------------------- -- Convert a string from Mac text to ANSI text ----------------------------------------------------------------- on AnsiToMacStr str ansiStr = "" numChars = str.chars.count repeat with x = 1 to numChars ansiStr = ansiStr & pAnsiToMacTable[ CharToNum( str.char[x] ) + 1 ] end repeat return ansiStr end AnsiToMacStr ----------------------------------------------------------------- -- Build the conversion table for Mac to ANSI ----------------------------------------------------------------- on SetupMacToAnsiTable if ( voidP( pMacToAnsiTable ) ) then pMacToAnsiTable = [] repeat with x = 0 to 127 pMacToAnsiTable.Append( NumToChar( x ) ) end repeat pMacToAnsiTable.append( NumToChar(196) ) -- 128 pMacToAnsiTable.append( NumToChar(197) ) pMacToAnsiTable.append( NumToChar(199) ) -- 130 pMacToAnsiTable.append( NumToChar(201) ) pMacToAnsiTable.append( NumToChar(209) ) pMacToAnsiTable.append( NumToChar(214) ) pMacToAnsiTable.append( NumToChar(220) ) pMacToAnsiTable.append( NumToChar(225) ) -- 135 pMacToAnsiTable.append( NumToChar(224) ) pMacToAnsiTable.append( NumToChar(226) ) pMacToAnsiTable.append( NumToChar(228) ) pMacToAnsiTable.append( NumToChar(227) ) pMacToAnsiTable.append( NumToChar(229) ) -- 140 pMacToAnsiTable.append( NumToChar(231) ) pMacToAnsiTable.append( NumToChar(233) ) pMacToAnsiTable.append( NumToChar(232) ) pMacToAnsiTable.append( NumToChar(234) ) pMacToAnsiTable.append( NumToChar(235) ) -- 145 pMacToAnsiTable.append( NumToChar(237) ) pMacToAnsiTable.append( NumToChar(236) ) pMacToAnsiTable.append( NumToChar(238) ) pMacToAnsiTable.append( NumToChar(239) ) pMacToAnsiTable.append( NumToChar(241) ) -- 150 pMacToAnsiTable.append( NumToChar(243) ) pMacToAnsiTable.append( NumToChar(242) ) pMacToAnsiTable.append( NumToChar(244) ) pMacToAnsiTable.append( NumToChar(246) ) pMacToAnsiTable.append( NumToChar(245) ) -- 155 pMacToAnsiTable.append( NumToChar(250) ) pMacToAnsiTable.append( NumToChar(249) ) pMacToAnsiTable.append( NumToChar(251) ) pMacToAnsiTable.append( NumToChar(252) ) pMacToAnsiTable.append( NumToChar(134) ) -- 160 pMacToAnsiTable.append( NumToChar(190) ) pMacToAnsiTable.append( NumToChar(162) ) pMacToAnsiTable.append( NumToChar(163) ) pMacToAnsiTable.append( NumToChar(167) ) pMacToAnsiTable.append( NumToChar(149) ) -- 165 pMacToAnsiTable.append( NumToChar(182) ) pMacToAnsiTable.append( NumToChar(223) ) pMacToAnsiTable.append( NumToChar(174) ) pMacToAnsiTable.append( NumToChar(169) ) pMacToAnsiTable.append( NumToChar(153) ) -- 170 pMacToAnsiTable.append( NumToChar(180) ) pMacToAnsiTable.append( NumToChar(168) ) pMacToAnsiTable.append( NumToChar(141) ) pMacToAnsiTable.append( NumToChar(198) ) pMacToAnsiTable.append( NumToChar(216) ) -- 175 pMacToAnsiTable.append( NumToChar(144) ) pMacToAnsiTable.append( NumToChar(177) ) pMacToAnsiTable.append( NumToChar(143) ) pMacToAnsiTable.append( NumToChar(142) ) pMacToAnsiTable.append( NumToChar(165) ) -- 180 pMacToAnsiTable.append( NumToChar(181) ) pMacToAnsiTable.append( NumToChar(240) ) pMacToAnsiTable.append( NumToChar(221) ) pMacToAnsiTable.append( NumToChar(222) ) pMacToAnsiTable.append( NumToChar(254) ) -- 185 pMacToAnsiTable.append( NumToChar(138) ) pMacToAnsiTable.append( NumToChar(170) ) pMacToAnsiTable.append( NumToChar(186) ) pMacToAnsiTable.append( NumToChar(253) ) pMacToAnsiTable.append( NumToChar(230) ) -- 190 pMacToAnsiTable.append( NumToChar(248) ) pMacToAnsiTable.append( NumToChar(191) ) pMacToAnsiTable.append( NumToChar(161) ) pMacToAnsiTable.append( NumToChar(172) ) pMacToAnsiTable.append( NumToChar(175) ) -- 195 pMacToAnsiTable.append( NumToChar(131) ) pMacToAnsiTable.append( NumToChar(188) ) pMacToAnsiTable.append( NumToChar(208) ) pMacToAnsiTable.append( NumToChar(171) ) pMacToAnsiTable.append( NumToChar(187) ) -- 200 pMacToAnsiTable.append( NumToChar(133) ) pMacToAnsiTable.append( NumToChar(160) ) pMacToAnsiTable.append( NumToChar(192) ) pMacToAnsiTable.append( NumToChar(195) ) pMacToAnsiTable.append( NumToChar(213) ) -- 205 pMacToAnsiTable.append( NumToChar(140) ) pMacToAnsiTable.append( NumToChar(156) ) pMacToAnsiTable.append( NumToChar(173) ) pMacToAnsiTable.append( NumToChar(151) ) pMacToAnsiTable.append( NumToChar(147) ) -- 210 pMacToAnsiTable.append( NumToChar(148) ) pMacToAnsiTable.append( NumToChar(145) ) pMacToAnsiTable.append( NumToChar(146) ) pMacToAnsiTable.append( NumToChar(247) ) pMacToAnsiTable.append( NumToChar(215) ) -- 215 pMacToAnsiTable.append( NumToChar(255) ) pMacToAnsiTable.append( NumToChar(159) ) pMacToAnsiTable.append( NumToChar(158) ) pMacToAnsiTable.append( NumToChar(164) ) pMacToAnsiTable.append( NumToChar(139) ) -- 220 pMacToAnsiTable.append( NumToChar(155) ) pMacToAnsiTable.append( NumToChar(128) ) pMacToAnsiTable.append( NumToChar(129) ) pMacToAnsiTable.append( NumToChar(135) ) pMacToAnsiTable.append( NumToChar(183) ) -- 225 pMacToAnsiTable.append( NumToChar(130) ) pMacToAnsiTable.append( NumToChar(132) ) pMacToAnsiTable.append( NumToChar(137) ) pMacToAnsiTable.append( NumToChar(194) ) pMacToAnsiTable.append( NumToChar(202) ) -- 230 pMacToAnsiTable.append( NumToChar(193) ) pMacToAnsiTable.append( NumToChar(203) ) pMacToAnsiTable.append( NumToChar(200) ) pMacToAnsiTable.append( NumToChar(205) ) pMacToAnsiTable.append( NumToChar(206) ) -- 235 pMacToAnsiTable.append( NumToChar(207) ) pMacToAnsiTable.append( NumToChar(204) ) pMacToAnsiTable.append( NumToChar(211) ) pMacToAnsiTable.append( NumToChar(212) ) pMacToAnsiTable.append( NumToChar(157) ) -- 240 pMacToAnsiTable.append( NumToChar(210) ) pMacToAnsiTable.append( NumToChar(218) ) pMacToAnsiTable.append( NumToChar(219) ) pMacToAnsiTable.append( NumToChar(217) ) pMacToAnsiTable.append( NumToChar(166) ) -- 245 pMacToAnsiTable.append( NumToChar(136) ) pMacToAnsiTable.append( NumToChar(152) ) pMacToAnsiTable.append( NumToChar(150) ) pMacToAnsiTable.append( NumToChar(154) ) pMacToAnsiTable.append( NumToChar(178) ) -- 250 pMacToAnsiTable.append( NumToChar(176) ) pMacToAnsiTable.append( NumToChar(184) ) pMacToAnsiTable.append( NumToChar(189) ) pMacToAnsiTable.append( NumToChar(179) ) pMacToAnsiTable.append( NumToChar(185) ) -- 255 end if end SetupMacToAnsiTable ----------------------------------------------------------------- -- Build the conversion table for ANSI to Mac ----------------------------------------------------------------- on SetupAnsiToMacTable if ( voidP( pAnsiToMacTable ) ) then pAnsiToMacTable = [] repeat with x = 0 to 127 pAnsiToMacTable.Append( NumToChar( x ) ) end repeat pAnsiToMacTable.Append( NumToChar(222) ) -- 128 pAnsiToMacTable.Append( NumToChar(223) ) pAnsiToMacTable.Append( NumToChar(226) ) -- 130 pAnsiToMacTable.Append( NumToChar(196) ) pAnsiToMacTable.Append( NumToChar(227) ) pAnsiToMacTable.Append( NumToChar(201) ) pAnsiToMacTable.Append( NumToChar(160) ) pAnsiToMacTable.Append( NumToChar(224) ) -- 135 pAnsiToMacTable.Append( NumToChar(246) ) pAnsiToMacTable.Append( NumToChar(228) ) pAnsiToMacTable.Append( NumToChar(186) ) pAnsiToMacTable.Append( NumToChar(220) ) pAnsiToMacTable.Append( NumToChar(206) ) -- 140 pAnsiToMacTable.Append( NumToChar(173) ) pAnsiToMacTable.Append( NumToChar(179) ) pAnsiToMacTable.Append( NumToChar(178) ) pAnsiToMacTable.Append( NumToChar(176) ) pAnsiToMacTable.Append( NumToChar(212) ) -- 145 pAnsiToMacTable.Append( NumToChar(213) ) pAnsiToMacTable.Append( NumToChar(210) ) pAnsiToMacTable.Append( NumToChar(211) ) pAnsiToMacTable.Append( NumToChar(165) ) pAnsiToMacTable.Append( NumToChar(248) ) -- 150 pAnsiToMacTable.Append( NumToChar(209) ) pAnsiToMacTable.Append( NumToChar(247) ) pAnsiToMacTable.Append( NumToChar(170) ) pAnsiToMacTable.Append( NumToChar(249) ) pAnsiToMacTable.Append( NumToChar(221) ) -- 155 pAnsiToMacTable.Append( NumToChar(207) ) pAnsiToMacTable.Append( NumToChar(240) ) pAnsiToMacTable.Append( NumToChar(218) ) pAnsiToMacTable.Append( NumToChar(217) ) pAnsiToMacTable.Append( NumToChar(202) ) -- 160 pAnsiToMacTable.Append( NumToChar(193) ) pAnsiToMacTable.Append( NumToChar(162) ) pAnsiToMacTable.Append( NumToChar(163) ) pAnsiToMacTable.Append( NumToChar(219) ) pAnsiToMacTable.Append( NumToChar(180) ) -- 165 pAnsiToMacTable.Append( NumToChar(245) ) pAnsiToMacTable.Append( NumToChar(164) ) pAnsiToMacTable.Append( NumToChar(172) ) pAnsiToMacTable.Append( NumToChar(169) ) pAnsiToMacTable.Append( NumToChar(187) ) -- 170 pAnsiToMacTable.Append( NumToChar(199) ) pAnsiToMacTable.Append( NumToChar(194) ) pAnsiToMacTable.Append( NumToChar(208) ) pAnsiToMacTable.Append( NumToChar(168) ) pAnsiToMacTable.Append( NumToChar(195) ) -- 175 pAnsiToMacTable.Append( NumToChar(251) ) pAnsiToMacTable.Append( NumToChar(177) ) pAnsiToMacTable.Append( NumToChar(250) ) pAnsiToMacTable.Append( NumToChar(254) ) pAnsiToMacTable.Append( NumToChar(171) ) -- 180 pAnsiToMacTable.Append( NumToChar(181) ) pAnsiToMacTable.Append( NumToChar(166) ) pAnsiToMacTable.Append( NumToChar(225) ) pAnsiToMacTable.Append( NumToChar(252) ) pAnsiToMacTable.Append( NumToChar(255) ) -- 185 pAnsiToMacTable.Append( NumToChar(188) ) pAnsiToMacTable.Append( NumToChar(200) ) pAnsiToMacTable.Append( NumToChar(197) ) pAnsiToMacTable.Append( NumToChar(253) ) pAnsiToMacTable.Append( NumToChar(161) ) -- 190 pAnsiToMacTable.Append( NumToChar(192) ) pAnsiToMacTable.Append( NumToChar(203) ) pAnsiToMacTable.Append( NumToChar(231) ) pAnsiToMacTable.Append( NumToChar(229) ) pAnsiToMacTable.Append( NumToChar(204) ) -- 195 pAnsiToMacTable.Append( NumToChar(128) ) pAnsiToMacTable.Append( NumToChar(129) ) pAnsiToMacTable.Append( NumToChar(174) ) pAnsiToMacTable.Append( NumToChar(130) ) pAnsiToMacTable.Append( NumToChar(233) ) -- 200 pAnsiToMacTable.Append( NumToChar(131) ) pAnsiToMacTable.Append( NumToChar(230) ) pAnsiToMacTable.Append( NumToChar(232) ) pAnsiToMacTable.Append( NumToChar(237) ) pAnsiToMacTable.Append( NumToChar(234) ) -- 205 pAnsiToMacTable.Append( NumToChar(235) ) pAnsiToMacTable.Append( NumToChar(236) ) pAnsiToMacTable.Append( NumToChar(198) ) pAnsiToMacTable.Append( NumToChar(132) ) pAnsiToMacTable.Append( NumToChar(241) ) -- 210 pAnsiToMacTable.Append( NumToChar(238) ) pAnsiToMacTable.Append( NumToChar(239) ) pAnsiToMacTable.Append( NumToChar(205) ) pAnsiToMacTable.Append( NumToChar(133) ) pAnsiToMacTable.Append( NumToChar(215) ) -- 215 pAnsiToMacTable.Append( NumToChar(175) ) pAnsiToMacTable.Append( NumToChar(244) ) pAnsiToMacTable.Append( NumToChar(242) ) pAnsiToMacTable.Append( NumToChar(243) ) pAnsiToMacTable.Append( NumToChar(134) ) -- 220 pAnsiToMacTable.Append( NumToChar(183) ) pAnsiToMacTable.Append( NumToChar(184) ) pAnsiToMacTable.Append( NumToChar(167) ) pAnsiToMacTable.Append( NumToChar(136) ) pAnsiToMacTable.Append( NumToChar(135) ) -- 225 pAnsiToMacTable.Append( NumToChar(137) ) pAnsiToMacTable.Append( NumToChar(139) ) pAnsiToMacTable.Append( NumToChar(138) ) pAnsiToMacTable.Append( NumToChar(140) ) pAnsiToMacTable.Append( NumToChar(190) ) -- 230 pAnsiToMacTable.Append( NumToChar(141) ) pAnsiToMacTable.Append( NumToChar(143) ) pAnsiToMacTable.Append( NumToChar(142) ) pAnsiToMacTable.Append( NumToChar(144) ) pAnsiToMacTable.Append( NumToChar(145) ) -- 235 pAnsiToMacTable.Append( NumToChar(147) ) pAnsiToMacTable.Append( NumToChar(146) ) pAnsiToMacTable.Append( NumToChar(148) ) pAnsiToMacTable.Append( NumToChar(149) ) pAnsiToMacTable.Append( NumToChar(182) ) -- 240 pAnsiToMacTable.Append( NumToChar(150) ) pAnsiToMacTable.Append( NumToChar(152) ) pAnsiToMacTable.Append( NumToChar(151) ) pAnsiToMacTable.Append( NumToChar(153) ) pAnsiToMacTable.Append( NumToChar(155) ) -- 245 pAnsiToMacTable.Append( NumToChar(154) ) pAnsiToMacTable.Append( NumToChar(214) ) pAnsiToMacTable.Append( NumToChar(191) ) pAnsiToMacTable.Append( NumToChar(157) ) pAnsiToMacTable.Append( NumToChar(156) ) -- 250 pAnsiToMacTable.Append( NumToChar(158) ) pAnsiToMacTable.Append( NumToChar(159) ) pAnsiToMacTable.Append( NumToChar(189) ) pAnsiToMacTable.Append( NumToChar(185) ) pAnsiToMacTable.Append( NumToChar(216) ) -- 255 end if end SetupAnsiToMacTable -- Test routine to make sure the tables convert back and forth -- symetrically. on testTables SetupCharConverter("dummy") repeat with x = 1 to 255 testChar = NumToChar( x ) ansiChar = MacToAnsiStr( testChar ) macChar = AnsiToMacStr( ansiChar ) if ( testChar <> macChar ) then put "Mismatch at "& string( x ) &" Test: "& QUOTE & testChar & QUOTE &" Mac: "& QUOTE & macChar & QUOTE &" ANSI: "& QUOTE & ansiChar & QUOTE end if end repeat put "Done" end testTables
This content requires Flash
To view this content, JavaScript must be enabled, and you need the latest version of the Adobe Flash Player.
Download the free Flash Player now!
