C++ CMake C
Switch branches/tags
Nothing to show
Clone or download
Fetching latest commit…
Cannot retrieve the latest commit at this time.

README.md

B2dPipe

2D Pipeline Compiler.

Introduction

B2dPipe is a 2D pipeline compiler written in C++. It's part of Blend2D project, but was designed to be used independently of it. The library itself doesn't depend on Blend2D and was especially designed to be used by other 2D rendering engines as a software rendering backend.

B2dPipe is not designed to be used as a '2d context', the library doesn't provide one. It only provides parts to construct pipelines dynamically. The pipeline compiler uses AsmJit as a backend and attaches to an existing instance of its CodeCompiler. This means that a very minimal knowledge of AsmJit is required to use the library. Since the pipeline compiler attaches to an existing CodeCompiler it's possible to construct multiple pipelines at the same time or to embed a pipeline into an existing function.

Disclaimer

This library should be considered a work-in-progress. It's used by Blend2D engine and all renderings shown on blend2d.com website were rendered by B2dPipe. However, the library still doesn't support all possible pixel fetches so use with caution. TODO list can be found at the end of this page.

Also, the library doesn't implement its own rasterizer, it just defines structures it can use to fill a rectangle or to consume "cells" produced by an analytic rasterizer like FreeType, AGG, or Blend2D. The rasterizer that is used by Blend2D will be most probably released as a separate project as well.

Building

You need the following libraries:

By default all build scripts and CMakeLists.txt assume that dependencies are located at the same directory level as b2dpipe. Thus, the safest example of building b2dpipe would be:

git clone https://github.com/asmjit/asmjit.git
git clone https://github.com/blend2d/b2dpipe.git

cd b2dpipe
mkdir build
cmake .. -G"Unix Makefiles" -DCMAKE_BUILD_TYPE="Release" -DASMJIT_DIR="../../asmjit" -DB2DPIPE_BUILD_TEST=1
make

B2dPipe uses cmake as as build system, but the source code (including asmjit) can be just added to any project if required as both projects don't need anything special to compile. By default B2dPipe embeds AsmJit, so you don't need to compile it separately.

Architecture

The library is based on the following main concepts:

  • PipePart
    • A single part (e.g. building block) of the pipeline.
    • Specializes into the following:
      • FillPart - Describes what to fill.
      • FetchPart - Describes the source and/or destination of the pipeline.
      • CombinePart - Describes how to combine (composite or blend) two pixels with an optional mask.
  • PipeCompiler
    • Responsible for defining the pipeline's body.
    • Holds information about the pipeline optimization level and other data that is used to adjust various settings of all pipeline parts it uses.
    • Contains a link to the root part, which must be of FillPart type.

The pipeline compiler produces functions of the following signature:

void (__cdecl* RenderFunc)(void* ctxData, void* fillData, const void* fetchData);

Where:

  • ctxData
    • Context data, should be of b2dpipe::ContextData type
    • Holds pixel pointers and other information that is required to sucessfully write to the target buffer.
    • This structure can be used to hold additional information related to combining operator in the future.
    • Never changed by built-in parts, however, it's allowed that third-party parts change the content during the rendering if they are designed that way.
  • fillData
    • Fill data, should be b2dpipe::FillData type:
      • FillData::BoxAA - Data used to describe axis-aligned rectangle to be filled.
      • FillData::BoxAU - Data used to describe axis-unaligned rectangle to be filled.
      • FillData::Analytic - Data used to describe area and coverage that comes from rasterizers such as FreeType and AntiGrain (Blend2D uses the same approach at the moment).
    • Never changed by built-in parts, however, it's allowed that third-party fillers change the content during the rendering as it's common in rasterizers that use active edge table (AET).
  • fetchData
    • Fetch data, should of b2dpipe::FetchData type:
      • FetchData::Solid - Data used to fetch solid fills, compatible with uint32_t* or uint64_t* (depending on target pixel format).
      • FetchData::Gradient - Data used to fetch linear, radial, or conical gradient.
      • FetchData::Texture - Data used to fetch texture either axis-aligned, translated, or transformed.
    • should not be changed during rendering, hence marked const.

Builtins

The pipeline compiler supports all it defines in b2dpipe/globals.h.

TODO List

Features Pending:

  • Pixel Format - A8 destination is not yet implemented
  • Pixel Format - XRGB32 destination is sometimes treated wrongly as PRGB32
  • Texture Fetch - Most of texture fetch operations can only work with 1 pixel at a time
  • Texture Fetch - It treats pixels as 32-bit quantities, that should be abstracted out
  • Texture Fetch - Texture feflection doesn't work for affine blits
  • Texture Fetch - Affine fetches currently require SSE4.1 (some tricks would be needed to make them working on SSE2 hardware), grep for TODO: SSE4.1 to see the relevant code
  • FillType - There should be FillData::Spans fill-type, that would just traverse horizontal spans that can be produced by any kind of rasterizer
  • FillType - Should the analytic rasterizer be part of B2dPipe?

Refactorization:

  • Make CombinePart abstract and move its functionality out.
  • Make intrinsic for rsub (A = B - A), it's used quite often.

API Usage

There is a test/b2dpipe_test.cpp application that shows basic pipeline construction and produces some images.

Authors & Maintainers