use crate::chan::Channel;
use std::any::Any;
pub trait Blend: Any + Copy + Clone {
fn composite<C: Channel>(dst: &mut C, da1: C, src: &C, sa1: C);
}
#[derive(Clone, Copy)]
pub struct Src;
#[derive(Clone, Copy)]
pub struct Dest;
#[derive(Clone, Copy)]
pub struct SrcOver;
#[derive(Clone, Copy)]
pub struct DestOver;
#[derive(Clone, Copy)]
pub struct SrcOut;
#[derive(Clone, Copy)]
pub struct DestOut;
#[derive(Clone, Copy)]
pub struct SrcIn;
#[derive(Clone, Copy)]
pub struct DestIn;
#[derive(Clone, Copy)]
pub struct SrcAtop;
#[derive(Clone, Copy)]
pub struct DestAtop;
#[derive(Clone, Copy)]
pub struct Xor;
#[derive(Clone, Copy)]
pub struct Clear;
#[derive(Clone, Copy)]
pub struct Plus;
impl Blend for Src {
fn composite<C: Channel>(dst: &mut C, _da1: C, src: &C, _sa1: C) {
*dst = *src;
}
}
impl Blend for Dest {
fn composite<C: Channel>(_dst: &mut C, _da1: C, _src: &C, _sa1: C) {
}
}
impl Blend for SrcOver {
fn composite<C: Channel>(dst: &mut C, _da1: C, src: &C, sa1: C) {
*dst = *src + *dst * sa1;
}
}
impl Blend for DestOver {
fn composite<C: Channel>(dst: &mut C, da1: C, src: &C, _sa1: C) {
*dst = *src * da1 + *dst;
}
}
impl Blend for SrcOut {
fn composite<C: Channel>(dst: &mut C, da1: C, src: &C, _sa1: C) {
*dst = *src * da1;
}
}
impl Blend for DestOut {
fn composite<C: Channel>(dst: &mut C, _da1: C, _src: &C, sa1: C) {
*dst = *dst * sa1;
}
}
impl Blend for SrcIn {
fn composite<C: Channel>(dst: &mut C, da1: C, src: &C, _sa1: C) {
let da = C::MAX - da1;
*dst = *src * da;
}
}
impl Blend for DestIn {
fn composite<C: Channel>(dst: &mut C, _da1: C, _src: &C, sa1: C) {
let sa = C::MAX - sa1;
*dst = *dst * sa;
}
}
impl Blend for SrcAtop {
fn composite<C: Channel>(dst: &mut C, da1: C, src: &C, sa1: C) {
let da = C::MAX - da1;
*dst = *src * da + *dst * sa1;
}
}
impl Blend for DestAtop {
fn composite<C: Channel>(dst: &mut C, da1: C, src: &C, sa1: C) {
let sa = C::MAX - sa1;
*dst = *src * da1 + *dst * sa;
}
}
impl Blend for Xor {
fn composite<C: Channel>(dst: &mut C, da1: C, src: &C, sa1: C) {
*dst = *src * da1 + *dst * sa1;
}
}
impl Blend for Clear {
fn composite<C: Channel>(dst: &mut C, _da1: C, _src: &C, _sa1: C) {
*dst = C::default();
}
}
impl Blend for Plus {
fn composite<C: Channel>(dst: &mut C, _da1: C, src: &C, _sa1: C) {
*dst = *src + *dst;
}
}