PDA

Показать полную графическую версию : [решено] _INetExplorerCapable ($s_IEString). Обратное преобразование.


SyDr
21-04-2009, 16:01
Есть строка - путь к файлу в интернете. В ней могут быть пробелы и другие символы, которые заменяются на %XX
Функция _INetExplorerCapable ($s_IEString) производит преобразование строки для совместимости с IE
Нужна функция или алгоритм, производящая(й) обратное преобразование.
[HR]
Пробывал переписать по аналогии с _INetExplorerCapable($s_IEString). К сожалению, срабатывает только для строк, преобразованных АвтоИтом.
http://ru.wikipedia.org/wiki/Википедия
http://ru.wikipedia.org/wiki/%D0%92%D0%B8%D0%BA%D0%B8%D0%BF%D0%B5%D0%B4%D0%B8%D1%8F
Такую строку обратно преобразовать у меня не получилось.

proxy
22-04-2009, 02:32
http://ru.wikipedia.org/wiki/Википедия
скорее всего в вики, русские буквы в адресе ни как не кодируются, а обробатываются на 404,
либо при загрузке скриптом.

попробуйте напрямую работать с этим адресов - возможно все получтся.

Creat0R
22-04-2009, 03:29
Такую строку обратно преобразовать у меня не получилось »
Вот так примерно можно:


$URL = "http://ru.wikipedia.org/wiki/%D0%92%D0%B8%D0%BA%D0%B8%D0%BF%D0%B5%D0%B4%D0%B8%D1%8F"

$sEncode_URL = _HexToURLString($URL)

ConsoleWrite($sEncode_URL)

Func _HexToURLString($sURLHex)
Local $aURLHexSplit = StringSplit($sURLHex, "")
Local $sRetString = "", $iDec, $iUbound = UBound($aURLHexSplit)

For $i = 1 To $iUbound - 1
If $aURLHexSplit[$i] = "%" And $i + 2 <= $iUbound - 1 Then
$i += 2
$iDec = Dec($aURLHexSplit[$i - 1] & $aURLHexSplit[$i])

If Not @error Then
$sRetString &= Chr($iDec)
Else
$sRetString &= $aURLHexSplit[$i - 2]
EndIf
Else
$sRetString &= $aURLHexSplit[$i]
EndIf
Next

;_UTF8ToANSI($sUTF8):

Local $sUTF8 = $sRetString

Local $iLen = StringLen($sUTF8)
Local $stBuf = DllStructCreate("byte[" & $iLen * 2 & "];byte[2]")

Local $aRet = DllCall("Kernel32.dll", "int", "MultiByteToWideChar", _
"int", 65001, "int", 0, _
"str", $sUTF8, "int", -1, _
"ptr", DllStructGetPtr($stBuf), "int", $iLen * 2 + 2)

Local $stOut = DllStructCreate("char[" & $iLen & "];char")

$aRet = DllCall("kernel32.dll", "int", "WideCharToMultiByte", _
"int", 0, "int", 0, _
"ptr", DllStructGetPtr($stBuf), "int", -1, _
"ptr", DllStructGetPtr($stOut), "int", $iLen + 1, _
"int", 0, "int", 0)

Return DllStructGetData($stOut, 1)
EndFunc

amel27
22-04-2009, 05:41
еще вариант (штатными средствами):
$s_IEString = "http://ru.wikipedia.org/wiki/%D0%92%D0%B8%D0%BA%D0%B8%D0%BF%D0%B5%D0%B4%D0%B8%D1%8F:%D0%9F%D1%80%D0%B5%D1%81%D1%81-%D1%80%D0%B5%D0%BB%D0%B8%D0%B7%D1%8B"
ConsoleWrite(_INetExplorerCapableUndo($s_IEString) &@CRLF)

Func _INetExplorerCapableUndo($s_IEString)
Local $a_IEChar = StringRegExp($s_IEString, "%[[:xdigit:]]{2}", 3)
If IsArray($a_IEChar) Then
For $i=0 To UBound($a_IEChar)-1
$s_IEString = StringReplace($s_IEString, $a_IEChar[$i], Chr(Dec(StringTrimLeft($a_IEChar[$i],1))))
Next
$s_IEString = BinaryToString(StringToBinary($s_IEString, 4), 4)
EndIf
Return $s_IEString
EndFunc

SyDr
22-04-2009, 07:53
Спасибо большое.
Первый вариант работает.

А второй - так же, как у меня. Строки, преобразованные через AutoIt он может обработать, а то, что нужно - нет:
http://ru.wikipedia.org/wiki/Википедия

amel27
22-04-2009, 08:20
А второй - так же, как у меня »тогда так :
$s_IEString = "http://ru.wikipedia.org/wiki/%D0%92%D0%B8%D0%BA%D0%B8%D0%BF%D0%B5%D0%B4%D0%B8%D1%8F:%D0%9F%D1%80%D0%B5%D1%81%D1%81-%D1%80%D0%B5%D0%BB%D0%B8%D0%B7%D1%8B"
MsgBox(0,"",_INetExplorerCapableUndo($s_IEString))

Func _INetExplorerCapableUndo($s_IEString)
Local $a_IEChar = StringRegExp($s_IEString, "%[[:xdigit:]]{2}", 3)
If IsArray($a_IEChar) Then
For $i=0 To UBound($a_IEChar)-1
$s_IEString = StringReplace($s_IEString, $a_IEChar[$i], Chr(Dec(StringTrimLeft($a_IEChar[$i],1))))
Next
$s_IEString = BinaryToString(StringToBinary($s_IEString), 4)
EndIf
Return $s_IEString
EndFunc


P.S. странно - первый вариант у меня выдал в консоль правильно, а на MsgBox() крякозябки :)

SyDr
22-04-2009, 08:24
Всё. Теперь всё работает :)
Спасибо всем

Creat0R
22-04-2009, 15:14
первый вариант у меня выдал в консоль правильно, а на MsgBox() крякозябки »
Т.к строка перекодирована в ANSI (твоя функция :)).

BinaryToString(StringToBinary($s_IEString), 4) »
Хм, получается UTF8 можно вот так просто перекодировать в ANSI?

Upd: Получается что да:

$sANSI_String = "Тест"

$sUTF8_String = _StringANSIToUTF8($sANSI_String)
$sANSI_String = _StringUTF8ToANSI($sUTF8_String)

ConsoleWrite("UTF-8: " & $sUTF8_String & @CRLF)
ConsoleWrite("ANSI: " & $sANSI_String & @CRLF)

Func _StringANSIToUTF8($sString)
Return BinaryToString(StringToBinary($sString, 4))
EndFunc

Func _StringUTF8ToANSI($sString)
Return BinaryToString(StringToBinary($sString), 4)
EndFunc

amel27
23-04-2009, 02:41
Т.к строка перекодирована в ANSI »не, я просто вернул строку обратно в UTF8, хотя и странным образом - как ANSI :) ... это видно из StringLen() ... получается, что ConsoleWrite() отображает UTF8, вот только не успел понять- всегда или в зависимости от настроек SciTE

Хм, получается UTF8 можно вот так просто перекодировать в ANSI? »угу, начиная не помню с какой версии, и не только UTF8, но и UTF16... жаль OEM нельзя :(




© OSzone.net 2001-2012