私は小さな問題で立ち往生しています。
2つのことを想像してください:フォーム、カバーする必要がある - カバーフォーム。 Cover-Form-Tilesをカバーするフォームが含まれます。 私の主な目標は、私のカバーフォームをタイルでカバーすることです。それでタイルのように見えます。私はこのイメージを以下のイメージで説明します
イエローはカバーフォーム、茶色のフォーム - タイルです。このイメージでは、フォームが互いに接近しすぎて配置されていることがわかります。フォーム間には空きスペースがありません。それだけが必要。
しかし、私が同じ効果に到達しようとすると、満足できない結果しか得られません。下の画像に表示されます
2番目の画像に最後のタイルの後にオフセットがあります。それはフォームのサイズが異なるために起こります。 Cover-Formの幅は正確に分かりません。私は単にCover-Formの全幅を3つに分割します。しかし、Cover-Formの幅が173ピクセルの場合、各タイルの幅は173/3 = 57.6ピクセルになります。これは58に丸められますが、58 * 3 = 174になります。デルファイのフォームの位置計算の誤り
以下のコードは、2番目の画像と同様に状況を実行します。
type
TTileArray = Array of Array of TPoint;
// This routine comes here from David's answer below and were changed by me
procedure EvenlySpacedTiles(PixelCountH, PixelCountV, TileCount: Integer; var ArrayOut: TTileArray);
var
X: Integer;
Y: Integer;
OldH: Integer;
OldV: Integer;
OldCount: Integer;
OldCount1: Integer;
TempInt: Integer;
begin
if (PixelCountH) or (PixelCountV) or(TileCount) = 0 then
Exit;
OldH := PixelCountH;
OldCount1 := TileCount;
for X:=Low(ArrayOut) to High(ArrayOut) do
begin
OldV := PixelCountV;
OldCount := TileCount;
TempInt := OldH div OldCount1;
Dec(OldH, TempInt);
Dec(OldCount1);
for Y:=Low(ArrayOut) to High(ArrayOut) do
begin
ArrayOut[X, Y] := Point(TempInt, OldV div OldCount);
Dec(OldV, ArrayOut[X, Y].Y);
Dec(OldCount);
end;
end;
end;
procedure TForm1.Button1Click(Sender: TObject);
var
F: TForm;
P: TForm;
Delta: Integer;
PrevLeft: Integer;
PrevTop: Integer;
X:Integer;
Y: Integer;
Arr: TTileArray;
IncLeft: Integer;
begin
Delta := 3;
F := TForm.Create(Application);
F.BorderStyle := Forms.bsNone;
F.SetBounds(0, 0, 173, 115);
F.Position := poDesktopCenter;
F.Color := $11DFEE;
F.Show;
SetLength(Arr, Delta, Delta);
EvenlySpacedTiles(F.Width, F.Height, Delta, Arr);
PrevLeft := F.Left;
PrevTop := F.Top;
IncLeft := 0;
for X:=Low(Arr) to High(Arr) do
begin
PrevTop := F.Top;
Inc(PrevLeft, IncLeft);
for Y:=Low(Arr) to High(Arr) do
begin
P := TForm.Create(Application);
P.FormStyle := fsStayOnTop;
P.BorderStyle := Forms.bsNone;
P.Color := Random($FFFFFF);//clSkyBlue;
P.Show;
P.Width := Arr[X, Y].X;
P.Height := Arr[X, Y].Y;
P.Left := PrevLeft;
P.Top := PrevTop;
P.Canvas.Rectangle(P.ClientRect);
Inc(PrevTop, Arr[X, Y].y);
IncLeft := Arr[X, Y].X;
end;
end;
end;
だから私の質問があります:どのように私は独立してカバーフォームの幅のすべてのタイル(行あたり3)の幅を調整することができますか?
ありがとうございます。
編集
P.S. 上記のコードの一部を変更しました。今では、非常に小さくて大きなカバーフォームの幅(67ピクセルから)でも完璧に動作します。 〜1237 px もちろん、このコードを改善する方法がありますが、主な目標が達成されています。 明日のタイルタイルを完成させて、この部分を公開することができると思います。
多くの点で、David氏のコメントは私にこれをどうやって行うかという考えを与えてくれます。ありがとう、デイビッド!
P.S.
私はDavidの最初のコメントを斜めに読んだので、別の方法で動作するようにコードを更新しますが、結果はまだ良くありません。あなたは下の写真でそれを見ることができます。
最初のタイルは57ピクセルです。幅; 2番目のもの - 59 px。 3番目のタイル - わずか31ピクセル。
Davidのコメントで提案されているアルゴリズムを使って、タイルを正しく配置する方法がわかりません。
P.S.S.
また、結果はありません。
右の赤い線は、最後のタイルの大きなサイズを示しています。各タイルの幅は58ピクセルです。
デビットはこれを書いています:
173/3 = 58です。 173-58 = 115。 115/2 = 58となる。 115-58 = 57。 57/1 = 57
実生活で計算することはできますが、コードで実装することはできません。
ソースコードが更新されました。
P.S.S.S.
ダビデの手続きは、何をすべきかをしません。下の図はそれを示しています。
最初のタイルと2番目のタイルとの間には隙間があり、前の画像と同じように右側に赤い線があります。
p.S.S.S.S.
この時点で、私の仕事の最初の部分が達成されます。もう1つはタイルを追加することですが、本当に必要なのかどうかはわかりません。そして、これに感謝してDavid Heffernan !!彼は私にいくつかのことを説明するのにとても時間を費やしています。そして、私は彼が単に「ありがとう」よりももっと彼に言いたいことを知らない。私は恐れるだけで、彼の評判を高め、答えとして彼のポストを受け入れることができます。それは本当に仕事です! 絵で私達は私が
を必要な結果を見ることができますP.S.S.S.S.S.S.
私はソースコードを更新しているので、タイルも垂直に配置することができます。
173は3で割り切れるわけではありません。Ergo、各列に同じ幅を使用することはできません。代わりに、このようにします。 Npxピクセルで開始します。 Ncolで割る、ラウンド。その値をカラム0に使用します.Npxからその値を減算し、Ncol-1で割ります。その値を丸めて列1に使用します。ピクセルと列がなくなるまで繰り返します。 –
また、簡潔にするために省略した理由がない限り、それぞれのタイルを別々のフォームに実装することはありません。代わりに、図形などを使用してください。 – DNR
@DavidHeffernan、あなたは次の状況を意味しますよね?私はCover-Formの幅が173ピクセルであるとします。私は1列に3つのタイルを配置する必要があることを知っているので、173/3 = 57で割ります。これは各タイルの幅です。そして、私は3タイルを57に乗算して171を得る。私は171が173未満であることを知っている。この事実に従って、私はこれを行うべきである:173 - 171 = 2。これは最後のタイルの後のサイズの場所で、イメージなので、最後のTIleの幅を広げてCover-Formに完全にフィットさせるだけです。この方法についてどう思いますか? – Dima