Форум: "Начинающим";
Текущий архив: 2010.02.28;
Скачать: [xml.tar.bz2];
Внизвывод части Bitmap Найти похожие ветки
← →
valussev@mail.ru (2009-12-24 19:06) [0]всем привет, возникла такая необходимость:
есть картинка в битмапе
область где должна быть выведена картинка разбита допустим на 16 равных квадратов
как сделать так, чтобы при нажатии на 1 из этих квадратов открывалась часть картинки из битмапа?
пробовал делать через массивы
pole: array[1..H, 1..W] of byte;
ex,ey: integer; // координаты пустой клетки
// правильное расположение клеток
stp : array[1..H, 1..W] of byte =
(( 1, 2, 3, 4),
( 5, 6, 7, 8),
( 9,10,11,12),
(13,14,15, 0));
for i:=1 to H do
for j:=1 to W do
pole[i,j] := stp[i,j];
но что то не получается
заранее спасибо
← →
RWolf © (2009-12-24 19:15) [1]закрыть рисунок 16-ю панелями; по нажатию на панель скрывать её.
← →
valussev@mail.ru (2009-12-24 19:18) [2]а как их тогда с маштабировать? если рисунок разных размеров?
← →
RWolf © (2009-12-24 20:29) [3]вызовом метода SetBounds.
← →
Джо © (2009-12-24 21:28) [4]Совершенно из вашего примера непонятно, как вы, собственно выводите картинку. Я бы сделал посредством BitBlt, очень удобно.
← →
Джо © (2009-12-24 21:30) [5]И зачем массивы?
У вас есть ширина-высота картинки, есть координаты, где щелкнул пользователь, есть равные квадраты. Определяете по координатам нужный квадрат и выводите его из заранее загруженной в TBitmap картинки.
← →
Amoeba © (2009-12-24 22:17) [6]
> RWolf © (24.12.09 19:15) [1]
>
> закрыть рисунок 16-ю панелями; по нажатию на панель скрывать
> её.
Это нерационально.
Все можно сделать предельно просто. Отрисовывать нужные части картинки в ячейках DrawGrid c GridLineWidth = 0 и DefaultDrawing = False (соответственно) в событии OnDrawCell (при этом в коде не должно быть if gdFocused in State then Canvas.DrawFocusRect(Rect);). Информацию о том, на каких ячейках щелкнули (и соответственно в каких рисовать) сохранять в двумерном массиве.
← →
Омлет © (2009-12-24 22:43) [7]> Все можно сделать предельно просто. Отрисовывать нужные
> части картинки в ячейках DrawGrid ...
весело )))
← →
Amoeba © (2009-12-24 23:00) [8]
> Омлет © (24.12.09 22:43) [7]
>
> > Все можно сделать предельно просто. Отрисовывать нужные
> > части картинки в ячейках DrawGrid ...
>
> весело )))
А что не так? Как раз случай использовать этот компонент по назначению. Не вижу причин для иронии.
← →
antonn © (2009-12-24 23:15) [9]Зачем использовать для этого контрол, да еще такой тяжеловесный?
← →
Amoeba © (2009-12-24 23:34) [10]
> antonn © (24.12.09 23:15) [9]
>
> Зачем использовать для этого контрол, да еще такой тяжеловесный?
>
И чего в нем тяжеловесного?
По-твоему, его следует использовать только ввода и отображения табличных данных, хранящихся в каком-либо контейнере?
Этот контрол идеально подходит, например, для написания собственного "Сапёра".
И для задач, подобным рассматриваемой, он также очень удобен.
← →
antonn © (2009-12-24 23:42) [11]сапера удобнее и быстрее рисовать прям на битмапе, DrawGrid костыль какой-то для этих дел...
сабж - http://desksoft.ru/index.php?downloads=attachments&id=247 (373кб)
← →
Не занят (2009-12-24 23:50) [12]Если реагирует на щелчки, значит и есть контрол. DrawGrid идеально подходит под задачу.
← →
{RASkov} © (2009-12-24 23:55) [13]DrawGrid +1
← →
antonn © (2009-12-24 23:56) [14]Я свой код дал, сделайте на DrawGrid, как это будет выглядеть идеально. Пожаааалуйста :)
← →
Amoeba © (2009-12-25 00:03) [15]
> antonn © (24.12.09 23:42) [11]
>
> сапера удобнее и быстрее рисовать прям на битмапе, DrawGrid
> костыль какой-то для этих дел...
Не смеши народ!
← →
antonn © (2009-12-25 00:08) [16]хочешь поспорить? :)
много саперов делал? :)
← →
Игорь Шевченко © (2009-12-25 00:09) [17]А для загрузки строк из файла нужно использовать TMemo
← →
Amoeba © (2009-12-25 00:14) [18]
> antonn © (24.12.09 23:56) [14]
>
> Я свой код дал, сделайте на DrawGrid, как это будет выглядеть
> идеально. Пожаааалуйста :)
Можно подумать, что у меня сейчас нет дел более важных, нежели заниматься написанием хоть и простенького, не ненужного мне кода. В свое время программировал аналогичную, но существенно более сложную задачу именно на основе DrawGrid.
Ты бы взял и сам сделал для сравнения на DrawGrid. Ничего сложного. Заодно бы опыта и новых знаний набрался и свою квалификацию повысил. Сам бы себе пользу принес.
А теперь заканчиваю дискуссию и пойду дописывать серьезную научную статью.
← →
antonn © (2009-12-25 00:15) [19]
> Ты бы взял и сам сделал для сравнения на DrawGrid. Ничего
> сложного. Заодно бы опыта и новых знаний набрался и свою
> квалификацию повысил. Сам бы себе пользу принес.
а мне есть с чем сравнивать.
Игорь хороший пример привел с Tmemo, из пушки по воробьям
← →
Amoeba © (2009-12-25 00:16) [20]
> antonn © (25.12.09 00:08) [16]
>
> хочешь поспорить? :)
> много саперов делал? :)
Делал куда более сложные вещи. А с тобой спорить - не много ли для тебя чести будет?
← →
antonn © (2009-12-25 00:17) [21]
> А с тобой спорить - не много ли для тебя чести будет?
отличный способ вести беседу, сразу чувствуется уважение и опыт.
← →
Не занят (2009-12-25 00:23) [22]
> а мне есть с чем сравнивать.
> Игорь хороший пример привел с Tmemo, из пушки по воробьям
TMemo - для показа и редактирования текста.
DrawGrid - для рисования клеток.
← →
Игорь Шевченко © (2009-12-25 00:24) [23]Я наверное чего-то не понимаю, для отображения в DrawGrid исходную картинку нужно будет разбивать на части, не правда ли ?
А если есть картинка, разбитая на части, почему бы не выводить ее сразу в битмап ?
← →
Игорь Шевченко © (2009-12-25 00:25) [24]Не занят (25.12.09 00:23) [22]
TMemo - для чтения строк из файла. Невидимый. Memo.Lines.LoadFromFile, обработка, Memo.Lines.SaveToFile
← →
Не занят (2009-12-25 00:32) [25]
> Игорь Шевченко © (25.12.09 00:24) [23]
> Я наверное чего-то не понимаю, для отображения в DrawGrid
> исходную картинку нужно будет разбивать на части, не правда
> ли ?
> А если есть картинка, разбитая на части, почему бы не выводить
> ее сразу в битмап ?
Контрол нужен - картинку показать пользователю, отреагировать на щелчки пользователя.
В DrawGrid уже есть готовые клетки, меньше работы.
В DrawGrid из "лишнего" и "тяжелого", отличающего его от других контролов - только эти самые клетки, которые иначе придется реализовывать самописным кодом. Почему бы не использовать?
← →
antonn © (2009-12-25 00:35) [26]потому что сначала нужно попробывать ;)
чтобы показать кратинку отлично подходит paintbox.
преобразовать координаты клика в номера "кубиков" - простейшая операция.
зато когда речь зайдет об эффектах открытия...
← →
Игорь Шевченко © (2009-12-25 00:36) [27]Не занят (25.12.09 00:32) [25]
Пример в студию
← →
Игорь Шевченко © (2009-12-25 00:38) [28]В DrawGrid наверное хорошо показывать много картинок, заранее неизвестного количества.
Типа thumbnails каких-нибудь.
← →
{RASkov} © (2009-12-25 00:48) [29]
unit Unit1;
interface
uses
Windows, Messages, SysUtils, Variants, Classes, Graphics, Controls, Forms,
Dialogs, StdCtrls, Grids;
type
TForm1 = class(TForm)
Button1: TButton;
StringGrid1: TStringGrid;
procedure Button1Click(Sender: TObject);
procedure FormCreate(Sender: TObject);
procedure StringGrid1DrawCell(Sender: TObject; ACol, ARow: Integer;
Rect: TRect; State: TGridDrawState);
procedure StringGrid1SelectCell(Sender: TObject; ACol, ARow: Integer;
var CanSelect: Boolean);
private
BMP: TBitMap;
{ Private declarations }
public
{ Public declarations }
end;
var
Form1: TForm1;
implementation
{$R *.dfm}
procedure TForm1.FormCreate(Sender: TObject);
begin
BMP:=TBitmap.Create;
StringGrid1.FixedCols:=0;
StringGrid1.FixedRows:=0;
StringGrid1.GridLineWidth:=0;
StringGrid1.DefaultRowHeight:=StringGrid1.DefaultColWidth;
StringGrid1.Width:=(StringGrid1.DefaultColWidth*StringGrid1.ColCount)+StringGrid1.ColCount;
StringGrid1.Height:=(StringGrid1.DefaultRowHeight*StringGrid1.RowCount)+StringGrid1.RowCount;
end;
procedure TForm1.Button1Click(Sender: TObject);
begin
with TOpenDialog.Create(nil) do try
Filter:="Bmp Files|*.bmp";
if Execute then begin
BMP.LoadFromFile(FileName);
StringGrid1.Invalidate;
end;
finally
Free;
end;
end;
procedure TForm1.StringGrid1DrawCell(Sender: TObject; ACol, ARow: Integer;
Rect: TRect; State: TGridDrawState);
begin
with Sender as TStringGrid do begin
if StringGrid1.Cells[ACol, ARow]="1" then Canvas.CopyRect(Rect, BMP.Canvas, Rect)
else begin
Canvas.Brush.Color:=clBlue;
Canvas.FillRect(Rect);
end;
end;
end;
procedure TForm1.StringGrid1SelectCell(Sender: TObject; ACol,
ARow: Integer; var CanSelect: Boolean);
begin
if StringGrid1.Cells[ACol, ARow]="1" then StringGrid1.Cells[ACol, ARow]:=""
else StringGrid1.Cells[ACol, ARow]:="1";
end;
end.
← →
antonn © (2009-12-25 00:52) [30]большая пушка, 150мм.
А главное в DrawGrid нету Cells[]
← →
{RASkov} © (2009-12-25 00:53) [31]не, я не призываю пользовать грид..... просто как альтернатива :)
и нужно понимать, что в [29] - это не готовый результат или даже не пример вообще, а просто намек... :о)
← →
{RASkov} © (2009-12-25 00:56) [32]> [30] antonn © (25.12.09 00:52)
> А главное в DrawGrid нету Cells[]
это не страшно
← →
Не занят (2009-12-25 01:00) [33]
> Игорь Шевченко © (25.12.09 00:36) [27]
> Не занят (25.12.09 00:32) [25]
>
> Пример в студию
>
>
Делфи, к сожалению, у меня нет на компьютере, вот что то набросал от руки. Это псевдокод, за точность названий методов и порядков параметров в них не ручаюсь.В CellClick
Opened[Col, Row] := True;
Grid.InvalidateCell(Col, Row);
В DrawCell
if Opened[Col, Row] then
Grid.Canvas.CopyRect(Source, CellRect, NumToPixels(Row, Col))
else
Grid.Canvas.FillRect(...)
function NumToPixels(Col, Row): TRect;
var
cellSize: Extended;
begin
cellSize := Source.Width / Grid.ColCount;
Result.Left := cellSize * Col;
Result.Width := Result.Left + cellSize;;
cellSize := Source.Height / Grid.ColCount;
Result.Top := cellSize * Col;
Result.Bottom := Result.Top + cellSize;;
end;
← →
Amoeba © (2009-12-25 01:26) [34]
> Игорь Шевченко © (25.12.09 00:24) [23]
>
> Я наверное чего-то не понимаю, для отображения в DrawGrid
> исходную картинку нужно будет разбивать на части, не правда
> ли ?
> А если есть картинка, разбитая на части, почему бы не выводить
> ее сразу в битмап ?
Заранее картинка ни на какие части не разбивается, просто отрисовывается только та ее часть, которая должна попасть в конкретную клетку.
← →
Германн © (2009-12-25 01:32) [35]Откуда такой спор на пустом месте?
Дельфи - это RAD-инструмент или как? Если RAD, то для ответа на частный вопрос вполне подходит способ с применением стандартного контрола (TDrawGrid), даже если количество "ячеек" заранее известно.
Делали (шахматы), знаем :)
А вот если бы в саже была озвучена конкретная задача, тогда бы был смысл в споре "что и как применять".
← →
Не занят (2009-12-25 01:36) [36]Картинку можно заранее порезать на квадратики, и поместить их в ImageList. Тогда ещё будет.
ImageIndex = Row * RowCount + Col
← →
Игорь Шевченко © (2009-12-25 01:36) [37]Amoeba © (25.12.09 01:26) [34]
> Заранее картинка ни на какие части не разбивается, просто
> отрисовывается только та ее часть, которая должна попасть
> в конкретную клетку.
Если честно - не вижу разницы. Под разбиванием я имел в виду не размещение по нескольким битмапам, а определение координат той части, которая должна быть нарисована.
Пример хотелось бы увидеть. Работающий.
← →
Не занят (2009-12-25 01:41) [38]А что этот пример даст? Понятно, что можно и так и так написать, и в этом простом случае сложность примеров не особо будет отличаться. Здесь вопрос глубже, идеологический. RAD или не RAD?
← →
Amoeba © (2009-12-25 01:43) [39]
> Не занят (25.12.09 01:36) [36]
>
> Картинку можно заранее порезать на квадратики, и поместить
> их в ImageList. Тогда ещё будет.
> ImageIndex = Row * RowCount + Col
А если картинка не одна единственная, а их несколько (даже одного размера)? Будем каждую заранее резать и запихивать в ImageList?
← →
Не занят (2009-12-25 01:47) [40]
> Amoeba © (25.12.09 01:43) [39]
Я же написал можно, а не нужно. Понятно, что от деталей зависит...
← →
Amoeba © (2009-12-25 01:51) [41]
> Игорь Шевченко © (25.12.09 01:36) [37]
> Пример хотелось бы увидеть. Работающий.
Есть один проект, к сожалению оставшийся незавершенным по независящим от меня обстоятельствам. Между прочим, картинка в битмап не грузится, файл отображается в память и прямо из него делается отрисовка в ячейках. Код работает. Кода много, а выковыривать нужную для демонстрации часть жалко времени, да и просто лень.
← →
Amoeba © (2009-12-25 01:55) [42]
> Не занят (25.12.09 01:47) [40]
>
>
> > Amoeba © (25.12.09 01:43) [39]
>
>
> Я же написал можно, а не нужно. Понятно, что от деталей
> зависит...
Не вижу предмета для спора. Полностью согласен.
← →
Игорь Шевченко © (2009-12-25 02:26) [43]Раз все такие ленивые, сделал я:
unit main;
interface
uses
Windows, Messages, SysUtils, Variants, Classes, Graphics, Controls, Forms,
Dialogs, Grids;
type
TForm1 = class(TForm)
Grid: TDrawGrid;
procedure FormCreate(Sender: TObject);
procedure GridDrawCell(Sender: TObject; ACol, ARow: Integer; Rect: TRect;
State: TGridDrawState);
procedure GridSelectCell(Sender: TObject; ACol, ARow: Integer;
var CanSelect: Boolean);
procedure FormResize(Sender: TObject);
private
FOriginalImage: TBitmap;
FWorkerImage: TBitmap;
//Это сделано намерено тупо
FOpened: array[0..10, 0..10] of Boolean;
procedure ResizeGrid;
end;
var
Form1: TForm1;
implementation
type TGridCracker = class(TCustomGrid) end;
{$R *.dfm}
procedure TForm1.FormCreate(Sender: TObject);
begin
FOriginalImage := TBitmap.Create;
FOriginalImage.LoadFromFile(".\core17.bmp");
ResizeGrid;
end;
function NumToPixels(Grid: TDrawGrid; Col, Row: Integer): TRect;
begin
Result.Left := Grid.DefaultColWidth * Col;
Result.Right := Result.Left + Grid.DefaultColWidth;
Result.Top := Grid.DefaultRowHeight * Row;
Result.Bottom := Result.Top + Grid.DefaultRowHeight;
end;
procedure TForm1.FormResize(Sender: TObject);
begin
FWorkerImage.Free;
ResizeGrid;
end;
procedure TForm1.GridDrawCell(Sender: TObject; ACol, ARow: Integer; Rect: TRect;
State: TGridDrawState);
begin
if FOpened[ACol, ARow] then
Grid.Canvas.CopyRect(Rect, FWorkerImage.Canvas, NumToPixels(Grid, ACol, ARow))
else
begin
Grid.Canvas.Brush.Color := clBlack;
Grid.Canvas.FillRect(Rect);
end;
end;
procedure TForm1.GridSelectCell(Sender: TObject; ACol, ARow: Integer;
var CanSelect: Boolean);
begin
FOpened[ACol, ARow] := not FOpened[ACol, ARow];
TGridCracker(Grid).InvalidateCell(ACol, ARow);
end;
procedure TForm1.ResizeGrid;
begin
FWorkerImage := TBitmap.Create;
FWorkerImage.Width := Grid.ClientWidth;
FWorkerImage.Height := Grid.ClientHeight;
FWorkerImage.Canvas.StretchDraw(
Rect(0, 0, FWorkerImage.Width, FWorkerImage.Height),
FOriginalImage);
Grid.DefaultRowHeight := Grid.ClientHeight div Grid.RowCount;
Grid.DefaultColWidth := Grid.ClientWidth div Grid.ColCount;
end;
end.
Что не понравилось - не нашел метода перерисовки отдельной ячейки у DrawGrid.
Что понравилось - возможность изменения размера под размер формы, без особенных ухищрений.
То есть, по сути, тот же PaintBox, только с отдельным окном.
← →
Германн © (2009-12-25 02:30) [44]
> Игорь Шевченко © (25.12.09 02:26) [43]
>
> Раз все такие ленивые, сделал я:
>
И что у тебя "чесалось" :)
← →
Игорь Шевченко © (2009-12-25 02:36) [45]Германн © (25.12.09 02:30) [44]
Гондурас, разумеется
← →
Германн © (2009-12-25 03:00) [46]
> Игорь Шевченко © (25.12.09 02:36) [45]
Мне бы твои проблемы :)
← →
MonoLife © (2009-12-25 05:33) [47]
> {RASkov} © (25.12.09 00:48) [29]
+1 Я тоже люблю StringGrid:)
Страницы: 1 2 вся ветка
Форум: "Начинающим";
Текущий архив: 2010.02.28;
Скачать: [xml.tar.bz2];
Память: 0.58 MB
Время: 0.006 c