Skip to content
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
14 changes: 10 additions & 4 deletions Cargo.toml
Original file line number Diff line number Diff line change
Expand Up @@ -5,18 +5,24 @@ version = "1.4.3"
authors = ["DarthSim <darthsim@gmail.com>"]
edition = "2024"
license-file = "LICENSE"
repository="https://github.com/DarthSim/quantizr"
repository = "https://github.com/DarthSim/quantizr"

[lib]
name = "quantizr"

[dependencies]
hashbrown = { version = "0.16.1", default-features = false }
num-traits = { version = "0.2.19", default-features = false, features = ["libm"] }

[features]
default = ["std"]
std = []
capi = ["std"]

[profile.release]
opt-level = 3
lto = true
debug = false
debug-assertions = false

[features]
"capi" = []

# See more keys and their definitions at https://doc.rust-lang.org/cargo/reference/manifest.html
13 changes: 7 additions & 6 deletions src/capi.rs
Original file line number Diff line number Diff line change
@@ -1,6 +1,7 @@
#![allow(clippy::missing_safety_doc)]

use std::slice;
use alloc::boxed::Box;
use core::slice;

use crate::error::Error;
use crate::histogram::Histogram;
Expand All @@ -17,7 +18,7 @@ pub enum QuantizrError {
QuantizrBufferTooSmall = 1,
}

impl std::convert::From<Error> for QuantizrError {
impl From<Error> for QuantizrError {
fn from(error: Error) -> Self {
match error {
Error::ValueOutOfRange => Self::QuantizrValueOutOfRange,
Expand Down Expand Up @@ -131,20 +132,20 @@ pub unsafe extern "C" fn quantizr_remap(

#[unsafe(no_mangle)]
pub extern "C" fn quantizr_free_result(result: Box<QuantizeResult>) {
std::mem::drop(result)
drop(result)
}

#[unsafe(no_mangle)]
pub extern "C" fn quantizr_free_histogram(hist: Box<Histogram>) {
std::mem::drop(hist)
drop(hist)
}

#[unsafe(no_mangle)]
pub extern "C" fn quantizr_free_image(image: Box<Image>) {
std::mem::drop(image)
drop(image)
}

#[unsafe(no_mangle)]
pub extern "C" fn quantizr_free_options(options: Box<Options>) {
std::mem::drop(options)
drop(options)
}
12 changes: 8 additions & 4 deletions src/cluster.rs
Original file line number Diff line number Diff line change
@@ -1,3 +1,7 @@
use alloc::vec::Vec;
#[cfg(not(feature = "std"))]
use num_traits::Float;

use crate::ord_float::OrdFloat32;

use crate::histogram::{Histogram, HistogramEntry};
Expand Down Expand Up @@ -186,7 +190,7 @@ impl<'clust> Cluster<'clust> {
#[inline(always)]
fn add_color(dst: &mut [f32; 4], src: &[f32; 4], weight: f32) {
unsafe {
use std::arch::x86_64::*;
use core::arch::x86_64::*;

let mut psrc = _mm_loadu_ps(src.as_ptr());
let mut pdst = _mm_loadu_ps(dst.as_ptr());
Expand All @@ -203,7 +207,7 @@ fn add_color(dst: &mut [f32; 4], src: &[f32; 4], weight: f32) {
#[inline(always)]
fn add_color(dst: &mut [f32; 4], src: &[f32; 4], weight: f32) {
unsafe {
use std::arch::aarch64::*;
use core::arch::aarch64::*;

let mut psrc = vld1q_f32(src.as_ptr());
let mut pdst = vld1q_f32(dst.as_ptr());
Expand Down Expand Up @@ -232,7 +236,7 @@ fn add_color(dst: &mut [f32; 4], src: &[f32; 4], weight: f32) {
#[inline(always)]
fn add_diff(dst: &mut [f32; 4], a: &[f32; 4], b: &[f32; 4], weight: f32) {
unsafe {
use std::arch::x86_64::*;
use core::arch::x86_64::*;

let pa = _mm_loadu_ps(a.as_ptr());
let pb = _mm_loadu_ps(b.as_ptr());
Expand All @@ -256,7 +260,7 @@ fn add_diff(dst: &mut [f32; 4], a: &[f32; 4], b: &[f32; 4], weight: f32) {
#[inline(always)]
fn add_diff(dst: &mut [f32; 4], a: &[f32; 4], b: &[f32; 4], weight: f32) {
unsafe {
use std::arch::aarch64::*;
use core::arch::aarch64::*;

let pa = vld1q_f32(a.as_ptr());
let pb = vld1q_f32(b.as_ptr());
Expand Down
8 changes: 6 additions & 2 deletions src/colormap.rs
Original file line number Diff line number Diff line change
@@ -1,3 +1,7 @@
use alloc::vec::Vec;
#[cfg(not(feature = "std"))]
use num_traits::Float;

use crate::ord_float::OrdFloat32;

use crate::vpsearch;
Expand Down Expand Up @@ -180,7 +184,7 @@ fn sort_colors(entries: &mut [[f32; 4]], weights: &mut [f32]) {
#[inline(always)]
fn add_color(dst: &mut [f32; 4], src: &[f32; 4], weight: f32) {
unsafe {
use std::arch::x86_64::*;
use core::arch::x86_64::*;

let mut psrc = _mm_loadu_ps(src.as_ptr());
let mut pdst = _mm_loadu_ps(dst.as_ptr());
Expand All @@ -197,7 +201,7 @@ fn add_color(dst: &mut [f32; 4], src: &[f32; 4], weight: f32) {
#[inline(always)]
fn add_color(dst: &mut [f32; 4], src: &[f32; 4], weight: f32) {
unsafe {
use std::arch::aarch64::*;
use core::arch::aarch64::*;

let mut psrc = vld1q_f32(src.as_ptr());
let mut pdst = vld1q_f32(dst.as_ptr());
Expand Down
4 changes: 2 additions & 2 deletions src/error.rs
Original file line number Diff line number Diff line change
@@ -1,4 +1,4 @@
use std::fmt;
use core::fmt;

#[non_exhaustive]
pub enum Error {
Expand All @@ -23,4 +23,4 @@ impl fmt::Debug for Error {
}
}

impl std::error::Error for Error {}
impl core::error::Error for Error {}
6 changes: 5 additions & 1 deletion src/histogram.rs
Original file line number Diff line number Diff line change
@@ -1,5 +1,9 @@
use core::hash::{BuildHasher, Hasher};

#[cfg(feature = "std")]
use std::collections::HashMap;
use std::hash::{BuildHasher, Hasher};
#[cfg(not(feature = "std"))]
use hashbrown::HashMap;

use crate::image::Image;

Expand Down
7 changes: 7 additions & 0 deletions src/lib.rs
Original file line number Diff line number Diff line change
@@ -1,5 +1,8 @@
//! Fast library for conversion of RGBA images to 8-bit paletted images.
//!
//! This crate supports `no_std` environments with the `alloc` crate.
//! Disable the default `std` feature to use in `no_std` mode.
//!
//! ### Quantizing an image
//!
//! ```
Expand Down Expand Up @@ -54,6 +57,10 @@
//! save_image2(palette, indexes2, width2, height2);
//! ```

#![cfg_attr(not(feature = "std"), no_std)]

extern crate alloc;

mod cluster;
mod colormap;
mod error;
Expand Down
2 changes: 1 addition & 1 deletion src/ord_float.rs
Original file line number Diff line number Diff line change
@@ -1,4 +1,4 @@
use std::cmp::Ordering;
use core::cmp::Ordering;

#[derive(Debug, Copy, Clone)]
#[repr(transparent)]
Expand Down
3 changes: 3 additions & 0 deletions src/palette.rs
Original file line number Diff line number Diff line change
@@ -1,3 +1,6 @@
#[cfg(not(feature = "std"))]
use num_traits::Float;

/// RGBA color
#[repr(C)]
#[derive(Clone, Copy, Default)]
Expand Down
5 changes: 4 additions & 1 deletion src/quantize.rs
Original file line number Diff line number Diff line change
@@ -1,3 +1,6 @@
use alloc::vec;
use core::mem;

use crate::cluster::Cluster;
use crate::colormap::Colormap;
use crate::error::Error;
Expand Down Expand Up @@ -200,7 +203,7 @@ impl QuantizeResult {
err[3] += err_a * 7.0;
}

std::mem::swap(&mut error_curr, &mut error_next);
mem::swap(&mut error_curr, &mut error_next);
error_next.fill_with(|| [0f32; 4]);
}
}
Expand Down
25 changes: 15 additions & 10 deletions src/vpsearch.rs
Original file line number Diff line number Diff line change
@@ -1,3 +1,8 @@
use alloc::boxed::Box;
use alloc::vec::Vec;
#[cfg(not(feature = "std"))]
use num_traits::Float;

use crate::ord_float::OrdFloat32;

#[derive(Clone)]
Expand Down Expand Up @@ -115,19 +120,19 @@ impl SearchNode {
if let Some(near) = &self.near {
near.visit(pin, nearest);
}
if distance_sq.sqrt() >= self.radius - nearest.distance {
if let Some(far) = &self.far {
far.visit(pin, nearest);
}
if distance_sq.sqrt() >= self.radius - nearest.distance
&& let Some(far) = &self.far
{
far.visit(pin, nearest);
}
} else {
if let Some(far) = &self.far {
far.visit(pin, nearest);
}
if distance_sq.sqrt() <= self.radius + nearest.distance {
if let Some(near) = &self.near {
near.visit(pin, nearest);
}
if distance_sq.sqrt() <= self.radius + nearest.distance
&& let Some(near) = &self.near
{
near.visit(pin, nearest);
}
}
}
Expand Down Expand Up @@ -177,7 +182,7 @@ impl SearchTree {
#[inline(always)]
fn dist(c1: &[f32; 4], c2: &[f32; 4]) -> f32 {
unsafe {
use std::arch::x86_64::*;
use core::arch::x86_64::*;

let pc1 = _mm_loadu_ps(c1.as_ptr());
let pc2 = _mm_loadu_ps(c2.as_ptr());
Expand All @@ -196,7 +201,7 @@ fn dist(c1: &[f32; 4], c2: &[f32; 4]) -> f32 {
#[inline(always)]
fn dist(c1: &[f32; 4], c2: &[f32; 4]) -> f32 {
unsafe {
use std::arch::aarch64::*;
use core::arch::aarch64::*;

let pc1 = vld1q_f32(c1.as_ptr());
let pc2 = vld1q_f32(c2.as_ptr());
Expand Down