На главную Наши проекты:
Журнал   ·   Discuz!ML   ·   Wiki   ·   DRKB   ·   Помощь проекту
ПРАВИЛА FAQ Помощь Участники Календарь Избранное RSS
msm.ru
! Правила раздела Visual C++ / MFC / WTL (далее Раздела)
1) На Раздел распространяются все Правила Форума.
2) Перед тем, как создать новый топик, убедитесь, что Вы читали Правила создания тем в Разделе.
3) Вопросы, не связанные с программированием (настройки MS Visual Studio, книги, библиотеки и т.д.),
обсуждаются в разделе C/C++: Прочее
4) Вопросы разработки .NET (Windows Form, C++/CLI и т.п.) приложений на Visual C++/C# обсуждаются в разделе .NET.
5) Нарушение Правил может повлечь наказание со стороны модераторов.

Полезные ссылки:
user posted image FAQ Раздела user posted image Обновления для FAQ Раздела user posted image Поиск по Разделу user posted image MSDN Library Online
Модераторы: ElcnU
  
> Копирование русского текста из мультибайтовой программы при английской раскладке , Копируется с ошибками
    Проблема стара, перечитав много статей так и не нашел ответа однозначного ответа. На форуме раза три точно поднималась.

    В мастере создаем диалоговое приложение CMainDlg с многобайтовой кодировкой, на него кладем CEdit, вводим русский текст, потом, переключаемся на английский язык, копируется мусор.
    Обратно копируются вопросы. Как я понял проблема в том, что буфер обмена думает, что в буфере английский язык, хотя там русский.

    Естественно команды при инициализации приложения: SetThreadLocale(1049); setlocale(LC_ALL,"Russian" ); не дают никакого эффекта.

    Вопрос: получается у нас единственный вариант отлавливать WM_PASTE в CMainDlg? Есть еще решение?
      Цитата MaIron @
      Обратно копируются вопросы. Как я понял проблема в том, что буфер обмена думает, что в буфере английский язык, хотя там русский.

      MaIron, думаю, что буфер обмена вообще ничего не думает.
      Какие байты ему дают, такие он хранит и обратно возвращает.
      ---
      Указанные классы я не использовал, но если смастерить эдит средствами
      winapi, никаких эффектов с искажениями информации мне обнаружить не удалось.
        Цитата MaIron @
        Естественно команды при инициализации приложения: SetThreadLocale(1049); setlocale(LC_ALL,"Russian" ); не дают никакого эффекта.

        Чего-чего? Какая кодировка инициализируется?

        Я правда юзал лишь windows api и всё всегда было нормой. По идее классы всего лишь обёртка над windows api и не должны заниматся самодеятельностью. Но одно лишь
        SetThreadLocale(1049)
        Вызывает огромные подозрение. Думаю, что именно оно и даёт эффект. Ну или ваши классы вовсе не широкосимвольные, а чёрт знает какие. Ведь широкосимвольные функции перекодировкой не занимаются.

        И да, на всякий случай, вы всё же проверьте, ту программу, куда пытаетесь вставить свой текст. Попробуйте блокнот. Он не должен вносить искажений в текст. Насколько я знаю, к примеру wordpad может проверить буфер и по своему попытатся интерпретировать его содержимое.
          Нет. Все стандартно класс CEdit, копирую в блокнот, проблема в MFC. Студия 2003я Win7 64bit
            Пришлось переопределять CEdit
            Если кому то пригодится привожу реализацию, код сильно не тестировал.
            ExpandedWrap disabled
              #pragma once
               
               
              // CCoreEdit
               
              class CCoreEdit : public CEdit
              {
                  DECLARE_DYNAMIC(CCoreEdit)
               
              public:
                  CCoreEdit();
                  virtual ~CCoreEdit();
              public:
                  DECLARE_MESSAGE_MAP()
                  afx_msg LRESULT OnCopy(WPARAM, LPARAM);
                  afx_msg LRESULT OnPaste(WPARAM, LPARAM);
               
              protected:
               
              };

            ExpandedWrap disabled
              // CoreEdit.cpp : implementation file
              //
               
              #include "stdafx.h"
              #include "CoreEdit.h"
               
               
              // CCoreEdit
               
              IMPLEMENT_DYNAMIC(CCoreEdit, CEdit)
              CCoreEdit::CCoreEdit()
              {
              }
               
              CCoreEdit::~CCoreEdit()
              {
              }
               
               
              BEGIN_MESSAGE_MAP(CCoreEdit, CExtEdit)
                  ON_MESSAGE(WM_COPY, OnCopy)
                  ON_MESSAGE(WM_PASTE, OnPaste)
              END_MESSAGE_MAP()
               
              LRESULT CCoreEdit::OnCopy(WPARAM, LPARAM) {
               
                  //Размер получаемого блока
                  int nStart = 0;
                  int nEnd = 0;
               
                  //Текущая строка
                  CString sText;
                  //Временная строка
                  CString sBlock;
                  
                  //Получаем текст
                  GetWindowText(sText);
               
                  //Получаем выделение
                  GetSel(nStart, nEnd);
                  
                  //Если не пустая стрка
                  if(!sText.IsEmpty() && nStart > -1){
                      //Получаем выделенный фрагмент
                      sBlock = sText.Right(sText.GetLength() - nStart);
                      sBlock = sBlock.Left(nEnd-nStart);
                      HGLOBAL hGlobal = ::GlobalAlloc( GHND, sBlock.GetLength()+ 1 );
                      void* mem = ::GlobalLock( hGlobal );
                      if ( mem ){
                          memcpy( mem, sBlock, sBlock.GetLength() + 1 );
                          ::GlobalUnlock( hGlobal );
                          if ( ::OpenClipboard( NULL ) )
                          ::EmptyClipboard();
                          LCID* lcid = (DWORD*) ( GlobalAlloc( GMEM_FIXED, sizeof(DWORD) ) );
                          *lcid = MAKELCID( MAKELANGID( LANG_RUSSIAN, SUBLANG_NEUTRAL ), SORT_DEFAULT );
                          ::SetClipboardData( CF_LOCALE, (HANDLE) lcid );
                          ::SetClipboardData( CF_TEXT, hGlobal );
                          ::CloseClipboard();
                      }
                  }
                 return 1;
              }
              LRESULT CCoreEdit::OnPaste(WPARAM, LPARAM)
              {
                  UINT nFlag = CF_TEXT;
                  if(!IsClipboardFormatAvailable(nFlag))
                  return 1;
                  if(!OpenClipboard())
                  return 1;
                  
                  LCID* lcid = (DWORD*) ( GlobalAlloc( GMEM_FIXED, sizeof(DWORD) ) );
                  *lcid = MAKELCID( MAKELANGID( LANG_RUSSIAN, SUBLANG_NEUTRAL ), SORT_DEFAULT );
                  ::SetClipboardData( CF_LOCALE, (HANDLE) lcid );
               
                  HGLOBAL hData = GetClipboardData(nFlag);
                  if(hData != NULL)
                  {
                      LPTSTR lptstr = (LPTSTR)GlobalLock(hData);
                      if(lptstr != NULL){
                          ReplaceSel(lptstr, TRUE);
                      }
                      GlobalUnlock(hData);
                  }
                      CloseClipboard();
                  return 1;
              }
            Сообщение отредактировано: MaIron -
            1 пользователей читают эту тему (1 гостей и 0 скрытых пользователей)
            0 пользователей:


            Рейтинг@Mail.ru
            [ Script execution time: 0,0295 ]   [ 15 queries used ]   [ Generated: 21.06.25, 22:12 GMT ]