笔者希望可以从文本中,将汉字读取出来,然后分段写到Editor内
无奈会出现文字半角问题。
汉字为2个字节,但是我们的RFile处理的都是8bit的流。使用RFile还有一个很重要的原因那就是。它提供了一个seek()很好用。
查了很多帖子。就目前的一个解决方案提出来。
直接上代码吧:
op_num++;
_LIT(path,"C:\\ebooks.txt");
TInt zero=0;
TText8 string[321];
TBuf8<320> rText;
file.Seek(ESeekStart,currentPosition);
file.Read(rText);
Mem::Copy(string,rText.Ptr(),rText.Size());
string[rText.Size()]='\0';
HBufC16* msg = ToUnicodeConvertL(string);
SetEditorText(*msg);
iEditor->DrawDeferred();
delete msg;
TInt iPos=PreToUnicodeConvertL(string);
currentPosition=currentPosition+320-iPos;
HBufC16* CPlainTextEditorContainer::ToUnicodeConvertL(TText8* aOrigin)
{
CCnvCharacterSetConverter* converter=CCnvCharacterSetConverter::NewLC();
//RFs fSession;
//需要打开文件服务器
//User::LeaveIfError(fSession.Connect());
//判断传入的源字符串是否GBK\GB2123码
if(converter->PrepareToConvertToOrFromL(KCharacterSetIdentifierGbk,CCoeEnv::Static()->FsSession())!=CCnvCharacterSetConverter::EAvailable)
{
//如果不是GBK\GBK2123码就退出
//fSessoin.Close();
CleanupStack::Pop(converter);
delete converter;
User::Leave(KErrNotSupported);
}
TText8* str = aOrigin;
TInt state=CCnvCharacterSetConverter::KStateDefault;
TPtrC8 source( str );
HBufC* iInfoText = HBufC::NewL( source.Length() );
TPtr16 ptr = iInfoText->Des();
if(CCnvCharacterSetConverter::EErrorIllFormedInput == converter->ConvertToUnicode(ptr, source, state))
User::Leave(KErrArgument);
//转换完成并清除转换器
CleanupStack::PopAndDestroy();
return iInfoText;
}
TInt CPlainTextEditorContainer::PreToUnicodeConvertL(TText8* aOrigin)
{
CCnvCharacterSetConverter* converter=CCnvCharacterSetConverter::NewLC();
//RFs fSession;
//需要打开文件服务器
//User::LeaveIfError(fSession.Connect());
//判断传入的源字符串是否GBK\GB2123码
if(converter->PrepareToConvertToOrFromL(KCharacterSetIdentifierGbk,CCoeEnv::Static()->FsSession())!=CCnvCharacterSetConverter::EAvailable)
{
//如果不是GBK\GBK2123码就退出
//fSessoin.Close();
CleanupStack::Pop(converter);
delete converter;
User::Leave(KErrNotSupported);
}
TText8* str = aOrigin;
TInt state=CCnvCharacterSetConverter::KStateDefault;
TPtrC8 source( str );
HBufC* iInfoText = HBufC::NewL( source.Length() );
TPtr16 ptr = iInfoText->Des();
TInt ipos=converter->ConvertToUnicode(ptr, source, state);
CleanupStack::PopAndDestroy();
return ipos;
}
代码中有一个currentPostion。他记录了当前位置。这位置不是随便取的。它保证了转换过程中,流的开头肯定不会发生截断。
如果发生截断,那肯定是在流的最后。然后对下一个读取位置进行相应的调整即可。
是否发生截断,是利用了API:TInt ipos=converter->ConvertToUnicode(ptr, source, state);
这个API的解释很多帖子都有提到。这里不再赘述。
缺点及未解决的问题:
1:由于从开头读取文本时。currentPostion为0.就保证了流的开头不会有截断。然后往后顺序截取转换。调整后都可以保证
currentPostion流的开头不会截断。笔者试着从当前位置往左截取一段。按照同样的原理来转换。但是效果不理想。
2:不能解决随机读得问题。
如果知道汉字边界检测的方法。就好办了。在网上查了一些。好像不多见。先使用这个方案吧。以后有更好的。再换。