彰化一整天的Blog留言版
第 439 筆/共 549 筆An anonymous person wrote : 訪客 (2012-05-20 21:39:11.020003) 提出 google adsense 使用css來放置 查看次數:None
google adsense 使用css來放置<style type="text/css">
<!--
#adsenseHeader { position: absolute; top: 100px; left: 350px; }
-->
</style>
<div id="adsenseHeader">INSERT ADSENSE CODE HERE</div>
第 438 筆/共 549 筆An anonymous person wrote : 訪客 (2012-05-20 20:39:38.716938) 提出 PHP 網頁訊息國際化與 gettext 使用經驗 查看次數:None
PHP 網頁訊息國際化與 gettext 使用經驗
PHP 很早就已經支援 GNU gettext 的國際化模組。在線上手冊與網路上也可以找到許多相關的討論文章。 但是部份內容沒有完善地理解區碼的設定方式,以至於程序員在 LANG 和 setlocale() 的問題之中糾纏不休。
本文首先將說明區碼的設定問題,再示範 gettext 的使用方式。
區碼的問題
當我們想要用 gettext 將我們以 PHP 設計的網站添加國際化的區域性訊息功能時,首先我們必須要使用 setlocale() 指定訊息區碼;這點與一般應用程式透過環境變數 LANG 的方式不同。例如《Vala with GNU gettext》中的範例,調用 setlocale() 時都不指定區碼,而由環境變數決定。但這種作法不適用於 PHP 建立的 Web 應用程式。因為 PHP 程式係由 httpd 服務行程調用,而 httpd 行程在系統啟動時便已載入,其環境變數已經固定。故我們基本上不應透過環境變數取定訊息區碼,而應使用 setlocale() 指定明確的區碼。
初學者在使用 setlocale() 設定區碼時,最常反應的問題是「我明明照文章上的寫法 setlocale(LC_ALL, "zh_TW")了,但是仍然不會顯示中文訊息」。這個問題的正確答案是「你的系統不認得 zh_TW 這個區碼」。基於歷史與傳統因素,I18N 的區碼並沒有採用嚴格的格式,同一個文化語系在不同的系統上,可能是用不同的區碼表示。例如臺灣地區正體中文語系的區碼,有些系統是用 "zh_TW",有些卻是 "zh_TW.utf8",甚至更早期的還有 "zh_TW.big5"。區區數字之差,就是令使用者抱怨明明設定了環境變數或 setlocale() 了,但軟體顯示的訊息還是沒變的原因。
php-gettext 可用的區碼係由作業系統的區碼表決定。執行指令 locale -a 將會列出作業系統目前的區碼表。 以 Ubuntu 10.04 為例,在我的系統設置上, locale -a 列出的臺灣區碼只有'zh_TW.utf8'。故我調用 setlocale() 時,必須指定 'zh_TW.utf8',gettext 才會正常地取得本地訊息。指定 'zh_TW' 則不會有影響。 但是有些系統並不是用這個名稱,例如有些系統用 'zh_TW'。此時我傳 'zh_TW.utf8' 給 setlocale() 反而錯了。
克服此系統設置差異的解決方案有二種:
1.修改區碼名稱表。
在 Debian/Ubuntu 家族中,區碼名稱表的文件名稱是 /etc/locale.alias 。 但這個方案需要經由系統管理者操作,則會影響到整個作業系統,並不建議採用。
2. 調用 setlocale() 時,給它多個區域代碼。
PHP 4.3.0 之後,setlocale() 允許傳多個區域代碼給它,它將逐一嘗試直到可用為止。 下節將細說此方案。
setlocale 的用法
PHP 4.3.0 之後,setlocale() 允許傳多個區域代碼給它,它將逐一嘗試直到可用為止。例如 setlocale(LC_ALL, "zh_TW.utf8", "zh_TW", "zh");
至於舊版的 PHP 用戶,也有解。當 setlocale() 發現你給它的區域代碼不可用時,它會回傳 false 。利用這個特性,舊版 PHP 也可以自行撰寫嘗試動作。下列為範例
setlocale_example.php
123456789101112131415161718192021222324
<?php $possible_locale_name_list = array( 'zh_TW.utf8', 'zh_TW', 'zh' ); if (PHP_VERSION_ID >= 40300) { $result = setlocale(LC_MESSAGES, $possible_locale_name_list); } else { foreach ($possible_locale_name_list as $l) { $result = setlocale(LC_MESSAGES, $l); if ($result) break; } } if ( $result ) { $current_locale = setlocale(LC_MESSAGES, 0); echo "目前的區碼是: $current_locale\n"; } else { echo "setlocale() 找不到符合的區碼\n"; }?>
使用 gettext 顯示區域化訊息
當我們正確地理解 setlocale() 與區碼的使用方式後,接著就要使用 gettext 取出本地化訊息顯示了。
在動手撰寫或修改程式之前,你需要先了解關於 gettext 訊息文件的編輯與產生的知識。這部份內容請參考《Vala with GNU gettext》,本文不再複述。
下列的範例程式 hello.php,有兩種執行形式。其一是在命令列執行,第一個參數指定訊息區碼。其二是網頁形式,在網頁網址後加上查詢字串 ?locale=區碼。如果不指定區碼,那麼就會顯示原始訊息 - 倒寫的句子。
hello.php
1234567891011121314151617181920212223242526272829303132333435363738394041424344454647484950
<?phperror_reporting(E_ALL);header('Content-type: text/plain; charset=utf-8'); const GETTEXT_PACKAGE = 'hello'; $arg_locale = false;if (PHP_SAPI == 'cli') { if ($argc >= 2) $arg_locale = $argv[1];}else { header('Content-type: text/plain; charset=utf-8'); if (isset($_GET['locale'])) $arg_locale = $_GET['locale'];} if ($arg_locale) { $possible_locale_name_list = array( $arg_locale . '.utf8', $arg_locale ); if (PHP_VERSION_ID >= 40300) { $result = setlocale(LC_MESSAGES, $possible_locale_name_list); } else { foreach ($possible_locale_name_list as $l) { $result = setlocale(LC_MESSAGES, $l); if ($result) break; } } if ( $result ) { $current_locale = setlocale(LC_MESSAGES, 0); echo "current locale: $current_locale\n"; } else { echo "failed to setlocale\n"; } bindtextdomain(GETTEXT_PACKAGE, './locale'); // 區域化內容放置路徑 textdomain(GETTEXT_PACKAGE); // 使用 hello.mo 的訊息 bind_textdomain_codeset(GETTEXT_PACKAGE, 'utf-8');} echo _("好你"), "\n";echo _("行一第的息訊長。\n行二第的息訊長。\n");?>
首先, hello.php 對於區碼格式採用新的方法從寬認定。例如使用者輸入 'zh_TW' 時,就會產生 {'zh_TW.utf8', 'zh_TW'} 的區碼清單,交給 setlocale() 指定訊息區碼。
指定區碼之後,接著要指示區域化內容放置路徑、文字範圍與訊息字元編碼格式。分別調用 bindtextdomain()、textdomain()、bind_textdomain_codeset() 函數指示前述項目。由於 PHP 被 httpd 行程調用時,其工作目錄就是 PHP 程式碼所在目錄,故我們可以將區域化內容資料夾建立在 PHP 程式碼所在目錄下。例如你的 PHP 程式碼放在 /var/www/my_web ,則可以建立 /var/www/my_web/locale 資料夾與區域化內容的目錄架構;將區域訊息文件(MO文件)放置在相對應用的區碼路徑,如 /var/www/my_web/locale/zh_TW/LC_MESSAGES。
最後使用 php-gettext 的函式取得本地化訊息。php-gettext 提供了多個相關的訊息函式,但以 gettext() 最為常用,並有一個慣例的簡短別名,即 _()。
寫好程式後,我們就可以使用 xgettext 工具,將待處理的訊息文字擷取為 POT 文件,再分別翻譯為各語系區碼的 PO 文件。 最後使用 msgfmt 工具產生 MO 文件後,便大工告成。具體的工具操作如下列所示。
$ xgettext --language=php --from-code=utf-8 --output=hello.pot hello.php
$ cp hello.pot hello-en_US.po
$ edit hello-en_US.po
$ cp hello.pot hello-zh_TW.po
$ edit hello-zh_TW.po
$ msgfmt --output=locale/en/LC_MESSAGES/hello.mo hello-en_US.po
$ msgfmt --output=locale/zh_TW/LC_MESSAGES/hello.mo hello-zh_TW.po
以下為範例程式以命令列形式執行的結果。
$ php hello.php
好你
行一第的息訊長。
行二第的息訊長。
$ php hello.php zh_TW
current locale: zh_TW.utf8
你好
長訊息的第一行。
長訊息的第二行。
$ php hello.php en_US
current locale: en_US.utf8
Hello
First line of long message.
Second line of long message.
以下為範例程式透過 Web 呈現的結果。
source: http://blog.roodo.com/rocksaying/archives/15193601.html
第 437 筆/共 549 筆An anonymous person wrote : 訪客 (2012-05-20 20:37:03.411511) 提出 php fgetcsv在unix系統讀取中文字會出現亂碼解決方法 查看次數:None
php fgetcsv在unix系統讀取中文字會出現亂碼解決方法<?php
$filename="test.csv";
if ( !$fp = fopen($filename,"r") )
{
echo "無法開啟 $filename\n";
exit;
}else
{
$current = file_get_contents($file_path);
//file_put_contents($file_path, addcslashes($current,'\\')); // 過濾反斜線 \
$size = filesize($filename)+1;
$row=0;
//匯入前先將資料刪除
//$sSQL="delete from score";
//$result=mysql_query($sSQL,$conn);
setlocale(LC_ALL,array('zh_TW.Big5'));
while($temp=fgetcsv($fp,$size,","))
{
if ($row>0){
$temp[0]=iconv( "Big5", "UTF-8" ,$temp[0]);
//echo "0={$temp[0]}";
$sSQL="INSERT INTO score (PersonalName,IDCard,Math,MathRank,MathPR,Chinese,ChineseRank,ChinesePR,English,EnglishRank,EnglishPR,Total,TotalRank,TotalPR) VALUES ('$temp[0]','$temp[1]',$temp[2],$temp[3],$temp[4],$temp[5],$temp[6],$temp[7],$temp[8],$temp[9],$temp[10],$temp[11],$temp[12],$temp[13])";
$result=mysql_query($sSQL,$conn);
echo mysql_error();
}
$row=$row+1;
}
fclose($fp);
//echo "<META HTTP-EQUIV='refresh' CONTENT='0; URL=admin_main.php'>";
}
?>
第 436 筆/共 549 筆An anonymous person wrote : 訪客 (2012-05-20 17:55:25.514939) 提出 設定FCKeditor,讓使用者上傳檔案到自己的目錄 查看次數:None
設定FCKeditor,讓使用者上傳檔案到自己的目錄目前的FCKeditor(註:嵌入網頁中,功能類似 Word 的文字編輯器介面)版本,並沒有提供讓使用者上傳檔案到自己的目錄的功能。不過,只要稍加修改它的程式碼,就能達到這項需求。
假設網站有兩個分別叫做 cubie 和 eric 的使用者要上傳影像檔。初次上傳檔案時,本文的修改程式將令 FCKeditor 在伺服器端的 uploads 路徑之下,以用戶的名稱建立新的資料夾。
首先使用Dreamweaver的「使用者驗證」伺服器行為指令,建立一個簡單的用戶登入PHP網頁(請參閱《碼上就會:Dreamweaver CS3 PHP、MySQL與AJAX》的9-2頁,「製作管理人員登入頁面」一節),如下圖所示:
從「程式碼」檢視模式可以看到,Dreamweaver將把用戶的帳號名稱記錄在名叫 "MM_Username" 的session變數。根據本文範例檔的設定,登入成功後,瀏覽器將切換到包含 FCKeditor 編輯器的 editor.php 頁面。
接著修改位於底下兩個路徑裡的 config.php 設定檔。第一個設定檔用於設定「上傳檔案」面版裡的上傳路徑;第二個設定檔用於設定「瀏覽檔案」面版裡的上傳檔案路徑:
C:\AppServ\www\fckeditor\editor\filemanager\browser\default\connectors\php\config.php
C:\AppServ\www\fckeditor\editor\filemanager\upload\php\config.php
開啟這兩個設定檔之後,在PHP程式第一行(亦即,<?php的下一行)輸入底下的敘述,啟用session變數:
session_start();
將書本範例程式裡的固定上傳檔案路徑:
$Config['UserFilesPath'] = '/uploads/' ; // 預設為'/userfiles/'
改成:
$Config['UserFilesPath'] = '/uploads/'. $_SESSION['MM_Username'] . '/' ;
假設登入用戶的帳號為 "cubie",那麼,該用戶的所有影像檔將自動存入底下的資料夾路徑中:
/uploads/cubie/images/
請按此連結下載範例檔。本範例檔僅包含「用戶登入」頁面(testUpload.php)以及嵌入FCKeditor的簡易編輯頁面(editor.php),用戶登入頁面的資料庫連線設定沿用書本的範例檔,請直接將範例檔解壓縮放在AppServ的www根目錄,並依照上文修改config.php設定檔之後,即可進行測試。
[2008.5.6補充] 解決FCKeditor 無法上傳檔案的問題
source: http://swf.com.tw/?p=130
第 435 筆/共 549 筆An anonymous person wrote : 訪客 (2012-05-18 16:28:28.896477) 提出 人與人的緣分,由無明的一方決定 查看次數:2
人與人的緣分,由無明的一方決定
當我覺醒後,我才發現,世間最可怕的 人,不是小人,也不是壞人,而是無明的人。
我有位女性朋友,才結婚幾個月就離婚,原因是她不想看別人的臉色過生活。她說,婚後先生就去上班,算是高收入的主管階級,她 在家閒著無聊,偶爾去逛街購物 刷卡,也不過十幾萬元,她先生 看了刷卡單,說要限制她的額 度,她一氣之下,就把卡丟到先 生臉上,說自己要去上班賺錢, 然後自己去辦卡,去購物,去過 自己的生活,再也不要看人家臉色。
我問她先生一個月的薪水多少?她很得意的說不多,大約只有十萬元。 我聽了她的回答,內心開始為她的人生感到遺憾。
因為, 從客觀的角度來看,她的先生不是個小氣的壞蛋,而且也應該是個能包容的人;相對的,她的衝動,反而是結束兩人緣分的關鍵。
⋯⋯ 尤其, 當一個男人當到了主管級,雖然 賺的錢不算少,但工作的壓力想必也是很大的,相信他也是怕老婆擔心,才沒有讓她知道工作上的辛苦,結果,她反而不知惜福,還覺得他的薪水太少。像她這種活在「無明」中的人,老實說,我們身邊就一大堆。
我的鄰居是一位老實人,但自從被公司裁員失業後,就一直意志消沉, 賦閒在家。他們家的每月開銷, 包括房貸和小孩子的學費,都由他老婆在餐廳當會計,一肩扛起 來。
雖然大 家都很熱心,幫這位鄰居介紹工 作,但他總是做沒幾天,就不想 上班。後來,他開始去和人家賭 博,一開始小賺一點錢,後來一 輸再輸,連孩子的學費和生活 費,也都拿去賭。
因此, 我經常可以在半夜,聽到他們夫 妻在吵架。後來,兩人吵到門 外,驚動里長,這位失業的鄰居 還請里長和我們這些住戶來評評 理。他的意思是,他也是為這個 家好,才會想去翻本,並不是他 愛賭,而且他已經摸到賭錢的祕 訣,只要再給他一點賭本,他會 贏很多錢回來養家。
然而, 他老婆卻哭著說,家裡的錢早就 被拿光了,現在身上的一點錢, 也是去娘家借來的,再拿走,小 孩子要吃什麼?
里長和 住戶們聽了,就說是鄰居不對, 鄰居一氣之下離家出走。後來, 聽說他欠了地下錢莊很多錢,從 此就沒有再回到這個家。
無知, 人皆有之,只要你承認自己的無 知,並不會危害他人。 然 而,無明就是很恐怖的東西。老 子說,知人者智,自知者明。
所謂的 無明,是你沒有覺察自己是無知 的,甚至相信自己是對的,聽不 進去別人的苦勸,而且還把自己 的妄想付諸行動,害人害己。因 此,無明的人,是最可怕的,尤其這個人, 是你的親人或有共同利害關係的 人。
據說, 我老家鄉下有一位大地主,生了 三個女兒,這三個姐妹感情非常 好,即使上學或回家讀書和睡 覺,都在一起,不願分開,在鄉 里間成為佳話。
然而, 三姐妹長大各自嫁人後,大姐和 二姐兩家人仍是住在一起,感情 和以前一樣好,只是小妹嫁到遠 地,嫁給了一個生意人。
過沒幾 年,小妹的先生似乎生意不順, 負債累累。有一天,小妹回家 來,要求父母提前把家產分一 分,父母聽了差點昏倒,大姐二 姐也罵小妹不孝,但小妹又哭又 鬧說自己本來就應該拿家產,現 在她缺錢,提前拿有什麼不對?
父母拗 不過她,最後答應把家裡的田產 和不動產,分了三份。小妹又哭 鬧起來,說應該分成四份,她拿 兩份,因為大姐二姐都沒有負 債,先生又都有賺錢和積蓄,她 的老公負債累累,難道全家人都 對她見死不救?不怕她老來沒有 依靠?
大姐二 姐聽了很難過,她們並非在意那 些家產,而是心寒小妺何時變得 如此現實自私,又不講道理。然 而,小妹仗著父母寵愛她,哭鬧 之外又絕食抗議,大家只好依了 她。小妹拿走了家產後,大姐二 姐也開始疏遠她,漸漸的和她形 同陌路,可以說,她為了家產, 斬斷了和家人的緣分。
人與人之間的 緣分,是深或淺,長或短,是否 會變成善緣或惡緣,全由無明的 一方決定。
我的一 位高中同學,是經營健康食品 的。有一天,他來找我借錢,說 周轉上有急用。我為了減輕他的 心理負擔,就說乾脆買他的健康 食品來吃,讓他有收入。
然而, 他似乎以為我很有錢,每隔幾 天,又抱一堆新的產品,來向我 說明,說吃了對身體哪裡很好, 很有幫助。我心想他可能又缺 錢,於是又向他買了一堆。同 時,向他暗示,我自己的收入也 不高,而且家裡的健康食品,也 已經堆成一座山了,幾年也吃不 完,可以暫時不要進貨了。
他笑著 說他懂這道理,我心想他應有自 知之明,不會再來了。想不到, 才隔了一個禮拜,他又抱一堆什 麼國外最新進口的產品,硬要我 買下,而且為了感謝我的支持, 除了再打折外,錢可以先欠著, 等我日後手頭方便,再來向我收。
我聽了,心裡為他感到遺憾。我很清楚,這一次,我跟他的緣分真的盡了。我開門見山的告訴他,不應該把我當呆子,把我的真心幫忙,看成是冤大頭。他聽了氣得 漲紅著臉,胡言亂語把我數落一 頓就走了。從此,兩人沒有再聯 絡。
人跟人,是否能做朋友,或是成為仇家,不是靠緣分,往往是由無明的一方決定的。
如果你在人際關係上,也有和我同樣的感慨和無奈,就先讓自己保持覺知吧!或許,在某些人眼裡,我們就是那個「無明的人」。更多