Luar's Flash Playground: 在HTML中傳送中文到Flash研究
在HTML中傳送中文到Flash研究 (30-12-2004)

在HTML中傳送參數到Flash,常用的方法有兩種:路徑參數(foo.swf?par=123)或FlashVars(<param name="FlashVars" value="par=123" />),參數又可以再分為是否URLEncoded;對於傳送中文,又再分為非Unicode(Big5/GB2312)和Unicode。最後IE和Mozilla處理上又有分別,換句話說,總共有2*2*2*2=16種可能性。

再加上SWF格式為Flash5或以前,Flash是用使用者系統編碼處理中文(非Unicode),Flash6或以後,Flash是用Unicode處理中文。因此,在HTML中傳送中文到Flash,看似很簡單的事,其實包含很多複雜的變化。(16*2=32種可能!!)

在新技術湧現的時代,要將參數傳送到Flash,可以用LoadVars、XML、Flash Remoting和Web Services等,但是在非Browser和連線的環境下,例如嵌入裝置、Flash嵌入其他程式和Server-side的Flash執行環境,仍然需要靠「路徑參數」這方法傳送參數到Flash。

以下講解會以Big5和Unicode為例,比較處理非Unicode和Unicode中文的分別,對於GB2312處理方法,跟Big5相同。第二,例子會用一個中英文混合句子來示範:

可以支援非Unicode的URLEncoded中文了!
Big5 URLEncoded為:
%A5i%A5H%A4%E4%B4%A9%ABDUnicode%AA%BAURLEncoded%A4%A4
%A4%E5%A4F%A1I
UTF-8 URLEncoded為:
%E5%8F%AF%E4%BB%A5%E6%94%AF%E6%8F%B4%E9%9D%9EUnicode
%E7%9A%84URLEncoded%E4%B8%AD%E6%96%87%E4%BA%86%EF%BC
%81


路徑參數

一個SWF格式為Flash6或以後,以路徑參數傳送中文,有以下結果:

Big5: debugTxt.swf?inTxt=%A5i%A5H...


Big5: debugTxt.swf?inTxt=可以...


UTF-8: debugTxt.swf?inTxt=%E5%8F...


UTF-8: debugTxt.swf?inTxt=可以...

Unicode當然沒有什麼問題,只是Big5 URLEncoded會出現亂碼,在Mozilla情況更壞,無論是否URLEncoded,都是亂碼。

Big5: debugTxt.swf?inTxt=%A5i%A5H...


Big5: debugTxt.swf?inTxt=可以...

第一個本能反應,當然是在Flash裡加上

System.useCodepage = true;
打開swfpath\original\debugTxt.fla看看,其實早已加了,但不起作用。因為所有參數都是在任何ActionScript執行前,已經進入了Flash,所以Flash是用Unicode去解碼這些URLEncoded的Big5,結果發生亂碼。

解決方法,當然是使Flash預設不是Unicode解碼,怎可能?將SWF發佈成Flash5就可以!Flash5的SWF只是一個加載器,主要用作接收參數,然後將真正的Flash加載到_level0,並傳入參數,這樣真正的Flash已經完全取代了Flash5的SWF,只要Flash Player是6/7,仍然可以執行Flash6/7支援的ActionScript。

loadMovieNum("debugTxt2.swf?inTxt="+inTxt, 0);

不過,唯一要留意,由於Flash接收時已經將參數URLDecoded,再傳入真正的Flash時,也是用Unicode去接收/解碼Big5的參數,仍有危機出現亂碼,因此應該將參數兩次URLEncoded,變成普通的英文字元:

loadMovieNum("debugTxt2.swf?inTxt="+escape(escape(inTxt)), 0);
到了真正的Flash時,先解除Flash預設的Unicode解碼,才去URLDecode接收的參數:
System.useCodepage = true;
debugtxt.text = unescape(inTxt);
[範例下載]


FlashVars

改用FlashVars傳送參數,無論IE/Mozilla,只有Big5 URLEncoded會出現亂碼,其他Big5 URLDecoded, UTF-8 URLEncoded/URLDecoded都是正常:

Big5: debugTxt.swf?inTxt=%A5i%A5H...


Big5: debugTxt.swf?inTxt=%A5i%A5H...

用剛才方法去解決,結果出現了亂碼:

Big5: debugTxt.swf?inTxt=%A5i%A5H...


Big5: debugTxt.swf?inTxt=%A5i%A5H...

在Flash5的SWF進行URLEncode時字與字之間多了%C2:

%C2%A5i%C2%A5H%C2%A4%E4%B4%A9%C2%ABDUnicode%C2%AA
%C2%BAURLEncoded%C2%A4%C2%A4%C2%A4%EF%BF%BD%C2%A1I
因此在真正的Flash,要將%C2弄走才進行URLDecode:
System.useCodepage = true;
inTxt = unescape(inTxt.split("%C2").join(""));
debugtxt.text = inTxt
遺憾的是,有一些字元,在FlashVars傳到Flash時,已經被破壞了,最後仍然是亂碼,例如「文」字:

Big5: debugTxt.swf?inTxt=%A5i%A5H...


Big5: debugTxt.swf?inTxt=%A5i%A5H...

[範例下載]


URLEncoding其他參考資料

本文章由發表。
意見
"; print "沒有意見。
 "; } ?>
  • 感謝!蠻詳細的說明~

    tanjun於31-12-2004發表

  • 看來很麻煩,不如轉做 base 64 ,之後在 flash 寫個 base 64 還原 function 好過,那麼就不需要理會瀏覽器的問題。

    Solomon@SW2於31-12-2004發表

同組文章