class HexaPDF::Layout::BoxFitter

  • If there are remaining boxes and fit results, some boxes were able to fit.
    - If there are remaining boxes but no fit results, the first box could not be fitted.
    - If there are no remaining boxes, all boxes were successfully fitted into the frames.
    methods can be used to get the result:
    * Once all boxes have been fitted, the #fit_results, #remaining_boxes and #fit_successful?
    * Then use the #fit method to fit boxes one after the other. No drawing is done.
    * First one needs to add the frame objects via #<< or provide them on initialization.
    == Usage
    frames for content.
    other in them. Such functionality is useful, for example, for boxes that provide multiple
    A BoxFitter instance contains an array of Frame objects and allows placing boxes one after the

def <<(frame)

Add the given frame to the list of frames.
def <<(frame)
  @frames << frame
  @initial_frame_y << frame.y
  @content_heights << 0
end

def content_heights

Returns an array with the heights of the content of each frame.
def content_heights
  @content_heights
end

def fit(box)

Fits the given box at the current location.
def fit(box)
  unless @remaining_boxes.empty?
    @remaining_boxes << box
    return
  end
  while (current_frame = @frames[@frame_index])
    result = current_frame.fit(box)
    if result.success?
      current_frame.remove_area(result.mask)
      @content_heights[@frame_index] = [@content_heights[@frame_index],
                                        @initial_frame_y[@frame_index] - result.mask.y].max
      @fit_results << result
      box = nil
      break
    elsif current_frame.full?
      @frame_index += 1
    else
      draw_box, box = current_frame.split(result)
      if draw_box
        current_frame.remove_area(result.mask)
        @content_heights[@frame_index] = [@content_heights[@frame_index],
                                          @initial_frame_y[@frame_index] - result.mask.y].max
        @fit_results << result
      elsif !current_frame.find_next_region
        @frame_index += 1
      end
    end
  end
  @remaining_boxes << box if box
end

def fit_successful?

Returns +true+ if all boxes were successfully fitted.
def fit_successful?
  @remaining_boxes.empty?
end

def initialize(frames = [])

Creates a new BoxFitter object for the given +frames+.
def initialize(frames = [])
  @frames = []
  @content_heights = []
  @initial_frame_y = []
  @frame_index = 0
  @fit_results = []
  @remaining_boxes = []
  frames.each {|frame| self << frame }
end