DYNSPLITTERWND.CPP
上传用户:hnhlzg
上传日期:2013-10-19
资源大小:289k
文件大小:6k
源码类别:

数学计算

开发平台:

Visual C++

  1. // SAGA Incorporated MFC Goodies
  2. //
  3. // SAGA Incorporated (saga@gis.net) MFC Goodies
  4. // Developed by Andrew Slivker for www.codeguru.com
  5. // 
  6. // DynSplitterWnd.cpp : implementation file
  7. //
  8. // Version: 1.0
  9. // Revision: 02/03/98
  10. #include "stdafx.h"
  11. #include <afxext.h>
  12. #include "DynSplitterWnd.h"
  13. #ifdef _DEBUG
  14. #define new DEBUG_NEW
  15. #undef THIS_FILE
  16. static char THIS_FILE[] = __FILE__;
  17. #endif
  18. #define CX_BORDER 1
  19. #define CY_BORDER 1
  20. #define FAR_POINT_XY -10000
  21. /////////////////////////////////////////////////////////////////////////////
  22. // CDynSplitterWnd
  23. CDynSplitterWnd::CDynSplitterWnd() 
  24. :m_OldPoint(FAR_POINT_XY,FAR_POINT_XY), m_bDynSplit(TRUE)
  25. {
  26. }
  27. CDynSplitterWnd::~CDynSplitterWnd()
  28. {
  29. }
  30. void CDynSplitterWnd::OnInvertTracker(const CRect& rect)
  31. {
  32. if(!m_bDynSplit)
  33. CSplitterWnd::OnInvertTracker(rect);
  34. else
  35. return;
  36. }
  37. void CDynSplitterWnd::StartTracking(int ht)
  38. {
  39. if(!m_bDynSplit)
  40. {
  41. CSplitterWnd::StartTracking(ht);
  42. return;
  43. }
  44. ASSERT_VALID(this);
  45. if (ht == noHit)
  46. return;
  47. // GetHitRect will restrict 'm_rectLimit' as appropriate
  48. GetInsideRect(m_rectLimit);
  49. if (ht >= splitterIntersection1 && ht <= splitterIntersection225)
  50. {
  51. // split two directions (two tracking rectangles)
  52. int row = (ht - splitterIntersection1) / 15;
  53. int col = (ht - splitterIntersection1) % 15;
  54. GetHitRect(row + vSplitterBar1, m_rectTracker);
  55. int yTrackOffset = m_ptTrackOffset.y;
  56. m_bTracking2 = TRUE;
  57. GetHitRect(col + hSplitterBar1, m_rectTracker2);
  58. m_ptTrackOffset.y = yTrackOffset;
  59. }
  60. else if (ht == bothSplitterBox)
  61. {
  62. // hit on splitter boxes (for keyboard)
  63. GetHitRect(vSplitterBox, m_rectTracker);
  64. int yTrackOffset = m_ptTrackOffset.y;
  65. m_bTracking2 = TRUE;
  66. GetHitRect(hSplitterBox, m_rectTracker2);
  67. m_ptTrackOffset.y = yTrackOffset;
  68. // center it
  69. m_rectTracker.OffsetRect(0, m_rectLimit.Height()/2);
  70. m_rectTracker2.OffsetRect(m_rectLimit.Width()/2, 0);
  71. }
  72. else
  73. {
  74. // only hit one bar
  75. GetHitRect(ht, m_rectTracker);
  76. }
  77. // steal focus and capture
  78. SetCapture();
  79. // set tracking state and appropriate cursor
  80. m_bTracking = TRUE;
  81. m_htTrack = ht;
  82. SetSplitCursor(ht);
  83. }
  84. void CDynSplitterWnd::StopTracking(BOOL bAccept)
  85. {
  86. ASSERT_VALID(this);
  87. if (!m_bTracking)
  88. return;
  89. ReleaseCapture();
  90. // erase tracker rectangle
  91. OnInvertTracker(m_rectTracker);
  92. if (m_bTracking2)
  93. OnInvertTracker(m_rectTracker2);
  94. m_bTracking = m_bTracking2 = FALSE;
  95. // save old active view
  96. CWnd* pOldActiveView = GetActivePane();
  97. // m_rectTracker is set to the new splitter position (without border)
  98. // (so, adjust relative to where the border will be)
  99. m_rectTracker.OffsetRect(-CX_BORDER , -CY_BORDER);
  100. m_rectTracker2.OffsetRect(-CX_BORDER, -CY_BORDER);
  101. if (bAccept)
  102. {
  103. if (m_htTrack == vSplitterBox)
  104. {
  105. SplitRow(m_rectTracker.top);
  106. }
  107. else if (m_htTrack >= vSplitterBar1 && m_htTrack <= vSplitterBar15)
  108. {
  109. // set row height
  110. TrackRowSize(m_rectTracker.top, m_htTrack - vSplitterBar1);
  111. RecalcLayout();
  112. }
  113. else if (m_htTrack == hSplitterBox)
  114. {
  115. SplitColumn(m_rectTracker.left);
  116. }
  117. else if (m_htTrack >= hSplitterBar1 && m_htTrack <= hSplitterBar15)
  118. {
  119. // set column width
  120. TrackColumnSize(m_rectTracker.left, m_htTrack - hSplitterBar1);
  121. RecalcLayout();
  122. }
  123. else if (m_htTrack >= splitterIntersection1 &&
  124. m_htTrack <= splitterIntersection225)
  125. {
  126. // set row height and column width
  127. int row = (m_htTrack - splitterIntersection1) / 15;
  128. int col = (m_htTrack - splitterIntersection1) % 15;
  129. TrackRowSize(m_rectTracker.top, row);
  130. TrackColumnSize(m_rectTracker2.left, col);
  131. RecalcLayout();
  132. }
  133. else if (m_htTrack == bothSplitterBox)
  134. {
  135. // rectTracker is vSplitter (splits rows)
  136. // rectTracker2 is hSplitter (splits cols)
  137. SplitRow(m_rectTracker.top);
  138. SplitColumn(m_rectTracker2.left);
  139. }
  140. }
  141. if ( (pOldActiveView == GetActivePane()) &&
  142.      (pOldActiveView != NULL)
  143.    )
  144. SetActivePane(-1, -1, pOldActiveView); // re-activate
  145. }
  146. BEGIN_MESSAGE_MAP(CDynSplitterWnd, CSplitterWnd)
  147. //{{AFX_MSG_MAP(CDynSplitterWnd)
  148. ON_WM_MOUSEMOVE()
  149. //}}AFX_MSG_MAP
  150. END_MESSAGE_MAP()
  151. /////////////////////////////////////////////////////////////////////////////
  152. // CDynSplitterWnd message handlers
  153. void CDynSplitterWnd::OnMouseMove(UINT nFlags, CPoint pt) 
  154. {
  155. if(!m_bDynSplit)
  156. {
  157. CSplitterWnd::OnMouseMove(nFlags, pt);
  158. return;
  159. }
  160. if (GetCapture() != this)
  161. StopTracking(FALSE);
  162. if (m_bTracking)
  163. {
  164. // move tracker to current cursor position
  165. pt.Offset(m_ptTrackOffset); // pt is the upper right of hit detect
  166. // limit the point to the valid split range
  167. if (pt.y < m_rectLimit.top)
  168. pt.y = m_rectLimit.top;
  169. else if (pt.y > m_rectLimit.bottom)
  170. pt.y = m_rectLimit.bottom;
  171. if (pt.x < m_rectLimit.left)
  172. pt.x = m_rectLimit.left;
  173. else if (pt.x > m_rectLimit.right)
  174. pt.x = m_rectLimit.right;
  175. if (m_htTrack == vSplitterBox ||
  176. m_htTrack >= vSplitterBar1 && m_htTrack <= vSplitterBar15)
  177. {
  178. if (m_rectTracker.top != pt.y)
  179. {
  180. OnInvertTracker(m_rectTracker);
  181. m_rectTracker.OffsetRect(0, pt.y - m_rectTracker.top);
  182. OnInvertTracker(m_rectTracker);
  183. }
  184. }
  185. else if (m_htTrack == hSplitterBox ||
  186. m_htTrack >= hSplitterBar1 && m_htTrack <= hSplitterBar15)
  187. {
  188. if (m_rectTracker.left != pt.x)
  189. {
  190. OnInvertTracker(m_rectTracker);
  191. m_rectTracker.OffsetRect(pt.x - m_rectTracker.left, 0);
  192. OnInvertTracker(m_rectTracker);
  193. }
  194. }
  195. else if (m_htTrack == bothSplitterBox ||
  196.    (m_htTrack >= splitterIntersection1 &&
  197. m_htTrack <= splitterIntersection225))
  198. {
  199. if (m_rectTracker.top != pt.y)
  200. {
  201. OnInvertTracker(m_rectTracker);
  202. m_rectTracker.OffsetRect(0, pt.y - m_rectTracker.top);
  203. OnInvertTracker(m_rectTracker);
  204. }
  205. if (m_rectTracker2.left != pt.x)
  206. {
  207. OnInvertTracker(m_rectTracker2);
  208. m_rectTracker2.OffsetRect(pt.x - m_rectTracker2.left, 0);
  209. OnInvertTracker(m_rectTracker2);
  210. }
  211. }
  212. OnLButtonUp(MK_LBUTTON,pt);
  213. OnLButtonDown(MK_LBUTTON,pt);
  214. if(m_OldPoint != pt)
  215. {
  216. RedrawWindow(NULL, NULL, RDW_ALLCHILDREN | RDW_UPDATENOW);
  217. m_OldPoint = pt;
  218. }
  219. }
  220. else
  221. {
  222. // simply hit-test and set appropriate cursor
  223. int ht = HitTest(pt);
  224. SetSplitCursor(ht);
  225. }
  226. }