Экспертная система Delphi.int.ru

Сообщество программистов
Общение, помощь, обмен опытом

Логин:
Пароль:
Регистрация | Забыли пароль?

Delphi.int.ru Expert

Другие разделы портала

Переход к вопросу:

#   

Статистика за сегодня:  


Лучшие эксперты

Подробнее »



Вопрос # 5 527

/ вопрос открыт /

Огромнейшее здравствуйте, эксперты!

Нужна серьёзная на мой взгляд помощь.

Проблема:
При программирования небольшого графического редактора, столкнулся с проблему добовления новых элементов уже имеющиеся примеры. В сути проблемы лежит следующее, мне нужно что бы в image при обрисовке добавлялось в нужной точке рисунок из image1, как бы получается такой эффект рисования кистью.Реализую следующим кодом,

 if checkbox1.Checked=true then
    begin
    if Button = mbLeft then
    Image.Canvas.BrushCopy(Rect(x-(Image1.Width div 2),
    y-(Image1.Height div 2), x+(Image1.Width div 2), y+(Image1.Height div 2)),
    Image.Picture.Bitmap, Rect(0, 0, Image1.Width, Image1.Height), 0);
    end;

После компиляции результат не совсем соответствует ожидаемому, вместо рисунка просто вставляется пустое пространство равное image1.

Как на ваш взгляд можно решить проблему???

Выполненные работы(исходный код с коментариями):
// ------------ Обработчик нажатия кнопки мыши на рисунке ----------------------
procedure TResForm.ImageMouseDown(Sender: TObject; Button: TMouseButton;
  Shift: TShiftState; X, Y: Integer);
begin
 case Button of // В зависимости от кнопки инициализируем глобальную переменную,
  mbLeft:RightButton:=False; // чтобы использовать её потом в других обработчиках,
  mbRight:RightButton:=True; // т.е. чертить примитивы цветом (FG) или фоном (BG).
 end; //case
 BeginPoint:=Point(x,y);     // Запоминаем начальную точку рисования
 case DrawOperation of       // В зависимости от выбранного инструмента:
  // Карандаш
  doPen:LastEndPoint:=Point(x,y);        // Запоминаем промежуточные точки для рисования карандашом
  // Заливка
  doFill:DrawFill(Image.Canvas,x,y);     // Делаем заливку с этой точки
  // Стёрка
  doEraser:Image.Canvas.Pen.Mode:=pmCopy;// Маска пера - сплошная
  // Кисть
  doBrush:begin
           LastEndPoint:=Point(x,y);     // Запоминаем промежуточные точки для рисования кистью
           Image.Canvas.Pen.Mode:=pmCopy;// Маска пера - сплошная
          end;
  // Всё остальное
  else begin
        LastEndPoint:=Point(-1,-1);  // Это нужно для немедленного выхода из процедур
                                     // DrawLine, DrawThickLine, DrawRectangle, DrawSelectRect,
                                     // DrawFillRectangle, DrawEllipse
        Image.Canvas.Pen.Mode:=pmNotXor; // Маска пера - xor-инверсная
        {Здесь - ключевой момент всей программы. Допустим мы хотим нарисовать точку на канве.
        Пусть, к примеру, цвет этой точки изначально равен $44B7C0, а цвет пера, допустим,
        равен $8AF607. Если маска пера (режим, Mode) равен pmCopy, то какой бы цвет
        изначально ни имела точка канвы, после рисования пером по ней она приобретёт
        цвет пера, т.е. $8AF607, а предыдущий цвет будет безвозвратно утерян. Так вот,
        маска (режим) пера pmNotXor применяется для восстановления исходного цвета точек
        после рисования по ним. Тут играет роль известное равенство:
        (A xor not B) xor not B = A. Т.е. если при режиме пера pmNotXor и цвете пера, равном
        $8AF607 = B нарисовать на точке цветом $44B7C0 = A, получим другой цвет: $31BE38.
        Теперь, чтобы восстановить первоначальный цвет точки, нарисуем на ней тем же цветом
        и режимом пера. Получим цвет $44B7C0, т.е. первоначальный цвет точки!
        В этой программе такие действия применяются, например, при рисовании отрезков,
        т.е. пользователь нажимает кнопку мыши, перемещает указатель. При каждом перемещении
        старая линия стирается и рисуется новая.}
       end;
 end; //case
 // Следующая ситуация возникает, когда пользователь выделил прямоугольный участок изображения,
 // потом (возможно) перетащил его в другое место и после этого нажал клавишу мыши
 // вне области выделения.
 if SelImage.Visible // Если сделано выделение (изображение выделения видимо)
  then with SelImage do
        begin
         PushUndo(Image.Picture); // Запоминаем откат
         // Копируем то, что выделено, на канву рисунка
         Image.Canvas.CopyRect(Rect(Left+1,Top+1,Left+Width-1,Top+Height-1),Canvas,Rect(1,1,Width-1,Height-1));
         Visible:=False; // Прячем выделение
        end;
 if DrawOperation<>doSelect // Если пользователь сделал что-то, кроме выделения,
  then PushUndo(Image.Picture); // запоминаем откат
 Drawed:=True; // Инициализируем глобальную переменную, показывающую
 
 if checkbox1.Checked=true then
    begin
    if Button = mbLeft then
    Image.Canvas.BrushCopy(Rect(x-(Image1.Width div 2),
    y-(Image1.Height div 2), x+(Image1.Width div 2), y+(Image1.Height div 2)),
    Image.Picture.Bitmap, Rect(0, 0, Image1.Width, Image1.Height), 0);
    end;
 
end;

Приложение:
  1.  


winner13 Вопрос ожидает решения (принимаются ответы, доступен мини-форум)

Вопрос задал: winner13 (статус: 1-ый класс)
Вопрос отправлен: 26 июля 2011, 12:40
Состояние вопроса: открыт, ответов: 0.


Мини-форум вопроса

Всего сообщений: 32; последнее сообщение — 28 июля 2011, 15:10; участников в обсуждении: 4.

Страницы: [1] [2] [Следующая »]

Gooddy

Gooddy (статус: 3-ий класс), 26 июля 2011, 13:07 [#1]:

Попробуй не BrushCopy а CopyRect.
Чисти код! Чисти код! Чисти код!
Gooddy

Gooddy (статус: 3-ий класс), 26 июля 2011, 13:14 [#2]:

checkbox1.Checked=true
Чисти код! Чисти код! Чисти код!
min@y™

min@y™ (статус: Доктор наук), 26 июля 2011, 13:19 [#3]:

Цитата (winner13):

Выполненные работы(исходный код с коментариями):

Ой, кросаффчег! Весь мой код 2002 года скопипастил! Программист от БОГА, честное пионерское! Даже вместе с комментариями! УМНИЦА, ТАК ДЕРЖАТЬ! Станешь великим программистом, палюбому! УВАЖУХА И РЕСПЕКТ! Да из таких, как ты, только гвозди делать, вся страна на таких держится! Молодчина!

// ------------ Обработчик нажатия кнопки мыши на рисунке ----------------------
procedure TMainForm.ImageMouseDown(Sender: TObject; Button: TMouseButton;
  Shift: TShiftState; X, Y: Integer);
begin
 case Button of // В зависимости от кнопки инициализируем глобальную переменную,
  mbLeft:RightButton:=False; // чтобы использовать её потом в других обработчиках,
  mbRight:RightButton:=True; // т.е. чертить примитивы цветом (FG) или фоном (BG).
 end; //case
 BeginPoint:=Point(x,y);     // Запоминаем начальную точку рисования
 case DrawOperation of       // В зависимости от выбранного инструмента:
  // Карандаш
  doPen:LastEndPoint:=Point(x,y);        // Запоминаем промежуточные точки для рисования карандашом
  // Заливка
  doFill:DrawFill(Image.Canvas,x,y);     // Делаем заливку с этой точки
  // Стёрка
  doEraser:Image.Canvas.Pen.Mode:=pmCopy;// Маска пера - сплошная
  // Кисть
  doBrush:begin
           LastEndPoint:=Point(x,y);     // Запоминаем промежуточные точки для рисования кистью
           Image.Canvas.Pen.Mode:=pmCopy;// Маска пера - сплошная
          end;
  // Всё остальное
  else begin
        LastEndPoint:=Point(-1,-1);  // Это нужно для немедленного выхода из процедур
                                     // DrawLine, DrawThickLine, DrawRectangle, DrawSelectRect,
                                     // DrawFillRectangle, DrawEllipse
        Image.Canvas.Pen.Mode:=pmNotXor; // Маска пера - xor-инверсная
        {Здесь - ключевой момент всей программы. Допустим мы хотим нарисовать точку на канве.
        Пусть, к примеру, цвет этой точки изначально равен $44B7C0, а цвет пера, допустим,
        равен $8AF607. Если маска пера (режим, Mode) равен pmCopy, то какой бы цвет
        изначально ни имела точка канвы, после рисования пером по ней она приобретёт
        цвет пера, т.е. $8AF607, а предыдущий цвет будет безвозвратно утерян. Так вот,
        маска (режим) пера pmNotXor применяется для восстановления исходного цвета точек
        после рисования по ним. Тут играет роль известное равенство:
        (A xor not B) xor not B = A. Т.е. если при режиме пера pmNotXor и цвете пера, равном
        $8AF607 = B нарисовать на точке цветом $44B7C0 = A, получим другой цвет: $31BE38.
        Теперь, чтобы восстановить первоначальный цвет точки, нарисуем на ней тем же цветом
        и режимом пера. Получим цвет $44B7C0, т.е. первоначальный цвет точки!
        В этой программе такие действия применяются, например, при рисовании отрезков,
        т.е. пользователь нажимает кнопку мыши, перемещает указатель. При каждом перемещении
        старая линия стирается и рисуется новая.}
       end;
 end; //case
 // Следующая ситуация возникает, когда пользователь выделил прямоугольный участок изображения,
 // потом (возможно) перетащил его в другое место и после этого нажал клавишу мыши
 // вне области выделения.
 if SelImage.Visible // Если сделано выделение (изображение выделения видимо)
  then with SelImage do
        begin
         PushUndo(Image.Picture); // Запоминаем откат
         // Копируем то, что выделено, на канву рисунка
         Image.Canvas.CopyRect(Rect(Left+1,Top+1,Left+Width-1,Top+Height-1),Canvas,Rect(1,1,Width-1,Height-1));
         Visible:=False; // Прячем выделение
        end;
 if DrawOperation<>doSelect // Если пользователь сделал что-то, кроме выделения,
  then PushUndo(Image.Picture); // запоминаем откат
 Drawed:=True; // Инициализируем глобальную переменную, показывающую
               // нажата ли левая кнопка мыши над рисунком (кнопка нажата, True).
end;
Делаю лабы и курсачи по Delphi и Turbo Pascal. За ПИВО! Пишите в личку, а лучше в аську. А ещё лучше - звоните в скайп!
Gooddy

Gooddy (статус: 3-ий класс), 26 июля 2011, 13:28 [#4]:

case Button of // В зависимости от кнопки инициализируем глобальную переменную,
  mbLeft:RightButton:=False; // чтобы использовать её потом в других обработчиках,
  mbRight:RightButton:=True; // т.е. чертить примитивы цветом (FG) или фоном (BG).
 end; //case

ЩИТО?

// Карандаш
  doPen

ЩИТО?
Чисти код! Чисти код! Чисти код!
Gooddy

Gooddy (статус: 3-ий класс), 26 июля 2011, 13:30 [#5]:

Ну ты минай перлов то наплодил! Жаль я свои старые исходники не нашёл. Там вообще жестянка небось.
Чисти код! Чисти код! Чисти код!
min@y™

min@y™ (статус: Доктор наук), 26 июля 2011, 13:35 [#6]:

Цитата (Gooddy):

Ну ты минай перлов то наплодил! Жаль я свои старые исходники не нашёл. Там вообще жестянка небось.

Это был курсач на заказ для подруги моей жены. Она попросила, чтобы исходник выглядел по-дилетантски. Вот я и поизвращался немножко.
Делаю лабы и курсачи по Delphi и Turbo Pascal. За ПИВО! Пишите в личку, а лучше в аську. А ещё лучше - звоните в скайп!
Gooddy

Gooddy (статус: 3-ий класс), 26 июля 2011, 13:40 [#7]:

Я думал что и ты простой смертный. Жаль что человек так бессовестно содрал и назвал 90% чужого кода (и не самого свежего (говнокод)) выполненной работой.
Чисти код! Чисти код! Чисти код!
min@y™

min@y™ (статус: Доктор наук), 26 июля 2011, 13:43 [#8]:

Цитата (Gooddy):

Я думал что и ты простой смертный.

А что, есть другие варианты?

Цитата (Gooddy):

Жаль что человек так бессовесно содрал и назвал 90% чужого кода

Мне тоже безмерно жаль!

Цитата (Gooddy):

и не самого свежего (говнокод)

Это даже не говнокод, это "кагбысдать и забыть".
Делаю лабы и курсачи по Delphi и Turbo Pascal. За ПИВО! Пишите в личку, а лучше в аську. А ещё лучше - звоните в скайп!
Gooddy

Gooddy (статус: 3-ий класс), 26 июля 2011, 13:46 [#9]:

Качественный говнокод. Порадовала конструкция
case Button of
  mbLeft:RightButton:=False; 
  mbRight:RightButton:=True; 
 end;
Чисти код! Чисти код! Чисти код!
Gooddy

Gooddy (статус: 3-ий класс), 26 июля 2011, 13:50 [#10]:

Кстати, МинайТМ, можно получить полный код?
Чисти код! Чисти код! Чисти код!
winner13

winner13 (статус: 1-ый класс), 26 июля 2011, 13:54 [#11]:

ребята , ребята, стопулики немного. Во первых Я копирайт указал, так что minay(tm) , может быть спокоен, в случае чего с ним свяжутся. =)

А ан счёт говно кода, я начинающий программист, нужно же мне чему-то учится, вот на примерах что мне сам минай(тм) и дал, я стараюсь что то сделать, не всем же дано от бога прям за месяц стать кодером высшей марки.(Я всего месяц как на делфе гоняю).Мне и на этом говно коде есть чему поучится.

П.С. Кстати выдрал из твоего редактора мета файлов general.pas со всем содержимым не изменял, и вот этот обработчик TMainForm.ImageMouseDown.
Не решимых проблем нет, есть неприятные для нас решения.
min@y™

min@y™ (статус: Доктор наук), 26 июля 2011, 14:04 [#12]:

Цитата (Gooddy):

Кстати, МинайТМ, можно получить полный код?

На кой хрен он тебе сдался-то?

Цитата (winner13):

не всем же дано от бога прям за месяц стать кодером высшей марки

НИКОМУ не дано!

Цитата (winner13):

Кстати выдрал из твоего редактора мета файлов general.pas со всем содержимым не изменял, и вот этот обработчик TMainForm.ImageMouseDown.

Да я уже выше писал, что ты молодец, гений и т.д. Не парься, всё правильно делаешь. Нахрена мне конкуренты?
Делаю лабы и курсачи по Delphi и Turbo Pascal. За ПИВО! Пишите в личку, а лучше в аську. А ещё лучше - звоните в скайп!
Gooddy

Gooddy (статус: 3-ий класс), 26 июля 2011, 14:07 [#13]:

min@y™: хочу захватить мир.
Чисти код! Чисти код! Чисти код!
min@y™

min@y™ (статус: Доктор наук), 26 июля 2011, 14:12 [#14]:

Цитата (winner13):

Я копирайт указал

ГДЕ?
Делаю лабы и курсачи по Delphi и Turbo Pascal. За ПИВО! Пишите в личку, а лучше в аську. А ещё лучше - звоните в скайп!
winner13

winner13 (статус: 1-ый класс), 26 июля 2011, 14:13 [#15]:

min@y™: Ё маё , да не обижайся ты, я просил помощи ты её оказал помнишь тогда в ирке???(звучи двусмысленно ну да ладно, кто как поймёт так поймёт).

Просто мне делат нечего не остаётся, на написания своего говнокода у меня уйдёт больше времяни и релаьно он ещё хуже чем твой в разы получится, считай я сейчас учусь на основе твоих исходников.

П.С. Я выбрал самый наихудший вариант своих действий из всего более херового что у меня имелось. По этому спасибо, и я бы был очень благодарен если бы ты мне помог разобраться, комментарии это одно, а сам автор это другое.
Не решимых проблем нет, есть неприятные для нас решения.
min@y™

min@y™ (статус: Доктор наук), 26 июля 2011, 14:13 [#16]:

Цитата (Gooddy):

хочу захватить мир.

Спроси у аффтара, он тебе скинет.
Как захватишь мир - сообщи. Устроюсь к тебе начальником. :)
Делаю лабы и курсачи по Delphi и Turbo Pascal. За ПИВО! Пишите в личку, а лучше в аську. А ещё лучше - звоните в скайп!
winner13

winner13 (статус: 1-ый класс), 26 июля 2011, 14:16 [#17]:

Копирайт в програмулине, я честнее чем ты думаешь. В списке авторов стоит пометка ников кто мне тут помогал и линк на ресурс.
Не решимых проблем нет, есть неприятные для нас решения.
Gooddy

Gooddy (статус: 3-ий класс), 26 июля 2011, 14:17 [#18]:

Программа как распространяться будет?
Чисти код! Чисти код! Чисти код!
min@y™

min@y™ (статус: Доктор наук), 26 июля 2011, 14:18 [#19]:

Цитата (winner13):

Ё маё , да не обижайся ты, я просил помощи ты её оказал

Да я не обижаюсь. Я уссываюсь!

Цитата (winner13):

Просто мне делат нечего не остаётся, на написания своего говнокода у меня уйдёт больше времяни и релаьно он ещё хуже чем твой в разы получится, считай я сейчас учусь на основе твоих исходников.

Вариант "мозги в положении ВКЛ" не катит? Странно, у меня всегда прокатывал. Что-то тут не то...

Цитата (winner13):

я бы был очень благодарен если бы ты мне помог разобраться, комментарии это одно, а сам автор это другое.

Ога, а наглость - второе счастье! У тебя готовая прога, разбирайся сам, там комментарии в каждой строке. А у меня работы дохрена + ещё 3 вагона. И ваще, я в отпуск хочу. Уже билет купил.
Делаю лабы и курсачи по Delphi и Turbo Pascal. За ПИВО! Пишите в личку, а лучше в аську. А ещё лучше - звоните в скайп!
min@y™

min@y™ (статус: Доктор наук), 26 июля 2011, 14:19 [#20]:

Цитата (Gooddy):

Программа как распространяться будет?

$100500, не меньше.
Делаю лабы и курсачи по Delphi и Turbo Pascal. За ПИВО! Пишите в личку, а лучше в аську. А ещё лучше - звоните в скайп!

Страницы: [1] [2] [Следующая »]

Чтобы оставлять сообщения в мини-форумах, Вы должны авторизироваться на сайте.

Версия движка: 2.6+ (26.01.2011)
Текущее время: 22 февраля 2025, 11:55
Выполнено за 0.04 сек.