| 44 | |
| 45 | |
| 46 | ResultType Line::ToolTip(LPTSTR aText, LPTSTR aX, LPTSTR aY, LPTSTR aID) |
| 47 | { |
| 48 | int window_index = *aID ? ATOI(aID) - 1 : 0; |
| 49 | if (window_index < 0 || window_index >= MAX_TOOLTIPS) |
| 50 | return LineError(_T("Max window number is ") MAX_TOOLTIPS_STR _T("."), FAIL_OR_OK, aID); |
| 51 | HWND tip_hwnd = g_hWndToolTip[window_index]; |
| 52 | |
| 53 | // Destroy windows except the first (for performance) so that resources/mem are conserved. |
| 54 | // The first window will be hidden by the TTM_UPDATETIPTEXT message if aText is blank. |
| 55 | // UPDATE: For simplicity, destroy even the first in this way, because otherwise a script |
| 56 | // that turns off a non-existent first tooltip window then later turns it on will cause |
| 57 | // the window to appear in an incorrect position. Example: |
| 58 | // ToolTip |
| 59 | // ToolTip, text, 388, 24 |
| 60 | // Sleep, 1000 |
| 61 | // ToolTip, text, 388, 24 |
| 62 | if (!*aText) |
| 63 | { |
| 64 | if (tip_hwnd && IsWindow(tip_hwnd)) |
| 65 | DestroyWindow(tip_hwnd); |
| 66 | g_hWndToolTip[window_index] = NULL; |
| 67 | return OK; |
| 68 | } |
| 69 | |
| 70 | // Use virtual desktop so that tooltip can move onto non-primary monitor in a multi-monitor system: |
| 71 | RECT dtw; |
| 72 | GetVirtualDesktopRect(dtw); |
| 73 | |
| 74 | bool one_or_both_coords_unspecified = !*aX || !*aY; |
| 75 | POINT pt, pt_cursor; |
| 76 | if (one_or_both_coords_unspecified) |
| 77 | { |
| 78 | // Don't call GetCursorPos() unless absolutely needed because it seems to mess |
| 79 | // up double-click timing, at least on XP. UPDATE: Is isn't GetCursorPos() that's |
| 80 | // interfering with double clicks, so it seems it must be the displaying of the ToolTip |
| 81 | // window itself. |
| 82 | GetCursorPos(&pt_cursor); |
| 83 | pt.x = pt_cursor.x + 16; // Set default spot to be near the mouse cursor. |
| 84 | pt.y = pt_cursor.y + 16; // Use 16 to prevent the tooltip from overlapping large cursors. |
| 85 | // Update: Below is no longer needed due to a better fix further down that handles multi-line tooltips. |
| 86 | // 20 seems to be about the right amount to prevent it from "warping" to the top of the screen, |
| 87 | // at least on XP: |
| 88 | //if (pt.y > dtw.bottom - 20) |
| 89 | // pt.y = dtw.bottom - 20; |
| 90 | } |
| 91 | |
| 92 | POINT origin = {0}; |
| 93 | if (*aX || *aY) // Need the offsets. |
| 94 | CoordToScreen(origin, COORD_MODE_TOOLTIP); |
| 95 | |
| 96 | // This will also convert from relative to screen coordinates if appropriate: |
| 97 | if (*aX) |
| 98 | pt.x = ATOI(aX) + origin.x; |
| 99 | if (*aY) |
| 100 | pt.y = ATOI(aY) + origin.y; |
| 101 | |
| 102 | TOOLINFO ti = {0}; |
| 103 | ti.cbSize = sizeof(ti); |
nothing calls this directly
no test coverage detected