|
Модераторы: Vitalik |
|
mr.Anderson |
|
||||||||||||||||||||||||||||||||||||||||
iOS Lead Developer Профиль Группа: Участник Клуба Сообщений: 3374 Регистрация: 20.12.2004 Где: далеко Репутация: 1 Всего: 128 |
Тему, я думаю, стоит закрепить. И вообще все, что связано с SynEdit из пакета SynMix, надо бы перенести в эту тему, мне кажется.
Итак. Поскольку SynEdit из пакета SynMix мне нужно использовать в своей программе как основной, мне пришлось изрядно перерыть его, чтобы заставить-таки работать, как надо. Привожу здесь мои добавления, произведенные в файле SynEdit.pas, а также обнаруженные и исправленные баги. Примечание: прошу обратить внимание на то, что номера строк, где происходило добавление, приведены для моего, уже исправленного и дополненного файла SynEdit.pas. В стандартном файле, разумеется, этих добавлений/исправлений нет, и по указанным номерам строк находится совсем другой код. Фикс №1 Строка 11664: пофиксен баг с отображением скрытого текста. Собственно фикс в том, что я увеличил добавляемые пробелы с пяти до шести.
До этого исправления, например, когда мы сворачивали примерно такой блок кода:
То в подсказке получали следующее:
Разницу видим? Обрезался последний символ первой строки свернутого блока. Такая же ошибка была даже в случае свертки вот такого блока:
В подсказке отображалось
Т.е. тоже обрезался последний (и в данном случае единственный) символ открывающейся скобки. Фикс №2 Строки 4017 и 4021: пофиксен баг с размещением [...]. Раньше было так, что при простом сворачивании блока кода, ограниченного { и }, блок [...] наезжал на переплет, а если блок был ограничен, например, begin и end, то [...] наезжал на слово begin. Теперь все нормально (###фикс - исправлено наезжание [...] на первую строку блока кода).
Фикс №3 В строках 12772 и 12773 добавлен код, предотвращающий ошибку в случае, если выделить первую строку свернутого блока и нажать Ctrl + Backspace (///###mod error with Ctrl+Backspace when SelAvail = True).
Мод №1 Добавлена общедоступная функция IsLineCollapsed() (в строке 786 - в классе, а в 6798-6801 - реализация). Функция принимает целый параметр - номер строки, с которой начинается блок кода. Функция возвращает True, если этот блок свернут, и False, если нет. Код крайне прост и занимает всего одну строчку.
Обнаруженный и грубовато исправленный баг Вынес это исправление в отдельную "категорию". Смысл таков: в SynEdit из пакета SynMix НЕ РАБОТАЕТ клавиша Delete! Я вообще был в шоке от этого. Жму Delete - ноль эмоций! Но зато если выделить часть текста и нажать Delete - все нормально. Поскольку я не смог поймать нажатие Delete в классе TCustomSynEdit (читайте ниже, почему), пришлось исправлять баг грубыми методами. О них - в модах №2 и №3. Мод №2 Добавлена общедоступная процедура Del() (строка 788 - объявление, 6808-6811 - реализация).
По сути, эта процедура - грубая замена нажатия клавиши Delete в SynEdit, создана для облегчения пользования этой неработающей клавишей. Для ее активации придется в программе переопределять метод AppMsg или WndProc, ловить там нажатие Delete и использовать эту функцию. Например, это может быть такой код:
Мод №3 Добавлена общедоступная процедура DeleteSelText() (строка 787 - объявление, 6803-6806 - реализация). По сути своей это просто синоним вышеописанной процедуры Del(), но может быть более привычно и удобно использовать понятную по своему действию процедуру DeleteSelText(), чем просто Del().
Обнаруженный и НЕ исправленный баг Если свернутую строку кода выделить и нажать Delete, то строка удаляется. Однако попытки отменить это (SynEdit.Undo()) ни к чему не приводят - отмены удаления не происходит. Я, кстати, вообще не смог отловить нажатие Delete. Ставил бряки на TCustomSynEdit.KeyPress, TCustomSynEdit.KeyDown, TCustomSynEdit.KeyUp, даже на TCustomSynEdit.WndProc() - бесполезно. Ловятся все клавиши, кроме Delete. Именно поэтому я и не смог отловить данный баг. В своей программе мне пришлось искусственно запретить срабатывание любых клавиш на строке, где находится свернутый блок (кроме Enter, клавиш вверх-вниз-влево-вправо, Home и End - это сделано для того, чтобы юзер не думал, что это еще один глюк). Объемный мод №4 В класс TCustomSynEdit добавлено свойство только для чтения CurrentHL. Это свойство нового перечислимого типа TCurrentHL, содержит словесный и числовой эквиваленты текущей подсветки. Иногда бывает нужно (мне вот понадобилось) узнать, какая сейчас в редакторе подсветка. Как это узнать обычными методами? А никак. Свойство Highlighter у TCustomSynEdit имеет тип TSynCustomHighlighter, а конкретный тип, например, TSynPasSyn, я не смогу узнать никакими методами. Поэтому я и добавил такую возможность в виде вышеназванного свойства. Теперь собственно о том, какой код был добавлен. Все, связанное с этим модом, помечено как
Повторю, все изменения производились в файле SynEdit.pas. Первое. В строках 216-224 добавлен тип TCurrentHL. Он содержит имена всех типов подсветки из пакета SynMix (например, TSynPasSyn, TSynVBScriptSyn и так далее). С компонентом UniHighlighter этот тип никак не связан и с ним использовать данный мод бесполезно.
Тип, разумеется, общедоступный и может использоваться в основной программе, где размещен компонент SynEdit. Второе. В строке 430 добавлена переменная fCurrentHL типа TCurrentHL. Эта переменная и содержит имя текущей подсветки.
Третье. В строке 737 объявлена процедура UpdateCurrentHL(). Она вводит в переменную fCurrentHL имя текущей подсветки (тип TCurrentHL).
Четвертое. В строке 935 прописано свойство CurrentHL (только для чтения, повторюсь).
Пятое. В строке 1550 (это код конструктора класса TCustomSynEdit) добавлена, по моему мнению, упущенная инициализация свойства Highlighter. Это даже к моду не относится, в принципе, это скорее фикс. А вот в строчке 1551 добавлен вызов вышеназванной процедуры UpdateCurrentHL(), которая, как мы увидим дальше по ее коду, в данном случае проинициализирует переменную fCurrentHL как lngNone (это одно из имен типа TCurrentHL, означающее, что текущей подсветки нет, т.к. свойство Highlighter равно nil).
Шестое. В строках 7266-7323 находится реализация процедуры UpdateCurrentHL().
И последняя часть кода, относящаяся к данному моду - это строчка 7348. В этой строке добавлен вызов UpdateCurrentHL(). Вызов находится в коде функции SetHighlighter() класса TCustomSynEdit, которая, как можно догадаться, изменяет свойство Highlighter. Поэтому вызов процедуры обновления переменной текущей подсветки находится именно в этом месте кода.
Теперь в любом месте вашей программы вы можете узнать текущую подсветку, проанализировав свойство CurrentHL компонента SynEdit. Например, так:
Это сообщение отредактировал(а) mr.Anderson - 29.7.2007, 19:40 |
||||||||||||||||||||||||||||||||||||||||
|
|||||||||||||||||||||||||||||||||||||||||
winsoft |
|
|||
Президент WINsoft Профиль Группа: Участник Сообщений: 49 Регистрация: 14.11.2005 Репутация: нет Всего: нет |
mr.Anderson, пока еще не проверил, как все работает, но заранее большое спасибо за проделанную работу!
|
|||
|
||||
mr.Anderson |
|
|||
iOS Lead Developer Профиль Группа: Участник Клуба Сообщений: 3374 Регистрация: 20.12.2004 Где: далеко Репутация: 1 Всего: 128 |
Не за что. Проверяйте, может, что неверно исправлено. Хотя в моей программе я свои исправления использую очень активно (особенно CurrentHL), пока все работает отлично.
Отпишитесь плз, как у вас успехи с проверкой исправлений. |
|||
|
||||
iddqd2 |
|
|||
Новичок Профиль Группа: Участник Сообщений: 2 Регистрация: 13.1.2008 Репутация: 1 Всего: 1 |
По поводу бага с несрабатыванием клавиши Delete
Происходит это из-за того, что клавиша Delete вызывает только событие KeyUp а не KeyDown, в то время как в SynEdit обработка событий стандартных клавиш происходит в KeyDown. Все необходимое для отработки нажатия Delete там есть. Так что делаем так:
|
|||
|
||||
mr.Anderson |
|
|||
iOS Lead Developer Профиль Группа: Участник Клуба Сообщений: 3374 Регистрация: 20.12.2004 Где: далеко Репутация: 1 Всего: 128 |
iddqd2, супер
|
|||
|
||||
BenderM |
|
|||
Новичок Профиль Группа: Участник Сообщений: 2 Регистрация: 11.6.2009 Репутация: нет Всего: нет |
mr.Anderson
Про выявление имени хайлайтера вы конечно перемудрили Добавлено через 4 минуты и 51 секунду Думаю этот код пригодился бы Вам полтора года назад
|
|||
|
||||
K0T9I |
|
||||||
Новичок Профиль Группа: Участник Сообщений: 44 Регистрация: 20.11.2009 Репутация: нет Всего: 2 |
когда делаем так, то удаление клавишей Delete возможно только при нажатии/отпускании клавиши по 1 символу за раз, при удерживании удаляется тоже 1 символ. если тоже самое, что подсказал iddqd2 вставить в KeyDown, все начинает работать как надо
|
||||||
|
|||||||
0 Пользователей читают эту тему (0 Гостей и 0 Скрытых Пользователей) | |
0 Пользователей: | |
« Предыдущая тема | SynUniHighlighter и SynEdit | Следующая тема » |
|
По вопросам размещения рекламы пишите на vladimir(sobaka)vingrad.ru
Отказ от ответственности Powered by Invision Power Board(R) 1.3 © 2003 IPS, Inc. |