📄 x.c
字号:
case 386: case 452: case 708:/* printf("depth=%d visualid=%x\n",x_driver.depth, vinfo.visualid); */ break; default: { unsigned char nevidim_te_ani_te_neslysim_ale_smrdis_jako_lejno[MAX_STR_LEN]; snprintf(nevidim_te_ani_te_neslysim_ale_smrdis_jako_lejno,MAX_STR_LEN, "Unsupported graphics mode: x_depth=%d, bits_per_pixel=%d, bytes_per_pixel=%d\n",x_driver.depth, x_depth, x_bitmap_bpp); x_free_hash_table(); if (x_driver_param) mem_free(x_driver_param); return stracpy(nevidim_te_ani_te_neslysim_ale_smrdis_jako_lejno); } } x_get_color_function=get_color_fn(x_driver.depth); if (!x_get_color_function) internal("Unknown bit depth: %d", x_driver.depth);#ifdef X_DEBUG { unsigned char txt[256]; sprintf(txt,"x_driver.depth=%d\n",x_driver.depth); MESSAGE(txt); }#endif x_colors=1<<x_depth; x_have_palette=0; if (vinfo.class==DirectColor||vinfo.class==PseudoColor) { unsigned char *t; x_have_palette=1; if((t=x_set_palette())){x_free_hash_table(); if (x_driver_param) mem_free(x_driver_param); return t;} } x_black_pixel=BlackPixel(x_display,x_screen); x_white_pixel=WhitePixel(x_display,x_screen); gcv.function=GXcopy; gcv.graphics_exposures=True; /* we want to receive GraphicsExpose events when uninitialized area is discovered during scroll */ gcv.fill_style=FillSolid; gcv.background=x_black_pixel; set_handlers(x_fd,x_process_events,0,0,0); x_delete_window_atom=XInternAtom(x_display,"WM_DELETE_WINDOW", False); x_wm_protocols_atom=XInternAtom(x_display,"WM_PROTOCOLS", False); x_sel_atom= XInternAtom(x_display, "SEL_PROP", False); x_targets_atom= XInternAtom(x_display, "TARGETS", False); if (x_have_palette) win_attr.colormap=x_colormap; else win_attr.colormap=XCreateColormap(x_display, x_root_window, x_default_visual, AllocNone); win_attr.border_pixel=x_black_pixel; fake_window=XCreateWindow( x_display, x_root_window, 0, 0, 10, 10, 0, x_depth, CopyFromParent, x_default_visual, CWColormap|CWBorderPixel, &win_attr ); x_normal_gc=XCreateGC(x_display,fake_window,GCFillStyle|GCBackground,&gcv); if (!x_normal_gc) {x_free_hash_table(); if (x_driver_param) mem_free(x_driver_param); return stracpy("Cannot create graphic context.\n");} x_copy_gc=XCreateGC(x_display,fake_window,GCFunction,&gcv); if (!x_copy_gc) {x_free_hash_table(); if (x_driver_param) mem_free(x_driver_param); return stracpy("Cannot create graphic context.\n");} x_drawbitmap_gc=XCreateGC(x_display,fake_window,GCFunction,&gcv); if (!x_drawbitmap_gc) {x_free_hash_table(); if (x_driver_param) mem_free(x_driver_param); return stracpy("Cannot create graphic context.\n");} x_scroll_gc=XCreateGC(x_display,fake_window,GCGraphicsExposures|GCBackground,&gcv); if (!x_scroll_gc) {x_free_hash_table(); if (x_driver_param) mem_free(x_driver_param); return stracpy("Cannot create graphic context.\n");} XSetLineAttributes(x_display,x_normal_gc,1,LineSolid,CapRound,JoinRound); XSync(x_display,False); register_bottom_half(x_process_events, NULL); return NULL;}/* close connection with the X server */static void x_shutdown_driver(void){#ifdef X_DEBUG MESSAGE("x_shutdown_driver\n");#endif XDestroyWindow(x_display,fake_window); XFreeGC(x_display,x_normal_gc); XFreeGC(x_display,x_copy_gc); XFreeGC(x_display,x_drawbitmap_gc); XFreeGC(x_display,x_scroll_gc); XCloseDisplay(x_display); x_free_hash_table(); if (x_driver_param)mem_free(x_driver_param); x_clear_clipboard();}/* create new window */static struct graphics_device* x_init_device(void){ struct graphics_device *gd; Window *win; XWMHints wm_hints; XClassHint class_hints; XTextProperty windowName; char *links_name="Links"; XSetWindowAttributes win_attr;#ifdef X_DEBUG MESSAGE("x_init_device\n");#endif gd=mem_alloc(sizeof(struct graphics_device)); win=mem_alloc(sizeof(Window)); gd->size.x1=0; gd->size.y1=0; gd->size.x2=x_default_window_width; gd->size.y2=x_default_window_height; if (x_have_palette) win_attr.colormap=x_colormap; else win_attr.colormap=XCreateColormap(x_display, x_root_window, x_default_visual, AllocNone); win_attr.border_pixel=x_black_pixel; *win=XCreateWindow( x_display, x_root_window, gd->size.x1, gd->size.y1, gd->size.x2, gd->size.y2, X_BORDER_WIDTH, x_depth, InputOutput, x_default_visual, CWColormap|CWBorderPixel, &win_attr ); if (!x_icon) { XImage *img; unsigned char *data; int w,h; get_links_icon(&data,&w,&h,x_driver.depth); img=XCreateImage(x_display,x_default_visual,x_depth,ZPixmap,0,0,w,h,x_bitmap_scanline_pad<<3,w*((x_driver.depth)&7)); if (!img){x_icon=0;goto nic_nebude_bobankove;} img->data=data; x_icon=XCreatePixmap(x_display,*win,w,h,x_depth); if (!x_icon){XDestroyImage(img);x_icon=0;goto nic_nebude_bobankove;} XPutImage(x_display,x_icon,x_copy_gc,img,0,0,0,0,w,h); XDestroyImage(img);nic_nebude_bobankove:; } wm_hints.flags=InputHint; wm_hints.input=True; if (x_icon) { wm_hints.flags=InputHint|IconPixmapHint; wm_hints.icon_pixmap=x_icon; } XSetWMHints(x_display, *win, &wm_hints); class_hints.res_name = links_name; class_hints.res_class = links_name; XSetClassHint(x_display, *win, &class_hints); XStringListToTextProperty(&links_name, 1, &windowName); XSetWMName(x_display, *win, &windowName); XStoreName(x_display,*win,links_name); XSetWMIconName(x_display, *win, &windowName); XMapWindow(x_display,*win); gd->clip.x1=gd->size.x1; gd->clip.y1=gd->size.y1; gd->clip.x2=gd->size.x2; gd->clip.y2=gd->size.y2; gd->drv=&x_driver; gd->driver_data=win; gd->user_data=0; XSetWindowBackgroundPixmap(x_display, *win, None); if (x_have_palette) XSetWindowColormap(x_display,*win,x_colormap); if (x_add_to_table(gd)){mem_free(win);mem_free(gd);return NULL;} XSetWMProtocols(x_display,*win,&x_delete_window_atom,1); XSelectInput(x_display,*win, ExposureMask| KeyPressMask| ButtonPressMask| ButtonReleaseMask| PointerMotionMask| ButtonMotionMask| StructureNotifyMask| 0 ); XSync(x_display,False); register_bottom_half(x_process_events, NULL); n_wins++; return gd;}/* close window */static void x_shutdown_device(struct graphics_device *gd){#ifdef X_DEBUG MESSAGE("x_shutdown_device\n");#endif if (!gd)return; n_wins--; XDestroyWindow(x_display,*(Window*)(gd->driver_data)); XSync(x_display,False); register_bottom_half(x_process_events, NULL); x_remove_from_table((Window*)(gd->driver_data)); mem_free(gd->driver_data); mem_free(gd);}/* n is in bytes. dest must begin on pixel boundary. If n is not a whole number * of pixels, rounding is performed downwards. */static inline void pixel_set(unsigned char *dest, int n,void * pattern){ int a; internal("ma to v sobe FIXME, tak jsem to zablokoval, aby to nikdo nepouzival"); /* Originally there was vga_bytes here but this function is not * used in planar modes so that it's OK :-) */ switch(x_bitmap_bpp) { case 1: memset(dest,*(char *)pattern,n); break; case 2: { short v=*(short *)pattern; /* !!! FIXME: nezavislost !!! */ int a; for (a=0;a<(n>>1);a++) ((short *)dest)[a]=v; } break; case 3: { unsigned char a,b,c; int i; a=*(char*)pattern; b=((char*)pattern)[1]; c=((char*)pattern)[2]; i=n/3; for (i=n/3;i;i--){ dest[0]=a; dest[1]=b; dest[2]=c; dest+=3; } } break; case 4: { long v=*(long *)pattern; /* !!! FIXME: nezavislost !!! */ int a; for (a=0;a<(n>>2);a++) ((long *)dest)[a]=v; } break; default: for (a=0;a<n/x_bitmap_bpp;a++,dest+=x_bitmap_bpp) memcpy(dest,pattern,x_bitmap_bpp); break; } }/*static int x_get_filled_bitmap(struct bitmap *bmp, long color){ struct x_pixmapa *p; XImage *image; Pixmap *pixmap; int pad;#ifdef X_DEBUG MESSAGE("x_get_filled_bitmap\n");#endif if (!bmp||!bmp->x||!bmp->y)internal("x_get_filled_bitmap called with strange arguments.\n"); p=mem_alloc(sizeof(struct x_pixmapa)); bmp->flags=p; pad=x_bitmap_scanline_pad-((bmp->x*x_bitmap_bpp)%x_bitmap_scanline_pad); if (pad==x_bitmap_scanline_pad)pad=0; bmp->skip=bmp->x*x_bitmap_bpp+pad; pixmap=mem_alloc(sizeof(Pixmap)); (*pixmap)=XCreatePixmap(x_display,fake_window,bmp->x,bmp->y,x_depth); if (!(*pixmap)) { int a; unsigned char *ptr; int PerM_si_odalokoval_vlastni_pytlik=(bmp->x*x_bitmap_bpp); mem_free(pixmap); p->type=X_TYPE_IMAGE; bmp->data=malloc(bmp->skip*bmp->y); if (!bmp->data)malloc_oom(); image=XCreateImage(x_display,x_default_visual,x_depth,ZPixmap,0,0,bmp->x,bmp->y,x_bitmap_scanline_pad<<3,bmp->skip); if (!image)internal("Cannot create image.\n"); image->data=bmp->data; for (a=0,ptr=image->data;a<bmp->y;a++,ptr+=bmp->skip) pixel_set(ptr,PerM_si_odalokoval_vlastni_pytlik,(void*)color); p->data.image=image; return 0; } else { XSetForeground(x_display,x_normal_gc,color); XFillRectangle( x_display, *pixmap, x_normal_gc, 0, 0, bmp->x, bmp->y ); p->type=X_TYPE_PIXMAP; p->data.pixmap=pixmap; return 2; }}*/static int x_get_empty_bitmap(struct bitmap *bmp){ int pad;#ifdef X_DEBUG MESSAGE("x_get_empty_bitmap\n");#endif pad=x_bitmap_scanline_pad-((bmp->x*x_bitmap_bpp)%x_bitmap_scanline_pad); if (pad==x_bitmap_scanline_pad)pad=0; bmp->skip=bmp->x*x_bitmap_bpp+pad; if (!(bmp->data=malloc(bmp->skip*bmp->y))) malloc_oom(); /* on error bmp->data should point to NULL */ bmp->flags=0; return 0;}static void x_unregister_bitmap(struct bitmap *bmp){#ifdef X_DEBUG MESSAGE("x_unregister_bitmap\n");#endif if (!bmp)return; if (!bmp->flags){free(bmp->data);return;} switch(XPIXMAPP(bmp->flags)->type) { case X_TYPE_PIXMAP: XFreePixmap(x_display,*(XPIXMAPP(bmp->flags)->data.pixmap)); /* free XPixmap from server's memory */ mem_free(XPIXMAPP(bmp->flags)->data.pixmap); /* XPixmap */ break; case X_TYPE_IMAGE: XDestroyImage(XPIXMAPP(bmp->flags)->data.image); /* free XImage from client's memory */ break; } mem_free(bmp->flags); /* struct x_pixmap */}/* prekonvertuje long z host do xserver byte order */static inline long _host_to_server(long num){ /* endianity test */ int big=(htonl(0x12345678L)==0x12345678L); /* nedelam to makrama, protoze tohle chodi i pri cross-kompilaci */ switch(x_bitmap_bit_order) { case LSBFirst: if (big) { /* je to sice VODPORNE POMALY, ale prenositelny */ unsigned char bla[sizeof(long)]; int a; for (a=0;a<(int)sizeof(long);a++) bla[a]=num&255,num>>=8; num=0; for (a=0;a<(int)sizeof(long);a++) num<<=8,num+=bla[a]; return num; } return num; case MSBFirst: if (big)return num; return htonl(num); default: internal("Unknown endianity got from xlib.\n"); } return 0; /* aby GCC melo radost */}static long x_get_color(int rgb){ long block; #ifdef X_DEBUG MESSAGE("x_get_color\n");#endif block=x_get_color_function(rgb); if (x_bitmap_bpp==1)return block; return _host_to_server(block);}static void x_fill_area(struct graphics_device *dev, int x1, int y1, int x2, int y2, long color){ /*int a;*/ #ifdef X_DEBUG { unsigned char txt[256]; sprintf(txt,"x_fill_area (x1=%d y1=%d x2=%d y2=%d)\n",x1,y1,x2,y2); MESSAGE(txt); }#endif /* Mikulas: v takovem pripade radsi neplnit nic ... */ /* if (x1>x2){a=x2;x2=x1;x1=a;} if (y1>y2){a=y2;y2=y1;y1=a;} */ if (x1 < dev->clip.x1) x1 = dev->clip.x1; if (x2 > dev->clip.x2) x2 = dev->clip.x2; if (y1 < dev->clip.y1) y1 = dev->clip.y1; if (y2 > dev->clip.y2) y2 = dev->clip.y2; if (x1>=x2) return; if (y1>=y2) return; XSetForeground(x_display,x_normal_gc,color); XFillRectangle( x_display, *((Window*)(dev->driver_data)), x_normal_gc, x1, y1, x2-x1, y2-y1 ); X_FLUSH();} static void x_draw_hline(struct graphics_device *dev, int left, int y, int right, long color){#ifdef X_DEBUG MESSAGE("x_draw_hline\n");#endif if (left>=right)return; if ((y>=dev->clip.y2)||(y<dev->clip.y1)) return; if (right<=dev->clip.x1||left>=dev->clip.x2)return; XSetForeground(x_display,x_normal_gc,color); XDrawLine( x_display, *((Window*)(dev->driver_data)), x_normal_gc, left,y,right-1,y ); X_FLUSH();}static void x_draw_vline(struct graphics_device *dev, int x, int top, int bottom, long color){#ifdef X_DEBUG MESSAGE("x_draw_vline\n");#endif if (top>=bottom)return; if ((x>=dev->clip.x2)||(x<dev->clip.x1)) return; if (bottom<=dev->clip.y1||top>=dev->clip.y2)return; XSetForeground(x_display,x_normal_gc,color); XDrawLine( x_display, *((Window*)(dev->driver_data)), x_normal_gc, x,top,x,bottom-1 ); X_FLUSH();}static void x_set_clip_area(struct graphics_device *dev, struct rect *r){ XRectangle xr; #ifdef X_DEBUG { unsigned char txt[512]; snprintf(txt,512,"x_set_clip_area(x1=%d, y1=%d, x2=%d, y2=%d\n",r->x1,r->y1,r->x2,r->y2); MESSAGE(txt); }#endif dev->clip.x1=r->x1; dev->clip.x2=r->x2; dev->clip.y1=r->y1; dev->clip.y2=r->y2; xr.x=r->x1; xr.y=r->y1; if (r->x2<r->x1)xr.width=0; else xr.width=(r->x2)-(r->x1); if (r->y2<r->y1)xr.height=0; else xr.height=(r->y2)-(r->y1); XSetClipRectangles(x_display,x_normal_gc,0,0,&xr,1,Unsorted); XSetClipRectangles(x_display,x_scroll_gc,0,0,&xr,1,Unsorted); XSetClipRectangles(x_display,x_drawbitmap_gc,0,0,&xr,1,Unsorted); X_FLUSH();}static void x_draw_bitmap(struct graphics_device *dev, struct bitmap *bmp, int x, int y){ int bmp_off_x, bmp_off_y, bmp_size_x, bmp_size_y;#ifdef X_DEBUG MESSAGE("x_draw_bitmap\n");#endif if (!bmp||!(bmp->flags)||!bmp->x||!bmp->y) return; if ((x>=dev->clip.x2)||(y>=dev->clip.y2)) return;
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -