Получить у textarea ближайшую к POINT позицию курсора
От: Hawk Россия  
Дата: 26.03.10 11:12
Оценка:
Насколько знаю, у edit-контролов (textarea, input) есть behavior-методы, позволяющие задать текущее выделение, получить выделенный текст и т.п. Однако, я не нашел функции для получения позиции в тексте из POINT (в WinAPI — сообщение EM_CHARFROMPOS).

Это может быть жизненно необходимо при реализации, например, drag-and-drop. Когда пользователь, зажав кнопку мыши, перемещает курсор внутри textarea, нужно каким-то образом вслед за мышью перемещать текстовый курсор. Сейчас, как я понимаю, реализовать это совершенно невозможно.

Или я ошибаюсь и это все-таки как-то можно сделать?
Re: Получить у textarea ближайшую к POINT позицию курсора
От: c-smile Канада http://terrainformatica.com
Дата: 30.03.10 16:23
Оценка:
Здравствуйте, Hawk, Вы писали:

H>Это может быть жизненно необходимо при реализации, например, drag-and-drop. Когда пользователь, зажав кнопку мыши, перемещает курсор внутри textarea, нужно каким-то образом вслед за мышью перемещать текстовый курсор. Сейчас, как я понимаю, реализовать это совершенно невозможно.


Придумаю чего-нибудь. Стандартный D&D не устраивает я так понимаю?
Re[2]: Получить у textarea ближайшую к POINT позицию курсора
От: Hawk Россия  
Дата: 02.04.10 09:15
Оценка:
Здравствуйте, c-smile, Вы писали:

CS>Стандартный D&D не устраивает я так понимаю?


А что значит "стандартный"? Вроде, там любой drag-and-drop работать не будет, т.к. попросту нет способа определить, куда надо перемещать курсор, чтобы указать точку сброса. Надо ведь не просто сбросить некий объект в textarea, а сбросить его в определенную позицию внутри textarea (т.е вставить строку в определенную позицию текста).

Сейчас для этого приходится встраивать в HTMLayout-окно стандартный edit-control, благо там есть такая возможность — из POINT получить позицию в тексте. Если удастся реализовать подобную функциональность непосредственно в <textarea>, то это будет просто фантастически здорово.
Re[3]: Получить у textarea ближайшую к POINT позицию курсора
От: c-smile Канада http://terrainformatica.com
Дата: 02.04.10 20:58
Оценка: 8 (1)
Здравствуйте, Hawk, Вы писали:

H>Сейчас для этого приходится встраивать в HTMLayout-окно стандартный edit-control, благо там есть такая возможность — из POINT получить позицию в тексте. Если удастся реализовать подобную функциональность непосредственно в <textarea>, то это будет просто фантастически здорово.


Приделаю чего-нибудь.
Re[4]: Получить у textarea ближайшую к POINT позицию курсора
От: Hawk Россия  
Дата: 08.10.10 12:02
Оценка:
Здравствуйте, c-smile, Вы писали:

CS>Приделаю чего-нибудь.


Что-то никаких изменений за полгода... Неужели я один такой извращенец, и кроме меня это никому не нужно?

Может, есть какой-то другой способ дропнуть текст в текстовое поле в указанную позицию? Чтобы было понятно, как это должно работать, можно поперетаскивать текст внутри textarea — это именно то, что нужно. Только тащить текст надо не из этого же, а из другого — не HTMLayout — окна.
Re[5]: Получить у textarea ближайшую к POINT позицию курсора
От: c-smile Канада http://terrainformatica.com
Дата: 08.10.10 17:14
Оценка:
Здравствуйте, Hawk, Вы писали:

H>Здравствуйте, c-smile, Вы писали:


CS>>Приделаю чего-нибудь.


H>Что-то никаких изменений за полгода...


А ты где смотришь?

Есть например вот такое:
dom::editbox::char_pos_at_xy(x,y)


H>Может, есть какой-то другой способ дропнуть текст в текстовое поле в указанную позицию? Чтобы было понятно, как это должно работать, можно поперетаскивать текст внутри textarea — это именно то, что нужно. Только тащить текст надо не из этого же, а из другого — не HTMLayout — окна.


Тебя устроит если просто будет поддержка drop из другого приложения?
Re[6]: Получить у textarea ближайшую к POINT позицию курсора
От: Hawk Россия  
Дата: 08.10.10 21:12
Оценка:
Здравствуйте, c-smile, Вы писали:

CS>А ты где смотришь?


CS>Есть например вот такое:

CS>
CS>dom::editbox::char_pos_at_xy(x,y)
CS>

Ничего не понимаю. Я прошерстил все файлы исходников в свежескаченной 3.3.2.14 и ничего похожего не нашел. В enum BEHAVIOR_METHOD_IDENTIFIERS ничего подобного нет. В определении класса dom::editbox — тоже...

S>Тебя устроит если просто будет поддержка drop из другого приложения?


Т.е. делать поддержку OLE Drag-and-Drop? Было бы неплохо. Только надо дать возможность пользователю самому извлекать данные из OLE drop source, т.к. форматы источников всегда разные. Но, в принципе, функции API, вроде той, что ты привел выше, вполне достаточно. Осталось дело за малым — определить, где она находится...
Re[7]: Получить у textarea ближайшую к POINT позицию курсора
От: c-smile Канада http://terrainformatica.com
Дата: 08.10.10 21:16
Оценка: 4 (1)
Здравствуйте, Hawk, Вы писали:

H>Здравствуйте, c-smile, Вы писали:


CS>>А ты где смотришь?


CS>>Есть например вот такое:

CS>>
CS>>dom::editbox::char_pos_at_xy(x,y)
CS>>

H>Ничего не понимаю. Я прошерстил все файлы исходников в свежескаченной 3.3.2.14 и ничего похожего не нашел. В enum BEHAVIOR_METHOD_IDENTIFIERS ничего подобного нет. В определении класса dom::editbox — тоже...

Это из Sciter SDK. Можешь просто скопировать оттуда определения — они совместимы.

S>>Тебя устроит если просто будет поддержка drop из другого приложения?


H>Т.е. делать поддержку OLE Drag-and-Drop? Было бы неплохо. Только надо дать возможность пользователю самому извлекать данные из OLE drop source, т.к. форматы источников всегда разные. Но, в принципе, функции API, вроде той, что ты привел выше, вполне достаточно. Осталось дело за малым — определить, где она находится...


Хочется обойтись малой кровью — т.е. не завязываться на форматы OLE вообще.
Re[8]: Получить у textarea ближайшую к POINT позицию курсора
От: Hawk Россия  
Дата: 11.10.10 11:31
Оценка:
Здравствуйте, c-smile, Вы писали:

CS>Это из Sciter SDK. Можешь просто скопировать оттуда определения — они совместимы.


Если я правильно понимаю, можно использовать htmlayout.dll и все должно работать? Не получается.

Определения скопировал:

  C:\...\HTMLayout\include\htmlayout_behavior.h
...
  // identifiers of methods currently supported by intrinsic behaviors,
  // see function HTMLayoutCallMethod 

  enum BEHAVIOR_METHOD_IDENTIFIERS
  {
    DO_CLICK = 0,
    GET_TEXT_VALUE = 1,
    SET_TEXT_VALUE,
      // p - TEXT_VALUE_PARAMS
    
    TEXT_EDIT_GET_SELECTION,
      // p - TEXT_EDIT_SELECTION_PARAMS

    TEXT_EDIT_SET_SELECTION,
      // p - TEXT_EDIT_SELECTION_PARAMS

    // Replace selection content or insert text at current caret position.
    // Replaced text will be selected. 
    TEXT_EDIT_REPLACE_SELECTION, 
      // p - TEXT_EDIT_REPLACE_SELECTION_PARAMS

    // Set value of type="vscrollbar"/"hscrollbar"
    SCROLL_BAR_GET_VALUE,
    SCROLL_BAR_SET_VALUE,

    // get current caret position, it returns rectangle that is relative to origin of the editing element.
    TEXT_EDIT_GET_CARET_POSITION,
      // p - TEXT_CARET_POSITION_PARAMS

    TEXT_EDIT_GET_SELECTION_TEXT, // p - TEXT_SELECTION_PARAMS, OutputStreamProc will receive stream of WCHARs
    TEXT_EDIT_GET_SELECTION_HTML, // p - TEXT_SELECTION_PARAMS, OutputStreamProc will receive stream of BYTEs - utf8 encoded html fragment.
    TEXT_EDIT_CHAR_POS_AT_XY,     // p - TEXT_EDIT_CHAR_POS_AT_XY_PARAMS

    IS_EMPTY      = 0xFC,       // p - IS_EMPTY_PARAMS // set VALUE_PARAMS::is_empty (false/true) reflects :empty state of the element.
    GET_VALUE     = 0xFD,       // p - VALUE_PARAMS 
    SET_VALUE     = 0xFE,       // p - VALUE_PARAMS 

    XCALL                       = 0xFF, // p - XCALL_PARAMS
    FIRST_APPLICATION_METHOD_ID = 0x100 
  };
...
  struct TEXT_EDIT_CHAR_POS_AT_XY_PARAMS: METHOD_PARAMS
  {
    INT x,y;         // in
    INT      char_pos;   // out
    HELEMENT he;     // out
    int      he_pos; // out
    TEXT_EDIT_CHAR_POS_AT_XY_PARAMS() { methodID = TEXT_EDIT_CHAR_POS_AT_XY; }
  };
...

  C:\...\HTMLayout\include\htmlayout_dom.hpp
...
    class editbox: public element
    {
        
      public: 
        ...
        int char_pos_at_xy(int x, int y) const
        {
          TEXT_EDIT_CHAR_POS_AT_XY_PARAMS sp;
          sp.x = x;
          sp.y = y;
          if(!const_cast<editbox*>(this)->call_behavior_method(&sp))
            return -1;
          return sp.char_pos;
        }
    };
...

Но толку никакого — call_behavior_method() возвращает false и, как следствие, editbox::char_pos_at_xy() возвращает -1. Причем, похоже, что всегда, независимо от координат:
...
if( edit.is_valid() )
{
    RECT rc = edit.get_location();
    int nCharPos1 = edit.char_pos_at_xy( rc.left + 5, rc.top + 5 ); // -1
    int nCharPos2 = edit.char_pos_at_xy( 5, 5 ); // -1
...
}

Оба варианта возвращают -1.

Или все-таки это зависит от координат? Тогда — в каком виде надо передавать координаты, чтобы сработало? Какова точка отсчета?
Re[9]: Получить у textarea ближайшую к POINT позицию курсора
От: Hawk Россия  
Дата: 11.10.10 14:08
Оценка:
Вдогонку — ради смеха состряпал код, проверяющий весь диапазон точек (у моего монитора разрешение 1280x1024), включая отрицательные:
htmlayout::dom::editbox edit;
...
ASSERT( edit.is_valid() );

edit.set_state( STATE_FOCUS );

for( int x = -1280; x < 1280; x++ )
{
    for( int y = -1024; y < 1024; y++ )
    {
        int nCharPos = edit.char_pos_at_xy( x, y );
        if( nCharPos != -1 )
        {
            ASSERT( FALSE );
        }
    }
}
Бесполезно — до последнего ASSERT'a дело не дошло ни разу. Т.е., похоже, функция char_pos_at_xy() не работает или соответствующего behavior-метода не существует в HTMLayout.
Re[10]: Получить у textarea ближайшую к POINT позицию курсор
От: c-smile Канада http://terrainformatica.com
Дата: 11.10.10 18:07
Оценка:
Здравствуйте, Hawk, Вы писали:

H>Т.е., похоже, функция char_pos_at_xy() не работает или соответствующего behavior-метода не существует в HTMLayout.


Посмотрю, может быть behavior:plaintext этот метод действительно не поддерживает.
Для behavior:edit должен работать точно.
Re[10]: Получить у textarea ближайшую к POINT позицию курсор
От: c-smile Канада http://terrainformatica.com
Дата: 12.10.10 05:16
Оценка: 12 (1)
Здравствуйте, Hawk, Вы писали:

Скачай SDK еще раз.

edit.char_pos_at_xy( x, y ); — должно работать. Свисти если что а то тест кейзы мне сегодня уже облом писать.
 
Подождите ...
Wait...
Пока на собственное сообщение не было ответов, его можно удалить.