Subversion Repositories Kolibri OS

Rev

Rev 1859 | Rev 1929 | Go to most recent revision | Blame | Compare with Previous | Last modification | View Log | Download | RSS feed

  1. ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
  2. ;;                                                              ;;
  3. ;; Copyright (C) KolibriOS team 2004-2010. All rights reserved. ;;
  4. ;; Copyright (C) MenuetOS 2000-2004 Ville Mikael Turjanmaa      ;;
  5. ;; Distributed under terms of the GNU General Public License    ;;
  6. ;;                                                              ;;
  7. ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
  8.  
  9. $Revision: 1899 $
  10.  
  11. ;==============================================================================
  12. ;///// public functions ///////////////////////////////////////////////////////
  13. ;==============================================================================
  14.  
  15. window.BORDER_SIZE = 4
  16.  
  17. macro FuncTable name, table_name, [label]
  18. {
  19.   common
  20.     align 4
  21.     \label name#.#table_name dword
  22.   forward
  23.     dd name#.#label
  24.   common
  25.     name#.sizeof.#table_name = $ - name#.#table_name
  26. }
  27.  
  28. uglobal
  29.   common_colours rd 32
  30.   draw_limits    RECT
  31. endg
  32.  
  33. align 4
  34. ;------------------------------------------------------------------------------
  35. syscall_draw_window: ;///// system function 0 /////////////////////////////////
  36. ;------------------------------------------------------------------------------
  37. ;? <description>
  38. ;------------------------------------------------------------------------------
  39.         mov     eax, edx
  40.         shr     eax, 24
  41.         and     al, 0x0f
  42.         cmp     al, 5
  43.         jae     .exit
  44.  
  45.         push    eax
  46.         inc     [mouse_pause]
  47.         call    [_display.disable_mouse]
  48.         call    window._.sys_set_window
  49.         call    [_display.disable_mouse]
  50.         pop     eax
  51.  
  52.         or      al, al
  53.         jnz     @f
  54.  
  55.         ; type I - original style
  56.         call    drawwindow_I
  57.         jmp     window._.draw_window_caption.2
  58.  
  59.     @@: dec     al
  60.         jnz     @f
  61.  
  62.         ; type II - only reserve area, no draw
  63.         call    sys_window_mouse
  64.         dec     [mouse_pause]
  65.         call    [draw_pointer]
  66.         jmp     .exit
  67.  
  68.     @@: dec     al
  69.         jnz     @f
  70.  
  71.         ; type III  - new style
  72.         call    drawwindow_III
  73.         jmp     window._.draw_window_caption.2
  74.  
  75.         ; type IV & V - skinned window (resizable & not)
  76.     @@: mov     eax, [TASK_COUNT]
  77.         movzx   eax, word[WIN_POS + eax * 2]
  78.         cmp     eax, [CURRENT_TASK]
  79.         setz    al
  80.         movzx   eax, al
  81.         push    eax
  82.         call    drawwindow_IV
  83.         jmp     window._.draw_window_caption.2
  84.  
  85.   .exit:
  86.         ret
  87.  
  88. align 4
  89. ;------------------------------------------------------------------------------
  90. syscall_display_settings: ;///// system function 48 ///////////////////////////
  91. ;------------------------------------------------------------------------------
  92. ;; Redraw screen:
  93. ;< ebx = 0
  94. ; - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
  95. ;; Set button style:
  96. ;< ebx = 1
  97. ;< ecx = 0 (flat) or 1 (with gradient)
  98. ; - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
  99. ;; Set system color palette:
  100. ;< ebx = 2
  101. ;< ecx = pointer to color table
  102. ;< edx = size of color table
  103. ; - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
  104. ;; Get system color palette:
  105. ;< ebx = 3
  106. ;< ecx = pointer to color table buffer
  107. ;< edx = size of color table buffer
  108. ; - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
  109. ;; Get skinned caption height:
  110. ;< ebx = 4
  111. ;> eax = height in pixels
  112. ; - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
  113. ;; Get screen working area:
  114. ;< ebx = 5
  115. ;> eax = pack[16(left), 16(right)]
  116. ;> ebx = pack[16(top), 16(bottom)]
  117. ; - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
  118. ;; Set screen working area:
  119. ;< ebx = 6
  120. ;< ecx = pack[16(left), 16(right)]
  121. ;< edx = pack[16(top), 16(bottom)]
  122. ; - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
  123. ;; Get skin margins:
  124. ;< ebx = 7
  125. ;> eax = pack[16(left), 16(right)]
  126. ;> ebx = pack[16(top), 16(bottom)]
  127. ; - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
  128. ;; Set skin:
  129. ;< ebx = 8
  130. ;< ecx = pointer to FileInfoBlock struct
  131. ;> eax = FS error code
  132. ;------------------------------------------------------------------------------
  133.         cmp     ebx, .sizeof.ftable / 4
  134.         ja      @f
  135.         jmp     [.ftable + ebx * 4]
  136.     @@: ret
  137.  
  138.  
  139. align 4
  140. syscall_display_settings.00:
  141.         xor     eax, eax
  142.         inc     ebx
  143.         cmp     [windowtypechanged], ebx
  144.         jne     .exit
  145.         mov     [windowtypechanged], eax
  146.  
  147.         jmp     syscall_display_settings._.redraw_whole_screen
  148.  
  149.   .exit:
  150.         ret
  151.  
  152. align 4
  153. syscall_display_settings.01:
  154.         and     ecx, 1
  155.         cmp     ecx, [buttontype]
  156.         je      .exit
  157.         mov     [buttontype], ecx
  158.         mov     [windowtypechanged], ebx
  159.  
  160.   .exit:
  161.         ret
  162.  
  163. align 4
  164. syscall_display_settings.02:
  165.         dec     ebx
  166.         mov     esi, ecx
  167.         and     edx, 127
  168.         mov     edi, common_colours
  169.         mov     ecx, edx
  170.         rep     movsb
  171.         mov     [windowtypechanged], ebx
  172.         ret
  173.  
  174. align 4
  175. syscall_display_settings.03:
  176.         mov     edi, ecx
  177.         and     edx, 127
  178.         mov     esi, common_colours
  179.         mov     ecx, edx
  180.         rep     movsb
  181.         ret
  182.  
  183. align 4
  184. syscall_display_settings.04:
  185.         mov     eax, [_skinh]
  186.         mov     [esp + 32], eax
  187.         ret
  188.  
  189. align 4
  190. syscall_display_settings.05:
  191.         mov     eax, [screen_workarea.left - 2]
  192.         mov     ax, word[screen_workarea.right]
  193.         mov     [esp + 32], eax
  194.         mov     eax, [screen_workarea.top - 2]
  195.         mov     ax, word[screen_workarea.bottom]
  196.         mov     [esp + 20], eax
  197.         ret
  198.  
  199. align 4
  200. syscall_display_settings.06:
  201.         xor     esi, esi
  202.  
  203.         mov     edi, [Screen_Max_X]
  204.         mov     eax, ecx
  205.         movsx   ebx, ax
  206.         sar     eax, 16
  207.         cmp     eax, ebx
  208.         jge     .check_horizontal
  209.         inc     esi
  210.         or      eax, eax
  211.         jge     @f
  212.         xor     eax, eax
  213.     @@: mov     [screen_workarea.left], eax
  214.         cmp     ebx, edi
  215.         jle     @f
  216.         mov     ebx, edi
  217.     @@: mov     [screen_workarea.right], ebx
  218.  
  219.   .check_horizontal:
  220.         mov     edi, [Screen_Max_Y]
  221.         mov     eax, edx
  222.         movsx   ebx, ax
  223.         sar     eax, 16
  224.         cmp     eax, ebx
  225.         jge     .check_if_redraw_needed
  226.         inc     esi
  227.         or      eax, eax
  228.         jge     @f
  229.         xor     eax, eax
  230.     @@: mov     [screen_workarea.top], eax
  231.         cmp     ebx, edi
  232.         jle     @f
  233.         mov     ebx, edi
  234.     @@: mov     [screen_workarea.bottom], ebx
  235.  
  236.   .check_if_redraw_needed:
  237.         or      esi, esi
  238.         jz      .exit
  239.  
  240.         call    repos_windows
  241.         jmp     syscall_display_settings._.calculate_whole_screen
  242.  
  243.   .exit:
  244.         ret
  245.  
  246. align 4
  247. syscall_display_settings.07:
  248.         mov     eax, [_skinmargins + 0]
  249.         mov     [esp + 32], eax
  250.         mov     eax, [_skinmargins + 4]
  251.         mov     [esp + 20], eax
  252.         ret
  253.  
  254. align 4
  255. syscall_display_settings.08:
  256.         mov     ebx, ecx
  257.         call    read_skin_file
  258.         mov     [esp + 32], eax
  259.         test    eax, eax
  260.         jnz     .exit
  261.  
  262.         call    syscall_display_settings._.calculate_whole_screen
  263.         jmp     syscall_display_settings._.redraw_whole_screen
  264.  
  265.   .exit:
  266.         ret
  267.  
  268. syscall_display_settings._.calculate_whole_screen:
  269.         xor     eax, eax
  270.         xor     ebx, ebx
  271.         mov     ecx, [Screen_Max_X]
  272.         mov     edx, [Screen_Max_Y]
  273.         jmp     calculatescreen
  274.  
  275. syscall_display_settings._.redraw_whole_screen:
  276.         xor     eax, eax
  277.         mov     [draw_limits.left], eax
  278.         mov     [draw_limits.top], eax
  279.         mov     eax, [Screen_Max_X]
  280.         mov     [draw_limits.right], eax
  281.         mov     eax, [Screen_Max_Y]
  282.         mov     [draw_limits.bottom], eax
  283.         mov     eax, window_data
  284.         jmp     redrawscreen
  285.  
  286. align 4
  287. ;------------------------------------------------------------------------------
  288. syscall_set_window_shape: ;///// system function 50 ///////////////////////////
  289. ;------------------------------------------------------------------------------
  290. ;; Set window shape address:
  291. ;> ebx = 0
  292. ;> ecx = shape data address
  293. ; - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
  294. ;; Set window shape scale:
  295. ;> ebx = 1
  296. ;> ecx = scale power (resulting scale is 2^ebx)
  297. ;------------------------------------------------------------------------------
  298.         mov     edi, [current_slot]
  299.  
  300.         test    ebx, ebx
  301.         jne     .shape_scale
  302.         mov     [edi + APPDATA.wnd_shape], ecx
  303.  
  304.   .shape_scale:
  305.         dec     ebx
  306.         jnz     .exit
  307.         mov     [edi + APPDATA.wnd_shape_scale], ecx
  308.  
  309.   .exit:
  310.         ret
  311.  
  312. align 4
  313. ;------------------------------------------------------------------------------
  314. syscall_move_window: ;///// system function 67 ////////////////////////////////
  315. ;------------------------------------------------------------------------------
  316. ;? <description>
  317. ;------------------------------------------------------------------------------
  318.         mov     edi, [CURRENT_TASK]
  319.         shl     edi, 5
  320.         add     edi, window_data
  321.  
  322.         test    [edi + WDATA.fl_wdrawn], 1
  323.         jz      .exit
  324.  
  325.         test    [edi + WDATA.fl_wstate], WSTATE_MAXIMIZED
  326.         jnz     .exit
  327.  
  328.         cmp     ebx, -1
  329.         jne     @f
  330.         mov     ebx, [edi + WDATA.box.left]
  331.         and     bl, 0xFC
  332.     @@: cmp     ecx, -1
  333.         jne     @f
  334.         mov     ecx, [edi + WDATA.box.top]
  335.         and     cl, 0xFE
  336.     @@: cmp     edx, -1
  337.         jne     @f
  338.         mov     edx, [edi + WDATA.box.width]
  339. ;       and     dl, 0xFC
  340.     @@: cmp     esi, -1
  341.         jne     @f
  342.         mov     esi, [edi + WDATA.box.height]
  343. ;       and     esi, 0xFFFFFFFE
  344.  
  345.     @@: push    esi edx ecx ebx
  346.         mov     eax, esp
  347.         mov     bl, [edi + WDATA.fl_wstate]
  348.         call    window._.set_window_box
  349.         add     esp, BOX.sizeof
  350.  
  351.   .exit:
  352.         ret
  353.  
  354. align 4
  355. ;------------------------------------------------------------------------------
  356. syscall_window_settings: ;///// system function 71 /////////////////////////////
  357. ;------------------------------------------------------------------------------
  358. ;? <description>
  359. ;------------------------------------------------------------------------------
  360.         dec     ebx     ; subfunction #1 - set window caption
  361.         jnz     .exit_fail
  362.  
  363.         ; NOTE: only window owner thread can set its caption,
  364.         ;       so there's no parameter for PID/TID
  365.  
  366.         mov     edi, [CURRENT_TASK]
  367.         shl     edi, 5
  368.  
  369.         mov     [edi * 8 + SLOT_BASE + APPDATA.wnd_caption], ecx
  370.         or      [edi + window_data + WDATA.fl_wstyle], WSTYLE_HASCAPTION
  371.  
  372.         call    window._.draw_window_caption
  373.  
  374.         xor     eax, eax ; eax = 0 (success)
  375.         ret
  376.  
  377. ;  .get_window_caption:
  378. ;        dec     eax     ; subfunction #2 - get window caption
  379. ;        jnz     .exit_fail
  380.  
  381.         ; not implemented yet
  382.  
  383.   .exit_fail:
  384.         xor     eax, eax
  385.         inc     eax     ; eax = 1 (fail)
  386.         ret
  387.  
  388. align 4
  389. ;------------------------------------------------------------------------------
  390. set_window_defaults: ;/////////////////////////////////////////////////////////
  391. ;------------------------------------------------------------------------------
  392. ;? <description>
  393. ;------------------------------------------------------------------------------
  394.         mov     byte [window_data + 0x20 + WDATA.cl_titlebar + 3], 1 ; desktop is not movable
  395.         push    eax ecx
  396.         xor     eax, eax
  397.         mov     ecx, WIN_STACK
  398.     @@: inc     eax
  399.         add     ecx, 2
  400.         ; process no
  401.         mov     [ecx + 0x000], ax
  402.         ; positions in stack
  403.         mov     [ecx + 0x400], ax
  404.         cmp     ecx, WIN_POS - 2
  405.         jne     @b
  406.         pop     ecx eax
  407.         ret
  408.  
  409. align 4
  410. ;------------------------------------------------------------------------------
  411. calculatescreen: ;/////////////////////////////////////////////////////////////
  412. ;------------------------------------------------------------------------------
  413. ;? Scan all windows from bottom to top, calling `setscreen` for each one
  414. ;? intersecting given screen area
  415. ;------------------------------------------------------------------------------
  416. ;> eax = left
  417. ;> ebx = top
  418. ;> ecx = right
  419. ;> edx = bottom
  420. ;------------------------------------------------------------------------------
  421.         push    esi
  422.         pushfd
  423.         cli
  424.  
  425.         mov     esi, 1
  426.         call    window._.set_screen
  427.  
  428.         push    ebp
  429.  
  430.         mov     ebp, [TASK_COUNT]
  431.         cmp     ebp, 1
  432.         jbe     .exit
  433.  
  434.         push    edx ecx ebx eax
  435.  
  436.   .next_window:
  437.         movzx   edi, word[WIN_POS + esi * 2]
  438.         shl     edi, 5
  439.  
  440.         cmp     [CURRENT_TASK + edi + TASKDATA.state], TSTATE_FREE
  441.         je      .skip_window
  442.  
  443.         add     edi, window_data
  444.         test    [edi + WDATA.fl_wstate], WSTATE_MINIMIZED
  445.         jnz     .skip_window
  446.  
  447.         mov     eax, [edi + WDATA.box.left]
  448.         cmp     eax, [esp + RECT.right]
  449.         jg      .skip_window
  450.         mov     ebx, [edi + WDATA.box.top]
  451.         cmp     ebx, [esp + RECT.bottom]
  452.         jg      .skip_window
  453.         mov     ecx, [edi + WDATA.box.width]
  454.         add     ecx, eax
  455.         cmp     ecx, [esp + RECT.left]
  456.         jl      .skip_window
  457.         mov     edx, [edi + WDATA.box.height]
  458.         add     edx, ebx
  459.         cmp     edx, [esp + RECT.top]
  460.         jl      .skip_window
  461.  
  462.         cmp     eax, [esp + RECT.left]
  463.         jae     @f
  464.         mov     eax, [esp + RECT.left]
  465.     @@: cmp     ebx, [esp + RECT.top]
  466.         jae     @f
  467.         mov     ebx, [esp + RECT.top]
  468.     @@: cmp     ecx, [esp + RECT.right]
  469.         jbe     @f
  470.         mov     ecx, [esp + RECT.right]
  471.     @@: cmp     edx, [esp + RECT.bottom]
  472.         jbe     @f
  473.         mov     edx, [esp + RECT.bottom]
  474.  
  475.     @@: push    esi
  476.         movzx   esi, word[WIN_POS + esi * 2]
  477.         call    window._.set_screen
  478.         pop     esi
  479.  
  480.   .skip_window:
  481.         inc     esi
  482.         dec     ebp
  483.         jnz     .next_window
  484.  
  485.         pop     eax ebx ecx edx
  486.  
  487.   .exit:
  488.         pop     ebp
  489.         popfd
  490.         pop     esi
  491.         ret
  492.  
  493. align 4
  494. ;------------------------------------------------------------------------------
  495. repos_windows: ;///////////////////////////////////////////////////////////////
  496. ;------------------------------------------------------------------------------
  497. ;? <description>
  498. ;------------------------------------------------------------------------------
  499.         mov     ecx, [TASK_COUNT]
  500.         mov     edi, window_data + WDATA.sizeof * 2
  501.         call    force_redraw_background
  502.         dec     ecx
  503.         jle     .exit
  504.  
  505.   .next_window:
  506.         mov     [edi + WDATA.fl_redraw], 1
  507.         test    [edi + WDATA.fl_wstate], WSTATE_MAXIMIZED
  508.         jnz     .fix_maximized
  509.  
  510.         mov     eax, [edi + WDATA.box.left]
  511.         add     eax, [edi + WDATA.box.width]
  512.         mov     ebx, [Screen_Max_X]
  513.         cmp     eax, ebx
  514.         jle     .fix_vertical
  515.         mov     eax, [edi + WDATA.box.width]
  516.         sub     eax, ebx
  517.         jle     @f
  518. ;       and     bl, 0xFC                        ; <<<<<<<
  519.         mov     [edi + WDATA.box.width], ebx
  520.     @@: sub     ebx, [edi + WDATA.box.width]
  521. ;       and     bl, 0xFC                        ; <<<<<<<
  522.         mov     [edi + WDATA.box.left], ebx
  523.  
  524.   .fix_vertical:
  525.         mov     eax, [edi + WDATA.box.top]
  526.         add     eax, [edi + WDATA.box.height]
  527.         mov     ebx, [Screen_Max_Y]
  528.         cmp     eax, ebx
  529.         jle     .fix_client_box
  530.         mov     eax, [edi + WDATA.box.height]
  531.         sub     eax, ebx
  532.         jle     @f
  533. ;       and     bl, 0xFE                        ; <<<<<<<
  534.         mov     [edi + WDATA.box.height], ebx
  535.     @@: sub     ebx, [edi + WDATA.box.height]
  536. ;       and     bl, 0xFE                        ; <<<<<<<
  537.         mov     [edi + WDATA.box.top], ebx
  538.         jmp     .fix_client_box
  539.  
  540.   .fix_maximized:
  541.         mov     eax, [screen_workarea.left]
  542.         mov     [edi + WDATA.box.left], eax
  543.         sub     eax, [screen_workarea.right]
  544.         neg     eax
  545.         mov     [edi + WDATA.box.width], eax
  546.         mov     eax, [screen_workarea.top]
  547.         mov     [edi + WDATA.box.top], eax
  548.         test    [edi + WDATA.fl_wstate], WSTATE_ROLLEDUP
  549.         jnz     .fix_client_box
  550.         sub     eax, [screen_workarea.bottom]
  551.         neg     eax
  552.         mov     [edi + WDATA.box.height], eax
  553.  
  554.   .fix_client_box:
  555.         call    window._.set_window_clientbox
  556.  
  557.         add     edi, WDATA.sizeof
  558.         dec     ecx
  559.         jne    .next_window     ; <<<<<<<<<<<
  560.  
  561.   .exit:
  562.         ret
  563.  
  564. align 4
  565. ;------------------------------------------------------------------------------
  566. sys_window_mouse: ;////////////////////////////////////////////////////////////
  567. ;------------------------------------------------------------------------------
  568. ;? <description>
  569. ;------------------------------------------------------------------------------
  570.         ; NOTE: commented out since doesn't provide necessary functionality
  571.         ;       anyway, to be reworked
  572. ;       push    eax
  573. ;
  574. ;       mov     eax, [timer_ticks]
  575. ;       cmp     [new_window_starting], eax
  576. ;       jb      .exit
  577. ;
  578. ;       mov     byte[MOUSE_BACKGROUND], 0
  579. ;       mov     byte[DONT_DRAW_MOUSE], 0
  580. ;
  581. ;       mov     [new_window_starting], eax
  582. ;
  583. ; .exit:
  584. ;       pop     eax
  585.         ret
  586.  
  587. align 4
  588. ;------------------------------------------------------------------------------
  589. draw_rectangle: ;//////////////////////////////////////////////////////////////
  590. ;------------------------------------------------------------------------------
  591. ;> eax = pack[16(left), 16(right)]
  592. ;> ebx = pack[16(top), 16(bottom)]
  593. ;> esi = color
  594. ;------------------------------------------------------------------------------
  595.         push    eax ebx ecx edi
  596.  
  597.         xor     edi, edi
  598.  
  599.   .flags_set:
  600.         push    ebx
  601.  
  602.         ; set line color
  603.         mov     ecx, esi
  604.  
  605.         ; draw top border
  606.         rol     ebx, 16
  607.         push    ebx
  608.         rol     ebx, 16
  609.         pop     bx
  610.         call    [draw_line]
  611.  
  612.         ; draw bottom border
  613.         mov     ebx, [esp - 2]
  614.         pop     bx
  615.         call    [draw_line]
  616.  
  617.         pop     ebx
  618.         add     ebx, 1 * 65536 - 1
  619.  
  620.         ; draw left border
  621.         rol     eax, 16
  622.         push    eax
  623.         rol     eax, 16
  624.         pop     ax
  625.         call    [draw_line]
  626.  
  627.         ; draw right border
  628.         mov     eax, [esp - 2]
  629.         pop     ax
  630.         call    [draw_line]
  631.  
  632.         pop     edi ecx ebx eax
  633.         ret
  634.  
  635.   .forced:
  636.         push    eax ebx ecx edi
  637.         xor     edi, edi
  638.         inc     edi
  639.         jmp     .flags_set
  640.  
  641. align 4
  642. ;------------------------------------------------------------------------------
  643. drawwindow_I_caption: ;////////////////////////////////////////////////////////
  644. ;------------------------------------------------------------------------------
  645. ;? <description>
  646. ;------------------------------------------------------------------------------
  647.         push    [edx + WDATA.cl_titlebar]
  648.         mov     esi, edx
  649.  
  650.         mov     edx, [esi + WDATA.box.top]
  651.         mov     eax, edx
  652.         lea     ebx, [edx + 21]
  653.         inc     edx
  654.         add     eax, [esi + WDATA.box.height]
  655.  
  656.         cmp     ebx, eax
  657.         jbe     @f
  658.         mov     ebx, eax
  659.     @@: push    ebx
  660.  
  661.         xor     edi, edi
  662.  
  663.   .next_line:
  664.         mov     ebx, edx
  665.         shl     ebx, 16
  666.         add     ebx, edx
  667.         mov     eax, [esi + WDATA.box.left]
  668.         inc     eax
  669.  
  670.         shl     eax, 16
  671.         add     eax, [esi + WDATA.box.left]
  672.         add     eax, [esi + WDATA.box.width]
  673.         dec     eax
  674.         mov     ecx, [esi + WDATA.cl_titlebar]
  675.         test    ecx, 0x80000000
  676.         jz      @f
  677.         sub     ecx, 0x00040404
  678.         mov     [esi + WDATA.cl_titlebar], ecx
  679.     @@: and     ecx, 0x00ffffff
  680.         call    [draw_line]
  681.         inc     edx
  682.         cmp     edx, [esp]
  683.         jb      .next_line
  684.  
  685.         add     esp, 4
  686.         pop     [esi + WDATA.cl_titlebar]
  687.         ret
  688.  
  689. align 4
  690. ;------------------------------------------------------------------------------
  691. drawwindow_I: ;////////////////////////////////////////////////////////////////
  692. ;------------------------------------------------------------------------------
  693. ;? <description>
  694. ;------------------------------------------------------------------------------
  695.         pushad
  696.  
  697.         ; window border
  698.  
  699.         mov     eax, [edx + WDATA.box.left - 2]
  700.         mov     ax, word[edx + WDATA.box.left]
  701.         add     ax, word[edx + WDATA.box.width]
  702.         mov     ebx, [edx + WDATA.box.top - 2]
  703.         mov     bx, word[edx + WDATA.box.top]
  704.         add     bx, word[edx + WDATA.box.height]
  705.  
  706.         mov     esi, [edx + WDATA.cl_frames]
  707.         call    draw_rectangle
  708.  
  709.         ; window caption
  710.  
  711.         call    drawwindow_I_caption
  712.  
  713.         ; window client area
  714.  
  715.         ; do we need to draw it?
  716.         mov     edi, [esi + WDATA.cl_workarea]
  717.         test    edi, 0x40000000
  718.         jnz     .exit
  719.  
  720.         ; does client area have a positive size on screen?
  721.         mov     edx, [esi + WDATA.box.top]
  722.         add     edx, 21 + 5
  723.         mov     ebx, [esi + WDATA.box.top]
  724.         add     ebx, [esi + WDATA.box.height]
  725.         cmp     edx, ebx
  726.         jg      .exit
  727.  
  728.         ; okay, let's draw it
  729.         mov     eax, 1
  730.         mov     ebx, 21
  731.         mov     ecx, [esi + WDATA.box.width]
  732.         mov     edx, [esi + WDATA.box.height]
  733.         call    [drawbar]
  734.  
  735.   .exit:
  736.         popad
  737.         ret
  738.  
  739. align 4
  740. ;------------------------------------------------------------------------------
  741. drawwindow_III_caption: ;/////////////////////////////////////////////////////
  742. ;------------------------------------------------------------------------------
  743. ;? <description>
  744. ;------------------------------------------------------------------------------
  745.         mov     ecx, [edx + WDATA.cl_titlebar]
  746.         push    ecx
  747.         mov     esi, edx
  748.         mov     edx, [esi + WDATA.box.top]
  749.         add     edx, 4
  750.         mov     ebx, [esi + WDATA.box.top]
  751.         add     ebx, 20
  752.         mov     eax, [esi + WDATA.box.top]
  753.         add     eax, [esi + WDATA.box.height]
  754.  
  755.         cmp     ebx, eax
  756.         jb      @f
  757.         mov     ebx, eax
  758.     @@: push    ebx
  759.  
  760.         xor     edi, edi
  761.  
  762.   .next_line:
  763.         mov     ebx, edx
  764.         shl     ebx, 16
  765.         add     ebx, edx
  766.         mov     eax, [esi + WDATA.box.left]
  767.         shl     eax, 16
  768.         add     eax, [esi + WDATA.box.left]
  769.         add     eax, [esi + WDATA.box.width]
  770.         add     eax, 4 * 65536 - 4
  771.         mov     ecx, [esi + WDATA.cl_titlebar]
  772.         test    ecx, 0x40000000
  773.         jz      @f
  774.         add     ecx, 0x00040404
  775.     @@: test    ecx, 0x80000000
  776.         jz      @f
  777.         sub     ecx, 0x00040404
  778.     @@: mov     [esi + WDATA.cl_titlebar], ecx
  779.         and     ecx, 0x00ffffff
  780.         call    [draw_line]
  781.         inc     edx
  782.         cmp     edx, [esp]
  783.         jb      .next_line
  784.  
  785.         add     esp, 4
  786.         pop     [esi + WDATA.cl_titlebar]
  787.         ret
  788.  
  789. align 4
  790. ;------------------------------------------------------------------------------
  791. drawwindow_III: ;//////////////////////////////////////////////////////////////
  792. ;------------------------------------------------------------------------------
  793. ;? <description>
  794. ;------------------------------------------------------------------------------
  795.         pushad
  796.  
  797.         ; window border
  798.  
  799.         mov     eax, [edx + WDATA.box.left - 2]
  800.         mov     ax, word[edx + WDATA.box.left]
  801.         add     ax, word[edx + WDATA.box.width]
  802.         mov     ebx, [edx + WDATA.box.top - 2]
  803.         mov     bx, word[edx + WDATA.box.top]
  804.         add     bx, word[edx + WDATA.box.height]
  805.  
  806.         mov     esi, [edx + WDATA.cl_frames]
  807.         shr     esi, 1
  808.         and     esi, 0x007f7f7f
  809.         call    draw_rectangle
  810.  
  811.         push    esi
  812.         mov     ecx, 3
  813.         mov     esi, [edx + WDATA.cl_frames]
  814.  
  815.   .next_frame:
  816.         add     eax, 1 * 65536 - 1
  817.         add     ebx, 1 * 65536 - 1
  818.         call    draw_rectangle
  819.         dec     ecx
  820.         jnz     .next_frame
  821.  
  822.         pop     esi
  823.         add     eax, 1 * 65536 - 1
  824.         add     ebx, 1 * 65536 - 1
  825.         call    draw_rectangle
  826.  
  827.         ; window caption
  828.  
  829.         call    drawwindow_III_caption
  830.  
  831.         ; window client area
  832.  
  833.         ; do we need to draw it?
  834.         mov     edi, [esi + WDATA.cl_workarea]
  835.         test    edi, 0x40000000
  836.         jnz     .exit
  837.  
  838.         ; does client area have a positive size on screen?
  839.         mov     edx, [esi + WDATA.box.top]
  840.         add     edx, 21 + 5
  841.         mov     ebx, [esi + WDATA.box.top]
  842.         add     ebx, [esi + WDATA.box.height]
  843.         cmp     edx, ebx
  844.         jg      .exit
  845.  
  846.         ; okay, let's draw it
  847.         mov     eax, 5
  848.         mov     ebx, 20
  849.         mov     ecx, [esi + WDATA.box.width]
  850.         mov     edx, [esi + WDATA.box.height]
  851.         sub     ecx, 4
  852.         sub     edx, 4
  853.         call    [drawbar]
  854.  
  855.   .exit:
  856.         popad
  857.         ret
  858.  
  859. align 4
  860. ;------------------------------------------------------------------------------
  861. waredraw: ;////////////////////////////////////////////////////////////////////
  862. ;------------------------------------------------------------------------------
  863. ;? Activate window, redrawing if necessary
  864. ;------------------------------------------------------------------------------
  865.         push    -1
  866.         mov     eax, [TASK_COUNT]
  867.         lea     eax, [WIN_POS + eax * 2]
  868.         cmp     eax, esi
  869.         pop     eax
  870.         je      .exit
  871.  
  872.         ; is it overlapped by another window now?
  873.         push    ecx
  874.         call    window._.check_window_draw
  875.         test    ecx, ecx
  876.         pop     ecx
  877.         jz      .do_not_draw
  878.  
  879.         ; yes it is, activate and update screen buffer
  880.         mov     byte[MOUSE_DOWN], 1
  881.         call    window._.window_activate
  882.  
  883.         pushad
  884.         mov     edi, [TASK_COUNT]
  885.         movzx   esi, word[WIN_POS + edi * 2]
  886.         shl     esi, 5
  887.         add     esi, window_data
  888.  
  889.         mov     eax, [esi + WDATA.box.left]
  890.         mov     ebx, [esi + WDATA.box.top]
  891.         mov     ecx, [esi + WDATA.box.width]
  892.         mov     edx, [esi + WDATA.box.height]
  893.  
  894.         add     ecx, eax
  895.         add     edx, ebx
  896.  
  897.         mov     edi, [TASK_COUNT]
  898.         movzx   esi, word[WIN_POS + edi * 2]
  899.         call    window._.set_screen
  900.         popad
  901.  
  902.         ; tell application to redraw itself
  903.         mov     [edi + WDATA.fl_redraw], 1
  904.         xor     eax, eax
  905.         jmp     .exit
  906.  
  907.   .do_not_draw:
  908.         ; no it's not, just activate the window
  909.         call    window._.window_activate
  910.         xor     eax, eax
  911.         mov     byte[MOUSE_BACKGROUND], al
  912.         mov     byte[DONT_DRAW_MOUSE], al
  913.  
  914.  
  915.   .exit:
  916.         mov     byte[MOUSE_DOWN], 0
  917.         inc     eax
  918.         ret
  919.  
  920. align 4
  921. ;------------------------------------------------------------------------------
  922. minimize_window: ;/////////////////////////////////////////////////////////////
  923. ;------------------------------------------------------------------------------
  924. ;> eax = window number on screen
  925. ;------------------------------------------------------------------------------
  926. ;# corrupts [dl*]
  927. ;------------------------------------------------------------------------------
  928.         push    edi
  929.         pushfd
  930.         cli
  931.  
  932.         ; is it already minimized?
  933.         movzx   edi, word[WIN_POS + eax * 2]
  934.         shl     edi, 5
  935.         add     edi, window_data
  936.         test    [edi + WDATA.fl_wstate], WSTATE_MINIMIZED
  937.         jnz     .exit
  938.  
  939.         push    eax ebx ecx edx esi
  940.  
  941.         ; no it's not, let's do that
  942.         or      [edi + WDATA.fl_wstate], WSTATE_MINIMIZED
  943.         mov     eax, [edi + WDATA.box.left]
  944.         mov     [draw_limits.left], eax
  945.         mov     ecx, eax
  946.         add     ecx, [edi + WDATA.box.width]
  947.         mov     [draw_limits.right], ecx
  948.         mov     ebx, [edi + WDATA.box.top]
  949.         mov     [draw_limits.top], ebx
  950.         mov     edx, ebx
  951.         add     edx, [edi + WDATA.box.height]
  952.         mov     [draw_limits.bottom], edx
  953.         call    calculatescreen
  954.         xor     esi, esi
  955.         xor     eax, eax
  956.         call    redrawscreen
  957.  
  958.         pop     esi edx ecx ebx eax
  959.  
  960.   .exit:
  961.         popfd
  962.         pop     edi
  963.         ret
  964.  
  965. align 4
  966. ;------------------------------------------------------------------------------
  967. restore_minimized_window: ;////////////////////////////////////////////////////
  968. ;------------------------------------------------------------------------------
  969. ;> eax = window number on screen
  970. ;------------------------------------------------------------------------------
  971. ;# corrupts [dl*]
  972. ;------------------------------------------------------------------------------
  973.         pushad
  974.         pushfd
  975.         cli
  976.  
  977.         ; is it already restored?
  978.         movzx   esi, word[WIN_POS + eax * 2]
  979.         mov     edi, esi
  980.         shl     edi, 5
  981.         add     edi, window_data
  982.         test    [edi + WDATA.fl_wstate], WSTATE_MINIMIZED
  983.         jz      .exit
  984.  
  985.         ; no it's not, let's do that
  986.         mov     [edi + WDATA.fl_redraw], 1
  987.         and     [edi + WDATA.fl_wstate], not WSTATE_MINIMIZED
  988.         mov     ebp, window._.set_screen
  989.         cmp     eax, [TASK_COUNT]
  990.         jz      @f
  991.         mov     ebp, calculatescreen
  992.     @@: mov     eax, [edi + WDATA.box.left]
  993.         mov     ebx, [edi + WDATA.box.top]
  994.         mov     ecx, [edi + WDATA.box.width]
  995.         mov     edx, [edi + WDATA.box.height]
  996.         add     ecx, eax
  997.         add     edx, ebx
  998.         call    ebp
  999.  
  1000.         mov     byte[MOUSE_BACKGROUND], 0
  1001.  
  1002.   .exit:
  1003.         popfd
  1004.         popad
  1005.         ret
  1006.  
  1007. align 4
  1008. ; TODO: remove this proc
  1009. ;------------------------------------------------------------------------------
  1010. window_check_events: ;/////////////////////////////////////////////////////////
  1011. ;------------------------------------------------------------------------------
  1012. ;? <description>
  1013. ;------------------------------------------------------------------------------
  1014.         ; do we have window minimize/restore request?
  1015.         cmp     [window_minimize], 0
  1016.         je      .exit
  1017.  
  1018.         ; okay, minimize or restore top-most window and exit
  1019.         mov     eax, [TASK_COUNT]
  1020.         mov     bl, 0
  1021.         xchg    [window_minimize], bl
  1022.         dec     bl
  1023.         jnz     @f
  1024.         call    minimize_window
  1025.         jmp     .exit
  1026.  
  1027.     @@: call    restore_minimized_window
  1028.  
  1029.   .exit:
  1030.         ret
  1031.  
  1032. align 4
  1033. ;------------------------------------------------------------------------------
  1034. sys_window_maximize_handler: ;/////////////////////////////////////////////////
  1035. ;------------------------------------------------------------------------------
  1036. ;? <description>
  1037. ;------------------------------------------------------------------------------
  1038. ;> esi = process slot
  1039. ;------------------------------------------------------------------------------
  1040.         mov     edi, esi
  1041.         shl     edi, 5
  1042.         add     edi, window_data
  1043.  
  1044.         ; can window change its height?
  1045.         ; only types 2 and 3 can be resized
  1046.         mov     dl, [edi + WDATA.fl_wstyle]
  1047.         test    dl, 2
  1048.         jz      .exit
  1049.  
  1050.         ; toggle normal/maximized window state
  1051.         mov     bl, [edi + WDATA.fl_wstate]
  1052.         xor     bl, WSTATE_MAXIMIZED
  1053.  
  1054.         ; calculate and set appropriate window bounds
  1055.         test    bl, WSTATE_MAXIMIZED
  1056.         jz      .restore_size
  1057.  
  1058.         mov     eax, [screen_workarea.left]
  1059.         mov     ecx, [screen_workarea.top]
  1060.         push    [screen_workarea.bottom] \
  1061.                 [screen_workarea.right] \
  1062.                 ecx \
  1063.                 eax
  1064.         sub     [esp + BOX.width], eax
  1065.         sub     [esp + BOX.height], ecx
  1066.         mov     eax, esp
  1067.         jmp     .set_box
  1068.  
  1069.   .restore_size:
  1070.         mov     eax, esi
  1071.         shl     eax, 8
  1072.         add     eax, SLOT_BASE + APPDATA.saved_box
  1073.         push    [eax + BOX.height] \
  1074.                 [eax + BOX.width] \
  1075.                 [eax + BOX.top] \
  1076.                 [eax + BOX.left]
  1077.         mov     eax, esp
  1078.  
  1079.   .set_box:
  1080.         test    bl, WSTATE_ROLLEDUP
  1081.         jz      @f
  1082.  
  1083.         xchg    eax, ecx
  1084.         call    window._.get_rolledup_height
  1085.         mov     [ecx + BOX.height], eax
  1086.         xchg    eax, ecx
  1087.  
  1088.     @@: call    window._.set_window_box
  1089.         add     esp, BOX.sizeof
  1090.  
  1091.   .exit:
  1092.         ret
  1093.  
  1094. align 4
  1095. ;------------------------------------------------------------------------------
  1096. sys_window_rollup_handler: ;///////////////////////////////////////////////////
  1097. ;------------------------------------------------------------------------------
  1098. ;? <description>
  1099. ;------------------------------------------------------------------------------
  1100. ;> esi = process slot
  1101. ;------------------------------------------------------------------------------
  1102.         mov     edx, esi
  1103.         shl     edx, 8
  1104.         add     edx, SLOT_BASE
  1105.  
  1106.         ; toggle normal/rolled up window state
  1107.         mov     bl, [edi + WDATA.fl_wstate]
  1108.         xor     bl, WSTATE_ROLLEDUP
  1109.  
  1110.         ; calculate and set appropriate window bounds
  1111.         test    bl, WSTATE_ROLLEDUP
  1112.         jz      .restore_size
  1113.  
  1114.         call    window._.get_rolledup_height
  1115.         push    eax \
  1116.                 [edi + WDATA.box.width] \
  1117.                 [edi + WDATA.box.top] \
  1118.                 [edi + WDATA.box.left]
  1119.         mov     eax, esp
  1120.         jmp     .set_box
  1121.  
  1122.   .restore_size:
  1123.         test    bl, WSTATE_MAXIMIZED
  1124.         jnz     @f
  1125.         add     esp, -BOX.sizeof
  1126.         lea     eax, [edx + APPDATA.saved_box]
  1127.         jmp     .set_box
  1128.  
  1129.     @@: mov     eax, [screen_workarea.top]
  1130.         push    [screen_workarea.bottom] \
  1131.                 [edi + WDATA.box.width] \
  1132.                 eax \
  1133.                 [edi + WDATA.box.left]
  1134.         sub     [esp + BOX.height], eax
  1135.         mov     eax, esp
  1136.  
  1137.   .set_box:
  1138.         call    window._.set_window_box
  1139.         add     esp, BOX.sizeof
  1140.  
  1141.         ret
  1142.  
  1143. align 4
  1144. ;------------------------------------------------------------------------------
  1145. sys_window_start_moving_handler: ;/////////////////////////////////////////////
  1146. ;------------------------------------------------------------------------------
  1147. ;? <description>
  1148. ;------------------------------------------------------------------------------
  1149. ;> eax = old (original) window box
  1150. ;> esi = process slot
  1151. ;------------------------------------------------------------------------------
  1152.         mov     edi, eax
  1153.         call    window._.draw_negative_box
  1154.  
  1155.         ret
  1156.  
  1157. align 4
  1158. ;------------------------------------------------------------------------------
  1159. sys_window_end_moving_handler: ;///////////////////////////////////////////////
  1160. ;------------------------------------------------------------------------------
  1161. ;? <description>
  1162. ;------------------------------------------------------------------------------
  1163. ;> eax = old (original) window box
  1164. ;> ebx = new (final) window box
  1165. ;> esi = process slot
  1166. ;------------------------------------------------------------------------------
  1167.         mov     edi, ebx
  1168.         call    window._.draw_negative_box
  1169.  
  1170.         mov     edi, esi
  1171.         shl     edi, 5
  1172.         add     edi, window_data
  1173.  
  1174.         mov     eax, ebx
  1175.         mov     bl, [edi + WDATA.fl_wstate]
  1176.         call    window._.set_window_box
  1177.         ret
  1178.  
  1179. align 4
  1180. ;------------------------------------------------------------------------------
  1181. sys_window_moving_handler: ;///////////////////////////////////////////////////
  1182. ;------------------------------------------------------------------------------
  1183. ;? <description>
  1184. ;------------------------------------------------------------------------------
  1185. ;> eax = old (from previous call) window box
  1186. ;> ebx = new (current) window box
  1187. ;> esi = process_slot
  1188. ;------------------------------------------------------------------------------
  1189.         mov     edi, eax
  1190.         call    window._.draw_negative_box
  1191.         mov     edi, ebx
  1192.         call    window._.draw_negative_box
  1193.         ret
  1194.  
  1195. ;==============================================================================
  1196. ;///// private functions //////////////////////////////////////////////////////
  1197. ;==============================================================================
  1198.  
  1199. iglobal
  1200.   FuncTable syscall_display_settings, ftable, \
  1201.     00, 01, 02, 03, 04, 05, 06, 07, 08
  1202.  
  1203.   align 4
  1204.   window_topleft dd \
  1205.     1, 21, \ ;type 0
  1206.     0,  0, \ ;type 1
  1207.     5, 20, \ ;type 2
  1208.     5,  ?, \ ;type 3 {set by skin}
  1209.     5,  ?    ;type 4 {set by skin}
  1210. endg
  1211.  
  1212. ;uglobal
  1213.   ; NOTE: commented out since doesn't provide necessary functionality anyway,
  1214.   ;       to be reworked
  1215. ; new_window_starting       dd ?
  1216. ;endg
  1217.  
  1218. align 4
  1219. ;------------------------------------------------------------------------------
  1220. window._.invalidate_screen: ;//////////////////////////////////////////////////
  1221. ;------------------------------------------------------------------------------
  1222. ;? <description>
  1223. ;------------------------------------------------------------------------------
  1224. ;> eax = old (original) window box
  1225. ;> ebx = new (final) window box
  1226. ;> edi = pointer to WDATA struct
  1227. ;------------------------------------------------------------------------------
  1228.         push    eax ebx
  1229.  
  1230.         ; TODO: do we really need `draw_limits`?
  1231.         ; Yes, they are used by background drawing code.
  1232.         mov     ecx, [eax + BOX.left]
  1233.         mov     edx, [ebx + BOX.left]
  1234.         cmp     ecx, edx
  1235.         jle     @f
  1236.         mov     ecx, edx
  1237.     @@: mov     [draw_limits.left], ecx
  1238.         mov     ecx, [eax + BOX.left]
  1239.         add     ecx, [eax + BOX.width]
  1240.         add     edx, [ebx + BOX.width]
  1241.         cmp     ecx, edx
  1242.         jae     @f
  1243.         mov     ecx, edx
  1244.     @@: mov     [draw_limits.right], ecx
  1245.         mov     ecx, [eax + BOX.top]
  1246.         mov     edx, [ebx + BOX.top]
  1247.         cmp     ecx, edx
  1248.         jle     @f
  1249.         mov     ecx, edx
  1250.     @@: mov     [draw_limits.top], ecx
  1251.         mov     ecx, [eax + BOX.top]
  1252.         add     ecx, [eax + BOX.height]
  1253.         add     edx, [ebx + BOX.height]
  1254.         cmp     ecx, edx
  1255.         jae     @f
  1256.         mov     ecx, edx
  1257.     @@: mov     [draw_limits.bottom], ecx
  1258.  
  1259.         ; recalculate screen buffer at old position
  1260.         push    ebx
  1261.         mov     edx, [eax + BOX.height]
  1262.         mov     ecx, [eax + BOX.width]
  1263.         mov     ebx, [eax + BOX.top]
  1264.         mov     eax, [eax + BOX.left]
  1265.         add     ecx, eax
  1266.         add     edx, ebx
  1267.         call    calculatescreen
  1268.         pop     eax
  1269.  
  1270.         ; recalculate screen buffer at new position
  1271.         mov     edx, [eax + BOX.height]
  1272.         mov     ecx, [eax + BOX.width]
  1273.         mov     ebx, [eax + BOX.top]
  1274.         mov     eax, [eax + BOX.left]
  1275.         add     ecx, eax
  1276.         add     edx, ebx
  1277.         call    calculatescreen
  1278.  
  1279.         mov     eax, edi
  1280.         call    redrawscreen
  1281.  
  1282.         ; tell window to redraw itself
  1283.         mov     [edi + WDATA.fl_redraw], 1
  1284.  
  1285.         pop     ebx eax
  1286.         ret
  1287.  
  1288. align 4
  1289. ;------------------------------------------------------------------------------
  1290. window._.set_window_box: ;/////////////////////////////////////////////////////
  1291. ;------------------------------------------------------------------------------
  1292. ;? <description>
  1293. ;------------------------------------------------------------------------------
  1294. ;> eax = pointer to BOX struct
  1295. ;> bl = new window state flags
  1296. ;> edi = pointer to WDATA struct
  1297. ;------------------------------------------------------------------------------
  1298.         push    eax ebx esi
  1299.  
  1300. ; don't do anything if the new box is identical to the old
  1301.         cmp     bl, [edi + WDATA.fl_wstate]
  1302.         jnz     @f
  1303.         mov     esi, eax
  1304.         push    edi
  1305. if WDATA.box
  1306.         add     edi, WDATA.box
  1307. end if
  1308.         mov     ecx, 4
  1309.         repz    cmpsd
  1310.         pop     edi
  1311.         jz      .exit
  1312. @@:
  1313.  
  1314.         add     esp, -BOX.sizeof
  1315.  
  1316.         mov     ebx, esp
  1317. if WDATA.box
  1318.         lea     esi, [edi + WDATA.box]
  1319. else
  1320.         mov     esi, edi ; optimization for WDATA.box = 0
  1321. end if
  1322.         xchg    eax, esi
  1323.         mov     ecx, BOX.sizeof
  1324.         call    memmove
  1325.         xchg    eax, esi
  1326.         xchg    ebx, esi
  1327.         call    memmove
  1328.         mov     eax, ebx
  1329.         mov     ebx, esi
  1330.  
  1331.         call    window._.check_window_position
  1332.         call    window._.set_window_clientbox
  1333.         call    window._.invalidate_screen
  1334.  
  1335.         add     esp, BOX.sizeof
  1336.  
  1337.         mov     cl, [esp + 4]
  1338.         mov     ch, cl
  1339.         xchg    cl, [edi + WDATA.fl_wstate]
  1340.  
  1341.         or      cl, ch
  1342.         test    cl, WSTATE_MAXIMIZED
  1343.         jnz     .exit
  1344.  
  1345.         mov     eax, edi
  1346.         sub     eax, window_data
  1347.         shl     eax, 3
  1348.         add     eax, SLOT_BASE
  1349.  
  1350.         lea     ebx, [edi + WDATA.box]
  1351.         xchg    esp, ebx
  1352.  
  1353.         pop     [eax + APPDATA.saved_box.left] \
  1354.                 [eax + APPDATA.saved_box.top] \
  1355.                 [eax + APPDATA.saved_box.width] \
  1356.                 edx
  1357.  
  1358.         xchg    esp, ebx
  1359.  
  1360.         test    ch, WSTATE_ROLLEDUP
  1361.         jnz     .exit
  1362.  
  1363.         mov     [eax + APPDATA.saved_box.height], edx
  1364.  
  1365.   .exit:
  1366.         pop     esi ebx eax
  1367.         ret
  1368.  
  1369. align 4
  1370. ;------------------------------------------------------------------------------
  1371. window._.set_window_clientbox: ;///////////////////////////////////////////////
  1372. ;------------------------------------------------------------------------------
  1373. ;? <description>
  1374. ;------------------------------------------------------------------------------
  1375. ;> edi = pointer to WDATA struct
  1376. ;------------------------------------------------------------------------------
  1377.         push    eax ecx edi
  1378.  
  1379.         mov     eax, [_skinh]
  1380.         mov     [window_topleft + 8 * 3 + 4], eax
  1381.         mov     [window_topleft + 8 * 4 + 4], eax
  1382.  
  1383.         mov     ecx, edi
  1384.         sub     edi, window_data
  1385.         shl     edi, 3
  1386.         test    [ecx + WDATA.fl_wstyle], WSTYLE_CLIENTRELATIVE
  1387.         jz      .whole_window
  1388.  
  1389.         movzx   eax, [ecx + WDATA.fl_wstyle]
  1390.         and     eax, 0x0F
  1391.         mov     eax, [eax * 8 + window_topleft + 0]
  1392.         mov     [edi + SLOT_BASE + APPDATA.wnd_clientbox.left], eax
  1393.         shl     eax, 1
  1394.         neg     eax
  1395.         add     eax, [ecx + WDATA.box.width]
  1396.         mov     [edi + SLOT_BASE + APPDATA.wnd_clientbox.width], eax
  1397.  
  1398.         movzx   eax, [ecx + WDATA.fl_wstyle]
  1399.         and     eax, 0x0F
  1400.         push    [eax * 8 + window_topleft + 0]
  1401.         mov     eax, [eax * 8 + window_topleft + 4]
  1402.         mov     [edi + SLOT_BASE + APPDATA.wnd_clientbox.top], eax
  1403.         neg     eax
  1404.         sub     eax, [esp]
  1405.         add     eax, [ecx + WDATA.box.height]
  1406.         mov     [edi + SLOT_BASE + APPDATA.wnd_clientbox.height], eax
  1407.         add     esp, 4
  1408.         jmp     .exit
  1409.  
  1410.   .whole_window:
  1411.         xor     eax, eax
  1412.         mov     [edi + SLOT_BASE + APPDATA.wnd_clientbox.left], eax
  1413.         mov     [edi + SLOT_BASE + APPDATA.wnd_clientbox.top], eax
  1414.         mov     eax, [ecx + WDATA.box.width]
  1415.         mov     [edi + SLOT_BASE + APPDATA.wnd_clientbox.width], eax
  1416.         mov     eax, [ecx + WDATA.box.height]
  1417.         mov     [edi + SLOT_BASE + APPDATA.wnd_clientbox.height], eax
  1418.  
  1419.   .exit:
  1420.         pop     edi ecx eax
  1421.         ret
  1422.  
  1423. align 4
  1424. ;------------------------------------------------------------------------------
  1425. window._.sys_set_window: ;/////////////////////////////////////////////////////
  1426. ;------------------------------------------------------------------------------
  1427. ;? <description>
  1428. ;------------------------------------------------------------------------------
  1429. ;< edx = pointer to WDATA struct
  1430. ;------------------------------------------------------------------------------
  1431.         mov     eax, [CURRENT_TASK]
  1432.         shl     eax, 5
  1433.         add     eax, window_data
  1434.  
  1435.         ; save window colors
  1436.         mov     [eax + WDATA.cl_workarea], edx
  1437.         mov     [eax + WDATA.cl_titlebar], esi
  1438.         mov     [eax + WDATA.cl_frames], edi
  1439.  
  1440.         mov     edi, eax
  1441.  
  1442.         ; was it already defined before?
  1443.         test    [edi + WDATA.fl_wdrawn], 1
  1444.         jnz     .set_client_box
  1445.         or      [edi + WDATA.fl_wdrawn], 1
  1446.  
  1447.         ; NOTE: commented out since doesn't provide necessary functionality
  1448.         ;       anyway, to be reworked
  1449. ;       mov     eax, [timer_ticks] ; [0xfdf0]
  1450. ;       add     eax, 100
  1451. ;       mov     [new_window_starting], eax
  1452.  
  1453.         ; no it wasn't, performing initial window definition
  1454.         movzx   eax, bx
  1455.         mov     [edi + WDATA.box.width], eax
  1456.         movzx   eax, cx
  1457.         mov     [edi + WDATA.box.height], eax
  1458.         sar     ebx, 16
  1459. ;       and     bl, 0xFC                ; <<<<<<<<
  1460.         sar     ecx, 16
  1461. ;       and     cl, 0xFE                ; <<<<<<<<
  1462.         mov     [edi + WDATA.box.left], ebx
  1463.         mov     [edi + WDATA.box.top], ecx
  1464.  
  1465.         call    window._.check_window_position
  1466.  
  1467.         push    ecx edi
  1468.  
  1469.         mov     cl, [edi + WDATA.fl_wstyle]
  1470.         mov     eax, [edi + WDATA.cl_frames]
  1471.  
  1472.         sub     edi, window_data
  1473.         shl     edi, 3
  1474.         add     edi, SLOT_BASE
  1475.  
  1476.         and     cl, 0x0F
  1477.         cmp     cl, 3
  1478.         je      @f
  1479.         cmp     cl, 4
  1480.         je      @f
  1481.  
  1482.         xor     eax, eax
  1483.  
  1484.     @@: mov     [edi + APPDATA.wnd_caption], eax
  1485.  
  1486.         mov     esi, [esp]
  1487.         add     edi, APPDATA.saved_box
  1488.         movsd
  1489.         movsd
  1490.         movsd
  1491.         movsd
  1492.  
  1493.         pop     edi ecx
  1494.  
  1495.         mov     esi, [CURRENT_TASK]
  1496.         movzx   esi, word[WIN_STACK + esi * 2]
  1497.         lea     esi, [WIN_POS + esi * 2]
  1498.         call    waredraw
  1499.  
  1500.         mov     eax, [edi + WDATA.box.left]
  1501.         mov     ebx, [edi + WDATA.box.top]
  1502.         mov     ecx, [edi + WDATA.box.width]
  1503.         mov     edx, [edi + WDATA.box.height]
  1504.         add     ecx, eax
  1505.         add     edx, ebx
  1506.         call    calculatescreen
  1507.  
  1508.         mov     byte[KEY_COUNT], 0           ; empty keyboard buffer
  1509.         mov     byte[BTN_COUNT], 0           ; empty button buffer
  1510.  
  1511.   .set_client_box:
  1512.         ; update window client box coordinates
  1513.         call    window._.set_window_clientbox
  1514.  
  1515.         ; reset window redraw flag and exit
  1516.         mov     [edi + WDATA.fl_redraw], 0
  1517.         mov     edx, edi
  1518.         ret
  1519.  
  1520. align 4
  1521. ;------------------------------------------------------------------------------
  1522. window._.check_window_position: ;//////////////////////////////////////////////
  1523. ;------------------------------------------------------------------------------
  1524. ;? Check if window is inside screen area
  1525. ;------------------------------------------------------------------------------
  1526. ;> edi = pointer to WDATA
  1527. ;------------------------------------------------------------------------------
  1528.         push    eax ebx ecx edx esi
  1529.  
  1530.         mov     eax, [edi + WDATA.box.left]
  1531.         mov     ebx, [edi + WDATA.box.top]
  1532.         mov     ecx, [edi + WDATA.box.width]
  1533.         mov     edx, [edi + WDATA.box.height]
  1534.  
  1535.         mov     esi, [Screen_Max_X]
  1536.         cmp     ecx, esi
  1537.         ja      .fix_width_high
  1538.  
  1539.   .check_left:
  1540.         or      eax, eax
  1541.         jl      .fix_left_low
  1542.         add     eax, ecx
  1543.         cmp     eax, esi
  1544.         jg      .fix_left_high
  1545.  
  1546.   .check_height:
  1547.         mov     esi, [Screen_Max_Y]
  1548.         cmp     edx, esi
  1549.         ja      .fix_height_high
  1550.  
  1551.   .check_top:
  1552.         or      ebx, ebx
  1553.         jl      .fix_top_low
  1554.         add     ebx, edx
  1555.         cmp     ebx, esi
  1556.         jg      .fix_top_high
  1557.  
  1558.   .exit:
  1559.         pop     esi edx ecx ebx eax
  1560.         ret
  1561.  
  1562.   .fix_width_high:
  1563.         mov     ecx, esi
  1564.         mov     [edi + WDATA.box.width], esi
  1565.         jmp     .check_left
  1566.  
  1567.   .fix_left_low:
  1568.         xor     eax, eax
  1569.         mov     [edi + WDATA.box.left], eax
  1570.         jmp     .check_height
  1571.  
  1572.   .fix_left_high:
  1573.         mov     eax, esi
  1574.         sub     eax, ecx
  1575.         mov     [edi + WDATA.box.left], eax
  1576.         jmp     .check_height
  1577.  
  1578.   .fix_height_high:
  1579.         mov     edx, esi
  1580.         mov     [edi + WDATA.box.height], esi
  1581.         jmp     .check_top
  1582.  
  1583.   .fix_top_low:
  1584.         xor     ebx, ebx
  1585.         mov     [edi + WDATA.box.top], ebx
  1586.         jmp     .exit
  1587.  
  1588.   .fix_top_high:
  1589.         mov     ebx, esi
  1590.         sub     ebx, edx
  1591.         mov     [edi + WDATA.box.top], ebx
  1592.         jmp     .exit
  1593.  
  1594. align 4
  1595. ;------------------------------------------------------------------------------
  1596. window._.get_titlebar_height: ;////////////////////////////////////////////////
  1597. ;------------------------------------------------------------------------------
  1598. ;? <description>
  1599. ;------------------------------------------------------------------------------
  1600. ;> edi = pointer to WDATA
  1601. ;------------------------------------------------------------------------------
  1602.         mov     al, [edi + WDATA.fl_wstyle]
  1603.         and     al, 0x0f
  1604.         cmp     al, 0x03
  1605.         jne     @f
  1606.         mov     eax, [_skinh]
  1607.         ret
  1608.     @@: mov     eax, 21
  1609.         ret
  1610.  
  1611. align 4
  1612. ;------------------------------------------------------------------------------
  1613. window._.get_rolledup_height: ;////////////////////////////////////////////////
  1614. ;------------------------------------------------------------------------------
  1615. ;? <description>
  1616. ;------------------------------------------------------------------------------
  1617. ;> edi = pointer to WDATA
  1618. ;------------------------------------------------------------------------------
  1619.         mov     al, [edi + WDATA.fl_wstyle]
  1620.         and     al, 0x0f
  1621.         cmp     al, 0x03
  1622.         jb      @f
  1623.         mov     eax, [_skinh]
  1624.         add     eax, 3
  1625.         ret
  1626.     @@: or      al, al
  1627.         jnz     @f
  1628.         mov     eax, 21
  1629.         ret
  1630.     @@: mov     eax, 21 + 2
  1631.         ret
  1632.  
  1633. align 4
  1634. ;------------------------------------------------------------------------------
  1635. window._.set_screen: ;/////////////////////////////////////////////////////////
  1636. ;------------------------------------------------------------------------------
  1637. ;? Reserve window area in screen buffer
  1638. ;------------------------------------------------------------------------------
  1639. ;> eax = left
  1640. ;> ebx = top
  1641. ;> ecx = right
  1642. ;> edx = bottom
  1643. ;> esi = process number
  1644. ;------------------------------------------------------------------------------
  1645. virtual at esp
  1646.   ff_x     dd ?
  1647.   ff_y     dd ?
  1648.   ff_width dd ?
  1649.   ff_xsz   dd ?
  1650.   ff_ysz   dd ?
  1651.   ff_map   dd ?
  1652.   ff_scale dd ?
  1653. end virtual
  1654.  
  1655.         pushad
  1656.  
  1657.         cmp     esi, 1
  1658.         jz      .check_for_shaped_window
  1659.         mov     edi, esi
  1660.         shl     edi, 5
  1661.         cmp     [window_data + edi + WDATA.box.width], 0
  1662.         jnz     .check_for_shaped_window
  1663.         cmp     [window_data + edi + WDATA.box.height], 0
  1664.         jz      .exit
  1665.  
  1666.   .check_for_shaped_window:
  1667.         mov     edi, esi
  1668.         shl     edi, 8
  1669.         add     edi, SLOT_BASE
  1670.         cmp     [edi + APPDATA.wnd_shape], 0
  1671.         jne     .shaped_window
  1672.  
  1673.         ; get x&y size
  1674.         sub     ecx, eax
  1675.         sub     edx, ebx
  1676.         inc     ecx
  1677.         inc     edx
  1678.         shr     ecx, 2          ; 1 tile = 4 pix
  1679.         shr     edx, 1          ; 1 tile = 2 lines
  1680.  
  1681.         ; get WinMap start
  1682.         push    esi
  1683.         mov     edi, [_WinMapWidth]
  1684.         mov     esi, edi
  1685.         shr     ebx, 1
  1686.         imul    edi, ebx
  1687.         shr     eax, 2
  1688.         add     edi, eax
  1689.         add     edi, [_WinMapAddress]
  1690.         pop     eax             ; al = process#
  1691. ;       mov     ah, al
  1692. ;       push    ax
  1693. ;       shl     eax, 16
  1694. ;       pop     ax              ; eax = 4 dup PROCESS_NUM
  1695.  
  1696.         sub     esi, ecx        ; map line increment (bytes)
  1697.         mov     ebx, ecx        ; map line width
  1698.   .next_line:
  1699. ;        shr     ecx, 2          ; 1dword = 4 tiles
  1700. ;       rep     stosd           ; filling the screen map
  1701. ;       mov     ecx, ebx      
  1702. ;       and     ecx, 3          ; 0 to 3 tiles remaining
  1703.         rep     stosb
  1704.         mov     ecx, ebx
  1705.         add     edi, esi        
  1706.         dec     edx
  1707.         jnz     .next_line
  1708.         jmp     .exit
  1709.  
  1710.   .shaped_window:
  1711.         ;  for (y=0; y <= y_size; y++)
  1712.         ;      for (x=0; x <= x_size; x++)
  1713.         ;          if (shape[coord(x,y,scale)]==1)
  1714.         ;             set_pixel(x, y, process_number);
  1715.  
  1716.         sub     ecx, eax
  1717.         sub     edx, ebx
  1718.         inc     ecx
  1719.         inc     edx
  1720.  
  1721.         push    [edi + APPDATA.wnd_shape_scale]                 ; push scale first -> for loop
  1722.  
  1723.         push    ebx
  1724.         push    eax
  1725.         mov     ebp, eax
  1726.         shr     ebp, 2
  1727.         add     ebp, [_WinMapAddress]
  1728.         mov     eax, [_WinMapWidth]
  1729.         shr     ebx, 1
  1730.         imul    eax, ebx
  1731.         add     ebp, eax        ; ebp = map origin
  1732.  
  1733.         mov     edi, [edi + APPDATA.wnd_shape]
  1734.         pop     eax
  1735.         pop     ebx
  1736.        
  1737.         push    ebp                                             ; for loop - screen map origin
  1738.  
  1739.         ; eax = x_start
  1740.         ; ebx = y_start
  1741.         ; ecx = x_size
  1742.         ; edx = y_size
  1743.         ; esi = process_number
  1744.         ; edi = &shape
  1745.         ; ebp = [ff_map]
  1746.         ;       [scale]
  1747.  
  1748.         push    edx ecx                                         ; for loop - x,y size
  1749.         mov     ecx, esi
  1750.         shl     ecx, 5
  1751.         mov     edx, [window_data + ecx + WDATA.box.top]
  1752.         push    [window_data + ecx + WDATA.box.width]           ; for loop - width
  1753.         mov     ecx, [window_data + ecx + WDATA.box.left]
  1754.         sub     ebx, edx
  1755.         sub     eax, ecx
  1756.         push    ebx eax                                         ; for loop - x,y
  1757.  
  1758.         add     [ff_xsz], eax
  1759.         add     [ff_ysz], ebx
  1760.  
  1761.         mov     ebx, [ff_y]
  1762.  
  1763.   .ff_new_y:
  1764.         mov     edx, [ff_x]
  1765.  
  1766.   .ff_new_x:
  1767.         ; -- body --
  1768.         mov     ecx, [ff_scale]
  1769.         mov     eax, [ff_width]
  1770.         inc     eax
  1771.         shr     eax, cl
  1772.         push    ebx edx
  1773.         shr     ebx, cl
  1774.         shr     edx, cl
  1775.         imul    eax, ebx
  1776.         add     eax, edx
  1777.         pop     edx ebx
  1778.         add     eax, edi
  1779.         call    .read_byte              ; al= shaped window pix-mask at a given point
  1780.         test    al,al
  1781.         jz      @f
  1782.         mov     eax, esi
  1783.         mov     [ebp], al               ; a tile belongs to the window if the 1st pixel's mask = 1
  1784.         ; -- end body --
  1785.     @@:
  1786.         add     edx, 4
  1787.         inc     ebp                    
  1788.         cmp     edx, [ff_xsz]
  1789.         jb      .ff_new_x
  1790.  
  1791.         inc     ebx
  1792.         inc     ebx
  1793.         cmp     ebx, [ff_ysz]
  1794.         jnb     @f
  1795.         mov     ebp, [ff_map]            
  1796.         add     ebp, [_WinMapWidth]     ; even line: jump to next map row
  1797.         mov     [ff_map], ebp
  1798.         jmp     .ff_new_y
  1799. @@:
  1800.         add     esp, 7*4
  1801.   .exit:
  1802.         popad
  1803.         ret
  1804.  
  1805.   .read_byte:
  1806.         ; eax - buffer address
  1807.         ; esi - slot#
  1808.         push    eax ecx edx esi
  1809.         xchg    eax, esi                
  1810.         lea     ecx, [esp + 12]         ; buffer addr = stacked [eax] to return
  1811.         mov     edx, 1                  ; buffer size
  1812.         call    read_process_memory     ; (core/taskman.inc) returns #bytes read
  1813.         pop     esi edx ecx eax         ; eax = PID
  1814.         ret
  1815.  
  1816. align 4
  1817. ;------------------------------------------------------------------------------
  1818. window._.window_activate: ;////////////////////////////////////////////////////
  1819. ;------------------------------------------------------------------------------
  1820. ;? Activate window
  1821. ;------------------------------------------------------------------------------
  1822. ;> esi = pointer to WIN_POS+ window data
  1823. ;------------------------------------------------------------------------------
  1824.         push    eax ebx
  1825.  
  1826.         ; if type of current active window is 3 or 4, it must be redrawn
  1827.         mov     ebx, [TASK_COUNT]
  1828.         movzx   ebx, word[WIN_POS + ebx * 2]
  1829.         shl     ebx, 5
  1830.         add     eax, window_data
  1831.         mov     al, [window_data + ebx + WDATA.fl_wstyle]
  1832.         and     al, 0x0f
  1833.         cmp     al, 0x03
  1834.         je      .set_window_redraw_flag
  1835.         cmp     al, 0x04
  1836.         jne     .move_others_down
  1837.  
  1838.   .set_window_redraw_flag:
  1839.         mov     [window_data + ebx + WDATA.fl_redraw], 1
  1840.  
  1841.   .move_others_down:
  1842.         ; ax <- process no
  1843.         movzx   ebx, word[esi]
  1844.         ; ax <- position in window stack
  1845.         movzx   ebx, word[WIN_STACK + ebx * 2]
  1846.  
  1847.         ; drop others
  1848.         xor     eax, eax
  1849.  
  1850.   .next_stack_window:
  1851.         cmp     eax, [TASK_COUNT]
  1852.         jae     .move_self_up
  1853.         inc     eax
  1854.         cmp     [WIN_STACK + eax * 2], bx
  1855.         jbe     .next_stack_window
  1856.         dec     word[WIN_STACK + eax * 2]
  1857.         jmp     .next_stack_window
  1858.  
  1859.   .move_self_up:
  1860.         movzx   ebx, word[esi]
  1861.         ; number of processes
  1862.         mov     ax, [TASK_COUNT]
  1863.         ; this is the last (and the upper)
  1864.         mov     [WIN_STACK + ebx * 2], ax
  1865.  
  1866.         ; update on screen - window stack
  1867.         xor     eax, eax
  1868.  
  1869.   .next_window_pos:
  1870.         cmp     eax, [TASK_COUNT]
  1871.         jae     .reset_vars
  1872.         inc     eax
  1873.         movzx   ebx, word[WIN_STACK + eax * 2]
  1874.         mov     [WIN_POS + ebx * 2], ax
  1875.         jmp     .next_window_pos
  1876.  
  1877.   .reset_vars:
  1878.         mov     byte[KEY_COUNT], 0
  1879.         mov     byte[BTN_COUNT], 0
  1880.         mov     word[MOUSE_SCROLL_H], 0
  1881.         mov     word[MOUSE_SCROLL_V], 0
  1882.  
  1883.         pop     ebx eax
  1884.         ret
  1885.  
  1886. align 4
  1887. ;------------------------------------------------------------------------------
  1888. window._.check_window_draw: ;//////////////////////////////////////////////////
  1889. ;------------------------------------------------------------------------------
  1890. ;? Check if window is necessary to draw
  1891. ;------------------------------------------------------------------------------
  1892. ;> edi = pointer to WDATA
  1893. ;------------------------------------------------------------------------------
  1894.         mov     cl, [edi + WDATA.fl_wstyle]
  1895.         and     cl, 0x0f
  1896.         cmp     cl, 3
  1897.         je      .exit.redraw      ; window type 3
  1898.         cmp     cl, 4
  1899.         je      .exit.redraw      ; window type 4
  1900.  
  1901.         push    eax ebx edx esi
  1902.  
  1903.         mov     eax, edi
  1904.         sub     eax, window_data
  1905.         shr     eax, 5
  1906.  
  1907.         movzx   eax, word[WIN_STACK + eax * 2]  ; get value of the curr process
  1908.         lea     esi, [WIN_POS + eax * 2]        ; get address of this process at 0xC400
  1909.  
  1910.   .next_window:
  1911.         add     esi, 2
  1912.  
  1913.         mov     eax, [TASK_COUNT]
  1914.         lea     eax, word[WIN_POS + eax * 2] ; number of the upper window
  1915.  
  1916.         cmp     esi, eax
  1917.         ja      .exit.no_redraw
  1918.  
  1919.         movzx   edx, word[esi]
  1920.         shl     edx, 5
  1921.         cmp     [CURRENT_TASK + edx + TASKDATA.state], TSTATE_FREE
  1922.         je      .next_window
  1923.  
  1924.         mov     eax, [edi + WDATA.box.top]
  1925.         mov     ebx, [edi + WDATA.box.height]
  1926.         add     ebx, eax
  1927.  
  1928.         mov     ecx, [window_data + edx + WDATA.box.top]
  1929.         cmp     ecx, ebx
  1930.         jge     .next_window
  1931.         add     ecx, [window_data + edx + WDATA.box.height]
  1932.         cmp     eax, ecx
  1933.         jge     .next_window
  1934.  
  1935.         mov     eax, [edi + WDATA.box.left]
  1936.         mov     ebx, [edi + WDATA.box.width]
  1937.         add     ebx, eax
  1938.  
  1939.         mov     ecx, [window_data + edx + WDATA.box.left]
  1940.         cmp     ecx, ebx
  1941.         jge     .next_window
  1942.         add     ecx, [window_data + edx + WDATA.box.width]
  1943.         cmp     eax, ecx
  1944.         jge     .next_window
  1945.  
  1946.         pop     esi edx ebx eax
  1947.  
  1948.   .exit.redraw:
  1949.         xor     ecx, ecx
  1950.         inc     ecx
  1951.         ret
  1952.  
  1953.   .exit.no_redraw:
  1954.         pop     esi edx ebx eax
  1955.         xor     ecx, ecx
  1956.         ret
  1957.  
  1958. align 4
  1959. ;------------------------------------------------------------------------------
  1960. window._.draw_window_caption: ;////////////////////////////////////////////////
  1961. ;------------------------------------------------------------------------------
  1962. ;? <description>
  1963. ;------------------------------------------------------------------------------
  1964.         inc     [mouse_pause]
  1965.         call    [_display.disable_mouse]
  1966.  
  1967.         xor     eax, eax
  1968.         mov     edx, [TASK_COUNT]
  1969.         movzx   edx, word[WIN_POS + edx * 2]
  1970.         cmp     edx, [CURRENT_TASK]
  1971.         jne     @f
  1972.         inc     eax
  1973.     @@: mov     edx, [CURRENT_TASK]
  1974.         shl     edx, 5
  1975.         add     edx, window_data
  1976.         movzx   ebx, [edx + WDATA.fl_wstyle]
  1977.         and     bl, 0x0F
  1978.         cmp     bl, 3
  1979.         je      .draw_caption_style_3
  1980.         cmp     bl, 4
  1981.         je      .draw_caption_style_3
  1982.  
  1983.         jmp     .not_style_3
  1984.  
  1985.   .draw_caption_style_3:
  1986.         push    edx
  1987.         call    drawwindow_IV_caption
  1988.         add     esp, 4
  1989.         jmp     .2
  1990.  
  1991.   .not_style_3:
  1992.         cmp     bl, 2
  1993.         jne     .not_style_2
  1994.  
  1995.         call    drawwindow_III_caption
  1996.         jmp     .2
  1997.  
  1998.   .not_style_2:
  1999.         cmp     bl, 0
  2000.         jne     .2
  2001.  
  2002.         call    drawwindow_I_caption
  2003.  
  2004.   .2:   mov     edi, [CURRENT_TASK]
  2005.         shl     edi, 5
  2006.         test    [edi + window_data + WDATA.fl_wstyle], WSTYLE_HASCAPTION
  2007.         jz      .exit
  2008.         mov     edx, [edi * 8 + SLOT_BASE + APPDATA.wnd_caption]
  2009.         or      edx, edx
  2010.         jz      .exit
  2011.  
  2012.         movzx   eax, [edi + window_data + WDATA.fl_wstyle]
  2013.         and     al, 0x0F
  2014.         cmp     al, 3
  2015.         je      .skinned
  2016.         cmp     al, 4
  2017.         je      .skinned
  2018.  
  2019.         jmp     .not_skinned
  2020.  
  2021.   .skinned:
  2022.         mov     ebp, [edi + window_data + WDATA.box.left - 2]
  2023.         mov     bp, word[edi + window_data + WDATA.box.top]
  2024.         movzx   eax, word[edi + window_data + WDATA.box.width]
  2025.         sub     ax, [_skinmargins.left]
  2026.         sub     ax, [_skinmargins.right]
  2027.         push    edx
  2028.         cwde
  2029.         cdq
  2030.         mov     ebx, 6
  2031.         idiv    ebx
  2032.         pop     edx
  2033.         or      eax, eax
  2034.         js      .exit
  2035.  
  2036.         mov     esi, eax
  2037.         mov     ebx, dword[_skinmargins.left - 2]
  2038.         mov     bx, word[_skinh]
  2039.         sub     bx, [_skinmargins.bottom]
  2040.         sub     bx, [_skinmargins.top]
  2041.         sar     bx, 1
  2042.         adc     bx, 0
  2043.         add     bx, [_skinmargins.top]
  2044.         add     bx, -3
  2045.         add     ebx, ebp
  2046.         jmp     .dodraw
  2047.  
  2048.   .not_skinned:
  2049.         cmp     al, 1
  2050.         je      .exit
  2051.  
  2052.         mov     ebp, [edi + window_data + WDATA.box.left - 2]
  2053.         mov     bp, word[edi + window_data + WDATA.box.top]
  2054.         movzx   eax, word[edi + window_data + WDATA.box.width]
  2055.         sub     eax, 16
  2056.         push    edx
  2057.         cwde
  2058.         cdq
  2059.         mov     ebx, 6
  2060.         idiv    ebx
  2061.         pop     edx
  2062.         or      eax, eax
  2063.         js      .exit
  2064.  
  2065.         mov     esi, eax
  2066.         mov     ebx, 0x00080007
  2067.         add     ebx, ebp
  2068.  
  2069.   .dodraw:
  2070.         mov     ecx, [common_colours + 16]
  2071.         or      ecx, 0x80000000
  2072.         xor     edi, edi
  2073.         call    dtext_asciiz_esi
  2074.  
  2075.   .exit:
  2076.         dec     [mouse_pause]
  2077.         call    [draw_pointer]
  2078.         ret
  2079.  
  2080. align 4
  2081. ;------------------------------------------------------------------------------
  2082. window._.draw_negative_box: ;//////////////////////////////////////////////////
  2083. ;------------------------------------------------------------------------------
  2084. ;? Draw negative box
  2085. ;------------------------------------------------------------------------------
  2086. ;> edi = pointer to BOX struct
  2087. ;------------------------------------------------------------------------------
  2088.         push    eax ebx esi
  2089.         mov     eax, [edi + BOX.left - 2]
  2090.         mov     ax, word[edi + BOX.left]
  2091.         add     ax, word[edi + BOX.width]
  2092.         mov     ebx, [edi + BOX.top - 2]
  2093.         mov     bx, word[edi + BOX.top]
  2094.         add     bx, word[edi + BOX.height]
  2095.         mov     esi, 0x01000000
  2096.         call    draw_rectangle.forced
  2097.         pop     esi ebx eax
  2098.         ret
  2099.  
  2100. diff16 "window code end",0,$
  2101. diff10 "window.inc size",syscall_draw_window,$
  2102.