powered by simpleCommunicator - 2.0.61     © 2026 Programmizd 02
Целевая тема:
Создать новую тему:
Автор:
Закрыть
Цитировать
Форумы / Delphi [игнор отключен] [закрыт для гостей] / Полная замена текста в SynEdit
17 сообщений из 17, страница 1 из 1
Полная замена текста в SynEdit
    #40022552
S_Gur
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
Доброго времени суток. Господа знатоки, если кто в курсе - скажите, пожалуйста, можно ли в SynEdit подменить весь текст так, чтобы он считал, что это именно редактирование. Тупое присвоение Text := '' он понимает как новый текст, при этом теряются все Undo. Я попробовал выделить весь текст и подменить SelText. Это работает, но при этом пометка текста также запоминается, как отдельная операция, и по Undo он восстанавливает это выделение. Не то, чтобы это смертельно, но некрасиво, хотелось бы этого избежать
...
Рейтинг: 0 / 0
Полная замена текста в SynEdit
    #40022553
Фотография DarkMaster
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
S_Gur,

Что конкретно ты хочешь получить? Чтобы при замене SynEdit.Text:='.......' он в Undo ничего не складывал?
...
Рейтинг: 0 / 0
Полная замена текста в SynEdit
    #40022555
S_Gur
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
DarkMaster, наоборот. Чтобы он считал, что подмена текста - это вариант изменения и чтобы можно было по Undo возвратить предыдущий текст
...
Рейтинг: 0 / 0
Полная замена текста в SynEdit
    #40022562
ъъъъъ
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Гость
S_Gur,



Если тебе нужно только то, что ты описал в начале - просто подправь исходники SynEdit.

Код: pascal
1.
2.
3.
4.
5.
6.
7.
8.
9.
10.
11.
12.
13.
14.
15.
16.
17.
18.
19.
20.
21.
procedure TCustomSynEdit.Undo;
var
...
  fIsDelete: Boolean; // Добавить
begin
...
  if Item <> nil then
  begin
    OldChangeNumber := Item.ChangeNumber;
    SaveChangeNumber := fRedoList.BlockChangeNumber;
    fRedoList.BlockChangeNumber := Item.ChangeNumber;
    fIsDelete := Item.ChangeReason = crDelete; // Добавить
...

      if Assigned(Item) and fIsDelete then // Добавить
          Undo() // Добавить

    finally
      fRedoList.BlockChangeNumber := SaveChangeNumber;
    end;
...


Коротко: если операция удаления - то Undo вызывается повторно (рекурсивно, однократно).
...
Рейтинг: 0 / 0
Полная замена текста в SynEdit
    #40022564
S_Gur
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
ъъъъъ, по-моему, это не совсем то, что нужно (либо я чего-то не догоняю). Я так понимаю, ты дал вариант сброса пометки блока. На Undo это не совсем удобно, блок я мог выставить и сам, руками, тогда сбрасывать его по Undo не надо, в этом случае все правильно. Я просто хочу вариант (очень желательно, штатный - трудно поверить, что его нет совсем), когда полная подмена текста воспринимается просто как очередное изменение
...
Рейтинг: 0 / 0
Полная замена текста в SynEdit
    #40022567
alekcvp
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
ъъъъъ

Код: pascal
1.
2.
3.
4.
5.
6.
  if Item <> nil then 
  begin
...
    fIsDelete := Item.ChangeReason = crDelete; // Добавить
    if Assigned(Item) and fIsDelete then // Добавить
      Undo() // Добавить



Тебя в этом коде ну вот вообще ничего не смущает?..

Почему не просто:
Код: pascal
1.
2.
if Item.ChangeReason = crDelete then 
  Undo();


?
...
Рейтинг: 0 / 0
Полная замена текста в SynEdit
    #40022569
ъъъъъ
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Гость
S_Gur,

Это редактор, операция "замена текста" вызывается только после выделения текста, который заменяется. Так сделано (1).

"Софтовая" операция .Text := '***' вызывает, кроме всего прочего, и ClearUndo. Так сделано (2).

Но ты можешь определить собственный обработчик OnCleared для свойства Lines контрола.

Код: pascal
1.
TSynEditStringList(<мой SynEdit контроль>.Lines).OnCleared := MyOnCleared;


Код: pascal
1.
2.
procedure TfrmMain.MyOnCleared(Sender: TObject);
begin


- в котором не очищать буфер Undo.

Однако, сохранения буфера Undo недостаточно: в буфере Undo не хранится весь текст, а только "дельта" - операции. То есть, придется где-то сохранять и весь буфер.
И тебе придется дополнить формат операций Undo и, соответственно, их обработку по Ctrl+Z/+R.
Не очень сложно.

А зачем тебе вообще эта головная боль? "Подмена текста" выполняется при инициализации контрола, какие там могут быть Undo?
...
Рейтинг: 0 / 0
Полная замена текста в SynEdit
    #40022570
ъъъъъ
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Гость
alekcvp,

в том месте. где многоточие -
ъъъъъ
Код: pascal
1.
...


Item меняется.

Код: pascal
1.
2.
3.
4.
    try
      repeat
        UndoItem;
        Item := fUndoList.PeekItem;
...
Рейтинг: 0 / 0
Полная замена текста в SynEdit
    #40022573
S_Gur
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
ъъъъъ, конкретно в моем случае я периодически выполняю конвертацию текста из одной кодировки в другую. И хочу иметь возможность откатить конвертацию. А операция замены текста может выполняться и иначе - например, несколько раз нажать в нужном месте Delete и ввести новый текст. При этом выделение вовсе необязательно, а редактор считает текст изменившимся - со всеми вытекающими из этого последствиями. Правда, при этом сохранится и соответствующее количество Undo, конечно...
...
Рейтинг: 0 / 0
Полная замена текста в SynEdit
    #40022578
Фотография DarkMaster
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
S_Gur,

Либо я мало что понял, либо ты натягиваешь сову на глобус.....
...
Рейтинг: 0 / 0
Полная замена текста в SynEdit
    #40022579
ъъъъъ
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Гость
S_Gur
ъъъъъ, конкретно в моем случае я периодически выполняю конвертацию текста из одной кодировки в другую. И хочу иметь возможность откатить конвертацию. А операция замены текста может выполняться и иначе - например, несколько раз нажать в нужном месте Delete и ввести новый текст. При этом выделение вовсе необязательно, а редактор считает текст изменившимся - со всеми вытекающими из этого последствиями. Правда, при этом сохранится и соответствующее количество Undo, конечно...

Я бы сделал функцию конвертации с двумя параметрами: (1) исходный код символа и (2) код после конвертации.
А класс контрола редактора дополнил бы методом - функцией высшего порядка, в которую бы передавал функцию конвертации. И этот метод последовательно обрабатывал бы все символы тестового буфера и буферов Undo-Redo.
Таким образом, undo-redo остался бы неизменным при смене кодировки, а саму кодировку бы менял "внешней" командой, без Ctrl/Z/R. Так, например, в Notepad++ сделано: undo/redo сам по себе, кодировка - сама по себе.
...
Рейтинг: 0 / 0
Полная замена текста в SynEdit
    #40022580
S_Gur
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
DarkMaster, может быть... На самом деле, проблема решена. Я нашел, в какой момент сбросить выделение, меня это вполне устраивает. Всем спасибо
...
Рейтинг: 0 / 0
Полная замена текста в SynEdit
    #40022581
ъъъъъ
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Гость
S_Gur
DarkMaster, может быть... На самом деле, проблема решена. Я нашел, в какой момент сбросить выделение, меня это вполне устраивает. Всем спасибо

И тут не расскажешь?
...
Рейтинг: 0 / 0
Полная замена текста в SynEdit
    #40022582
S_Gur
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
ъъъъъ, а можно как-то узнать текущий индекс UndoList, чтобы проверить ChangeReason?

P. S. Могу рассказать. Дело в том, что я нашел способ отловить именно тот Undo, который возвращает текст к состоянию до конвертации. Пока я просто по умолчанию считаю, что он возвращает этот текст помеченным и снимаю пометку. Но хотелось бы понять, с каким именно айтемом из андулиста я в данный момент имею дело и проверить его ChangeReason - так, по-моему, будет красивее
...
Рейтинг: 0 / 0
Полная замена текста в SynEdit
    #40022586
ъъъъъ
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Гость
S_Gur
как-то узнать текущий индекс UndoList

"Текущий" - то этот, который находится сверху. :)

Код: pascal
1.
2.
3.
4.
var
  Item :TSynEditUndoItem;
...
Item = SynEdit1.UndoList.PeekItem
...
Рейтинг: 0 / 0
Полная замена текста в SynEdit
    #40022587
ъъъъъ
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Гость
S_Gur,

или
Код: pascal
1.
var index : integer =  SynEdit1.UndoList.ItemCount - 1
...
Рейтинг: 0 / 0
Полная замена текста в SynEdit
    #40022589
S_Gur
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
ъъъъъ, Странно... Наверное, я еще не все понял. После Undo PeekItem Nil, UndoList.ItemCount 0, но текст все равно выделенный. Видимо, SelectAll, который я вызываю перед заменой текста, не входит в UndoList. Ладно, это уже не настолько важно - выделение я сбрасываю. Еще раз спасибо за помощь
...
Рейтинг: 0 / 0
17 сообщений из 17, страница 1 из 1
Форумы / Delphi [игнор отключен] [закрыт для гостей] / Полная замена текста в SynEdit
Найденые пользователи ...
Разблокировать пользователей ...
Читали форум (0):
Пользователи онлайн (0):
x
x
Закрыть


Просмотр
0 / 0
Close
Debug Console [Select Text]