我的程序已经设置为_UNICODE编译方式
程序中从一个文件读取了一段泰文到WCHAR类型的字串中,在AfxMessageBox()显示也能正确显示,但使用ExtTextOut或ExtTextOutW却不能正确显示。如果WCHAR类型的字串中的是中文,ExtTextOut或ExtTextOutW却能正确显示,为什么????,泰文怎样使用ExtTextOut或ExtTextOutW来显示呢???
程序中从一个文件读取了一段泰文到WCHAR类型的字串中,在AfxMessageBox()显示也能正确显示,但使用ExtTextOut或ExtTextOutW却不能正确显示。如果WCHAR类型的字串中的是中文,ExtTextOut或ExtTextOutW却能正确显示,为什么????,泰文怎样使用ExtTextOut或ExtTextOutW来显示呢???
如果要全部弄明白,我也说不清楚,不过你如果愿意,可把你的源码拿来看.([email protected]).
_Application app;
Workbooks books;
_Workbook book;
Worksheets sheets;
_Worksheet sheet;
Range range;
Font font;
Range cols;
if(!app.CreateDispatch(_T("Excel.Application")))
{
AfxMessageBox(_T("Couldn't start Excel and get Application object."));
return;
}
books = app.GetWorkbooks(); COleVariant FilenameOpen(_T("d:\\dang.xls")),
UpdateLinks((short)0),
Password(_T("")),
WriteResPassword(_T("")),
Delimiter (_T(",")),
Origin((short)2), // xlWindows
Formats((short)5),
ConsecutiveDelimiter((long)FALSE, VT_BOOL),
ReadOnly((long)FALSE, VT_BOOL),
Editable ((long)FALSE, VT_BOOL),
IgnoreReadOnlyRecommended ((long)TRUE, VT_BOOL),
Notify((long)TRUE, VT_BOOL),
AddToMru((long)FALSE, VT_BOOL),
Converter((short)0);
books.Open(_T("d:\\dang.xls"), UpdateLinks,ReadOnly,Formats,Password,WriteResPassword,
IgnoreReadOnlyRecommended,Origin,Delimiter,Editable,Notify,Converter,AddToMru,AddToMru,AddToMru);
//const VARIANT& AddToMru, const VARIANT& Local, const VARIANT& CorruptLoad)
book = books.GetItem( COleVariant((short) 1));
sheets =book.GetSheets();
sheet = sheets.GetItem(COleVariant((short)1));
range = sheet.GetRange(COleVariant(_T("A1")), COleVariant(L"A1"));
COleVariant str,str1;
wchar_t s1[300]=L"中国共产党",s2[300]=L"";
short i=19;
str=range.GetItem(COleVariant((short)i),COleVariant((short)1));
wsprintf(s2,L"%s",(wchar_t*)(_bstr_t )str);
AfxMessageBox(s2); //能正确显示
HDC hdc=::GetDC(this->GetSafeHwnd());
RECT ret;
ret.left=0;
ret.top=0;
ret.right=300;
ret.bottom=300;
ExtTextOutW(hdc,20,70,ETO_CLIPPED,&ret,s1,wcslen(s1),NULL);//能正确显示
ExtTextOutW(hdc,20,100,ETO_CLIPPED,&ret,s2,wcslen(s2),NULL); //显示乱码
CFont font;
VERIFY(font.CreateFont(
12, // nHeight
0, // nWidth
0, // nEscapement
0, // nOrientation
FW_NORMAL, // nWeight
FALSE, // bItalic
FALSE, // bUnderline
0, // cStrikeOut
ANSI_CHARSET, // nCharSet
OUT_DEFAULT_PRECIS, // nOutPrecision
CLIP_DEFAULT_PRECIS, // nClipPrecision
DEFAULT_QUALITY, // nQuality
DEFAULT_PITCH | FF_SWISS, // nPitchAndFamily
_T("Tahoma"))); // lpszFacename
CFont *pOldFont=pDC->SelectObject(&font);
WCHAR str[256];
FILE *pFile;
pFile=fopen("E:\\aaa.txt","rb");//aaa.Txt中包含三个泰文字符
int n=fread(str,sizeof(WCHAR),3,pFile);
if(n>256)
n=255;
str[n]=0;
pDC->TextOut(0,0,str);
pDC->SelectObject(pOldFont);
fclose(pFile);
谢谢!!我去试试,这500分,我一定给,还有一个问题:
我用钩子钩住了ExtTextOutW()函数,发现到了ExtTextOutW()后,字符串就与我原来送到AfxMessageBox()的不同了,每个字总是差了0x9cd!!,说明了系统进行了什么转换,谁能告诉我为什么?我另给500分!!!!!
_Application app;
Workbooks books;
_Workbook book;
Worksheets sheets;
_Worksheet sheet;
Range range;
Font font;
Range cols;
long l; // Start Excel and get Application object.
if(!app.CreateDispatch(_T("Excel.Application")))
{
AfxMessageBox(_T("Couldn't start Excel and get Application object."));
return;
} //Get a new workbook.
books = app.GetWorkbooks(); COleVariant FilenameOpen(_T("d:\\dang.xls")),
UpdateLinks((short)0),
Password(_T("")),
WriteResPassword(_T("")),
Delimiter (_T(",")),
Origin((short)2), // xlWindows
Formats((short)5),
ConsecutiveDelimiter((long)FALSE, VT_BOOL),
ReadOnly((long)FALSE, VT_BOOL),
Editable ((long)FALSE, VT_BOOL),
IgnoreReadOnlyRecommended ((long)TRUE, VT_BOOL),
Notify((long)TRUE, VT_BOOL),
AddToMru((long)FALSE, VT_BOOL),
Converter((short)0);
books.Open(_T("d:\\dang.xls"), UpdateLinks,ReadOnly,Formats,Password,WriteResPassword,
IgnoreReadOnlyRecommended,Origin,Delimiter,Editable,Notify,Converter,AddToMru,AddToMru,AddToMru);
book = books.GetItem( COleVariant((short) 1));
sheets =book.GetSheets();
sheet = sheets.GetItem(COleVariant((short)1));
range = sheet.GetRange(COleVariant(_T("A1")), COleVariant(L"A1"));
COleVariant str,str1;
wchar_t s1[300];
short i = 19;
str=range.GetItem(COleVariant((short)i),COleVariant((short)1));
str1=range.GetItem(COleVariant((short)i),COleVariant((short)2));
wsprintf(s1,L"%s",(wchar_t*)(_bstr_t )str);
AfxMessageBox(s1); //正确显示
CDC *pDC = GetDC();
CFont font1;
VERIFY(font1.CreateFont(
12, // nHeight
0, // nWidth
0, // nEscapement
0, // nOrientation
FW_NORMAL, // nWeight
FALSE, // bItalic
FALSE, // bUnderline
0, // cStrikeOut
ANSI_CHARSET, // nCharSet
OUT_DEFAULT_PRECIS, // nOutPrecision
CLIP_DEFAULT_PRECIS, // nClipPrecision
DEFAULT_QUALITY, // nQuality
DEFAULT_PITCH | FF_SWISS, // nPitchAndFamily
_T("Tahoma"))); // lpszFacename
CFont *pOldFont=(CFont *)pDC->SelectObject(&font); RECT ret;
ret.left =0;
ret.top=0;
ret.right=240;
ret.bottom=250;
ExtTextOutW(pDC->GetSafeHdc(),00,0,ETO_CLIPPED,&ret,s1,wcslen(s1),NULL);//不能正确显示
pDC->SelectObject(pOldFont);
你没有看清楚,我是用_UNICODE方式编译的,所以不用"%ls"或"lS"也能传给unicode字符串
我再研究研究!!
处理这种问题不需要用_UNICODE方式编译。系统本身提供了接口,(IMLangCodePages),可以对任何Unicode字符串计算其Code page, 并能够获得字符串中不同Code page的字符串长度, 然后再选择字符集输出即可。我曾经给公司写过UNICODE Edit, 就用这种方式,在任何系统下,输入各种文字都可以正确的输出和显示,前提是系统必须安装了这种字体,也就是说支持这种字符集。
因为系统默认code page 是 local code page, 显示中文自然没有问题;系统在输出时绝不仅仅是调用谋个函数就搞定的,否则其提供的Interface是多余的。
具体用法可以看MSDN。
app.CreateDispatch(_T("Excel.Application"));
这句失败,因此无法测试,如果你能重写一个用文件加载泰文字串而不是用EXCEL加载的测试程序,再发过来,那就更好了.我在你的基础上写一个用文件加载泰文字串方法,显示结果正常.从你的源码来看,并无明显的错误.我认为这个问题的原因多半在于机器的设定以及对话框的缺省字体这两方面.在我的机器,LOCALE是China,语言是Engligh,没有改你的对话框任何设置.加载两个txt文件,UNICODE存贮方式,一个是泰文,一个是中文.所有显示都是正确的.
非常感谢您的提示,您好的提示对我确实很有用。但现在还有点问题请教:
我想在API钩子中使用IMLangCodePages,但编译不通过,是不是在API钩子中不能使用IMLangCodePages??,相同的程序在普通的程序确能正常编译和运行。有没有与IMLangCodePages功能相同的直接的API调用??
谁能解决这个问题,我出500分!!
to bluebohe(薄荷):
问题还没有能解决,还不能结,我开新贴子给你分!
http://expert.csdn.net/Expert/topic/2462/2462463.xml?temp=7.893008E-02
http://expert.csdn.net/Expert/topic/2462/2462464.xml?temp=.9308893
另外,既然你的程序都编译成_UNICODE版本的了,还要代码页何用?
lstrcpy()