1 /* 2 * Copyright 2006-2008, Haiku, Inc. All Rights Reserved. 3 * Distributed under the terms of the MIT License. 4 * 5 * Authors: 6 * Axel Dörfler, axeld@pinc-software.de 7 */ 8 9 10 #include "accelerant_protos.h" 11 #include "accelerant.h" 12 13 #include <string.h> 14 15 16 status_t 17 intel_set_cursor_shape(uint16 width, uint16 height, uint16 hotX, uint16 hotY, 18 uint8* andMask, uint8* xorMask) 19 { 20 if (width > 64 || height > 64) 21 return B_BAD_VALUE; 22 23 write32(INTEL_CURSOR_CONTROL, 0); 24 // disable cursor 25 26 // In two-color mode, the data is ordered as follows (always 64 bit per 27 // line): 28 // plane 1: line 0 (AND mask) 29 // plane 0: line 0 (XOR mask) 30 // plane 1: line 1 (AND mask) 31 // ... 32 // 33 // If the planes add to the value 0x2, the corresponding pixel is 34 // transparent, for 0x3 it inverts the background, so only the first 35 // two palette entries will be used (since we're using the 2 color mode). 36 37 uint8* data = gInfo->shared_info->cursor_memory; 38 uint8 byteWidth = (width + 7) / 8; 39 40 for (int32 y = 0; y < height; y++) { 41 for (int32 x = 0; x < byteWidth; x++) { 42 data[16 * y + x] = andMask[byteWidth * y + x]; 43 data[16 * y + x + 8] = xorMask[byteWidth * y + x]; 44 } 45 } 46 47 // set palette entries to white/black 48 write32(INTEL_CURSOR_PALETTE + 0, 0x00ffffff); 49 write32(INTEL_CURSOR_PALETTE + 4, 0); 50 51 gInfo->shared_info->cursor_format = CURSOR_FORMAT_2_COLORS; 52 53 write32(INTEL_CURSOR_CONTROL, 54 CURSOR_ENABLED | gInfo->shared_info->cursor_format); 55 write32(INTEL_CURSOR_SIZE, height << 12 | width); 56 57 write32(INTEL_CURSOR_BASE, 58 (uint32)gInfo->shared_info->physical_graphics_memory 59 + gInfo->shared_info->cursor_buffer_offset); 60 61 // changing the hot point changes the cursor position, too 62 63 if (hotX != gInfo->shared_info->cursor_hot_x 64 || hotY != gInfo->shared_info->cursor_hot_y) { 65 int32 x = read32(INTEL_CURSOR_POSITION); 66 int32 y = x >> 16; 67 x &= 0xffff; 68 69 if (x & CURSOR_POSITION_NEGATIVE) 70 x = -(x & CURSOR_POSITION_MASK); 71 if (y & CURSOR_POSITION_NEGATIVE) 72 y = -(y & CURSOR_POSITION_MASK); 73 74 x += gInfo->shared_info->cursor_hot_x; 75 y += gInfo->shared_info->cursor_hot_y; 76 77 gInfo->shared_info->cursor_hot_x = hotX; 78 gInfo->shared_info->cursor_hot_y = hotY; 79 80 intel_move_cursor(x, y); 81 } 82 83 return B_OK; 84 } 85 86 87 void 88 intel_move_cursor(uint16 _x, uint16 _y) 89 { 90 int32 x = (int32)_x - gInfo->shared_info->cursor_hot_x; 91 int32 y = (int32)_y - gInfo->shared_info->cursor_hot_x; 92 93 if (x < 0) 94 x = -x | CURSOR_POSITION_NEGATIVE; 95 if (y < 0) 96 y = -y | CURSOR_POSITION_NEGATIVE; 97 98 write32(INTEL_CURSOR_POSITION, (y << 16) | x); 99 } 100 101 102 void 103 intel_show_cursor(bool isVisible) 104 { 105 if (gInfo->shared_info->cursor_visible == isVisible) 106 return; 107 108 write32(INTEL_CURSOR_CONTROL, (isVisible ? CURSOR_ENABLED : 0) 109 | gInfo->shared_info->cursor_format); 110 write32(INTEL_CURSOR_BASE, 111 (uint32)gInfo->shared_info->physical_graphics_memory 112 + gInfo->shared_info->cursor_buffer_offset); 113 114 gInfo->shared_info->cursor_visible = isVisible; 115 } 116 117