-
Notifications
You must be signed in to change notification settings - Fork 3
Commit
This commit does not belong to any branch on this repository, and may belong to a fork outside of the repository.
Add (unimplemented) coalesce_available_sections
This method will allow you to combine free sections within the bin. When working under a tight performance budget you have the ability to distribute this coalescing over multiple calculations. I don't need it quite yet, so I'll implement it later. But exposing it now in case someone else needs it and wants to implement it.
- Loading branch information
Showing
3 changed files
with
92 additions
and
0 deletions.
There are no files selected for viewing
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,84 @@ | ||
use crate::TargetBin; | ||
use std::ops::Range; | ||
|
||
impl TargetBin { | ||
/// Over time as you use [`TargetBin.push_available_bin_section`] to return remove packed | ||
/// rectangles from the [`TargetBin`], you may end up with neighboring bin sections that can | ||
/// be combined into a larger bin section. | ||
/// | ||
/// Combining bin sections in this was is desirable because a larger bin section allows you to | ||
/// place larger rectangles that might not fit into the smaller bin sections. | ||
/// | ||
/// In order to coalesce, or combine a bin section with other bin sections, we need to check | ||
/// every other available bin section to see if they are neighbors. | ||
/// | ||
/// This means that fully coalescing the entire list of available bin sections is O(n^2) time | ||
/// complexity, where n is the number of available empty sections. | ||
/// | ||
/// # Basic Usage | ||
/// | ||
/// ```ignore | ||
/// # use rectangle_pack::TargetBin; | ||
/// let target_bin = my_target_bin(); | ||
/// | ||
/// for idx in 0..target_bin.available_bin_sections().len() { | ||
/// let len = target_bin.available_bin_sections().len(); | ||
/// target_bin.coalesce_available_sections(idx, 0..len); | ||
/// } | ||
/// | ||
/// # fn my_target_bin () -> TargetBin { | ||
/// # TargetBin::new(1, 2, 3) | ||
/// # } | ||
/// ``` | ||
/// | ||
/// # Distributing the Workload | ||
/// | ||
/// It is possible that you are developing an application that can in some cases have a lot of | ||
/// heavily fragmented bins that need to be coalesced. If your application has a tight | ||
/// performance budget, such as a real time simulation, you may not want to do all of your | ||
/// coalescing at once. | ||
/// | ||
/// This method allows you to split the work over many frames by giving you fine grained control | ||
/// over which bin sections is getting coalesced and which other bin sections it gets tested | ||
/// against. | ||
/// | ||
/// So, for example, say you have an application where you want to fully coalesce the entire | ||
/// bin every ten seconds, and you are running at 60 frames per second. You would then | ||
/// distribute the coalescing work such that it would take 600 calls to compare every bin | ||
/// section. | ||
/// | ||
/// Here's a basic eample of splitting the work. | ||
/// | ||
/// ```ignore | ||
/// # use rectangle_pack::TargetBin; | ||
/// let target_bin = my_target_bin(); | ||
/// | ||
/// let current_frame: usize = get_current_frame() % 600; | ||
/// | ||
/// for idx in 0..target_bin.available_bin_sections().len() { | ||
/// let len = target_bin.available_bin_sections().len(); | ||
/// | ||
/// let start = len / 600 * current_frame; | ||
/// let end = start + len / 600; | ||
/// | ||
/// target_bin.coalesce_available_sections(idx, start..end); | ||
/// } | ||
/// | ||
/// # fn my_target_bin () -> TargetBin { | ||
/// # TargetBin::new(1, 2, 3) | ||
/// # } | ||
/// # | ||
/// # fn get_current_frame () -> usize { | ||
/// # 0 | ||
/// # } | ||
/// ``` | ||
/// | ||
/// [`TargetBin.push_available_bin_section`]: #method.push_available_bin_section | ||
// TODO: Write tests, implement then remove the "ignore" from the examples above. | ||
// Tests cases should have a rectangle and then a neighbor (above, below, left, right) and | ||
// verify that they get combined, but only if the comparison indices are correct and only if | ||
// the neighbor has the same width (uf above/below) or height (if left/right). | ||
pub fn coalesce_available_sections(bin_section_index: usize, compare_to_indices: Range<usize>) { | ||
unimplemented!() | ||
} | ||
} |