1*68353368SRudolf Cornelissen /* 2*68353368SRudolf Cornelissen Copyright 1999, Be Incorporated. All Rights Reserved. 3*68353368SRudolf Cornelissen This file may be used under the terms of the Be Sample Code License. 4*68353368SRudolf Cornelissen 5*68353368SRudolf Cornelissen Other authors: 6*68353368SRudolf Cornelissen Mark Watson, 7*68353368SRudolf Cornelissen Rudolf Cornelissen 4/2003-5/2004 8*68353368SRudolf Cornelissen */ 9*68353368SRudolf Cornelissen 10*68353368SRudolf Cornelissen #define MODULE_BIT 0x20000000 11*68353368SRudolf Cornelissen 12*68353368SRudolf Cornelissen #include "acc_std.h" 13*68353368SRudolf Cornelissen 14*68353368SRudolf Cornelissen status_t SET_CURSOR_SHAPE(uint16 width, uint16 height, uint16 hot_x, uint16 hot_y, uint8 *andMask, uint8 *xorMask) 15*68353368SRudolf Cornelissen { 16*68353368SRudolf Cornelissen LOG(4,("SET_CURSOR_SHAPE: width %d, height %d, hot_x %d, hot_y %d\n", 17*68353368SRudolf Cornelissen width, height, hot_x, hot_y)); 18*68353368SRudolf Cornelissen 19*68353368SRudolf Cornelissen if ((width != 16) || (height != 16)) 20*68353368SRudolf Cornelissen { 21*68353368SRudolf Cornelissen return B_ERROR; 22*68353368SRudolf Cornelissen } 23*68353368SRudolf Cornelissen else if ((hot_x >= width) || (hot_y >= height)) 24*68353368SRudolf Cornelissen { 25*68353368SRudolf Cornelissen return B_ERROR; 26*68353368SRudolf Cornelissen } 27*68353368SRudolf Cornelissen else 28*68353368SRudolf Cornelissen { 29*68353368SRudolf Cornelissen head1_cursor_define(andMask,xorMask); 30*68353368SRudolf Cornelissen if ((si->dm.flags & DUALHEAD_BITS) != DUALHEAD_OFF) 31*68353368SRudolf Cornelissen head2_cursor_define(andMask,xorMask); 32*68353368SRudolf Cornelissen 33*68353368SRudolf Cornelissen /* Update cursor variables appropriately. */ 34*68353368SRudolf Cornelissen si->cursor.width = width; 35*68353368SRudolf Cornelissen si->cursor.height = height; 36*68353368SRudolf Cornelissen si->cursor.hot_x = hot_x; 37*68353368SRudolf Cornelissen si->cursor.hot_y = hot_y; 38*68353368SRudolf Cornelissen } 39*68353368SRudolf Cornelissen 40*68353368SRudolf Cornelissen return B_OK; 41*68353368SRudolf Cornelissen } 42*68353368SRudolf Cornelissen 43*68353368SRudolf Cornelissen /* Move the cursor to the specified position on the desktop, taking account of virtual/dual issues */ 44*68353368SRudolf Cornelissen void MOVE_CURSOR(uint16 x, uint16 y) 45*68353368SRudolf Cornelissen { 46*68353368SRudolf Cornelissen uint16 hds = si->dm.h_display_start; /* the current horizontal starting pixel */ 47*68353368SRudolf Cornelissen uint16 vds = si->dm.v_display_start; /* the current vertical starting line */ 48*68353368SRudolf Cornelissen uint16 h_adjust; 49*68353368SRudolf Cornelissen 50*68353368SRudolf Cornelissen /* clamp cursor to display */ 51*68353368SRudolf Cornelissen if (x >= si->dm.virtual_width) x = si->dm.virtual_width - 1; 52*68353368SRudolf Cornelissen if (y >= si->dm.virtual_height) y = si->dm.virtual_height - 1; 53*68353368SRudolf Cornelissen 54*68353368SRudolf Cornelissen /* store, for our info */ 55*68353368SRudolf Cornelissen si->cursor.x = x; 56*68353368SRudolf Cornelissen si->cursor.y = y; 57*68353368SRudolf Cornelissen 58*68353368SRudolf Cornelissen /* setting up minimum amount to scroll not needed: 59*68353368SRudolf Cornelissen * Nvidia cards can always do pixelprecise panning on both heads */ 60*68353368SRudolf Cornelissen h_adjust = 0x00; 61*68353368SRudolf Cornelissen 62*68353368SRudolf Cornelissen /* adjust h/v_display_start to move cursor onto screen */ 63*68353368SRudolf Cornelissen switch (si->dm.flags & DUALHEAD_BITS) 64*68353368SRudolf Cornelissen { 65*68353368SRudolf Cornelissen case DUALHEAD_ON: 66*68353368SRudolf Cornelissen case DUALHEAD_SWITCH: 67*68353368SRudolf Cornelissen if (x >= ((si->dm.timing.h_display * 2) + hds)) 68*68353368SRudolf Cornelissen { 69*68353368SRudolf Cornelissen hds = ((x - (si->dm.timing.h_display * 2)) + 1 + h_adjust) & ~h_adjust; 70*68353368SRudolf Cornelissen /* make sure we stay within the display! */ 71*68353368SRudolf Cornelissen if ((hds + (si->dm.timing.h_display * 2)) > si->dm.virtual_width) 72*68353368SRudolf Cornelissen hds -= (h_adjust + 1); 73*68353368SRudolf Cornelissen } 74*68353368SRudolf Cornelissen else if (x < hds) 75*68353368SRudolf Cornelissen hds = x & ~h_adjust; 76*68353368SRudolf Cornelissen break; 77*68353368SRudolf Cornelissen default: 78*68353368SRudolf Cornelissen if (x >= (si->dm.timing.h_display + hds)) 79*68353368SRudolf Cornelissen { 80*68353368SRudolf Cornelissen hds = ((x - si->dm.timing.h_display) + 1 + h_adjust) & ~h_adjust; 81*68353368SRudolf Cornelissen /* make sure we stay within the display! */ 82*68353368SRudolf Cornelissen if ((hds + si->dm.timing.h_display) > si->dm.virtual_width) 83*68353368SRudolf Cornelissen hds -= (h_adjust + 1); 84*68353368SRudolf Cornelissen } 85*68353368SRudolf Cornelissen else if (x < hds) 86*68353368SRudolf Cornelissen hds = x & ~h_adjust; 87*68353368SRudolf Cornelissen break; 88*68353368SRudolf Cornelissen } 89*68353368SRudolf Cornelissen 90*68353368SRudolf Cornelissen if (y >= (si->dm.timing.v_display + vds)) 91*68353368SRudolf Cornelissen vds = y - si->dm.timing.v_display + 1; 92*68353368SRudolf Cornelissen else if (y < vds) 93*68353368SRudolf Cornelissen vds = y; 94*68353368SRudolf Cornelissen 95*68353368SRudolf Cornelissen /* reposition the desktop _and_ the overlay on the display if required */ 96*68353368SRudolf Cornelissen if ((hds!=si->dm.h_display_start) || (vds!=si->dm.v_display_start)) 97*68353368SRudolf Cornelissen { 98*68353368SRudolf Cornelissen MOVE_DISPLAY(hds,vds); 99*68353368SRudolf Cornelissen nv_bes_move_overlay(); 100*68353368SRudolf Cornelissen } 101*68353368SRudolf Cornelissen 102*68353368SRudolf Cornelissen /* put cursor in correct physical position, so stay onscreen (rel. to CRTC) */ 103*68353368SRudolf Cornelissen if (x > (hds + si->cursor.hot_x)) x -= (hds + si->cursor.hot_x); 104*68353368SRudolf Cornelissen else x = 0; 105*68353368SRudolf Cornelissen if (y > (vds + si->cursor.hot_y)) y -= (vds + si->cursor.hot_y); 106*68353368SRudolf Cornelissen else y = 0; 107*68353368SRudolf Cornelissen 108*68353368SRudolf Cornelissen /* position the cursor on the display */ 109*68353368SRudolf Cornelissen switch (si->dm.flags & DUALHEAD_BITS) 110*68353368SRudolf Cornelissen { 111*68353368SRudolf Cornelissen case DUALHEAD_CLONE: 112*68353368SRudolf Cornelissen head1_cursor_position(x,y); 113*68353368SRudolf Cornelissen head2_cursor_position(x,y); 114*68353368SRudolf Cornelissen break; 115*68353368SRudolf Cornelissen case DUALHEAD_ON: 116*68353368SRudolf Cornelissen case DUALHEAD_SWITCH: 117*68353368SRudolf Cornelissen if (x < si->dm.timing.h_display) 118*68353368SRudolf Cornelissen { 119*68353368SRudolf Cornelissen if (si->cursor.dh_right) 120*68353368SRudolf Cornelissen { 121*68353368SRudolf Cornelissen LOG(4,("MOVE_CURSOR: now on left side\n")); 122*68353368SRudolf Cornelissen head2_cursor_hide(); 123*68353368SRudolf Cornelissen head1_cursor_show(); 124*68353368SRudolf Cornelissen si->cursor.dh_right = false; 125*68353368SRudolf Cornelissen } 126*68353368SRudolf Cornelissen head1_cursor_position(x, y); 127*68353368SRudolf Cornelissen } 128*68353368SRudolf Cornelissen else 129*68353368SRudolf Cornelissen { 130*68353368SRudolf Cornelissen if (!si->cursor.dh_right) 131*68353368SRudolf Cornelissen { 132*68353368SRudolf Cornelissen LOG(4,("MOVE_CURSOR: now on right side\n")); 133*68353368SRudolf Cornelissen head1_cursor_hide(); 134*68353368SRudolf Cornelissen head2_cursor_show(); 135*68353368SRudolf Cornelissen si->cursor.dh_right = true; 136*68353368SRudolf Cornelissen } 137*68353368SRudolf Cornelissen head2_cursor_position((x - si->dm.timing.h_display), y); 138*68353368SRudolf Cornelissen } 139*68353368SRudolf Cornelissen break; 140*68353368SRudolf Cornelissen default: /* singlehead mode */ 141*68353368SRudolf Cornelissen head1_cursor_position(x,y); 142*68353368SRudolf Cornelissen break; 143*68353368SRudolf Cornelissen } 144*68353368SRudolf Cornelissen } 145*68353368SRudolf Cornelissen 146*68353368SRudolf Cornelissen void SHOW_CURSOR(bool is_visible) 147*68353368SRudolf Cornelissen { 148*68353368SRudolf Cornelissen /* record for our info */ 149*68353368SRudolf Cornelissen si->cursor.is_visible = is_visible; 150*68353368SRudolf Cornelissen 151*68353368SRudolf Cornelissen switch (si->dm.flags & DUALHEAD_BITS) 152*68353368SRudolf Cornelissen { 153*68353368SRudolf Cornelissen case DUALHEAD_CLONE: 154*68353368SRudolf Cornelissen if (is_visible) 155*68353368SRudolf Cornelissen { 156*68353368SRudolf Cornelissen head1_cursor_show(); 157*68353368SRudolf Cornelissen head2_cursor_show(); 158*68353368SRudolf Cornelissen } 159*68353368SRudolf Cornelissen else 160*68353368SRudolf Cornelissen { 161*68353368SRudolf Cornelissen head1_cursor_hide(); 162*68353368SRudolf Cornelissen head2_cursor_hide(); 163*68353368SRudolf Cornelissen } 164*68353368SRudolf Cornelissen break; 165*68353368SRudolf Cornelissen case DUALHEAD_ON: 166*68353368SRudolf Cornelissen case DUALHEAD_SWITCH: 167*68353368SRudolf Cornelissen if (is_visible) 168*68353368SRudolf Cornelissen { 169*68353368SRudolf Cornelissen if (!si->cursor.dh_right) 170*68353368SRudolf Cornelissen { 171*68353368SRudolf Cornelissen head1_cursor_show(); 172*68353368SRudolf Cornelissen } 173*68353368SRudolf Cornelissen else 174*68353368SRudolf Cornelissen { 175*68353368SRudolf Cornelissen head2_cursor_show(); 176*68353368SRudolf Cornelissen } 177*68353368SRudolf Cornelissen } 178*68353368SRudolf Cornelissen else 179*68353368SRudolf Cornelissen { 180*68353368SRudolf Cornelissen head1_cursor_hide(); 181*68353368SRudolf Cornelissen head2_cursor_hide(); 182*68353368SRudolf Cornelissen } 183*68353368SRudolf Cornelissen break; 184*68353368SRudolf Cornelissen default: /* singlehead mode */ 185*68353368SRudolf Cornelissen if (is_visible) 186*68353368SRudolf Cornelissen { 187*68353368SRudolf Cornelissen head1_cursor_show(); 188*68353368SRudolf Cornelissen } 189*68353368SRudolf Cornelissen else 190*68353368SRudolf Cornelissen { 191*68353368SRudolf Cornelissen head1_cursor_hide(); 192*68353368SRudolf Cornelissen } 193*68353368SRudolf Cornelissen break; 194*68353368SRudolf Cornelissen } 195*68353368SRudolf Cornelissen } 196