Это называется 2D Strip Packing, над которым работал Мартелло. Если вы выполните поиск в Google по их статье, их алгоритм должен быть довольно простым для реализации. Один из способов сделать это - решить вашу проблему с помощью ветвления и привязки. Сначала вычислите жадное решение, чтобы получить максимальную высоту, необходимую вашей упаковке.
Ваш алгоритм должен сначала найти многообещающий набор x-координат, а затем найти y-координаты для ваших прямоугольников. Другими словами, для каждого прямоугольника ответвляются все возможные x-координаты, которые вы можете назначить. В любой момент времени вы можете сохранить сумму общей высоты, занимающую любую конкретную x-координату (это называется кумулятивным ограничением), и обрезать, если высота превышает вашу максимальную глобальную высоту. Для каждого полного решения по x-координатам, где были назначены x-координаты всех прямоугольников, теперь вы можете попытаться найти действительные y-координаты. Вы можете сделать это таким же образом, разветвляя для каждого прямоугольника различные возможные координаты y, обрезая, когда вы знаете, что два прямоугольника перекрывают друг друга. В нижней части дерева вы найдете координаты x и y для ваших прямоугольников, в которых вы можете вычислить требуемую высоту и обновить максимальную верхнюю границу.
Если вы сохраняли текущее решение всякий раз, когда обновляли верхнюю границу, то, когда ваш алгоритм завершается, у вас будет оптимальное решение.