Unicode

Тема в разделе "Delphi - FAQ", создана пользователем slavas, 22 июн 2008.

Статус темы:
Закрыта.
  1. slavas

    slavas Гость

    Мне нужно отредактировать в TMemo текстовый файл (он в формате Unicode). Каким образом мне его загрузить в Memo?
    Просто командой Memo1.Lines.LoadFromFile() отображается что-то непонятное. А потом его ещё и сохранить так чтобы он остался в Unicode?
    Пожалуйста работающий примерчик. У меня Дельфи 7
    -----
    Два дня прошло - ответов нет. Неужто сложный вопрос? Ладно.
    Вот что я нашел в моих поисках:
    Помогите это дело перевести для случая с Unicode. У меня не получается.
    Все время какая то проблема с несовместимыми типами.
     
  2. slavas

    slavas Гость

    Ну и что мне делать? Кто нибудь знает ответ на этот вопрос? Для чего тогда функции WideCharToStrVar, OleStrToStrVar с текстовыми переменными с широкой строкой, если я попросту не могу эти переменные заполнить? Помогите.
     
  3. etc

    etc Гость

    Либо используйте компоненты которые поддерживают юникод, либо надо установить соотв. чарсет контролам, либо конвертировать с пом. спец функций
    вот их тут есть: AnsiToUtf8, PUCS4Chars, StringToWideChar, UCS4StringToWideString, UnicodeToUtf8, UTF8Decode, UTF8Encode, Utf8ToAnsi, Utf8ToUnicode, WideCharLenToString, WideCharLenToStrVar, WideCharLenToStrVar, WideCharToString, WideCharToStrVar, WideStringToUCS4String ..
     
  4. slavas

    slavas Гость

    Так как раз в этом и проблема! Функции известны, а воспользоваться ими не могу. Попросту текст не могу взять из файла!
    Не забываем, что он там в Юникоде (не UTF8). Кстати такой файл можно создать и сохранить в Блокноте, выбрав там Юникод.
    А компоненты, поддерживающие Юникод, надо специально искать? или они есть в стандартном Дельфи 7?
     
  5. slavas

    slavas Гость

    Искал и в Гугде и в Яндексе, еще до вопроса в форуме, и сейчас посмотрел, ничего там в интернете не изменилось. ответа на мой вопрос нет. Повторюсь. Как загрузить из файла текст(букву) (Юникод UTF16) в переменную типа PWideChar? Похоже, только с этим типом работают нужные мне функции преобразования.
     
  6. etc

    etc Гость

    Вторая ссылка из пред. поста ведет на компоненты, поддерживающие юникод.
     
  7. slavas

    slavas Гость

    15 мегов, да... С моей то сотовой связью. Если что нибудь не придумаю, буду качать. Хотелось попроще. Я уже так много знаю об этом Юникоде, что уже в теории могу сам перекодировщик написать. Взять текст как file of byte; первую пару выкидываем-это признак Юникода, далее каждой паре байт соответствует свой символ. Единственный недостаток это составлять для всех символов однозначное соответствие. Большой объем кода получается. Может кто написал проще, без этой таблицы? Пишите.
    Спасибо за ответы, Вы дали мне направление, как можно решить эту проблему.
     
  8. zubr

    zubr Гость

    Код (Text):
    unit Unit1;

    interface

    uses
    Windows, Messages, SysUtils, Variants, Classes, Graphics, Controls, Forms,
    Dialogs, StdCtrls;

    type
    TForm1 = class(TForm)
    Button1: TButton;
    Memo1: TMemo;
    Button2: TButton;
    procedure FormCreate(Sender: TObject);
    procedure Button1Click(Sender: TObject);
    procedure Button2Click(Sender: TObject);
    private
    { Private declarations }
    public
    { Public declarations }
    end;

    TMemoWithUnicod = class(TCustomMemo)
    private
    FMemStream: TMemoryStream;
    public
    procedure LoadFromUnicodFile(const FileName: string);
    procedure SaveToUnicodFile(const FileName: string);

    constructor Create(AOwner: TComponent); override;
    destructor Destroy; override;
    end;

    var
    Form1: TForm1;

    implementation

    {$R *.dfm}

    var
    MemoWithUnicod:TMemoWithUnicod;

    constructor TMemoWithUnicod.Create(AOwner: TComponent);
    begin
    inherited Create(AOwner);
    FMemStream := TMemoryStream.Create;
    end;

    destructor TMemoWithUnicod.Destroy;
    begin
    FMemStream.Free;
    inherited Destroy;
    end;

    procedure TMemoWithUnicod.LoadFromUnicodFile(const FileName: string);
    var
    wbuf: PChar;
    zag: Word;
    begin
    FMemStream.LoadFromFile(FileName);
    If FMemStream.Size < 2 then
    exit;
    FMemStream.Position := 0;
    FMemStream.Read(zag, 2);
    If zag <> $FEFF then
    exit;

    FMemStream.Position := 2;
    wbuf := StrAlloc(FMemStream.Size);
    try
    ZeroMemory(wbuf, FMemStream.Size);
    FMemStream.Read(wbuf^, FMemStream.Size-2);
    Lines.Text := WideCharToString(PWideChar(wbuf));
    finally
    StrDispose(wbuf);
    end;
    end;

    procedure TMemoWithUnicod.SaveToUnicodFile(const FileName: string);
    var
    dest: PWideChar;
    zag: Word;
    begin
    FMemStream.Clear;
    FMemStream.Position := 0;
    zag := $FEFF;
    FMemStream.Write(zag, 2);

    FMemStream.Position := 2;
    GetMem(dest, (Length(Lines.Text)+1)*2);
    try
    ZeroMemory(dest, (Length(Lines.Text)+1)*2);
    StringToWideChar(Lines.Text, dest, Length(Lines.Text)+1);
    FMemStream.Write(dest^, Length(Lines.Text)*2);
    FMemStream.SaveToFile(FileName);
    finally
    FreeMem(dest);
    end;
    end;

    procedure TForm1.FormCreate(Sender: TObject);
    begin
    MemoWithUnicod := TMemoWithUnicod.Create(Self);
    MemoWithUnicod.Parent := Self;
    MemoWithUnicod.Left := 20;
    MemoWithUnicod.Top := 20;
    MemoWithUnicod.ScrollBars := ssVertical;
    end;

    procedure TForm1.Button1Click(Sender: TObject);
    begin
    MemoWithUnicod.LoadFromUnicodFile('MyUnicodFile.txt');
    end;

    procedure TForm1.Button2Click(Sender: TObject);
    begin
    MemoWithUnicod.SaveToUnicodFile('MyUnicodFile.txt');
    end;

    end.
     
  9. slavas

    slavas Гость

    Нехило! Проверил, работает. Гораздо лучше, чем мои таблицы. При моём уровне развития такого я бы не смог сделать. Будем изучать, применять в работе. Спасибо. Вопрос закрыт.
     
Загрузка...
Статус темы:
Закрыта.

Поделиться этой страницей