Форум программистов
 

Восстановите пароль или Зарегистрируйтесь на форуме, о проблемах и с заказом рекламы пишите сюда - alarforum@yandex.ru, проверяйте папку спам!

Вернуться   Форум программистов > Delphi программирование > Общие вопросы Delphi
Регистрация

Восстановить пароль
Повторная активизация e-mail

Купить рекламу на форуме - 42 тыс руб за месяц

Ответ
 
Опции темы Поиск в этой теме
Старый 03.12.2013, 19:42   #1
Alex2009
Proger Man
Форумчанин
 
Аватар для Alex2009
 
Регистрация: 07.03.2009
Сообщений: 584
По умолчанию Перемещение текста по canvas

Приветствую, уважаемые.
Нужна ваша помощь, так как у самого ума не хватает как это реализовать с канвой раньше не имел дела.
Такова суть, есть изображение на canvas, затем я вывожу на него текст. Задача такова что мне нужно перемещать этот текст по изображению, что бы была возможность вручную позиционировать его с помощью мыши.

Код:
procedure TForm1.Button2Click(Sender: TObject);
var
  pic: TPicture;
  Rec:TRect;
begin
  pic := TPicture.Create;
  // Путь к изображению
  pic.LoadFromFile('F:\899264883.jpg');

  // Узнаем размер изображения
  Rec.Top:=0;
  Rec.Left:=0;
  Rec.Width := PaintBox1.Width;
  Rec.Height := PaintBox1.Height;

  // Выводим изображение
  PaintBox1.Canvas.Draw(0,0,pic.Graphic);
  PaintBox1.Canvas.StretchDraw(Rec,Pic.Graphic);
  pic.Free;
end;

procedure TForm1.Button1Click(Sender: TObject);
begin
  PaintBox1.Canvas.brush.style:=bsClear;
  PaintBox1.Canvas.Font.Name:='Impact';
  PaintBox1.Canvas.Font.Size := 22;
  PaintBox1.Canvas.Font.color:=clWhite;
  PaintBox1.Canvas.TextOut(0,0,Edit1.Tex);
end;
ShowMessage('Добро пожаловать!');

Последний раз редактировалось Alex2009; 03.12.2013 в 19:47.
Alex2009 вне форума Ответить с цитированием
Старый 03.12.2013, 20:31   #2
phomm
personality
Старожил
 
Аватар для phomm
 
Регистрация: 28.04.2009
Сообщений: 2,882
По умолчанию

Вот тема с подобными вопросами http://programmersforum.ru/showthread.php?t=243215
Возможно, пригодится.
Ну а в целом, ничего сложного в задаче нет. Нужны обработчики событий нажатия отпускания и движения мышки, нужен флаг нажатия мыши и переменная для хранения координат.
При нажатии мыши запомнить во флаг, при отжатии снять флаг. При движении мыши проверять если флаг поставлен - переместить координаты на те, что пришли в событии (там они параметрами), и вызвать перерисовку.
В перерисовке нарисовать картинку, поверх в нужных координатах текст.
phomm вне форума Ответить с цитированием
Старый 03.12.2013, 20:43   #3
Аватар
Старожил
 
Аватар для Аватар
 
Регистрация: 17.11.2010
Сообщений: 18,922
По умолчанию

Проще текст прозрачным лэйбом перемещать примерно так (jpeg в uses не забыть)
Код:
var Picture: TPicture;
    Moved: Boolean;
    Xstart,Ystart: Integer;

procedure TForm1.FormCreate(Sender: TObject);
begin
  Picture:=TPicture.Create;
  Picture.LoadFromFile('Кошак.jpg');
  Moved:=False;
  DoubleBuffered:=True;
  Label1.Transparent:=True;
end;

procedure TForm1.FormDestroy(Sender: TObject);
begin
  Picture.Free;
end;

procedure TForm1.Label1MouseDown(Sender: TObject; Button: TMouseButton;
  Shift: TShiftState; X, Y: Integer);
begin
  Xstart:=X;
  Ystart:=Y;
  Moved:=True;
end;

procedure TForm1.Label1MouseUp(Sender: TObject; Button: TMouseButton;
  Shift: TShiftState; X, Y: Integer);
begin
  Moved:=False;
end;

procedure TForm1.Label1MouseMove(Sender: TObject; Shift: TShiftState; X,
  Y: Integer);
var i: Integer;
begin
  if Moved then begin
    i:=Label1.Left-Xstart+X;
    if i<PaintBox1.Left then i:=PaintBox1.Left
    else if i+Label1.Width>PaintBox1.Left+PaintBox1.Width then i:=PaintBox1.Left+PaintBox1.Width-Label1.Width;
    Label1.Left:=i;
    i:=Label1.Top-Ystart+Y;
    if i<PaintBox1.Top then i:=PaintBox1.Top
    else if i+Label1.Height>PaintBox1.Top+PaintBox1.Height then i:=PaintBox1.Top+PaintBox1.Height-Label1.Height;
    Label1.Top:=i;
  end;
end;

procedure TForm1.PaintBox1Paint(Sender: TObject);
begin
  PaintBox1.Canvas.StretchDraw(PaintBox1.ClientRect,Picture.Graphic);
end;
Если бы архитекторы строили здания так, как программисты пишут программы, то первый залетевший дятел разрушил бы цивилизацию
Аватар вне форума Ответить с цитированием
Старый 03.12.2013, 21:00   #4
Alex2009
Proger Man
Форумчанин
 
Аватар для Alex2009
 
Регистрация: 07.03.2009
Сообщений: 584
По умолчанию

Разве с помощью Label я смогу сохранить потом изображение с наложенным текстом?
ShowMessage('Добро пожаловать!');
Alex2009 вне форума Ответить с цитированием
Старый 03.12.2013, 21:11   #5
Аватар
Старожил
 
Аватар для Аватар
 
Регистрация: 17.11.2010
Сообщений: 18,922
По умолчанию

Почему нет, спокойно. Сохраняя например канвас паинтбокса через промежуточный битмап
Если бы архитекторы строили здания так, как программисты пишут программы, то первый залетевший дятел разрушил бы цивилизацию
Аватар вне форума Ответить с цитированием
Старый 03.12.2013, 21:23   #6
Alex2009
Proger Man
Форумчанин
 
Аватар для Alex2009
 
Регистрация: 07.03.2009
Сообщений: 584
По умолчанию

а можно то же самое но без label, в задании нужно использовать именно canvas. Получилось только сделать при нажатии ЛКМ создание текста по координатам. Но старый текст остается. Читал о перерисовке, но так и не понял что к чему.

И чисто для себя спрошу "промежуточный битмап" какая функция?
ShowMessage('Добро пожаловать!');
Alex2009 вне форума Ответить с цитированием
Старый 03.12.2013, 21:53   #7
Аватар
Старожил
 
Аватар для Аватар
 
Регистрация: 17.11.2010
Сообщений: 18,922
По умолчанию

Без лейбла почти также, точно знать рект текста и те же события, только на паинтбоксе. Промежуточный битмап - копирование с канвас паинтбокса в битмар, а от туда в файл
Если бы архитекторы строили здания так, как программисты пишут программы, то первый залетевший дятел разрушил бы цивилизацию
Аватар вне форума Ответить с цитированием
Старый 03.12.2013, 22:04   #8
Alex2009
Proger Man
Форумчанин
 
Аватар для Alex2009
 
Регистрация: 07.03.2009
Сообщений: 584
По умолчанию

Код:
procedure CanvasTextShadowBorder(Canvas:TCanvas; text:string;x,y:integer; sh_color: TColor = 0; width: integer = 2);
var c:TColor; st:TBrushStyle;
begin
  With Canvas do begin
    c:=Font.Color;
    st:=Brush.Style;
    Font.Color:=sh_color;
    TextOut(x+width,y+width,text);
    Brush.Style:=bsClear;
    TextOut(x-width,y-width,text);
    TextOut(x+width,y-width,text);
    TextOut(x-width,y+width,text);
    Canvas.Font.Color:=c;
    TextOut(x,y,text);
    Brush.Style:=st;
  end;
end;

procedure TForm1.Button1Click(Sender: TObject);
begin
  PaintBox1.Canvas.brush.style:=bsClear;
  PaintBox1.Canvas.Font.Name:='Impact';
  PaintBox1.Canvas.Font.Size := 22;
  PaintBox1.Canvas.Font.color:=clWhite;

  CanvasTextShadowBorder(PaintBox1.Canvas,Edit1.Text,Xstart,Ystart);
end;

procedure TForm1.FormCreate(Sender: TObject);
begin
  DoubleBuffered := True;
  pic:=TPicture.Create;
  pic.LoadFromFile('F:\Изображения\Сообщество влюбленных\Для мемов\899264883.jpg');
  Moved:=False;
end;

procedure TForm1.FormDestroy(Sender: TObject);
begin
  pic.Free;
end;

procedure TForm1.PaintBox1MouseDown(Sender: TObject; Button: TMouseButton;
  Shift: TShiftState; X, Y: Integer);
begin
  Xstart:=X;
  Ystart:=Y;
  Moved:=True;
end;

procedure TForm1.PaintBox1MouseMove(Sender: TObject; Shift: TShiftState; X,
  Y: Integer);
var i: Integer;
begin
  if Moved then begin
     {i:=Label1.Left-Xstart+X;
      if i<PaintBox1.Left then i:=PaintBox1.Left
        else if i+Label1.Width>PaintBox1.Left+PaintBox1.Width then i:=PaintBox1.Left+PaintBox1.Width-Label1.Width;
          Label1.Left:=i;
          i:=Label1.Top-Ystart+Y;
      if i<PaintBox1.Top then i:=PaintBox1.Top
        else if i+Label1.Height>PaintBox1.Top+PaintBox1.Height then i:=PaintBox1.Top+PaintBox1.Height-Label1.Height;
        Label1.Top:=i; }
  end;
end;

procedure TForm1.PaintBox1MouseUp(Sender: TObject; Button: TMouseButton;
  Shift: TShiftState; X, Y: Integer);
begin
  Moved:=False;
end;

procedure TForm1.PaintBox1Paint(Sender: TObject);
begin
  PaintBox1.Canvas.StretchDraw(PaintBox1.ClientRect,Pic.Graphic);
end;
Не пойму PaintBox1MouseMove что там менять, тобишь Label1.Left, Label1.Top если делаю через канву? пробовал такое CanvasTextShadowBorder(PaintBox1.Ca nvas,Edit1.Text,Xstart+X,Ystart+Y); но не помогает.
ShowMessage('Добро пожаловать!');

Последний раз редактировалось Alex2009; 03.12.2013 в 22:16.
Alex2009 вне форума Ответить с цитированием
Старый 03.12.2013, 22:59   #9
Аватар
Старожил
 
Аватар для Аватар
 
Регистрация: 17.11.2010
Сообщений: 18,922
По умолчанию

Цитата:
но не помогает
И не поможет, не туда смотрите. В OnMouseDown оценить на тексте ли курсор мыши, для этого и знать рект текста. И только если на тексте запускать перемещение. В OnMouseMove пересчитывать новое положение текста и его рект соответственно и выполнять Paint паинтбокса, прорисовівать картинку и текст в OnPaint
Если бы архитекторы строили здания так, как программисты пишут программы, то первый залетевший дятел разрушил бы цивилизацию

Последний раз редактировалось Аватар; 03.12.2013 в 23:01.
Аватар вне форума Ответить с цитированием
Старый 03.12.2013, 23:39   #10
Alex2009
Proger Man
Форумчанин
 
Аватар для Alex2009
 
Регистрация: 07.03.2009
Сообщений: 584
По умолчанию

Много непонятного для меня вы сказали, извините но с канвой не работал ранее, мне сетевое по душе)
Можете дать наглядный пример, или ссылку на тот же "рект" так как для меня не понятно что это и как получить, и все остальное.
ShowMessage('Добро пожаловать!');
Alex2009 вне форума Ответить с цитированием
Ответ


Купить рекламу на форуме - 42 тыс руб за месяц



Похожие темы
Тема Автор Раздел Ответов Последнее сообщение
Поиск текста с копированием ячеек типа ВПР но для сложного текста! Elkin_087 Microsoft Office Excel 1 24.06.2012 22:06
перемещение текста syrga Общие вопросы Delphi 3 05.05.2012 02:26
Выбор последнего записанного текста (именно текста а не значения) из соседнего листа Uralmaster Microsoft Office Excel 1 28.01.2011 21:06
Выравнивание текста в canvas Чай_ник Помощь студентам 2 06.12.2010 00:38
перемещение текста по монитору StakanpORTvejna Общие вопросы Delphi 5 12.10.2008 17:59