TDbf и ОЕМ кодировка
Модератор: Модераторы
-
Guest
в понедельник если интересно смогу дать эти функции...
у меня есть, я сейчас как раз программулинку пишу которая текстовые файлы перекодирует
хотя остальные кодировки это какие?
а то тут только win,koi8r,dos и какой-то iso
я взял от сюда - <a href='http://pascal.sources.ru/text/coder.zip' target='_blank'>http://pascal.sources.ru/text/coder.zip</a>
Вот универсальная функция:
Конечно, можно еще немного оптимизировать, но работает.
from (из) и to_ (в) показывают направление кодировки:
w - ANSI
d - ASCII
k - KOI8R
Код: Выделить всё
function convert_cyr_string(str : string; from, to_ : char) : string;
var
i : integer;
p : integer;
c : char;
fromstr : string;
tostr : string;
begin
case from of
'w' : fromstr := 'абвгдеёжзийклмнопрстуфхцчшщъыьэюяАБВГДЕЁЖЗИЙКЛМНОПРСТУФХЦЧШЩЪЫЬЭЮЯ';
'd' : fromstr := #160#161#162#163#164#165#241#166#167#168#169#170#171#172#173#174#175#224#225#226#227#228#229#230#231#232#233#234#235#236#237#238#239#128#129#130#131#132#133#240#134#135#136#137#138#139#140#141#142#143#144#145#146#147#148#149#150#151#152#153#154#155#156#157#158#159;
'k' : fromstr := 'БВЧЗДЕJЦЪЙКЛМНОПРТУФХЖИГЮЫЭЯЩШЬАСбвчздеjцъйклмнопртуфхжигюыэящшьас';
else
fromstr := 'абвгдеёжзийклмнопрстуфхцчшщъыьэюяАБВГДЕЁЖЗИЙКЛМНОПРСТУФХЦЧШЩЪЫЬЭЮЯ';
end;
case to_ of
'w' : tostr := 'абвгдеёжзийклмнопрстуфхцчшщъыьэюяАБВГДЕЁЖЗИЙКЛМНОПРСТУФХЦЧШЩЪЫЬЭЮЯ';
'd' : tostr := #160#161#162#163#164#165#241#166#167#168#169#170#171#172#173#174#175#224#225#226#227#228#229#230#231#232#233#234#235#236#237#238#239#128#129#130#131#132#133#240#134#135#136#137#138#139#140#141#142#143#144#145#146#147#148#149#150#151#152#153#154#155#156#157#158#159;
'k' : tostr := 'БВЧЗДЕJЦЪЙКЛМНОПРТУФХЖИГЮЫЭЯЩШЬАСбвчздеjцъйклмнопртуфхжигюыэящшьас';
else
tostr := 'абвгдеёжзийклмнопрстуфхцчшщъыьэюяАБВГДЕЁЖЗИЙКЛМНОПРСТУФХЦЧШЩЪЫЬЭЮЯ';
end;
for i := 1 to length(str) do
begin
c := str[i];
p := pos(c, fromstr);
if p <> 0 then
begin
c := tostr[p];
str[i] := c;
end;
str[i] := c;
end;
convert_cyr_string := str;
end;
Конечно, можно еще немного оптимизировать, но работает.
from (из) и to_ (в) показывают направление кодировки:
w - ANSI
d - ASCII
k - KOI8R
-
SAK
- постоялец
- Сообщения: 158
- Зарегистрирован: 17.02.2006 23:45:14
- Откуда: Тим
- Контактная информация:
Вчера посмотрел исходники и обнаружил там функцию TDbf.Translate.
Которая, как я понимаю, задумывалась как раз для перекодировки, но почему-то не применяется при чтении/записи данных полей базы, но зато используется для перекодирования Memo полей, что в общем случае делать нельзя, т.к. там может быть не только текст, но и двоичные данные. Либо я не понял назначения этой функции, либо она очень криво построена.
Пока ограничился изменением 2-х функций:
Для полноценной работы с разными кодировками, как мне кажется, придется хорошенько порыться в исходнике.
Которая, как я понимаю, задумывалась как раз для перекодировки, но почему-то не применяется при чтении/записи данных полей базы, но зато используется для перекодирования Memo полей, что в общем случае делать нельзя, т.к. там может быть не только текст, но и двоичные данные. Либо я не понял назначения этой функции, либо она очень криво построена.
Пока ограничился изменением 2-х функций:
Код: Выделить всё
function TDbf.GetFieldData(Field: TField; Buffer: Pointer; NativeFormat: Boolean): Boolean; {overload; override;}
begin
// pretend nativeformat is true
Result := inherited GetFieldData(Field, Buffer, True);
if (Field.DataType = ftString)and(Buffer<>nil) then
OemToCharBuff(Buffer, Buffer, Field.DataSize);
end;
procedure TDbf.SetFieldData(Field: TField; Buffer: Pointer; NativeFormat: Boolean); {overload; override;}
var buf: array[0..1024]of char;
begin
if (Field.DataType = ftString)and(Buffer<>nil) then
begin
CharToOemBuff(Buffer, Buf, Field.DataSize);
Buffer:=@buf
end;
// pretend nativeformat is true
inherited SetFieldData(Field, Buffer, True);
end;
Для полноценной работы с разными кодировками, как мне кажется, придется хорошенько порыться в исходнике.
-
Джентельмен
- постоялец
- Сообщения: 162
- Зарегистрирован: 16.10.2005 10:47:26
- Откуда: Украина Донбасс Краматорск
- Контактная информация:
А может как-то с UTF-8 можно завязаться? Ну, чтобы потом не мучиться.
Честно говоря мне лично сейчас не совсем понятно кто устанавливает стандарт (де факто) для DBF. Это же не изобретение сообщества OpenSource
DBF вроде подерживается, но не не уверен, что развивается.
Что-то у нас спецы по БД молчат...
-
SAK
- постоялец
- Сообщения: 158
- Зарегистрирован: 17.02.2006 23:45:14
- Откуда: Тим
- Контактная информация:
Мне кажется там и развиваться-то некуда, достоинство этого формата в его документированности и наличия большого количества программ для просмотра/редактирования и исправления ошибок. Кроме того надо писать программы и к уже существующим базам.
Если ближе к теме, то судя по документации в Delphi функция TDataset.Translate действительно предназначена для перекодировки строковых полей и вызывается из TStringField.GetValue. В Lazarus в TStringField такой вызов не предусмотрен, вот и получается функция есть, но не используется.
Что касается стандартов, то если в заголовке DBF по смещению 29 не указана кодировка, то подразумевается OEM, в противном случае указанная (например cp1251).
Если ближе к теме, то судя по документации в Delphi функция TDataset.Translate действительно предназначена для перекодировки строковых полей и вызывается из TStringField.GetValue. В Lazarus в TStringField такой вызов не предусмотрен, вот и получается функция есть, но не используется.
Что касается стандартов, то если в заголовке DBF по смещению 29 не указана кодировка, то подразумевается OEM, в противном случае указанная (например cp1251).
Что касается стандартов, то если в заголовке DBF по смещению 29 не указана кодировка, то подразумевается OEM, в противном случае указанная (например cp1251).
хм...это меняет дело
я тут заглянул в исходники - в классе TDBF есть свойство CodePage:cardinal
Судя по описанию взятому мною с <a href='http://tdbf.sourceforge.net/' target='_blank'>http://tdbf.sourceforge.net/</a> он как раз и содержит значение кодовой страницы данных. Правда я еще пока не совсем понимаю как это можно использовать... :unsure:
но похоже автоматом оно точно не используется
и какие константы использовать как значения тоже не ясно... :unsure:
-
Alexey
