Перекодировка текста
|
|
WQ | Дата: Воскресенье, 15.06.2014, 23:05 | Сообщение # 1 |
Полковник
Группа: Проверенные
Сообщений: 215
Статус: Offline
| Вот такой код: Код #Include "window9.bi" Dim As Integer event Dim As HWND hwnd Dim As String*1024 sData Dim As String sRet Dim As Integer iBytes
hwnd=OpenWindow("",10,10,640,660) : CenterWindow(hwnd)
Dim As HINTERNET hOpen,hUrl
hOpen = InetOpen
hUrl = OpenUrl(hOpen,"http://news.yandex.ru/index.rss")
Do sRet &= Left(sData , iBytes) iBytes = InetReadFile(hUrl,Cast(String Ptr,@sData),1024) Loop Until iBytes = 0
EditorGadget(1,10,10,600,600, sRet)
Do event=WaitEvent() If Event=EventClose Then End Loop
Нужно перекодировать, чтобы читался текст на русском. Возможно ли это?
|
|
| |
haav | Дата: Понедельник, 16.06.2014, 18:22 | Сообщение # 2 |
Генералиссимус
Группа: Администраторы
Сообщений: 1373
Статус: Offline
| Код #Include "window9.bi" Dim As Integer event Dim As HWND hwnd Dim As String*1024 sData Dim As String sRet Dim As Integer iBytes
Function unicodeTO (ProcStr AS ZString Ptr) AS String Var OutLen = MultiByteToWideChar(CP_UTF8, 0, ProcStr, -1, 0, 0) Dim AS WString Ptr WStrTemp = CAllocate(OutLen*2+2) MultiByteToWideChar(CP_UTF8, 0, ProcStr, -1, WStrTemp, OutLen) OutLen = WideCharToMultiByte(CP_ACP, 0, WStrTemp, -1, 0, 0, 0, 0) Dim As ZString ptr szbuf Dim As String sRet szbuf = Callocate(OutLen) WideCharToMultiByte(CP_ACP, 0, WStrTemp, -1, CPtr(LPSTR, szbuf), OutLen, 0, 0) sRet = *szbuf Deallocate(szbuf) Deallocate(WStrTemp) Return sRet End Function
hwnd=OpenWindow("",10,10,640,660) : CenterWindow(hwnd)
Dim As HINTERNET hOpen,hUrl
hOpen = InetOpen
hUrl = OpenUrl(hOpen,"http://news.yandex.ru/index.rss")
Do sRet &= Left(sData , iBytes) iBytes = InetReadFile(hUrl,Cast(String Ptr,@sData),1024) Loop Until iBytes = 0
EditorGadget(1,10,10,600,600, unicodeTO(StrPtr(sRet)))
Do event=WaitEvent() If Event=EventClose Then End Loop
Вы сохраняете власть над людьми покуда оставляете им что-то…Отберите у человека все, и этот человек уже будет неподвластен вам…
|
|
| |
WQ | Дата: Вторник, 28.10.2014, 14:21 | Сообщение # 3 |
Полковник
Группа: Проверенные
Сообщений: 215
Статус: Offline
| Спасибо!
Добавлено (28.10.2014, 14:21) --------------------------------------------- Задача усложнилась - теперь нужно получить не обычную кирилицу, а расширенную, чтобы читался текст на казахском языке, сейчас эти символы заменяются вопросиками. А, вообще, возможно, и до иероглифов дойдет) Включил юникод, и теперь сообщение в конце кода может отображать такие символы, так что можно проверить. Я так понимаю, функции не могут возвращать результат типа Wstring?
Код #define UNICODE #Include "window9.bi" Dim As String*1024 sData Dim As String sRet Dim As Integer iBytes
Function unicodeTO (ProcStr As ZString Ptr) As String Var OutLen = MultiByteToWideChar(CP_UTF8, 0, ProcStr, -1, 0, 0) Dim As WString Ptr WStrTemp = Callocate(OutLen*2+2) MultiByteToWideChar(CP_UTF8, 0, ProcStr, -1, WStrTemp, OutLen) OutLen = WideCharToMultiByte(CP_ACP, 0, WStrTemp, -1, 0, 0, 0, 0) Dim As ZString Ptr szbuf Dim As String sRet szbuf = Callocate(OutLen) WideCharToMultiByte(CP_ACP, 0, WStrTemp, -1, CPtr(LPSTR, szbuf), OutLen, 0, 0) sRet = *szbuf DeAllocate(szbuf) DeAllocate(WStrTemp) Return sRet End Function
Dim As HINTERNET hOpen,hUrl
hOpen = InetOpen
hUrl = OpenUrl(hOpen,"http://bilimsite.kz/rss.xml")
Do sRet &= Left(sData , iBytes) iBytes = InetReadFile(hUrl,Cast(String Ptr,@sData),1024) Loop Until iBytes = 0
MessageBox(null, unicodeTO(StrPtr(sRet)), "Text", 0)
Сообщение отредактировал WQ - Вторник, 28.10.2014, 14:24 |
|
| |
haav | Дата: Среда, 29.10.2014, 07:53 | Сообщение # 4 |
Генералиссимус
Группа: Администраторы
Сообщений: 1373
Статус: Offline
| Цитата WQ ( ) Я так понимаю, функции не могут возвращать результат типа Wstring?
Какие функции? Если из библиотеки window9 , то да все библиотека заточена под ASCII.
Вы сохраняете власть над людьми покуда оставляете им что-то…Отберите у человека все, и этот человек уже будет неподвластен вам…
|
|
| |
WQ | Дата: Среда, 29.10.2014, 11:40 | Сообщение # 5 |
Полковник
Группа: Проверенные
Сообщений: 215
Статус: Offline
| Цитата haav ( ) Какие функции? Если из библиотеки window9 , то да все библиотека заточена под ASCII. Любые функции - если пишу возвращать результат типа Wstring, компилятор ругается.
А так еще два вопроса: 1) InetReadFile в принципе позволяет получить из сети всякие иероглифы и т.д.? 2) Если да, то как переделать unicodeTO из кода выше, чтобы добраться до этих символов?
Я разобрался с отображением unicod-символов средствами winapi, а теперь проблема в получении их с интернет-страниц.
|
|
| |
haav | Дата: Среда, 29.10.2014, 13:32 | Сообщение # 6 |
Генералиссимус
Группа: Администраторы
Сообщений: 1373
Статус: Offline
| Цитата WQ ( ) Любые функции - если пишу возвращать результат типа Wstring, компилятор ругается.
Ну как любые? Берем API функцию GetWindowText
Для исходника ASCII компилятор будет использовать эту декларацию:
Код declare function GetWindowText alias "GetWindowTextA" (byval as HWND, byval as LPSTR, byval as integer) as integer
Для исходника Unicode эту:
Код declare function GetWindowText alias "GetWindowTextW" (byval as HWND, byval as LPWSTR, byval as integer) as integer
Как видишь, в первом случае второй параметр принимает LPSTR или zstring ptr . Во втором случае LPWSTR или Wstring ptr.
Цитата WQ ( ) InetReadFile в принципе позволяет получить из сети всякие иероглифы и т.д.?
Данная функция попросту заполняет данными переданный ей буфер. Что это будет за буфер, зависит от программиста. Функции глубоко наплевать на то: будет это Byte ptr или zstring ptr или integer ptr. Она возьмет указатель на буфер (то есть адрес начала буфера) , посмотрит на 3 параметр (сколько байт нужно считать) и считает столько , сколько получится за раз , совсем необязательно столько сколько указано в 3 параметре. То есть она как бы копирует данные с сетевого источника в твой буфер. А уж что ты дальше будешь делать со своим буфером, в какой будешь формат (текстовый или не текстовый) перегонять , это твое дело. К примеру ты передал буфер и после вызова функции в твоем буфере появились следующие байты:
CC E8 F0
Что это за байты??? Если ты хочешь видеть их в OEM формате, то получится что-то вроде этого:
А если в ASCII, то:
В UTF-8 тоже что-то получится, но вряд ли я смогу сюда записать этот символ. Понимаешь, буфер один и тот же, а как ты представишь в текстовую информацию данный буфер, зависит от тебя.
Цитата Если да, то как переделать unicodeTO из кода выше, чтобы добраться до этих символов?
WQ! Ты бы хоть немного почитал про функции MultiByteToWideChar, WideCharToMultiByte. Вся информация по ним есть на сайте мелкософта, а может даже есть где и русская инфа. А так и будешь постоянно только подставлять готовое, не понимая как это работает. Ладно , вот рабочий код для этого RSS:
Код #define UNICODE #Include "window9.bi" Dim Shared As Byte bData(10000000) Dim As Integer iBytes,iAllBytes Dim shared As WString Ptr WStrTemp
Function unicodeTO (ProcStr As Byte Ptr) As WString Ptr Var OutLen = MultiByteToWideChar(CP_UTF8, 0, ProcStr, -1, 0, 0) WStrTemp = Callocate(OutLen*2+2) MultiByteToWideChar(CP_UTF8, 0, ProcStr, -1, WStrTemp, OutLen) OutLen = WideCharToMultiByte(CP_ACP, 0, WStrTemp, -1, 0, 0, 0, 0) Return WStrTemp End Function
Dim As HINTERNET hOpen,hUrl
hOpen = InetOpen
hUrl = OpenUrl(hOpen,"http://bilimsite.kz/rss.xml")
Do iBytes = InetReadFile(hUrl,@bData(iAllBytes),1024) iAllBytes+=iBytes DeAllocate(WStrTemp) Loop Until iBytes = 0
Dim msg As MSG
Dim As hwnd hwnd = CreateWindowEx(0,"#32770","RSS",WS_VISIBLE Or WS_OVERLAPPEDWINDOW,100,100,800,600,0,0,0,0)
setwindowtext(CreateWindowEx(0,"EDIT","",WS_VISIBLE Or WS_CHILD Or ES_MULTILINE Or ES_AUTOVSCROLL _ Or ES_AUTOHSCROLL Or WS_HSCROLL Or WS_VSCROLL,0,0,750,550,hwnd, 0,0,0),unicodeTO(@bData(0))) While GetMessage(@msg,0,0,0) DispatchMessage(@msg) If msg.message=WM_COMMAND Then Exit While Wend
Вы сохраняете власть над людьми покуда оставляете им что-то…Отберите у человека все, и этот человек уже будет неподвластен вам…
|
|
| |
WQ | Дата: Среда, 08.07.2015, 23:02 | Сообщение # 7 |
Полковник
Группа: Проверенные
Сообщений: 215
Статус: Offline
| Цитата haav ( ) WQ! Ты бы хоть немного почитал про функции MultiByteToWideChar, WideCharToMultiByte. Вся информация по ним есть на сайте мелкософта, а может даже есть где и русская инфа. А так и будешь постоянно только подставлять готовое, не понимая как это работает Ну, конечно, я читал про эти функции) Просто я перехожу на Freebasic с Autoit, где поддержка юникода и некоторые другие вещи реализованы лучше, и, например, получение данных с такой интернет-страницы будет занимать одну строку кода.
Вот, кстати, что я написал сам, еще до того, как увидел ответ здесь: Код #define UNICODE #Include "window9.bi" Dim As String*1024 sData Dim As String sRet Dim As Integer iBytes
Function unicodeToW (ProcStr As WString Ptr) As WString Ptr Var OutLen = MultiByteToWideChar(CP_UTF8, 0, ProcStr, -1, 0, 0) Dim As WString Ptr WStrTemp = Callocate(OutLen*2+2) MultiByteToWideChar(CP_UTF8, 0, ProcStr, -1, WStrTemp, OutLen) 'OutLen = WideCharToMultiByte(CP_ACP, 0, WStrTemp, -1, 0, 0, 0, 0) 'DeAllocate(WStrTemp) Return WStrTemp End Function
Dim As HINTERNET hOpen,hUrl
hOpen = InetOpen hUrl = OpenUrl(hOpen,"http://bilimsite.kz/rss.xml")
Do sRet &= Left(sData , iBytes) iBytes = InetReadFile(hUrl,Cast(WString Ptr, @sData), 1024) Loop Until iBytes = 0
Dim As WString*200000 sRetW sRetW=*(unicodeToW(StrPtr(sRet)))
MessageBox(null, sRetW, "Text", 0) Так что, думаю, я не безнадежен)
Обычно, прежде чем задавать вопрос на этом форуме, я стараюсь изучить всю возможную информацию по этому направлению, и решить проблему самостоятельно. В данном конкретном случае, возможно, я поторопился, решение было ближе, чем я думал.
Код программы, которую я пишу, сейчас уже около 12000 строк, и это только половина. Если бы я каждый раз задавал вопросы, когда испытывал затруднения, то размер форума вырос бы в несколько раз)
Добавлено (08.07.2015, 23:02) --------------------------------------------- К сожалению, опять проблема с кодировками Работаю с IUP. Там для отображения юникода используется кодировка UTF8 (с версии 3.9), т.е., весь текст вводимый и выводимый любыми способами, будет в UTF8, в данном случае, в виде Zstring - крякозяблов. вообще это довольно удобно, т.к. эти zstring-строки можно обрабатывать обычными текстовыми функциями, а с wstring куча проблем Как переводить из UTF8 в Wstring, я разобрался, например, бросаешь на форму файл с названием из иероглифов - отображается название файла и он открывается средствами WinApi (встроенные средства Freebasic не поддерживают юникод, по крайней мере, в версии 1.00)
А вот как перевестиWstring в UTF8 так, чтобы IUP могла показать их, разобраться не могу
Код: Цитата #include "inc/iup.bi"
#Define unicode #include "windows.bi" #include "crt.bi"
IupOpen(0,0) ?*IupVersion() ' > 3.9 IupSetGlobal("UTF8MODE","YES") Dim Shared AS ZString Ptr WStrResult
Function unicode1(ProcStr As WString Ptr) As ZString Ptr Var OutLen = MultiByteToWideChar(CP_ACP, 0, ProcStr, -1, 0, 0) Dim AS WString Ptr WStrTemp = CAllocate(OutLen*2+2) MultiByteToWideChar(CP_ACP, 0, ProcStr, -1, WStrTemp, OutLen) OutLen = WideCharToMultiByte(CP_UTF8, 0, WStrTemp, -1, 0, 0, 0, 0) WStrResult = Reallocate(WStrResult, OutLen) WideCharToMultiByte(CP_UTF8, 0, WStrTemp, -1, CPtr(LPSTR, WStrResult), OutLen, 0, 0) Deallocate(WStrTemp) Return WStrResult End Function
Dim As WString Ptr s
s=VarPtr(WChr(1199))
Dim As Ihandle Ptr ml ml = IupMessageDlg() IupSetAttribute(ml, "DIALOGTYPE", "WARNING") IupSetAttribute(ml, "TITLE", "IupMessageDlg Test") IupSetAttribute(ml, "VALUE", *unicode1(s)) ' "Т±")
IupPopup(ml, IUP_CURRENT, IUP_CURRENT)
IupMainLoop ()
WChr(1199) - ұ - буква казахского алфавита - взята для примера, а так нужно преобразовывать довольно большие тексты. В UTF8 эта буква выглядит как Т± Функция unicode1 вроде бы должна переводить в Zstring, но в итоге что-то не то.
Надо бы здесь на форуме выложить сборку IUP 3.15
Сообщение отредактировал WQ - Среда, 08.07.2015, 23:04 |
|
| |
haav | Дата: Пятница, 10.07.2015, 11:17 | Сообщение # 8 |
Генералиссимус
Группа: Администраторы
Сообщений: 1373
Статус: Offline
| Для винды можно использовать функции MultiByteToWideChar и WideCharToMultiByte. Не знаю правда как с казахским... Для Linux iconv
Вот пример перевода в UTF8 и обратно:
Код #Include "windows.bi"
Dim As DWORD dwNum = MultiByteToWideChar(CP_ACP, 0, "Здравствуй мир!", -1, NULL, 0) Dim As WString Ptr wstr_ = Allocate(dwNum*2+2) MultiByteToWideChar(CP_ACP, 0,"Здравствуй мир!" , -1, wstr_, dwNum) dwNum = WideCharToMultiByte(CP_UTF8, 0, wstr_, -1, NULL, 0, NULL, NULL) Dim As String utf8 = Space(dwNum) WideCharToMultiByte(CP_UTF8, 0, wstr_, -1, utf8,dwNum , NULL, NULL) DeAllocate(wstr_) ? RTrim(utf8)
dwNum = MultiByteToWideChar(CP_UTF8, 0, utf8, -1, NULL, 0) wstr_ = Allocate(dwNum*2+2) MultiByteToWideChar(CP_UTF8, 0,utf8 , -1, wstr_, dwNum) dwNum = WideCharToMultiByte(CP_ACP, 0, wstr_, -1, NULL, 0, NULL, NULL) Dim As String ANSI = Space(dwNum) WideCharToMultiByte(CP_ACP, 0, wstr_, -1, ANSI,dwNum , NULL, NULL) DeAllocate(wstr_) ? RTrim(ANSI) Sleep
Вы сохраняете власть над людьми покуда оставляете им что-то…Отберите у человека все, и этот человек уже будет неподвластен вам…
|
|
| |
WQ | Дата: Пятница, 10.07.2015, 22:20 | Сообщение # 9 |
Полковник
Группа: Проверенные
Сообщений: 215
Статус: Offline
| Спасибо! Я еще обнаружил функции для работы с UTF в FLTK, вроде они кроссплатформенные. А так в Ubuntu вроде все в UTF, например, если в названиях файлов есть иероглифы, Freebasic нормально с ними работает, в отличие от Win
|
|
| |
|