Properly double buffering
This commit is contained in:
@@ -1,4 +1,4 @@
|
|||||||
use crate::wayland::shm::ShmPool;
|
use crate::wayland::{shm::ShmPool, wl_shm::wl_buffer};
|
||||||
use super::drawable::{Drawable, color_blend};
|
use super::drawable::{Drawable, color_blend};
|
||||||
|
|
||||||
// x and y are center of circle
|
// x and y are center of circle
|
||||||
@@ -16,24 +16,34 @@ impl Circle {
|
|||||||
}
|
}
|
||||||
|
|
||||||
impl Drawable for Circle {
|
impl Drawable for Circle {
|
||||||
fn draw(&self, shm_pool: &mut ShmPool) {
|
fn update(&mut self) {
|
||||||
|
self.x += 1;
|
||||||
|
}
|
||||||
|
|
||||||
|
fn draw(&self, buffer: &wl_buffer, shm_pool: &mut ShmPool) {
|
||||||
for l_row in 1..self.radius {
|
for l_row in 1..self.radius {
|
||||||
let inner_diff = (((self.radius-1).pow(2) - l_row.pow(2)) as f64).sqrt();
|
let inner_diff = (((self.radius-1).pow(2) - l_row.pow(2)) as f64).sqrt();
|
||||||
let outer_diff = ((self.radius.pow(2) - l_row.pow(2)) as f64).sqrt();
|
let outer_diff = ((self.radius.pow(2) - l_row.pow(2)) as f64).sqrt();
|
||||||
let row: Vec<u32> = vec![self.color; 2*(inner_diff.floor() as usize)];
|
let row: Vec<u32> = vec![self.color; 2*(inner_diff.floor() as usize)];
|
||||||
shm_pool.write(&row, (self.y-l_row)*shm_pool.width + self.x - inner_diff.floor() as usize);
|
shm_pool.write(&row, (self.y-l_row)*buffer.width + self.x - inner_diff.floor() as usize + buffer.offset);
|
||||||
shm_pool.write(&row, (self.y+l_row-1)*shm_pool.width + self.x - inner_diff.floor() as usize);
|
shm_pool.write(&row, (self.y+l_row-1)*buffer.width + self.x - inner_diff.floor() as usize + buffer.offset);
|
||||||
for l_col in (inner_diff.floor() as usize+1)..(outer_diff.ceil() as usize) {
|
for l_col in (inner_diff.floor() as usize+1)..(outer_diff.ceil() as usize) {
|
||||||
let distance = ((l_row.pow(2) + l_col.pow(2)) as f64).sqrt();
|
let distance = ((l_row.pow(2) + l_col.pow(2)) as f64).sqrt();
|
||||||
let offset = (self.y-l_row)*shm_pool.width + self.x - l_col;
|
let offset = (self.y-l_row)*buffer.width + self.x - l_col + buffer.offset;
|
||||||
shm_pool.write_pixel(color_blend(self.color, shm_pool.read_pixel(offset), distance.fract()), offset as isize);
|
shm_pool.write_pixel(color_blend(self.color, shm_pool.read_pixel(offset).unwrap(), distance.fract()), offset);
|
||||||
let offset = (self.y-l_row)*shm_pool.width + self.x + l_col-1;
|
let offset = (self.y-l_row)*buffer.width + self.x + l_col-1 + buffer.offset;
|
||||||
shm_pool.write_pixel(color_blend(self.color, shm_pool.read_pixel(offset), distance.fract()), offset as isize);
|
shm_pool.write_pixel(color_blend(self.color, shm_pool.read_pixel(offset).unwrap(), distance.fract()), offset);
|
||||||
let offset = (self.y+l_row-1)*shm_pool.width + self.x - l_col;
|
let offset = (self.y+l_row-1)*buffer.width + self.x - l_col + buffer.offset;
|
||||||
shm_pool.write_pixel(color_blend(self.color, shm_pool.read_pixel(offset), distance.fract()), offset as isize);
|
shm_pool.write_pixel(color_blend(self.color, shm_pool.read_pixel(offset).unwrap(), distance.fract()), offset);
|
||||||
let offset = (self.y+l_row-1)*shm_pool.width + self.x + l_col-1;
|
let offset = (self.y+l_row-1)*buffer.width + self.x + l_col-1 + buffer.offset;
|
||||||
shm_pool.write_pixel(color_blend(self.color, shm_pool.read_pixel(offset), distance.fract()), offset as isize);
|
shm_pool.write_pixel(color_blend(self.color, shm_pool.read_pixel(offset).unwrap(), distance.fract()), offset);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
impl Into<Box<dyn Drawable>> for Circle {
|
||||||
|
fn into(self) -> Box<dyn Drawable> {
|
||||||
|
Box::new(self)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|||||||
@@ -1,10 +1,12 @@
|
|||||||
use crate::wayland::shm::ShmPool;
|
use crate::wayland::{shm::ShmPool, wl_shm::wl_buffer};
|
||||||
|
|
||||||
pub fn color_blend(col1: u32, col2: u32, diff: f64) -> u32 {
|
pub fn color_blend(col1: u32, col2: u32, diff: f64) -> u32 {
|
||||||
// TODO: Account for alpha channel
|
// TODO: Account for alpha channel
|
||||||
|
let a1 = (col1 & 0xff000000) >> 24;
|
||||||
let r1 = (col1 & 0x00ff0000) >> 16;
|
let r1 = (col1 & 0x00ff0000) >> 16;
|
||||||
let g1 = (col1 & 0x0000ff00) >> 8;
|
let g1 = (col1 & 0x0000ff00) >> 8;
|
||||||
let b1 = col1 & 0x000000ff;
|
let b1 = col1 & 0x000000ff;
|
||||||
|
let a2 = (col2 & 0xff000000) >> 24;
|
||||||
let r2 = (col2 & 0x00ff0000) >> 16;
|
let r2 = (col2 & 0x00ff0000) >> 16;
|
||||||
let g2 = (col2 & 0x0000ff00) >> 8;
|
let g2 = (col2 & 0x0000ff00) >> 8;
|
||||||
let b2 = col2 & 0x000000ff;
|
let b2 = col2 & 0x000000ff;
|
||||||
@@ -26,6 +28,7 @@ pub fn color_blend(col1: u32, col2: u32, diff: f64) -> u32 {
|
|||||||
return 0xff000000 + (r3 << 16) + (g3 << 8) + b3;
|
return 0xff000000 + (r3 << 16) + (g3 << 8) + b3;
|
||||||
}
|
}
|
||||||
|
|
||||||
pub trait Drawable {
|
pub trait Drawable : Send {
|
||||||
fn draw(&self, shm_pool: &mut ShmPool);
|
fn update(&mut self);
|
||||||
|
fn draw(&self, buffer: &wl_buffer, shm_pool: &mut ShmPool);
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -1,7 +1,6 @@
|
|||||||
use crate::wayland::shm::ShmPool;
|
use crate::wayland::{shm::ShmPool, wl_shm::wl_buffer};
|
||||||
use super::drawable::{Drawable, color_blend};
|
use super::drawable::{Drawable, color_blend};
|
||||||
|
|
||||||
|
|
||||||
// x and y and topleft corner of rect
|
// x and y and topleft corner of rect
|
||||||
pub struct Rectangle {
|
pub struct Rectangle {
|
||||||
x: usize,
|
x: usize,
|
||||||
@@ -19,27 +18,37 @@ impl Rectangle {
|
|||||||
}
|
}
|
||||||
|
|
||||||
impl Drawable for Rectangle {
|
impl Drawable for Rectangle {
|
||||||
fn draw(&self, shm_pool: &mut ShmPool) {
|
fn update(&mut self) {
|
||||||
|
// self.x += 1;
|
||||||
|
}
|
||||||
|
|
||||||
|
fn draw(&self, buffer: &wl_buffer, shm_pool: &mut ShmPool) {
|
||||||
for g_row in self.y+self.radius..self.y+self.height-self.radius+1 {
|
for g_row in self.y+self.radius..self.y+self.height-self.radius+1 {
|
||||||
shm_pool.write(&vec![self.color; self.width], g_row*shm_pool.width+self.x);
|
shm_pool.write(&vec![self.color; self.width], g_row*buffer.width as usize+self.x + buffer.offset);
|
||||||
}
|
}
|
||||||
for l_row in 1..self.radius {
|
for l_row in 1..self.radius {
|
||||||
let inner_diff = (((self.radius-1).pow(2) - l_row.pow(2)) as f64).sqrt();
|
let inner_diff = (((self.radius-1).pow(2) - l_row.pow(2)) as f64).sqrt();
|
||||||
let outer_diff = ((self.radius.pow(2) - l_row.pow(2)) as f64).sqrt();
|
let outer_diff = ((self.radius.pow(2) - l_row.pow(2)) as f64).sqrt();
|
||||||
shm_pool.write(&vec![self.color; self.width - (2*(self.radius - inner_diff.floor() as usize-1))], (self.y+self.radius-l_row)*shm_pool.width + self.x + self.radius - inner_diff.floor() as usize-1);
|
shm_pool.write(&vec![self.color; self.width - (2*(self.radius - inner_diff.floor() as usize-1))], (self.y+self.radius-l_row)*buffer.width as usize + self.x + self.radius - inner_diff.floor() as usize-1 + buffer.offset);
|
||||||
shm_pool.write(&vec![self.color; self.width - (2*(self.radius - inner_diff.floor() as usize-1))], (self.y+self.height-self.radius+l_row)*shm_pool.width + self.x + self.radius - inner_diff.floor() as usize-1);
|
shm_pool.write(&vec![self.color; self.width - (2*(self.radius - inner_diff.floor() as usize-1))], (self.y+self.height-self.radius+l_row)*buffer.width as usize + self.x + self.radius - inner_diff.floor() as usize-1 + buffer.offset);
|
||||||
for l_col in inner_diff.floor() as usize+1..outer_diff.ceil() as usize {
|
for l_col in inner_diff.floor() as usize+1..outer_diff.ceil() as usize {
|
||||||
|
// TODO: handle error from read_pixel
|
||||||
let distance = ((l_row.pow(2) + l_col.pow(2)) as f64).sqrt();
|
let distance = ((l_row.pow(2) + l_col.pow(2)) as f64).sqrt();
|
||||||
let offset = (self.y+self.radius-l_row)*shm_pool.width + self.x + self.radius - l_col - 1;
|
let offset = (self.y+self.radius-l_row)*buffer.width as usize + self.x + self.radius - l_col - 1 + buffer.offset;
|
||||||
shm_pool.write_pixel(color_blend(self.color, shm_pool.read_pixel(offset), distance.fract()), offset as isize);
|
shm_pool.write_pixel(color_blend(self.color, shm_pool.read_pixel(offset).unwrap(), distance.fract()), offset);
|
||||||
let offset = (self.y+self.radius-l_row)*shm_pool.width + self.x + self.width - self.radius + l_col;
|
let offset = (self.y+self.radius-l_row)*buffer.width as usize + self.x + self.width - self.radius + l_col + buffer.offset;
|
||||||
shm_pool.write_pixel(color_blend(self.color, shm_pool.read_pixel(offset), distance.fract()), offset as isize);
|
shm_pool.write_pixel(color_blend(self.color, shm_pool.read_pixel(offset).unwrap(), distance.fract()), offset);
|
||||||
let offset = (self.y+self.height-self.radius+l_row)*shm_pool.width + self.x + self.radius - l_col - 1;
|
let offset = (self.y+self.height-self.radius+l_row)*buffer.width as usize + self.x + self.radius - l_col - 1 + buffer.offset;
|
||||||
shm_pool.write_pixel(color_blend(self.color, shm_pool.read_pixel(offset), distance.fract()), offset as isize);
|
shm_pool.write_pixel(color_blend(self.color, shm_pool.read_pixel(offset).unwrap(), distance.fract()), offset);
|
||||||
let offset = (self.y+self.height-self.radius+l_row)*shm_pool.width + self.x + self.width - self.radius + l_col;
|
let offset = (self.y+self.height-self.radius+l_row)*buffer.width as usize + self.x + self.width - self.radius + l_col + buffer.offset;
|
||||||
shm_pool.write_pixel(color_blend(self.color, shm_pool.read_pixel(offset), distance.fract()), offset as isize);
|
shm_pool.write_pixel(color_blend(self.color, shm_pool.read_pixel(offset).unwrap(), distance.fract()), offset);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
impl Into<Box<dyn Drawable>> for Rectangle {
|
||||||
|
fn into(self) -> Box<dyn Drawable> {
|
||||||
|
Box::new(self)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|||||||
@@ -1,4 +1,4 @@
|
|||||||
use std::{error::Error, io::Write, sync::atomic::Ordering};
|
use std::{error::Error, io::Write, sync::atomic::Ordering, thread, time::Duration};
|
||||||
use crate::wayland::{surface::UnsetErr, vec_utils::WlMessage, wl_client::WlClient};
|
use crate::wayland::{surface::UnsetErr, vec_utils::WlMessage, wl_client::WlClient};
|
||||||
|
|
||||||
const NAMESPACE: &str = "chlorostart";
|
const NAMESPACE: &str = "chlorostart";
|
||||||
@@ -42,12 +42,18 @@ impl WlClient {
|
|||||||
Ok(())
|
Ok(())
|
||||||
}
|
}
|
||||||
|
|
||||||
pub fn layer_surface_configure(&self, event: &Vec<u8>) -> Result<(), Box<dyn Error>> {
|
pub fn layer_surface_configure(&self, event: &Vec<u8>) -> Result<(), Box<dyn Error + '_>> {
|
||||||
let mut offset: usize = 0;
|
let mut offset: usize = 0;
|
||||||
let serial = event.read_u32(&mut offset);
|
let serial = event.read_u32(&mut offset);
|
||||||
let width = event.read_u32(&mut offset);
|
let width = event.read_u32(&mut offset);
|
||||||
let height = event.read_u32(&mut offset);
|
let height = event.read_u32(&mut offset);
|
||||||
|
|
||||||
|
println!(
|
||||||
|
"Configure layer surface:\n\twidth: {}\n\theight: {}",
|
||||||
|
width,
|
||||||
|
height
|
||||||
|
);
|
||||||
|
|
||||||
// TODO: Resize based on configure
|
// TODO: Resize based on configure
|
||||||
|
|
||||||
// Ack configure
|
// Ack configure
|
||||||
@@ -68,9 +74,7 @@ impl WlClient {
|
|||||||
request.write_u32(&serial, &mut offset);
|
request.write_u32(&serial, &mut offset);
|
||||||
|
|
||||||
self.socket.lock().unwrap().write(&request)?;
|
self.socket.lock().unwrap().write(&request)?;
|
||||||
|
self.wl_surface_frame()?;
|
||||||
self.wl_surface_attach()?;
|
|
||||||
self.wl_surface_commit()?;
|
|
||||||
|
|
||||||
Ok(())
|
Ok(())
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -5,13 +5,10 @@ pub struct ShmPool {
|
|||||||
pub fd: i32,
|
pub fd: i32,
|
||||||
pub addr: *mut c_void,
|
pub addr: *mut c_void,
|
||||||
pub size: usize,
|
pub size: usize,
|
||||||
pub width: usize,
|
|
||||||
}
|
}
|
||||||
|
|
||||||
impl ShmPool {
|
impl ShmPool {
|
||||||
pub fn new(width: usize, height: usize) -> std::io::Result<ShmPool> {
|
pub fn new(size: usize) -> std::io::Result<ShmPool> {
|
||||||
let size = width * height * 4;
|
|
||||||
|
|
||||||
let shm_path: *const i8 = b"/chlorostart\0".as_ptr() as *const i8;
|
let shm_path: *const i8 = b"/chlorostart\0".as_ptr() as *const i8;
|
||||||
let fd = unsafe { shm_open(shm_path, O_RDWR | O_EXCL | O_CREAT, 0o600) };
|
let fd = unsafe { shm_open(shm_path, O_RDWR | O_EXCL | O_CREAT, 0o600) };
|
||||||
if fd == -1 {
|
if fd == -1 {
|
||||||
@@ -39,17 +36,16 @@ impl ShmPool {
|
|||||||
fd,
|
fd,
|
||||||
addr,
|
addr,
|
||||||
size,
|
size,
|
||||||
width,
|
|
||||||
})
|
})
|
||||||
}
|
}
|
||||||
|
|
||||||
pub fn from_fd(fd: i32, size: usize) -> std::io::Result<ShmPool> {
|
pub fn from_fd(fd: i32, size: usize) -> std::io::Result<ShmPool> {
|
||||||
let addr = unsafe { mmap(std::ptr::null_mut(), size, PROT_READ, MAP_PRIVATE, fd, 0) };
|
let addr = unsafe { mmap(std::ptr::null_mut(), size, PROT_READ, MAP_PRIVATE, fd, 0) };
|
||||||
if addr == MAP_FAILED {
|
if addr == MAP_FAILED {
|
||||||
eprint!("mmap in ShmPool::from_fd() failed: ");
|
eprint!("mmap in ShmPool::from_fd() failed with fd {}", fd);
|
||||||
return Err(std::io::Error::last_os_error());
|
return Err(std::io::Error::last_os_error());
|
||||||
}
|
}
|
||||||
Ok(ShmPool {fd, addr, size, width: 0})
|
Ok(ShmPool {fd, addr, size})
|
||||||
}
|
}
|
||||||
|
|
||||||
pub fn read_string(&self, offset: usize) -> std::io::Result<String> {
|
pub fn read_string(&self, offset: usize) -> std::io::Result<String> {
|
||||||
@@ -74,30 +70,31 @@ impl ShmPool {
|
|||||||
}
|
}
|
||||||
|
|
||||||
pub fn write(&mut self, data: &Vec<u32>, offset: usize) {
|
pub fn write(&mut self, data: &Vec<u32>, offset: usize) {
|
||||||
if offset > self.size {
|
if offset + data.len() >= self.size {
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
unsafe {
|
unsafe {
|
||||||
std::ptr::copy_nonoverlapping(
|
std::ptr::copy_nonoverlapping(
|
||||||
data.as_ptr() as *const u32, // src: data as *const u32
|
data.as_ptr() as *const u32, // src: data as *const u32
|
||||||
self.addr.offset(4*offset as isize) as *mut u32, // dst: ShmPool address as *mut u32
|
self.addr.offset(4*offset as isize) as *mut u32, // dst: ShmPool address as *mut u32
|
||||||
if offset + data.len() * 4 <= self.size {
|
data.len()
|
||||||
data.len()
|
|
||||||
} else {
|
|
||||||
data.len() - offset
|
|
||||||
}
|
|
||||||
);
|
);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
pub fn write_pixel(&mut self, data: u32, offset: isize) {
|
pub fn write_pixel(&mut self, data: u32, offset: usize) {
|
||||||
// TODO: Bounds check
|
// TODO: Return error if out of bounds
|
||||||
unsafe {*(self.addr.offset(offset*4) as *mut u32) = data;}
|
if offset + 3 > self.size {
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
unsafe {*(self.addr.offset(offset as isize*4) as *mut u32) = data;}
|
||||||
}
|
}
|
||||||
|
|
||||||
pub fn read_pixel(&self, offset: usize) -> u32 {
|
pub fn read_pixel(&self, offset: usize) -> Option<u32> {
|
||||||
// TODO: Bounds check
|
if offset + 3 > self.size {
|
||||||
return unsafe {*(self.addr.offset(4*offset as isize) as *const u32)};
|
return None;
|
||||||
|
}
|
||||||
|
return Some(unsafe {*(self.addr.offset(4*offset as isize) as *const u32)});
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|||||||
@@ -1,6 +1,6 @@
|
|||||||
use std::{error::Error, io::Write, sync::atomic::Ordering};
|
use std::{error::Error, io::Write, sync::atomic::Ordering};
|
||||||
|
|
||||||
use crate::wayland::{vec_utils::WlMessage, wl_client::WlClient};
|
use crate::wayland::{vec_utils::WlMessage, wl_client::WlClient, wl_shm::wl_buffer};
|
||||||
|
|
||||||
use std::fmt;
|
use std::fmt;
|
||||||
|
|
||||||
@@ -40,17 +40,16 @@ impl WlClient {
|
|||||||
Ok(())
|
Ok(())
|
||||||
}
|
}
|
||||||
|
|
||||||
pub fn wl_surface_attach(&self) -> Result<(), Box<dyn Error>> {
|
pub fn wl_surface_attach(&self, buffer: &wl_buffer) -> Result<(), Box<dyn Error + '_>> {
|
||||||
|
|
||||||
|
let id = buffer.id;
|
||||||
|
|
||||||
let object = self.surface_id.load(Ordering::Relaxed);
|
let object = self.surface_id.load(Ordering::Relaxed);
|
||||||
if object == 0 {
|
if object == 0 {
|
||||||
return Err(UnsetErr("surface_id".to_string()).into());
|
return Err(UnsetErr("surface_id".to_string()).into());
|
||||||
}
|
}
|
||||||
const OPCODE: u16 = 1;
|
const OPCODE: u16 = 1;
|
||||||
const MSG_SIZE: u16 = 20;
|
const MSG_SIZE: u16 = 20;
|
||||||
let buffer = self.buffer_id.load(Ordering::Relaxed);
|
|
||||||
if buffer == 0 {
|
|
||||||
return Err(UnsetErr("buffer_id".to_string()).into());
|
|
||||||
}
|
|
||||||
const X: u32 = 0;
|
const X: u32 = 0;
|
||||||
const Y: u32 = 0;
|
const Y: u32 = 0;
|
||||||
|
|
||||||
@@ -60,11 +59,11 @@ impl WlClient {
|
|||||||
request.write_u32(&object, &mut offset);
|
request.write_u32(&object, &mut offset);
|
||||||
request.write_u16(&OPCODE, &mut offset);
|
request.write_u16(&OPCODE, &mut offset);
|
||||||
request.write_u16(&MSG_SIZE, &mut offset);
|
request.write_u16(&MSG_SIZE, &mut offset);
|
||||||
request.write_u32(&buffer, &mut offset);
|
request.write_u32(&id, &mut offset);
|
||||||
request.write_u32(&X, &mut offset);
|
request.write_u32(&X, &mut offset);
|
||||||
request.write_u32(&Y, &mut offset);
|
request.write_u32(&Y, &mut offset);
|
||||||
|
|
||||||
self.socket.lock().unwrap().write(&request)?;
|
self.socket.lock()?.write(&request)?;
|
||||||
|
|
||||||
Ok(())
|
Ok(())
|
||||||
}
|
}
|
||||||
@@ -89,6 +88,49 @@ impl WlClient {
|
|||||||
Ok(())
|
Ok(())
|
||||||
}
|
}
|
||||||
|
|
||||||
|
pub fn wl_surface_frame(&self) -> Result<(), Box<dyn Error + '_>> {
|
||||||
|
let object = self.surface_id.load(Ordering::Relaxed);
|
||||||
|
if object == 0 {
|
||||||
|
return Err(UnsetErr("surface_id".to_string()).into());
|
||||||
|
}
|
||||||
|
const OPCODE: u16 = 3;
|
||||||
|
const MSG_SIZE: u16 = 12;
|
||||||
|
let id = self.current_id.fetch_add(1, Ordering::Relaxed) + 1;
|
||||||
|
|
||||||
|
let mut request = vec![0u8; MSG_SIZE as usize];
|
||||||
|
let mut offset: usize = 0;
|
||||||
|
|
||||||
|
request.write_u32(&object, &mut offset);
|
||||||
|
request.write_u16(&OPCODE, &mut offset);
|
||||||
|
request.write_u16(&MSG_SIZE, &mut offset);
|
||||||
|
request.write_u32(&id, &mut offset);
|
||||||
|
self.socket.lock()?.write(&request)?;
|
||||||
|
self.frame_hint_id.store(id, Ordering::Relaxed);
|
||||||
|
|
||||||
|
let buf_lock = if self.active_buffer.fetch_update(
|
||||||
|
Ordering::Relaxed,
|
||||||
|
Ordering::Relaxed,
|
||||||
|
|b| { Some(!b) }
|
||||||
|
).unwrap() {
|
||||||
|
&self.buffer1
|
||||||
|
} else {
|
||||||
|
&self.buffer2
|
||||||
|
}.lock()?;
|
||||||
|
let buffer = buf_lock.as_ref().ok_or(UnsetErr("buffer".to_string()))?;
|
||||||
|
|
||||||
|
self.wl_surface_attach(buffer)?;
|
||||||
|
let mut drawables = self.drawables.lock()?;
|
||||||
|
let mut shm_pool = self.shm_pool.lock()?;
|
||||||
|
shm_pool.write(&vec![0x00000000; 800 * 800 * 2], 0);
|
||||||
|
for drawable in &mut *drawables {
|
||||||
|
drawable.update();
|
||||||
|
drawable.draw(buffer, &mut *shm_pool);
|
||||||
|
}
|
||||||
|
self.wl_surface_commit()?;
|
||||||
|
|
||||||
|
Ok(())
|
||||||
|
}
|
||||||
|
|
||||||
pub fn xdg_wm_base_pong(&self, event: &Vec<u8>) -> Result<(), Box<dyn Error>> {
|
pub fn xdg_wm_base_pong(&self, event: &Vec<u8>) -> Result<(), Box<dyn Error>> {
|
||||||
let object = self.xdg_wm_base_id.load(Ordering::Relaxed);
|
let object = self.xdg_wm_base_id.load(Ordering::Relaxed);
|
||||||
if object == 0 {
|
if object == 0 {
|
||||||
|
|||||||
@@ -1,11 +1,6 @@
|
|||||||
use std::{collections::HashMap, env::var, error::Error, fmt::Debug, io::{IoSliceMut, Write}, os::unix::net::{AncillaryData, SocketAncillary, UnixStream}, sync::{atomic::{AtomicBool, AtomicU32, Ordering}, mpsc, Arc, Mutex, RwLock}, thread::{self}, time::Duration, u32};
|
use std::{collections::HashMap, env::var, error::Error, fmt::Debug, io::{IoSliceMut, Write}, os::unix::net::{AncillaryData, SocketAncillary, UnixStream}, sync::{atomic::{AtomicBool, AtomicU32, Ordering}, mpsc, Arc, Mutex, RwLock}, thread::{self}, time::Duration, u32};
|
||||||
|
|
||||||
use crate::wayland::{shm, vec_utils::WlMessage};
|
use crate::{graphics::{circle::Circle, drawable::Drawable, rectangle::Rectangle}, wayland::{shm, surface::UnsetErr, vec_utils::WlMessage, wl_shm::wl_buffer}};
|
||||||
|
|
||||||
#[derive(PartialEq)]
|
|
||||||
pub enum ThreadMessage {
|
|
||||||
}
|
|
||||||
use ThreadMessage::*;
|
|
||||||
|
|
||||||
struct WlHeader {
|
struct WlHeader {
|
||||||
object: u32,
|
object: u32,
|
||||||
@@ -15,23 +10,26 @@ struct WlHeader {
|
|||||||
|
|
||||||
pub struct WlClient {
|
pub struct WlClient {
|
||||||
pub socket: Mutex<UnixStream>,
|
pub socket: Mutex<UnixStream>,
|
||||||
pub sender: mpsc::Sender<ThreadMessage>,
|
|
||||||
pub running: AtomicBool,
|
pub running: AtomicBool,
|
||||||
pub current_id: AtomicU32,
|
pub current_id: AtomicU32,
|
||||||
pub registry_id: AtomicU32,
|
pub registry_id: AtomicU32,
|
||||||
pub shm_id: AtomicU32,
|
pub shm_id: AtomicU32,
|
||||||
pub shmpool_id: AtomicU32,
|
pub shmpool_id: AtomicU32,
|
||||||
pub shm_pool: Mutex<shm::ShmPool>,
|
pub shm_pool: Mutex<shm::ShmPool>,
|
||||||
pub buffer_id: AtomicU32,
|
|
||||||
pub compositor_id: AtomicU32,
|
pub compositor_id: AtomicU32,
|
||||||
pub surface_id: AtomicU32,
|
pub surface_id: AtomicU32,
|
||||||
|
pub active_buffer: AtomicBool,
|
||||||
|
pub buffer1: Mutex<Option<wl_buffer>>,
|
||||||
|
pub buffer2: Mutex<Option<wl_buffer>>,
|
||||||
|
pub frame_hint_id: AtomicU32,
|
||||||
pub xdg_wm_base_id: AtomicU32,
|
pub xdg_wm_base_id: AtomicU32,
|
||||||
pub layer_shell_id: AtomicU32,
|
pub layer_shell_id: AtomicU32,
|
||||||
pub layer_surface_id: AtomicU32,
|
pub layer_surface_id: AtomicU32,
|
||||||
pub seat_id: AtomicU32,
|
pub seat_id: AtomicU32,
|
||||||
pub keyboard_id: AtomicU32,
|
pub keyboard_id: AtomicU32,
|
||||||
pub keymap_fd: Mutex<Option<shm::ShmPool>>,
|
pub keymap_fd: Mutex<Option<shm::ShmPool>>,
|
||||||
pub keymap: RwLock<Option<HashMap<u32, Vec<String>>>>
|
pub keymap: RwLock<Option<HashMap<u32, Vec<String>>>>,
|
||||||
|
pub drawables: Mutex<Vec<Box<dyn Drawable>>>,
|
||||||
}
|
}
|
||||||
|
|
||||||
impl WlClient {
|
impl WlClient {
|
||||||
@@ -43,18 +41,18 @@ impl WlClient {
|
|||||||
))?;
|
))?;
|
||||||
sock.set_nonblocking(true)?;
|
sock.set_nonblocking(true)?;
|
||||||
|
|
||||||
let (sender, receiver) = mpsc::channel::<ThreadMessage>();
|
|
||||||
|
|
||||||
let mut arc_wl_client = Arc::new(WlClient {
|
let mut arc_wl_client = Arc::new(WlClient {
|
||||||
socket: Mutex::new(sock),
|
socket: Mutex::new(sock),
|
||||||
sender,
|
|
||||||
running: AtomicBool::from(false),
|
running: AtomicBool::from(false),
|
||||||
current_id: AtomicU32::from(1),
|
current_id: AtomicU32::from(1),
|
||||||
registry_id: AtomicU32::from(0),
|
registry_id: AtomicU32::from(0),
|
||||||
shm_id: AtomicU32::from(0),
|
shm_id: AtomicU32::from(0),
|
||||||
shmpool_id: AtomicU32::from(0),
|
shmpool_id: AtomicU32::from(0),
|
||||||
shm_pool: Mutex::new(shm::ShmPool::new(800, 800)?),
|
shm_pool: Mutex::new(shm::ShmPool::new(800 * 800 * 4 * 2)?),
|
||||||
buffer_id: AtomicU32::from(0),
|
active_buffer: AtomicBool::from(false),
|
||||||
|
buffer1: Mutex::new(None),
|
||||||
|
buffer2: Mutex::new(None),
|
||||||
|
frame_hint_id: AtomicU32::from(0),
|
||||||
compositor_id: AtomicU32::from(0),
|
compositor_id: AtomicU32::from(0),
|
||||||
surface_id: AtomicU32::from(0),
|
surface_id: AtomicU32::from(0),
|
||||||
xdg_wm_base_id: AtomicU32::from(0),
|
xdg_wm_base_id: AtomicU32::from(0),
|
||||||
@@ -64,8 +62,13 @@ impl WlClient {
|
|||||||
keyboard_id: AtomicU32::from(0),
|
keyboard_id: AtomicU32::from(0),
|
||||||
keymap: RwLock::new(None),
|
keymap: RwLock::new(None),
|
||||||
keymap_fd: Mutex::new(None),
|
keymap_fd: Mutex::new(None),
|
||||||
|
drawables: Mutex::new(Vec::new()),
|
||||||
});
|
});
|
||||||
arc_wl_client.wl_display_get_registry();
|
arc_wl_client.wl_display_get_registry();
|
||||||
|
if let Ok(mut drawables) = arc_wl_client.drawables.lock() {
|
||||||
|
drawables.push(Rectangle::new(50, 50, 300, 300, 16, 0xffff8800).into());
|
||||||
|
drawables.push(Circle::new(150, 80, 25, 0xff00ffff).into());
|
||||||
|
}
|
||||||
arc_wl_client.running.store(true, Ordering::Relaxed);
|
arc_wl_client.running.store(true, Ordering::Relaxed);
|
||||||
|
|
||||||
let wl_client = arc_wl_client.clone();
|
let wl_client = arc_wl_client.clone();
|
||||||
@@ -75,21 +78,12 @@ impl WlClient {
|
|||||||
}
|
}
|
||||||
})?;
|
})?;
|
||||||
|
|
||||||
// let wl_client = arc_wl_client.clone();
|
|
||||||
// let recvloop = thread::Builder::new().name("recvloop".to_string()).spawn(move || {
|
|
||||||
// while wl_client.running.load(Ordering::Relaxed) {
|
|
||||||
// match receiver.recv().unwrap() {
|
|
||||||
// }
|
|
||||||
// }
|
|
||||||
// })?;
|
|
||||||
//
|
|
||||||
// recvloop.join();
|
|
||||||
readloop.join();
|
readloop.join();
|
||||||
|
|
||||||
Ok(())
|
Ok(())
|
||||||
}
|
}
|
||||||
|
|
||||||
pub fn read_event(self: &Arc<Self>) -> Result<(), Box<dyn Error>> {
|
pub fn read_event(self: &Arc<Self>) -> Result<(), Box<dyn Error + '_>> {
|
||||||
// TODO: Don't realloc header and event
|
// TODO: Don't realloc header and event
|
||||||
|
|
||||||
// FIXME: Using fd like this is unreliable because fd could be before or after
|
// FIXME: Using fd like this is unreliable because fd could be before or after
|
||||||
@@ -126,8 +120,8 @@ impl WlClient {
|
|||||||
)?;
|
)?;
|
||||||
for ancillary_result in ancillary.messages() {
|
for ancillary_result in ancillary.messages() {
|
||||||
if let AncillaryData::ScmRights(scm_rights) = ancillary_result.unwrap() {
|
if let AncillaryData::ScmRights(scm_rights) = ancillary_result.unwrap() {
|
||||||
scm_rights.for_each(|fd| {
|
scm_rights.for_each(|received| {
|
||||||
println!("found {}", fd);
|
fd = received;
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@@ -139,7 +133,6 @@ impl WlClient {
|
|||||||
}
|
}
|
||||||
else if header.object == 1 && header.opcode == 0 { // wl_display::error
|
else if header.object == 1 && header.opcode == 0 { // wl_display::error
|
||||||
WlClient::wl_display_error(&event);
|
WlClient::wl_display_error(&event);
|
||||||
dbg!(&self);
|
|
||||||
}
|
}
|
||||||
else if header.object == self.shm_id.load(Ordering::Relaxed) && header.opcode == 0 { // wl_shm::format
|
else if header.object == self.shm_id.load(Ordering::Relaxed) && header.opcode == 0 { // wl_shm::format
|
||||||
WlClient::wl_shm_format(&event);
|
WlClient::wl_shm_format(&event);
|
||||||
@@ -151,10 +144,10 @@ impl WlClient {
|
|||||||
self.layer_surface_configure(&event)?;
|
self.layer_surface_configure(&event)?;
|
||||||
}
|
}
|
||||||
else if header.object == self.surface_id.load(Ordering::Relaxed) && header.opcode == 2 { // wl_surface::preferred_buffer_scale
|
else if header.object == self.surface_id.load(Ordering::Relaxed) && header.opcode == 2 { // wl_surface::preferred_buffer_scale
|
||||||
println!("Preferred buffer scale: {}", i32::from_ne_bytes(event[0..4].try_into().unwrap()));
|
// println!("Preferred buffer scale: {}", i32::from_ne_bytes(event[0..4].try_into().unwrap()));
|
||||||
}
|
}
|
||||||
else if header.object == self.surface_id.load(Ordering::Relaxed) && header.opcode == 3 { // wl_surface::preferred_buffer_transform
|
else if header.object == self.surface_id.load(Ordering::Relaxed) && header.opcode == 3 { // wl_surface::preferred_buffer_transform
|
||||||
println!("Preferred buffer transform: {}", i32::from_ne_bytes(event[0..4].try_into().unwrap()));
|
// println!("Preferred buffer transform: {}", i32::from_ne_bytes(event[0..4].try_into().unwrap()));
|
||||||
}
|
}
|
||||||
else if header.object == self.seat_id.load(Ordering::Relaxed) && header.opcode == 0 { // wl_seat::capabilities
|
else if header.object == self.seat_id.load(Ordering::Relaxed) && header.opcode == 0 { // wl_seat::capabilities
|
||||||
self.wl_seat_capabilities(&event)?;
|
self.wl_seat_capabilities(&event)?;
|
||||||
@@ -163,7 +156,7 @@ impl WlClient {
|
|||||||
self.wl_seat_name(&event);
|
self.wl_seat_name(&event);
|
||||||
}
|
}
|
||||||
else if header.object == self.keyboard_id.load(Ordering::Relaxed) && header.opcode == 0 { // wl_keyboard::keymap
|
else if header.object == self.keyboard_id.load(Ordering::Relaxed) && header.opcode == 0 { // wl_keyboard::keymap
|
||||||
self.wl_keyboard_keymap(&event, fd);
|
self.wl_keyboard_keymap(&event, fd)?;
|
||||||
}
|
}
|
||||||
else if header.object == self.keyboard_id.load(Ordering::Relaxed) && header.opcode == 3 { // wl_keyboard::key
|
else if header.object == self.keyboard_id.load(Ordering::Relaxed) && header.opcode == 3 { // wl_keyboard::key
|
||||||
let wl_client = self.clone();
|
let wl_client = self.clone();
|
||||||
@@ -171,6 +164,9 @@ impl WlClient {
|
|||||||
wl_client.wl_keyboard_key(&event);
|
wl_client.wl_keyboard_key(&event);
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
|
else if header.object == self.frame_hint_id.load(Ordering::Relaxed) && header.opcode == 0 { // wl_callback<frame_hint>::done
|
||||||
|
self.wl_surface_frame()?;
|
||||||
|
}
|
||||||
else {
|
else {
|
||||||
println!(
|
println!(
|
||||||
"Received event:\n\tObject: {}\n\tOpcode: {}\n\tSize: {}",
|
"Received event:\n\tObject: {}\n\tOpcode: {}\n\tSize: {}",
|
||||||
@@ -183,9 +179,8 @@ impl WlClient {
|
|||||||
Ok(())
|
Ok(())
|
||||||
}
|
}
|
||||||
|
|
||||||
pub fn destroy_object(&self, id: &AtomicU32, opcode: u16) {
|
pub fn destroy_object(&self, id: u32, opcode: u16) {
|
||||||
let object = id.load(Ordering::Relaxed);
|
if id == 0 {
|
||||||
if object == 0 {
|
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
const REQ_SIZE: u16 = 8;
|
const REQ_SIZE: u16 = 8;
|
||||||
@@ -193,7 +188,7 @@ impl WlClient {
|
|||||||
let mut request = vec![0; REQ_SIZE as usize];
|
let mut request = vec![0; REQ_SIZE as usize];
|
||||||
let mut offset = 0;
|
let mut offset = 0;
|
||||||
|
|
||||||
request.write_u32(&object, &mut offset);
|
request.write_u32(&id, &mut offset);
|
||||||
request.write_u16(&opcode, &mut offset);
|
request.write_u16(&opcode, &mut offset);
|
||||||
request.write_u16(&REQ_SIZE, &mut offset);
|
request.write_u16(&REQ_SIZE, &mut offset);
|
||||||
|
|
||||||
@@ -201,12 +196,13 @@ impl WlClient {
|
|||||||
self.shmpool_id.store(0, Ordering::Relaxed);
|
self.shmpool_id.store(0, Ordering::Relaxed);
|
||||||
}
|
}
|
||||||
|
|
||||||
pub fn exit(&self) {
|
pub fn exit(&self) -> Result<(), Box<dyn Error + '_>> {
|
||||||
println!("Exiting!");
|
println!("Exiting!");
|
||||||
self.destroy_object(&self.layer_surface_id, 7);
|
self.destroy_object(self.layer_surface_id.load(Ordering::Relaxed), 7);
|
||||||
self.destroy_object(&self.buffer_id, 0);
|
self.destroy_object(self.buffer1.lock()?.as_ref().ok_or(UnsetErr("buffer1".to_string()))?.id, 0);
|
||||||
self.keymap_fd.lock().unwrap().take();
|
self.keymap_fd.lock().unwrap().take();
|
||||||
self.running.store(false, Ordering::Relaxed);
|
self.running.store(false, Ordering::Relaxed);
|
||||||
|
Ok(())
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -217,7 +213,8 @@ impl Debug for WlClient {
|
|||||||
registry_id: {},
|
registry_id: {},
|
||||||
shm_id: {},
|
shm_id: {},
|
||||||
shmpool_id: {},
|
shmpool_id: {},
|
||||||
buffer_id: {},
|
buffer1: {:?},
|
||||||
|
buffer2: {:?},
|
||||||
compositor_id: {},
|
compositor_id: {},
|
||||||
surface_id: {},
|
surface_id: {},
|
||||||
xdg_wm_base_id: {},
|
xdg_wm_base_id: {},
|
||||||
@@ -230,7 +227,8 @@ impl Debug for WlClient {
|
|||||||
self.registry_id.load(Ordering::Relaxed),
|
self.registry_id.load(Ordering::Relaxed),
|
||||||
self.shm_id.load(Ordering::Relaxed),
|
self.shm_id.load(Ordering::Relaxed),
|
||||||
self.shmpool_id.load(Ordering::Relaxed),
|
self.shmpool_id.load(Ordering::Relaxed),
|
||||||
self.buffer_id.load(Ordering::Relaxed),
|
self.buffer1.lock().unwrap(),
|
||||||
|
self.buffer2.lock().unwrap(),
|
||||||
self.compositor_id.load(Ordering::Relaxed),
|
self.compositor_id.load(Ordering::Relaxed),
|
||||||
self.surface_id.load(Ordering::Relaxed),
|
self.surface_id.load(Ordering::Relaxed),
|
||||||
self.xdg_wm_base_id.load(Ordering::Relaxed),
|
self.xdg_wm_base_id.load(Ordering::Relaxed),
|
||||||
|
|||||||
@@ -1,8 +1,8 @@
|
|||||||
use crate::wayland::{surface::UnsetErr, vec_utils::WlMessage, wl_client::WlClient};
|
use crate::wayland::{surface::UnsetErr, vec_utils::WlMessage, wl_client::WlClient, wl_shm::wl_buffer};
|
||||||
use std::{error::Error, io::Write, sync::atomic::{AtomicU32, Ordering}};
|
use std::{error::Error, io::Write, sync::{atomic::{AtomicU32, Ordering}, Arc}};
|
||||||
|
|
||||||
impl WlClient {
|
impl WlClient {
|
||||||
fn init_toplevel(&self) -> Result<(), Box<dyn Error>> {
|
fn init_toplevel(&self) -> Result<(), Box<dyn Error + '_>> {
|
||||||
if self.shm_id.load(Ordering::Relaxed) == 0 {
|
if self.shm_id.load(Ordering::Relaxed) == 0 {
|
||||||
return Err(Box::new(UnsetErr("shm_id".to_string())));
|
return Err(Box::new(UnsetErr("shm_id".to_string())));
|
||||||
}
|
}
|
||||||
@@ -26,8 +26,25 @@ impl WlClient {
|
|||||||
self.layer_surface_set_keyboard_interactivity()?;
|
self.layer_surface_set_keyboard_interactivity()?;
|
||||||
self.wl_surface_commit()?;
|
self.wl_surface_commit()?;
|
||||||
|
|
||||||
self.wl_shm_create_pool(800, 800)?;
|
self.wl_shm_create_pool()?;
|
||||||
self.wl_shm_pool_create_buffer(0, 800, 800)?;
|
|
||||||
|
let current_id = self.current_id.fetch_add(2, Ordering::Relaxed);
|
||||||
|
let mut buffer1 = self.buffer1.lock().unwrap();
|
||||||
|
let mut buffer2 = self.buffer2.lock().unwrap();
|
||||||
|
*buffer1 = Some(wl_buffer {
|
||||||
|
id: current_id + 1,
|
||||||
|
offset: 0,
|
||||||
|
width: 800,
|
||||||
|
height: 800
|
||||||
|
});
|
||||||
|
*buffer2 = Some(wl_buffer {
|
||||||
|
id: current_id + 2,
|
||||||
|
offset: 800 * 800, // pixel offset
|
||||||
|
width: 800,
|
||||||
|
height: 800
|
||||||
|
});
|
||||||
|
self.wl_shm_pool_create_buffer(buffer1.as_ref().unwrap())?;
|
||||||
|
self.wl_shm_pool_create_buffer(buffer2.as_ref().unwrap())?;
|
||||||
|
|
||||||
Ok(())
|
Ok(())
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -1,27 +1,28 @@
|
|||||||
|
use std::sync::atomic::AtomicU32;
|
||||||
use std::{error::Error, io::Write, os::unix::net::SocketAncillary, sync::atomic::Ordering, u8};
|
use std::{error::Error, io::Write, os::unix::net::SocketAncillary, sync::atomic::Ordering, u8};
|
||||||
use crate::graphics::drawable::Drawable;
|
use crate::wayland::{surface::UnsetErr, vec_utils::WlMessage, wl_client::WlClient};
|
||||||
use crate::wayland::{shm, surface::UnsetErr, vec_utils::WlMessage, wl_client::WlClient};
|
|
||||||
use crate::graphics::{rectangle::Rectangle, circle::Circle};
|
|
||||||
|
|
||||||
const STRIDE: usize = 4;
|
const STRIDE: usize = 4;
|
||||||
|
|
||||||
|
#[derive(Debug)]
|
||||||
|
pub struct wl_buffer {
|
||||||
|
pub id: u32,
|
||||||
|
pub offset: usize,
|
||||||
|
pub width: usize,
|
||||||
|
pub height: usize,
|
||||||
|
}
|
||||||
|
|
||||||
impl WlClient {
|
impl WlClient {
|
||||||
pub fn wl_shm_format(event: &Vec<u8>) {
|
pub fn wl_shm_format(event: &Vec<u8>) {
|
||||||
// let mut offset = 0;
|
// let mut offset = 0;
|
||||||
// println!("Received pixel format: {:x}", event.read_u32(&mut offset));
|
// println!("Received pixel format: {:x}", event.read_u32(&mut offset));
|
||||||
}
|
}
|
||||||
|
|
||||||
pub fn wl_shm_create_pool(&self, width: usize, height: usize) -> Result<(), Box<dyn Error>> {
|
pub fn wl_shm_create_pool(&self) -> Result<(), Box<dyn Error>> {
|
||||||
let mut shm_pool = self.shm_pool.lock().unwrap();
|
let shm_pool = self.shm_pool.lock().unwrap();
|
||||||
let current_id = self.current_id.fetch_add(1, Ordering::Relaxed) + 1;
|
let current_id = self.current_id.fetch_add(1, Ordering::Relaxed) + 1;
|
||||||
self.shmpool_id.store(current_id, Ordering::Relaxed);
|
self.shmpool_id.store(current_id, Ordering::Relaxed);
|
||||||
|
|
||||||
// shm_pool.write(&vec![0xffff0000; width * height], 0);
|
|
||||||
let rect = Rectangle::new(100, 100, 200, 50, 20, 0xffffff);
|
|
||||||
rect.draw(&mut shm_pool);
|
|
||||||
// let circle = Circle::new(250, 150, 20, 0xff00ffff);
|
|
||||||
// circle.draw(&mut shm_pool);
|
|
||||||
|
|
||||||
let object = self.shm_id.load(Ordering::Relaxed);
|
let object = self.shm_id.load(Ordering::Relaxed);
|
||||||
if object == 0 {
|
if object == 0 {
|
||||||
return Err(UnsetErr("shm_id".to_string()).into());
|
return Err(UnsetErr("shm_id".to_string()).into());
|
||||||
@@ -61,17 +62,17 @@ impl WlClient {
|
|||||||
|
|
||||||
pub fn wl_shm_pool_create_buffer(
|
pub fn wl_shm_pool_create_buffer(
|
||||||
&self,
|
&self,
|
||||||
shm_offset: u32,
|
buffer: &wl_buffer
|
||||||
width: u32,
|
|
||||||
height: u32
|
|
||||||
) -> Result<(), Box<dyn Error>> {
|
) -> Result<(), Box<dyn Error>> {
|
||||||
let object: u32 = self.shmpool_id.load(Ordering::Relaxed);
|
let object: u32 = self.shmpool_id.load(Ordering::Relaxed);
|
||||||
const REQ_SIZE: u16 = 32;
|
const REQ_SIZE: u16 = 32;
|
||||||
const OPCODE: u16 = 0;
|
const OPCODE: u16 = 0;
|
||||||
|
|
||||||
|
let byte_offset: u32 = buffer.offset as u32 * 4;
|
||||||
|
let width: u32 = buffer.width as u32;
|
||||||
|
let height: u32 = buffer.height as u32;
|
||||||
let stride: u32 = width * 4;
|
let stride: u32 = width * 4;
|
||||||
let current_id = self.current_id.fetch_add(1, Ordering::Relaxed) + 1;
|
let id = buffer.id;
|
||||||
let id = current_id;
|
|
||||||
let format = 0;
|
let format = 0;
|
||||||
|
|
||||||
let mut offset: usize = 0;
|
let mut offset: usize = 0;
|
||||||
@@ -82,7 +83,7 @@ impl WlClient {
|
|||||||
request.write_u16(&REQ_SIZE, &mut offset);
|
request.write_u16(&REQ_SIZE, &mut offset);
|
||||||
|
|
||||||
request.write_u32(&id, &mut offset);
|
request.write_u32(&id, &mut offset);
|
||||||
request.write_u32(&shm_offset, &mut offset);
|
request.write_u32(&byte_offset, &mut offset);
|
||||||
request.write_u32(&width, &mut offset);
|
request.write_u32(&width, &mut offset);
|
||||||
request.write_u32(&height, &mut offset);
|
request.write_u32(&height, &mut offset);
|
||||||
request.write_u32(&stride, &mut offset);
|
request.write_u32(&stride, &mut offset);
|
||||||
@@ -90,9 +91,6 @@ impl WlClient {
|
|||||||
|
|
||||||
self.socket.lock().unwrap().write(&request)?;
|
self.socket.lock().unwrap().write(&request)?;
|
||||||
|
|
||||||
self.buffer_id.store(current_id, Ordering::Relaxed);
|
|
||||||
|
|
||||||
Ok(())
|
Ok(())
|
||||||
}
|
}
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|||||||
Reference in New Issue
Block a user