Дмитрий777
Гость
|
|
« : 04-02-2009 13:49 » |
|
Извиняюсь за дурацкий вопрос, но я только начал осваивать азы . Мне нужно вызвать подпрограмму перерисовки шрифта ячеек стринггрида при нажатии кнопки. Делаю так: // сама подпрограмма procedure TForm1.StringGrid1DrawCell(Sender: TObject; ACol, ARow: Integer; Rect: TRect; State: TGridDrawState); begin // здесь все работает, если запускать отдельно end; А это программа вызова подпрограммы procedure TForm1.Button1Click(Sender: TObject); begin StringGrid1DrawCell ; end; Вот здесь компилятор ругается. Что я делаю не так?
|
|
|
Записан
|
|
|
|
Sla
|
|
« Ответ #1 : 04-02-2009 14:11 » |
|
а передать параметры в процедуру?
|
|
|
Записан
|
Мы все учились понемногу... Чему-нибудь и как-нибудь.
|
|
|
Дмитрий777
Гость
|
|
« Ответ #2 : 04-02-2009 14:49 » |
|
А разве тех параметров, которые указаны при запуске подпрограммы недостаточно? И если при вызове п/п нужно указать пареметры, то какие именно ?
|
|
|
Записан
|
|
|
|
Sla
|
|
« Ответ #3 : 04-02-2009 15:02 » |
|
Вот гляди. Ты сам написал. // сама подпрограмма procedure TForm1.StringGrid1DrawCell(Sender: TObject; ACol, ARow: Integer; Rect: TRect; State: TGridDrawState); begin // здесь все работает, если запускать отдельно end; Тем самым ты ее (подпрограмму объявил с параметрами Sender: TObject; ACol, ARow: Integer; Rect: TRect; State: TGridDrawState Здесь ты ее вызываешь procedure TForm1.Button1Click(Sender: TObject); begin StringGrid1DrawCell ; end;
Но уже без параметров. Компилятор - естественно будет ругаться. Объявление и вызов - это разные вещи. у тебя должно быть что-то подобное procedure TForm1.Button1Click(Sender: TObject); begin StringGrid1DrawCell(Sender, ACol, ARow,Rect, State); end;
|
|
|
Записан
|
Мы все учились понемногу... Чему-нибудь и как-нибудь.
|
|
|
zubr
Гость
|
|
« Ответ #4 : 04-02-2009 15:24 » |
|
StringGrid1DrawCell - это обработчик события перерисовки ячеек грида. Какой смысл вызывать процедуру обработки данного события по нажатию кнопки? Оставь данный обработчик в покое. А в обработчике нажатия кнопки вызови перерисовку грида: procedure TForm1.Button1Click(Sender: TObject); begin StringGrid1.Refresh; end;
И будет счастье.
|
|
|
Записан
|
|
|
|
Дмитрий777
Гость
|
|
« Ответ #5 : 04-02-2009 18:39 » |
|
Вот весь текст В первой колонке стринггрида находятся заголовки разделов, а во 2 и 4 колонках и, в следующих строках, данные. Программа построчно проверяет содержимое колонок 2 и 4. Отсутствие данных в этих колонках свидетельствует о том, что в колонке 1 данной строки находится заголовок. Шрифт заголовка изменяется на полужирный и продолжается проверка следующих строк. var k:integer; //подпрограмма изменения шрифта в строке (глобальная переменная - k )
procedure TForm1.StringGrid1DrawCell(Sender: TObject; ACol, ARow: Integer; Rect: TRect; State: TGridDrawState); begin if (ACol = 1)and(ARow = k) then with StringGrid1.Canvas do begin FillRect(Rect); //Изменяем атрибут шрифта Font.Style:= [fsBold]; TextOut(Rect.Left, Rect.Top, StringGrid1.Cells[ACol,ARow]); end; end;
// Поиск и изменение заголовка
procedure TForm1.Button1Click(Sender: TObject); var label M_1 ; begin for k :=0 to StringGrid1.RowCount-1 do begin if StringGrid1.Cells[2,k] = '' then // проверка колонки 2 else goto M_1 ; if StringGrid1.Cells[4,k] = '' then // проверка колонки 4 else goto M_1 ; begin // Вызов подпрограммы изменения шрифта в проверенной строке StringGrid1DrawCell(Sender, ACol, ARow,Rect, State); end; M_1: end; end;
end. Sla. - Компилятор сообщает о незадекларированных ACol, ARow, State. Перерисовывать всю таблицу. А если там 10000 строк и перерисовать нужно 1000 раз. Мелькать не будет?
|
|
|
Записан
|
|
|
|
zubr
Гость
|
|
« Ответ #6 : 04-02-2009 21:30 » |
|
Перерисовка происходит всякий раз, когда пользователь выводит окно на передний план, а следовательно происходит событие StringGrid1DrawCell (попробуй в отладке поставь брикпоинт в коде данного обработчика - как только ты будешь пытаться вывести окно программы на передний план, отладчик будет останавливаться на этом брикпоинте). При этом, заметь ничего не мелькает, конечно в случае если у тебя код обработчика оптимальный. Если ты будешь что то рисовать в контексте грида не в обработчике данного события, то естественно, например при сворачивании окна и затем последующего его восстановления от нарисованного не останется и следа.
|
|
« Последнее редактирование: 04-02-2009 21:32 от zubr »
|
Записан
|
|
|
|
Дмитрий777
Гость
|
|
« Ответ #7 : 05-02-2009 07:53 » |
|
Не понял.. Перерисовка грида не изменит атрибуты шрифта в нужных ячейках. Их же нужно изменять "принудительно". Может проще разобраться с вызовом подпрограммы. Почему компилятор сообщает о незадекларированных ACol, ARow, State. Где я их должен задекларировать? В учебнике об этом мало и непонятно.
|
|
|
Записан
|
|
|
|
zubr
Гость
|
|
« Ответ #8 : 05-02-2009 08:42 » |
|
Дмитрий777, 1. ты читать умеешь? Я вроде по русски пишу. Советую почитать на тему оконных сообщений Windows. Еще раз разъясняю: StringGrid1DrawCell - это процедура (как бы пустой шаблон), предусмотренная разработчиками Borland для компонента TStringGrid, которая вызывается при получении окном TStringGrid от Windows сообщения WM_PAINT (обновления изображения окна). Код, который ты пропишешь в тело данной процедуры будет выполняться всякий раз при перерисовки окна компонента. 2. Брикпоинт ставил в теле обработчика StringGrid1DrawCell?
|
|
|
Записан
|
|
|
|
Вад
|
|
« Ответ #9 : 05-02-2009 08:47 » |
|
zubr, я вот думаю, следует уточнить: она будет выполняться при перерисовке для всех ячеек - то есть, по разу на каждую - ведь так? Остаётся вопрос, как задаётся стиль текста в ячейке (не помню, есть ли такое свойство у ячейки, или это нужно свою матрицу хранить, чтобы при вызове StringGrid1DrawCell для нужной ячейки с нетривиальным стилем выводить что-то специфическое, а потом возвращать стиль в дефолт)?
Дмитрий777, я думаю, отдельно стоит с языком поближе ознакомиться. Потому что если бы сначала изучался сам диалект, а уже потом шли попытки соорудить свой UI, не было бы нелепых вопросов про объявление переменных и передачу параметров в процедуры и функции.
|
|
|
Записан
|
|
|
|
Алексей++
глобальный и пушистый
Глобальный модератор
Offline
Сообщений: 13
|
|
« Ответ #10 : 05-02-2009 08:51 » |
|
zubr, Остаётся вопрос, как задаётся стиль текста в ячейке (не помню, есть ли такое свойство у ячейки, или это нужно свою матрицу хранить, чтобы при вызове StringGrid1DrawCell для нужной ячейки с нетривиальным стилем выводить что-то специфическое, а потом возвращать стиль в дефолт)?
думаю, надо создать динамический массив с некими дескрипторами стилей, в которых всё что на до описано, а для каждой ячейки сопоставить свойство - ID дескриптора
|
|
|
Записан
|
|
|
|
zubr
Гость
|
|
« Ответ #11 : 05-02-2009 09:34 » |
|
Вад, у него код этого обработчика приложен, там шрифты меняются в ячейках при определенных условиях if (ACol = 1)and(ARow = k) then with StringGrid1.Canvas do begin FillRect(Rect); //Изменяем атрибут шрифта Font.Style:= [fsBold]; TextOut(Rect.Left, Rect.Top, StringGrid1.Cells[ACol,ARow]); end;
Исходя из этого кода ничего тормозить не будет. Ведь по большому счету при перерисовке грид все равно для каждой видимой ячейки по новому отрисовывает текст, при скролинге опять происходит перерисовка. В видимую же часть окна входит не так много ячеек, что бы что то тормозило. Тут все что надо сделать - это по нажатию кнопки вызвать перерисовку и компонент перерисует видимую часть окна. При скролинге она сама перерисуется.
|
|
|
Записан
|
|
|
|
Вад
|
|
« Ответ #12 : 05-02-2009 09:38 » |
|
zubr, а фонт сам восстановится? В смысле, не надо ли сохранить стиль, а после TextOut вернуть на место?
|
|
|
Записан
|
|
|
|
zubr
Гость
|
|
« Ответ #13 : 05-02-2009 10:20 » |
|
Не надо. Так как компонент в своей внутренней части обработчика практически делает то же самое (TextOut), но для установки параметров прорисовки использует данные из внутренних переменных, которые пользователем устанавливаются из свойств. StringGrid1.Canvas.Font.Style:= [fsBold]; - данная же конструкция свойства шрифта компонента не меняет, а напрямую меняет параметры контекста компонента.
|
|
|
Записан
|
|
|
|
|