> For the complete documentation index, see [llms.txt](https://docs.degirum.com/llms.txt). Markdown versions of documentation pages are available by appending `.md` to page URLs; this page is available as [Markdown](https://docs.degirum.com/degirum-tools/tile_compound_models.md).

# Tile Compound Models

DeGirum Tools API Reference Guide. Process large images by tiling and combining model results.

{% hint style="info" %}
This API Reference is based on DeGirum Tools version 1.2.0.
{% endhint %}

## Tile Compound Models Module Overview <a href="#tile-compound-models-module-overview" id="tile-compound-models-module-overview"></a>

This module implements tiling-based compound models for object detection. It provides pseudo-models that extract image tiles and combine results from real detection models to efficiently process large images.

Key Features

* **Tile Extraction**: Generate local and global tiles with configurable overlap
* **Two-Stage Processing**: Run detection on each tile then merge results
* **Edge-Aware Fusion**: Optional fusion of detections near tile boundaries
* **Motion Filtering**: Skip tiles without motion to reduce computation
* **Result Management**: Translate box coordinates and apply NMS

Typical Usage

1. Create a `TileExtractorPseudoModel` with grid parameters
2. Wrap it in `TileModel` or a derived class along with a detection model
3. Iterate over `predict_batch` to obtain merged detection results

Integration Notes

* Designed for DeGirum PySDK models
* Works with compound model utilities such as cropping and NMS
* Supports customization of crop extent and overlap thresholds
* Compatible with local and cloud inference backends

Key Classes

* `TileExtractorPseudoModel`: Produces image tiles for downstream models
* `TileModel`: Runs detection on each tile and merges results
* `LocalGlobalTileModel`: Combines global and local tiles with size-based filtering
* `BoxFusionTileModel`: Fuses edge detections across tiles

Configuration Options

* Tile grid size and overlap
* Motion detection thresholds
* Edge fusion parameters
* NMS settings for final results

## Classes <a href="#classes" id="classes"></a>

## TileExtractorPseudoModel <a href="#tileextractorpseudomodel" id="tileextractorpseudomodel"></a>

`TileExtractorPseudoModel`

Bases: `ModelLike`

Extracts a grid of (optionally-overlapping) image tiles.

The class behaves like a DeGirum pseudo-model: instead of running inference it produces synthetic detection results whose bounding boxes correspond to tile coordinates. These results are then consumed by a second, real model in a two-stage compound pipeline.

Parameters:

| Name              | Type                          | Description                                                                                                                                                                     | Default    |
| ----------------- | ----------------------------- | ------------------------------------------------------------------------------------------------------------------------------------------------------------------------------- | ---------- |
| `cols`            | `int`                         | Number of columns in the tile grid.                                                                                                                                             | *required* |
| `rows`            | `int`                         | Number of rows in the tile grid.                                                                                                                                                | *required* |
| `overlap_percent` | `float`                       | Desired overlap between neighbouring tiles, expressed as a fraction in \[0, 1].                                                                                                 | *required* |
| `model2`          | `Model`                       | The downstream model that will receive each tile.                                                                                                                               | *required* |
| `global_tile`     | `bool`                        | If True, emit an additional tile that represents the entire image (label "GLOBAL"). Mutually exclusive with tile\_mask and motion\_detect. Defaults to False.                   | `False`    |
| `tile_mask`       | `list[int] \| None`           | Indices of tiles (0-based, row-major) to keep. Tiles not listed are skipped. Ignored when global\_tile is True.                                                                 | `None`     |
| `motion_detect`   | `MotionDetectOptions \| None` | Enable per-tile motion filtering. Tiles in which less than threshold x area pixels changed during the last look\_back frames are suppressed. Ignored when global\_tile is True. | `None`     |

Raises:

| Type             | Description                                   |
| ---------------- | --------------------------------------------- |
| `AssertionError` | If mutually-exclusive arguments are supplied. |

### TileExtractorPseudoModel Methods <a href="#tileextractorpseudomodel-methods" id="tileextractorpseudomodel-methods"></a>

#### \_\_init\_\_(cols, ...) <a href="#init" id="init"></a>

`__init__(cols, rows, overlap_percent, model2, *, global_tile=False, tile_mask=None, motion_detect=None)`

Constructor.

Parameters:

| Name              | Type                          | Description                                                                                                                                   | Default    |
| ----------------- | ----------------------------- | --------------------------------------------------------------------------------------------------------------------------------------------- | ---------- |
| `cols`            | `int`                         | Number of columns to divide the image into.                                                                                                   | *required* |
| `rows`            | `int`                         | Number of rows to divide the image into.                                                                                                      | *required* |
| `overlap_percent` | `float`                       | Desired overlap between neighbouring tiles.                                                                                                   | *required* |
| `model2`          | `Model`                       | Model which will be used as a second step of the compound model pipeline.                                                                     | *required* |
| `global_tile`     | `bool`                        | Indicates whether the global (whole) image should also be sent to model2.                                                                     | `False`    |
| `tile_mask`       | `list[int] \| None`           | Optional list of indices to keep during tile generation. Tile indices are counted starting from the top row to the bottom row, left to right. | `None`     |
| `motion_detect`   | `MotionDetectOptions \| None` | Motion detection options. When None, motion detection is disabled. When enabled, ROI boxes where motion is not detected will be skipped.      | `None`     |

#### predict\_batch(data) <a href="#predict_batch" id="predict_batch"></a>

`predict_batch(data)`

Perform whole inference lifecycle for all objects in given iterator object (for example, `list`).

Parameters:

| Name   | Type       | Description                                                                                                                                                               | Default    |
| ------ | ---------- | ------------------------------------------------------------------------------------------------------------------------------------------------------------------------- | ---------- |
| `data` | `Iterable` | Inference input data iterator object such as list or generator function. Each element returned by this iterator should be compatible to that regular PySDK model accepts. | *required* |

Yields:

| Type               | Description                                                                                  |
| ------------------ | -------------------------------------------------------------------------------------------- |
| `DetectionResults` | Combined inference result objects. This allows you directly using the result in `for` loops. |

## TileModel <a href="#tilemodel" id="tilemodel"></a>

`TileModel`

Bases: `CroppingAndDetectingCompoundModel`

Tiling wrapper that runs detection on every tile.

This compound model wires a TileExtractorPseudoModel (model 1) to a normal detection model (model 2). Each tile is cropped, passed to model 2, and the resulting boxes are translated back to the original image coordinates. Optionally, detections from model 1 can be merged or deduplicated via NMS.

Parameters:

| Name                 | Type                       | Description                                                                                    | Default                      |
| -------------------- | -------------------------- | ---------------------------------------------------------------------------------------------- | ---------------------------- |
| `model1`             | `TileExtractorPseudoModel` | The tile generator.                                                                            | *required*                   |
| `model2`             | `Model`                    | A detection model compatible with model1's image backend.                                      | *required*                   |
| `crop_extent`        | `float`                    | Extra context (percent of box size) to include around every tile before passing it to model 2. | `0`                          |
| `crop_extent_option` | `CropExtentOptions`        | How the extra context is applied.                                                              | `ASPECT_RATIO_NO_ADJUSTMENT` |
| `add_model1_results` | `bool`                     | If True, detections produced by model 1 are appended to the final result.                      | `False`                      |
| `nms_options`        | `NmsOptions \| None`       | Non-maximum suppression settings performed on the merged result.                               | `None`                       |

Attributes:

| Name                      | Type  | Description                                                                                          |
| ------------------------- | ----- | ---------------------------------------------------------------------------------------------------- |
| `output_postprocess_type` | `str` | Mirrors model2.output\_postprocess\_type so downstream tooling recognises this as a detection model. |

Raises:

| Type        | Description                                      |
| ----------- | ------------------------------------------------ |
| `Exception` | If the two models use different image back-ends. |

### TileModel Methods <a href="#tilemodel-methods" id="tilemodel-methods"></a>

#### \_\_init\_\_(model1, ...) <a href="#init" id="init"></a>

`__init__(model1, model2, *, crop_extent=0, crop_extent_option=CropExtentOptions.ASPECT_RATIO_NO_ADJUSTMENT, add_model1_results=False, nms_options=None)`

Constructor.

Parameters:

| Name                 | Type                       | Description                                                      | Default                      |
| -------------------- | -------------------------- | ---------------------------------------------------------------- | ---------------------------- |
| `model1`             | `TileExtractorPseudoModel` | Tile extractor pseudo-model.                                     | *required*                   |
| `model2`             | `Model`                    | PySDK object detection model.                                    | *required*                   |
| `crop_extent`        | `float`                    | Extent of cropping in percent of bbox size.                      | `0`                          |
| `crop_extent_option` | `CropExtentOptions`        | Method of applying extending crop to the input image for model2. | `ASPECT_RATIO_NO_ADJUSTMENT` |
| `add_model1_results` | `bool`                     | True to add detections of model1 to the combined result.         | `False`                      |
| `nms_options`        | `NmsOptions \| None`       | Non-maximum suppression (NMS) options.                           | `None`                       |

## LocalGlobalTileModel <a href="#localglobaltilemodel" id="localglobaltilemodel"></a>

`LocalGlobalTileModel`

Bases: `TileModel`

Runs a fine-/coarse tiling strategy with size-based result fusion.

Two kinds of tiles are produced:

* Local: the regular grid (fine resolution)
* Global: a single full-frame tile

After detection:

* Large objects (area >= large\_object\_threshold x image\_area) are kept only from the global tile.
* Small objects are kept only from the local tiles.

Parameters:

| Name                     | Type                       | Description                                                                                    | Default                      |
| ------------------------ | -------------------------- | ---------------------------------------------------------------------------------------------- | ---------------------------- |
| `model1`                 | `TileExtractorPseudoModel` | Must be configured with global\_tile=True.                                                     | *required*                   |
| `model2`                 | `Model`                    | Detection model run on each tile.                                                              | *required*                   |
| `large_object_threshold` | `float`                    | Area ratio separating "large" from "small" objects. Defaults to 0.01.                          | `0.01`                       |
| `crop_extent`            | `float`                    | Extra context (percent of box size) to include around every tile before passing it to model 2. | `0`                          |
| `crop_extent_option`     | `CropExtentOptions`        | How the extra context is applied.                                                              | `ASPECT_RATIO_NO_ADJUSTMENT` |
| `add_model1_results`     | `bool`                     | If True, detections produced by model 1 are appended to the final result.                      | `False`                      |
| `nms_options`            | `NmsOptions \| None`       | Non-maximum suppression settings performed on the merged result.                               | `None`                       |

Note

Unlike BoxFusionLocalGlobalTileModel, no edge fusion is applied; objects that overlap tile borders may be duplicated.

### LocalGlobalTileModel Methods <a href="#localglobaltilemodel-methods" id="localglobaltilemodel-methods"></a>

#### \_\_init\_\_(model1, ...) <a href="#init" id="init"></a>

`__init__(model1, model2, large_object_threshold=0.01, *, crop_extent=0, crop_extent_option=CropExtentOptions.ASPECT_RATIO_NO_ADJUSTMENT, add_model1_results=False, nms_options=None)`

Constructor.

Parameters:

| Name                     | Type                       | Description                                                                                                           | Default                      |
| ------------------------ | -------------------------- | --------------------------------------------------------------------------------------------------------------------- | ---------------------------- |
| `model1`                 | `TileExtractorPseudoModel` | Tile extractor pseudo-model.                                                                                          | *required*                   |
| `model2`                 | `Model`                    | PySDK object detection model.                                                                                         | *required*                   |
| `large_object_threshold` | `float`                    | A threshold to determine if an object is considered large or not. This is relative to the area of the original image. | `0.01`                       |
| `crop_extent`            | `float`                    | Extent of cropping in percent of bbox size.                                                                           | `0`                          |
| `crop_extent_option`     | `CropExtentOptions`        | Method of applying extending crop to the input image for model2.                                                      | `ASPECT_RATIO_NO_ADJUSTMENT` |
| `add_model1_results`     | `bool`                     | True to add detections of model1 to the combined result.                                                              | `False`                      |
| `nms_options`            | `NmsOptions \| None`       | Non-maximum suppression (NMS) options.                                                                                | `None`                       |

#### transform\_result2(result2) <a href="#transform_result2" id="transform_result2"></a>

`transform_result2(result2)`

Transform result of the **second model**.

This implementation combines results of the **second model** over all bboxes detected by the first model, translating bbox coordinates to original image coordinates.

Parameters:

| Name      | Type               | Description                               | Default    |
| --------- | ------------------ | ----------------------------------------- | ---------- |
| `result2` | `DetectionResults` | Detection result of the **second model**. | *required* |

Returns:

| Type                       | Description                                                                                                                                                                                           |
| -------------------------- | ----------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------- |
| `DetectionResults or None` | Combined results of the **second model** over all bboxes detected by the first model, where bbox coordinates are translated to original image coordinates. Returns None if no new frame is available. |

## BoxFusionTileModel <a href="#boxfusiontilemodel" id="boxfusiontilemodel"></a>

`BoxFusionTileModel`

Bases: `_EdgeMixin`, `TileModel`

TileModel with edge/overlap-aware bounding-box fusion.

After model 2 has produced detections for every tile, boxes whose centres fall within the user-defined edge band are compared with neighbours. If the 1-D IoU in either axis exceeds fusion\_threshold the boxes are merged (weighted-box fusion).

Parameters:

| Name                 | Type                       | Description                                                                                    | Default                      |
| -------------------- | -------------------------- | ---------------------------------------------------------------------------------------------- | ---------------------------- |
| `model1`             | `TileExtractorPseudoModel` | Tile generator.                                                                                | *required*                   |
| `model2`             | `Model`                    | Detection model.                                                                               | *required*                   |
| `edge_threshold`     | `float`                    | Size of the edge band expressed as a fraction of tile width/height. Defaults to 0.02.          | `0.02`                       |
| `fusion_threshold`   | `float`                    | 1-D IoU needed to fuse two edge boxes. Defaults to 0.8.                                        | `0.8`                        |
| `crop_extent`        | `float`                    | Extra context (percent of box size) to include around every tile before passing it to model 2. | `0`                          |
| `crop_extent_option` | `CropExtentOptions`        | How the extra context is applied.                                                              | `ASPECT_RATIO_NO_ADJUSTMENT` |
| `add_model1_results` | `bool`                     | If True, detections produced by model 1 are appended to the final result.                      | `False`                      |
| `nms_options`        | `NmsOptions \| None`       | Non-maximum suppression settings performed on the merged result.                               | `None`                       |

### BoxFusionTileModel Methods <a href="#boxfusiontilemodel-methods" id="boxfusiontilemodel-methods"></a>

#### \_\_init\_\_(model1, ...) <a href="#init" id="init"></a>

`__init__(model1, model2, edge_threshold=0.02, fusion_threshold=0.8, *, crop_extent=0, crop_extent_option=CropExtentOptions.ASPECT_RATIO_NO_ADJUSTMENT, add_model1_results=False, nms_options=None)`

Constructor.

Parameters:

| Name                 | Type                       | Description                                                                                                                                                                                                                                                                                                  | Default                      |
| -------------------- | -------------------------- | ------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------ | ---------------------------- |
| `model1`             | `TileExtractorPseudoModel` | Tile extractor pseudo-model.                                                                                                                                                                                                                                                                                 | *required*                   |
| `model2`             | `Model`                    | PySDK object detection model.                                                                                                                                                                                                                                                                                | *required*                   |
| `edge_threshold`     | `float`                    | A threshold to determine if an object is considered an edge detection or not. The edge\_threshold determines the amount of space next to the tiles edges where if a detection overlaps this space it is considered an edge detection. This edge space is relative (a percent) of the width/height of a tile. | `0.02`                       |
| `fusion_threshold`   | `float`                    | A threshold to determine whether or not to fuse two edge detections. This corresponds to the 1D-IoU of two boxes, of either dimension. If the boxes overlap in both dimensions and one of the dimension's 1D-IoU is greater than the fusion\_threshold, the boxes are fused.                                 | `0.8`                        |
| `crop_extent`        | `float`                    | Extent of cropping in percent of bbox size.                                                                                                                                                                                                                                                                  | `0`                          |
| `crop_extent_option` | `CropExtentOptions`        | Method of applying extending crop to the input image for model2.                                                                                                                                                                                                                                             | `ASPECT_RATIO_NO_ADJUSTMENT` |
| `add_model1_results` | `bool`                     | True to add detections of model1 to the combined result.                                                                                                                                                                                                                                                     | `False`                      |
| `nms_options`        | `NmsOptions \| None`       | Non-maximum suppression (NMS) options.                                                                                                                                                                                                                                                                       | `None`                       |

#### transform\_result2(result2) <a href="#transform_result2" id="transform_result2"></a>

`transform_result2(result2)`

Transform result of the **second model**.

This implementation combines results of the **second model** over all bboxes detected by the first model, translating bbox coordinates to original image coordinates.

Parameters:

| Name      | Type               | Description                               | Default    |
| --------- | ------------------ | ----------------------------------------- | ---------- |
| `result2` | `DetectionResults` | Detection result of the **second model**. | *required* |

Returns:

| Type                       | Description                                                                                                                                                                                           |
| -------------------------- | ----------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------- |
| `DetectionResults or None` | Combined results of the **second model** over all bboxes detected by the first model, where bbox coordinates are translated to original image coordinates. Returns None if no new frame is available. |

## BoxFusionLocalGlobalTileModel <a href="#boxfusionlocalglobaltilemodel" id="boxfusionlocalglobaltilemodel"></a>

`BoxFusionLocalGlobalTileModel`

Bases: `BoxFusionTileModel`

Local-/global-tiling plus edge fusion.

Combines the size-based filtering of LocalGlobalTileModel with the edge-aware fusion of BoxFusionTileModel.

Parameters:

| Name                     | Type                       | Description                                                                                    | Default                      |
| ------------------------ | -------------------------- | ---------------------------------------------------------------------------------------------- | ---------------------------- |
| `model1`                 | `TileExtractorPseudoModel` | Must output a global tile.                                                                     | *required*                   |
| `model2`                 | `Model`                    | Detection model.                                                                               | *required*                   |
| `large_object_threshold` | `float`                    | Area ratio that classifies a detection as "large". Defaults to 0.01.                           | `0.01`                       |
| `edge_threshold`         | `float`                    | Width of the edge band as a fraction of tile dimensions. Defaults to 0.02.                     | `0.02`                       |
| `fusion_threshold`       | `float`                    | 1-D IoU used by the fusion logic. Defaults to 0.8.                                             | `0.8`                        |
| `crop_extent`            | `float`                    | Extra context (percent of box size) to include around every tile before passing it to model 2. | `0`                          |
| `crop_extent_option`     | `CropExtentOptions`        | How the extra context is applied.                                                              | `ASPECT_RATIO_NO_ADJUSTMENT` |
| `add_model1_results`     | `bool`                     | If True, detections produced by model 1 are appended to the final result.                      | `False`                      |
| `nms_options`            | `NmsOptions \| None`       | Non-maximum suppression settings performed on the merged result.                               | `None`                       |

### BoxFusionLocalGlobalTileModel Methods <a href="#boxfusionlocalglobaltilemodel-methods" id="boxfusionlocalglobaltilemodel-methods"></a>

#### \_\_init\_\_(model1, ...) <a href="#init" id="init"></a>

`__init__(model1, model2, large_object_threshold=0.01, edge_threshold=0.02, fusion_threshold=0.8, *, crop_extent=0, crop_extent_option=CropExtentOptions.ASPECT_RATIO_NO_ADJUSTMENT, add_model1_results=False, nms_options=None)`

Constructor.

Parameters:

| Name                     | Type                       | Description                                                                                                                                                                                                                                                                                                  | Default                      |
| ------------------------ | -------------------------- | ------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------ | ---------------------------- |
| `model1`                 | `TileExtractorPseudoModel` | Tile extractor pseudo-model.                                                                                                                                                                                                                                                                                 | *required*                   |
| `model2`                 | `Model`                    | PySDK object detection model.                                                                                                                                                                                                                                                                                | *required*                   |
| `large_object_threshold` | `float`                    | A threshold to determine if an object is considered large or not. This is relative to the area of the original image.                                                                                                                                                                                        | `0.01`                       |
| `edge_threshold`         | `float`                    | A threshold to determine if an object is considered an edge detection or not. The edge\_threshold determines the amount of space next to the tiles edges where if a detection overlaps this space it is considered an edge detection. This edge space is relative (a percent) of the width/height of a tile. | `0.02`                       |
| `fusion_threshold`       | `float`                    | A threshold to determine whether or not to fuse two edge detections. This corresponds to the 1D-IoU of two boxes, of either dimension. If the boxes overlap in both dimensions and one of the dimension's 1D-IoU is greater than the fusion\_threshold, the boxes are fused.                                 | `0.8`                        |
| `crop_extent`            | `float`                    | Extent of cropping in percent of bbox size.                                                                                                                                                                                                                                                                  | `0`                          |
| `crop_extent_option`     | `CropExtentOptions`        | Method of applying extending crop to the input image for model2.                                                                                                                                                                                                                                             | `ASPECT_RATIO_NO_ADJUSTMENT` |
| `add_model1_results`     | `bool`                     | True to add detections of model1 to the combined result.                                                                                                                                                                                                                                                     | `False`                      |
| `nms_options`            | `NmsOptions \| None`       | Non-maximum suppression (NMS) options.                                                                                                                                                                                                                                                                       | `None`                       |

#### transform\_result2(result2) <a href="#transform_result2" id="transform_result2"></a>

`transform_result2(result2)`

Transform result of the **second model**.

This implementation combines results of the **second model** over all bboxes detected by the first model, translating bbox coordinates to original image coordinates.

Parameters:

| Name      | Type               | Description                               | Default    |
| --------- | ------------------ | ----------------------------------------- | ---------- |
| `result2` | `DetectionResults` | Detection result of the **second model**. | *required* |

Returns:

| Type                       | Description                                                                                                                                                                                           |
| -------------------------- | ----------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------- |
| `DetectionResults or None` | Combined results of the **second model** over all bboxes detected by the first model, where bbox coordinates are translated to original image coordinates. Returns None if no new frame is available. |
