Commit d1311a55 authored by robbycerantola's avatar robbycerantola

fix pixel_fast() , new image_fast2(), new Mode::Legacy, improve resilience, update image_bench.rs

parent d6727c1f
extern crate orbclient;
extern crate time;
use orbclient::{Color, Window, Renderer, EventOption};
use orbclient::{Color, Window, Renderer, EventOption, Mode};
const TIMES:i32 = 10;
......@@ -32,7 +32,9 @@ fn main() {
}
let mut t2 = time::now();
let dt4 = (t2-t)/TIMES;
println!("image_over {:?}",dt4);
println!("image_over {:?}",dt4);
window.mode().set(Mode::Legacy);
t = time::now();
......@@ -41,7 +43,18 @@ fn main() {
}
t2 = time::now();
let dt = (t2-t)/TIMES;
println!("image_legacy (pixel_fast) {:?}",dt );
println!("image_legacy (pixel_legacy) {:?}",dt );
window.mode().set(Mode::Blend);
t = time::now();
for _i in 0..TIMES {
window.image_legacy(15,15,750,550, &data[..]);
}
t2 = time::now();
let dt = (t2-t)/TIMES;
println!("image_legacy (pixel_fast) {:?}",dt );
t = time::now();
......@@ -50,7 +63,16 @@ fn main() {
}
t2 = time::now();
let dt2 = (t2-t)/TIMES;
println!("image_fast {:?}",dt2);
println!("image_fast {:?}",dt2);
t = time::now();
for _i in 0..TIMES {
window.image_fast2(40,40,750,550, &data3[..]);
}
t2 = time::now();
let dt2 = (t2-t)/TIMES;
println!("image_fast2 {:?}",dt2);
t = time::now();
for _i in 0..TIMES {
......@@ -58,18 +80,18 @@ fn main() {
}
t2 = time::now();
let dt3 = (t2-t)/TIMES;
println!("image_parallel {:?}",dt3);
println!("image_parallel {:?}",dt3);
t = time::now();
for _i in 0..TIMES {
window.image_opaque(40,40,750,550, &data4[..]);
window.image_opaque(50,50,750,550, &data4[..]);
}
t2 = time::now();
let dt3 = (t2-t)/TIMES;
println!("image_opaque {:?}",dt3);
println!("image_opaque {:?}",dt3);
//println!("difference {:?}", dt-dt3);
println!("-------------------------");
println!("------------------------------------------------");
window.sync();
......
......@@ -38,7 +38,8 @@ pub enum WindowFlag {
#[derive(Clone, Copy, Debug)]
pub enum Mode {
Blend, //Composite
Overwrite //Replace
Overwrite, //Replace
Legacy
}
#[cfg(all(not(feature="no_std"), target_os = "redox"))]
......
......@@ -55,8 +55,9 @@ pub trait Renderer {
///Draw a pixel
fn pixel(&mut self, x: i32, y: i32, color: Color) {
match self.mode().get() {
Mode::Blend => self.pixel_fast(x, y, color),
Mode::Blend => self.pixel_fast(x, y, color),
Mode::Overwrite => self.pixel_legacy(x, y, color, true),
Mode::Legacy => self.pixel_legacy(x, y, color, false),
};
}
......@@ -102,17 +103,19 @@ pub trait Renderer {
let new = color.data;
let alpha = (new >> 24) & 0xFF;
//let alpha = (new & 0xFF000000) >> 24;
let old = unsafe{ &mut data[y as usize * w as usize + x as usize].data};
let n_alpha = 255 - alpha;
let rb = ((n_alpha * ( *old & 0x00FF00FF)) +
(alpha * (new & 0x00FF00FF))) >> 8;
let ag = (n_alpha * ((*old & 0xFF00FF00)) >> 8) +
( alpha * (0x01000000 | ((new & 0xFF00FF00) >>8)));
*old = (rb & 0x00FF00FF) | (ag & 0xFF00FF00);
if alpha >= 255 {
*old = new;
} else if alpha >0 {
let n_alpha = 255 - alpha;
let rb = ((n_alpha * ( *old & 0x00FF00FF)) + (alpha * (new & 0x00FF00FF))) >> 8;
let ag = (n_alpha * ((*old & 0xFF00FF00) >> 8)) + ( alpha * (0x01000000 | ((new & 0xFF00FF00) >>8)));
*old = (rb & 0x00FF00FF) | (ag & 0xFF00FF00);
}
}
}
......@@ -305,7 +308,7 @@ pub trait Renderer {
fn rect(&mut self, x: i32, y: i32, w: u32, h: u32, color: Color) {
let replace = match self.mode().get() {
Mode::Blend => false,
Mode::Blend | Mode::Legacy => false,
Mode::Overwrite => true,
};
let self_w = self.width();
......@@ -339,13 +342,9 @@ pub trait Renderer {
/// Display an image
fn image(&mut self, start_x: i32, start_y: i32, w: u32, h: u32, data: &[Color]) {
match self.mode().get() {
Mode::Blend => if (w + start_x as u32) > self.width() {
self.image_legacy(start_x, start_y, w, h, data)
} else {
self.image_fast(start_x, start_y, w, h, data);
},
Mode::Blend => self.image_fast2(start_x, start_y, w, h, data),
Mode::Overwrite => self.image_opaque(start_x, start_y, w, h, data),
//and so on with many more modes and implementations....
Mode::Legacy => self.image_legacy(start_x, start_y, w, h, data),
}
}
......@@ -384,7 +383,9 @@ pub trait Renderer {
let height = self.height() as usize;
let start_x = start_x as usize;
let start_y =start_y as usize;
//check boundaries
if start_x >= width || start_y >= height { return }
if h + start_y > height {
h = height - start_y;
}
......@@ -403,7 +404,7 @@ pub trait Renderer {
}
window_data[start..stop]
.copy_from_slice(&image_data[begin..end]);
}
}
}
// Speed improved, but image has to be all inside of window boundary
......@@ -432,17 +433,56 @@ pub trait Renderer {
let n_alpha = 255 - alpha;
let rb = ((n_alpha * ( *old & 0x00FF00FF)) +
(alpha * (new & 0x00FF00FF))) >> 8;
let ag = (n_alpha * ((*old & 0xFF00FF00)) >> 8) +
let ag = (n_alpha * ((*old & 0xFF00FF00) >> 8)) +
( alpha * (0x01000000 | ((new & 0xFF00FF00) >>8)));
*old = (rb & 0x00FF00FF) | (ag & 0xFF00FF00);
}
}
}
}
}
// Speed improved, image can even be outside of window boundary
#[inline(always)]
fn image_fast2 (&mut self, start_x: i32, start_y: i32, w: u32, h: u32, image_data: &[Color]) {
let w = w as usize;
let h = h as usize;
let width = self.width() as usize;
let start_x = start_x as usize;
let start_y =start_y as usize;
let window_data = self.data_mut();
let offset = start_y * width + start_x;
//copy image slices to window line by line
for l in 0..h {
let start = offset + l * width;
let begin = l * w;
let end = begin + cmp::min(w, width - start_x);
let mut k = 0;
for i in begin..end {
if i < image_data.len() {
let new = image_data[i].data;
let alpha = (new >> 24) & 0xFF;
if alpha > 0 && start+k < window_data.len(){
let old = unsafe{ &mut window_data[start + k].data};
if alpha >= 255 {
*old = new;
} else {
let n_alpha = 255 - alpha;
let rb = ((n_alpha * ( *old & 0x00FF00FF)) +
(alpha * (new & 0x00FF00FF))) >> 8;
let ag = (n_alpha * ((*old & 0xFF00FF00) >> 8)) +
( alpha * (0x01000000 | ((new & 0xFF00FF00) >>8)));
*old = (rb & 0x00FF00FF) | (ag & 0xFF00FF00);
}
}
k += 1;
}
}
}
}
///Render an image using parallel threads if possible
//Works in Linux but not in Redox !
fn image_parallel(&mut self, start_x: i32, start_y: i32, w: u32, h: u32, image_data: &[Color]) {
......@@ -491,7 +531,7 @@ pub trait Renderer {
let n_alpha = 255 - alpha;
let rb = ((n_alpha * ( *old & 0x00FF00FF)) +
(alpha * (new & 0x00FF00FF))) >> 8;
let ag = (n_alpha * ((*old & 0xFF00FF00)) >> 8) +
let ag = (n_alpha * ((*old & 0xFF00FF00) >> 8)) +
( alpha * (0x01000000 | ((new & 0xFF00FF00) >>8)));
*old = (rb & 0x00FF00FF) | (ag & 0xFF00FF00);
......
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment