summaryrefslogtreecommitdiff
path: root/video/compositor.c
diff options
context:
space:
mode:
authorMiguel <m.i@gmx.at>2018-09-29 19:57:52 +0200
committerMiguel <m.i@gmx.at>2018-09-29 19:57:52 +0200
commit75433d155c152b809e9f25b1099fc06d6106308b (patch)
treef4f84309e6cf2aa9bc0d9df5ae532b94a60fea0f /video/compositor.c
parent73e80bf4b6c69b92a04b525f114a072a1c4b0d3a (diff)
improving window compositor
Diffstat (limited to 'video/compositor.c')
-rw-r--r--video/compositor.c125
1 files changed, 84 insertions, 41 deletions
diff --git a/video/compositor.c b/video/compositor.c
index 924664b..e5aa325 100644
--- a/video/compositor.c
+++ b/video/compositor.c
@@ -11,14 +11,16 @@
#include "lib/string/string.h"
+#define MAX_WINDOWS 100
+
static uint32_t backbuffer[VESA_MAX_WIDTH*VESA_MAX_HEIGHT];
static uint32_t bgimage[VESA_MAX_WIDTH*VESA_MAX_HEIGHT];
static uint32_t *vmem=VMEM_FRAMEBUFFER;
struct window
{
- uint16_t posx;
- uint16_t posy;
+ int16_t posx;
+ int16_t posy;
uint16_t width;
uint16_t height;
uint32_t color;
@@ -26,14 +28,12 @@ struct window
struct pdirectory *vmem;
};
+struct window windows[MAX_WINDOWS];
+
static uint16_t next_window=0;
static uint16_t next_x=50;
static uint16_t next_y=50;
-#define MAX_WINDOWS 100
-
-struct window windows[MAX_WINDOWS];
-
static uint16_t vesa_width;
static uint16_t vesa_height;
static uint16_t vesa_pitch;
@@ -47,32 +47,26 @@ static void put_pixel(int x,int y, uint32_t color)
vmem[y*vesa_width+x]=color;
}
-static void put_rect(struct window *win)
+static void put_win(struct window *win)
{
- struct pdirectory* mydir=x86_get_page_directory();
- if(win->vmem)
- {
- x86_set_page_directory(win->vmem);
- }
+ struct pdirectory* mydir=x86_get_page_directory();
-uint32_t *user_vmem=VMEM_USER_FRAMEBUFFER;
-uint32_t userx=0;
-uint32_t usery=0;
+ if(win->vmem)
+ {
+ x86_set_page_directory(win->vmem);
+ }
+ uint32_t *user_vmem=VMEM_USER_FRAMEBUFFER;
+ uint32_t userx=0;
+ uint32_t usery=0;
- for(uint16_t x=win->posx;x<win->posx+win->width;x++)
- {
- backbuffer[(win->posy-1)*vesa_width+x]=0xffffff;
- backbuffer[(win->posy+win->height)*vesa_width+x]=0xffffff;
- }
+ // iterate over complete window area
for(uint16_t x=win->posx;x<win->posx+win->width;x++)
{
usery=0;
- userx++;
for(uint16_t y=win->posy;y<win->posy+win->height;y++)
{
- usery++;
if(!win->active)
{
uint8_t dst_b=backbuffer[y*vesa_width+x]&0xff;
@@ -82,31 +76,43 @@ uint32_t usery=0;
uint8_t src_b=win->color&0xff;
uint8_t src_g=(win->color&0xff00)>>8;
uint8_t src_r=(win->color&0xff0000)>>16;
+ uint16_t a;
- //we encoded alpha in the highest octet. 1-opaque 0-transparent
- //user premultiplied alpha please!
- uint16_t a=(0xff-((win->color&0xff000000)>>24));
-
- uint8_t out_r=src_r+((a*dst_r)>>8);
- uint8_t out_g=src_g+((a*dst_g)>>8);
- uint8_t out_b=src_b+((a*dst_b)>>8);
-
- if(win->vmem)
- {
- if(userx<640&&usery<480)backbuffer[y*vesa_width+x]=user_vmem[userx+usery*640];
- }
-
+ if(win->vmem)
+ {
+ uint32_t col=0xff0000;
+ col=user_vmem[userx+usery*640];
+ src_b=col&0xff;
+ src_g=(col&0xff00)>>8;
+ src_r=(col&0xff0000)>>16;
+ a=0x44;
+ }
else
{
- backbuffer[y*vesa_width+x]=(out_r<<16)+(out_g<<8)+out_b;
+ // just for testing
+ src_b=win->color&0xff;
+ src_g=(win->color&0xff00)>>8;
+ src_r=(win->color&0xff0000)>>16;
+
+ a=(0xff-((win->color&0xff000000)>>24));
}
+ //we encoded alpha in the highest octet. 1-opaque 0-transparent
+ //no premultiplied alpha. TODO: change maybe?
+ //
+
+ uint8_t out_r=((src_r*(0xff-a))>>8)+((a*dst_r)>>8);
+ uint8_t out_g=((src_g*(0xff-a))>>8)+((a*dst_g)>>8);
+ uint8_t out_b=((src_b*(0xff-a))>>8)+((a*dst_b)>>8);
+
+ backbuffer[y*vesa_width+x]=(out_r<<16)+(out_g<<8)+out_b;
+
}
else
{
if(win->vmem)
{
- if(userx<640&&usery<480)backbuffer[y*vesa_width+x]=~(user_vmem[userx+usery*640]);
+ backbuffer[y*vesa_width+x]=(user_vmem[userx+usery*640]);
}
else
{
@@ -114,13 +120,29 @@ uint32_t usery=0;
}
}
+ usery++;
}
+ userx++;
}
if(win->vmem)
{
x86_set_page_directory(mydir);
- }
+ }
+
+ //draw boundaries
+ for(uint16_t x=win->posx;x<win->posx+win->width;x++)
+ {
+ backbuffer[(win->posy)*vesa_width+x]=0xffffff; //TOP
+ backbuffer[(win->posy+win->height-1)*vesa_width+x]=0xffffff; //BOTTOM
+ //backbuffer[(win->posy+win->height-3)*vesa_width+x]=0xffffff; //BOTTOM
+ }
+ for(uint16_t y=win->posy;y<win->posy+win->height;y++)
+ {
+ backbuffer[(y)*vesa_width+(win->posx)]=0xffffff; //LEFT
+ backbuffer[(y)*vesa_width+win->posx+win->width-1]=0xffffff; //RIGHT
+ }
+ //
}
static void put_mouse()
@@ -139,6 +161,22 @@ static void put_mouse()
}
}
+void compositor_del_window(uint32_t addr)
+{
+ for(int i=0;i<next_window;i++)
+ {
+ if(windows[i].vmem==(void *)addr)
+ {
+ if(i!=next_window-1)
+ {
+ windows[i]=windows[next_window-1];
+ }
+
+ next_window--;
+ }
+ }
+}
+
void compositor_add_window(uint32_t addr)
{
if (next_window>=MAX_WINDOWS)kpanic("max number of windows reached. increase MAX_WINDOWS");
@@ -161,7 +199,6 @@ void compositor_add_window(uint32_t addr)
next_window++;
}
-
void compositor_init(uint16_t width, uint16_t height, uint16_t pitch)
{
vesa_width=width;
@@ -178,7 +215,7 @@ void compositor_swap_buffers()
for(int i=next_window-1;i>=0;i--)
{
- put_rect(&windows[i]);
+ put_win(&windows[i]);
}
put_mouse();
@@ -212,8 +249,15 @@ void compositor_mouse_handle(uint16_t x,uint16_t y, uint8_t key)
{
w->posx-=last_mouse_x-mouse_x;
last_mouse_x=mouse_x;
+
w->posy-=last_mouse_y-mouse_y;
last_mouse_y=mouse_y;
+
+ if(w->posx<0)w->posx=0;
+ if(w->posy<0)w->posy=0;
+ if(w->posx+w->width>=1920)w->posx=1920-640;
+ if(w->posy+w->height>=1080)w->posy=1080-480;
+
}
w->active=true;
@@ -253,5 +297,4 @@ void compositor_set_background(char *ppm_raw_filename)
}
klog("finished");
-
}