6

画面に最適に表示したい、同じ比率でサイズの長方形のオブジェクトが動的に多数あります。オブジェクトのサイズを変更できますが、比率を維持する必要があります。

私は画面のサイズが何であるかを知っています。

画面を分割するために必要な行と列の最適な数と、オブジェクトをスケーリングするために必要なサイズを計算するにはどうすればよいですか?

ありがとう、

ジェイミー。

4

5 に答える 5

5

すべての長方形の寸法と方向が同じであり、変更しないでください。

遊ぼう!

// Proportion of the screen
// w,h width and height of your rectangles
// W,H width and height of the screen
// N number of your rectangles that you would like to fit in

// ratio
r = (w*H) / (h*W)

// This ratio is important since we can define the following relationship
// nbRows and nbColumns are what you are looking for
// nbColumns = nbRows * r (there will be problems of integers)
// we are looking for the minimum values of nbRows and nbColumns such that
// N <= nbRows * nbColumns = (nbRows ^ 2) * r
nbRows = ceil ( sqrt ( N / r ) ) // r is positive...
nbColumns = ceil ( N / nbRows )

私は私の数学が正しいことを願っていますが、それはあなたが探しているものから遠くはありません;)

編集:比率と幅と高さの間に大きな違いはありません...

// If ratio = w/h
r = ratio * (H/W)

// If ratio = h/w
r = H / (W * ratio)

次に、「r」を使用して、行と列がどれだけ使用されているかを調べます。

于 2009-10-05T14:56:46.243 に答える
2

これは、ここSOに関するケネスの質問とほぼ同じです。彼はまた彼のブログにそれを書いた

正方形をパックするように1次元で比率をスケーリングする場合、同じ問題になります。

于 2009-10-11T05:46:57.507 に答える
2

ジェイミー、私は「行と列の最適な数」を「必要な比率と画面サイズと一致する最大の長方形を提供する行と列の数」を意味すると解釈しました。その解釈のための簡単なアプローチを次に示します。

可能な選択肢 (四角形の行と列の数) ごとに、指定された比率で可能な最大サイズの四角形が得られます。可能な選択肢をループし、結果のサイズを計算すると、可能なソリューションの空間で単純な線形検索が実装されます。480 x 640 のサンプル画面と 3 x 5 の比率の長方形を使用して、これを行うコードを次に示します。

def min (a, b)
  a < b ? a : b
end

screenh, screenw = 480, 640
recth, rectw = 3.0, 5.0
ratio = recth / rectw

puts ratio

nrect = 14

(1..nrect).each do |nhigh|
  nwide = ((nrect + nhigh - 1) / nhigh).truncate
  maxh, maxw = (screenh / nhigh).truncate, (screenw / nwide).truncate
  relh, relw = (maxw * ratio).truncate, (maxh / ratio).truncate
  acth, actw = min(maxh, relh), min(maxw, relw)
  area = acth * actw
  puts ([nhigh, nwide, maxh, maxw, relh, relw, acth, actw, area].join("\t"))
end

そのコードを実行すると、次のトレースが提供されます。

1 14 480 45 27 800 27 45 1215
2 7 240 91 54 400 54 91 4914
3 5 160 128 76 266 76 128 9728
4 4 120 160 96 200 96 160 15360
5 3 96 213 127 160 96 160 15360
6 3 80 213 127 133 80 133 10640
7 2 68 320 192 113 68 113 7684
8 2 60 320 192 100 60 100 6000
9 2 53 320 192 88 53 88 4664
10 2 48 320 192 80 48 80 3840
11 2 43 320 192 71 43 71 3053
12 2 40 320 192 66 40 66 2640
13 2 36 320 192 60 36 60 2160
14 1 34 640 384 56 34 56 1904

このことから、4x4 または 5x3 レイアウトのいずれかが最大の長方形を生成することは明らかです。四角形のサイズ (行数の関数として) は、両端で最悪 (最小) になり、中間点で最良 (最大) になることも明らかです。長方形の数が少ないと仮定すると、選択した言語で上記の計算を単純にコーディングできますが、結果の面積が最大に達した後に減少し始めるとすぐに救済されます。

これは手っ取り早く汚い (しかし、かなり明白であることを願っています) 解決策です。四角形の数が気になるほど大きくなった場合は、さまざまな方法でパフォーマンスを調整できます。

  • より洗練された検索アルゴリズムを使用する (スペースを分割し、最適なセグメントを再帰的に検索する)、
  • プログラム中に四角形の数が増えている場合は、前の結果を保持し、近くのソリューションのみを検索します。
  • 少し計算を適用して、より高速で正確ですが、あまり明白ではない式を取得します。
于 2009-10-07T12:58:37.520 に答える
1

私が好んで行う方法の 1 つは、面積の平方根を使用することです。

させて

r = number of rectangles

w = width of display

h = height of display

それで、

A = (w * h) / rは四角形あたりの面積です

L = sqrt(A)各長方形の底辺の長さです。

それらが正方形でない場合は、それに応じて乗算して同じ比率を維持します。

同様のことを行う別の方法は、長方形の数の平方根を取ることです。これにより、グリッドの 1 つのディメンション (つまり、列の数) が得られます。

C = sqrt(n)グリッド内の列の数です

R = n / C行数です。

これらの 1 つが必要でceilingあり、もう1 つが必要であることに注意してくださいfloor

于 2009-10-05T14:36:38.037 に答える
0

行と列についての言及は、おそらくいくつかのスペース(たとえば、一番下の行の一部)が埋められていない状態で、長方形をグリッドに配置することを想定していたことを示唆しています。これが事実であると仮定します:

n(まだ不明な数) オブジェクトが画面全体に収まるようにオブジェクトをスケーリングするとします。それで

objectScale=screenWidth/(n*objectWidth)

ここで、N 個のオブジェクトがあると仮定すると、次のようになります。

nRows = ceil(N/n)

オブジェクトの行 (ceil はCeiling 関数)。

nRows*objectScale*objectHeight

垂直高さの。を見つける必要があり、この距離が より小さいn最小のものを選択したいと考えています。nscreenHeight

の単純な数式nは、天井関数の存在によって複雑になります。列の数がかなり少なくなる場合、おそらく最も簡単な方法は、不等式が満たされるまでn増加をループすることです。n

編集:上限でループを開始できます

floor(sqrt(N*objectHeight*screenWidth/(screenHeight*objectWidth)))

n について、下に作業します。解は O(sqrt(N)) で見つかります。O(1) ソリューションは、

nRows = N/n + 1

または取る

n=ceil(sqrt(N*objectHeight*screenWidth/(screenHeight*objectWidth)))

n(Matthieu M. の解) しかし、これらには の値が最適でない可能性があるという欠点があります。

境界ケースは、N=0、 、およびN=1オブジェクトの縦横比が次のような場合に発生objectHeight/objectWidth > screenHeight/screenWidthします。これらはどちらも簡単に処理できます。

于 2009-10-05T14:09:39.153 に答える