xref: /trunk/main/sc/source/ui/view/gridmerg.cxx (revision b3f79822)
1 /**************************************************************
2  *
3  * Licensed to the Apache Software Foundation (ASF) under one
4  * or more contributor license agreements.  See the NOTICE file
5  * distributed with this work for additional information
6  * regarding copyright ownership.  The ASF licenses this file
7  * to you under the Apache License, Version 2.0 (the
8  * "License"); you may not use this file except in compliance
9  * with the License.  You may obtain a copy of the License at
10  *
11  *   http://www.apache.org/licenses/LICENSE-2.0
12  *
13  * Unless required by applicable law or agreed to in writing,
14  * software distributed under the License is distributed on an
15  * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
16  * KIND, either express or implied.  See the License for the
17  * specific language governing permissions and limitations
18  * under the License.
19  *
20  *************************************************************/
21 
22 
23 
24 // MARKER(update_precomp.py): autogen include statement, do not remove
25 #include "precompiled_sc.hxx"
26 
27 
28 
29 #include <vcl/outdev.hxx>
30 
31 #include "gridmerg.hxx"
32 
33 //------------------------------------------------------------------
34 
ScGridMerger(OutputDevice * pOutDev,long nOnePixelX,long nOnePixelY)35 ScGridMerger::ScGridMerger( OutputDevice* pOutDev, long nOnePixelX, long nOnePixelY ) :
36 	pDev( pOutDev ),
37 	nOneX( nOnePixelX ),
38 	nOneY( nOnePixelY ),
39 	nCount( 0 ),
40 	bVertical( sal_False )
41 {
42 	//	optimize (DrawGrid) only for pixel MapMode,
43 	//	to avoid rounding errors
44 
45 	bOptimize = ( pDev->GetMapMode().GetMapUnit() == MAP_PIXEL );
46 }
47 
~ScGridMerger()48 ScGridMerger::~ScGridMerger()
49 {
50 	Flush();
51 }
52 
AddLine(long nStart,long nEnd,long nPos)53 void ScGridMerger::AddLine( long nStart, long nEnd, long nPos )
54 {
55 	if ( nCount )
56 	{
57 		//	not first line - test fix position
58 		//	more than one previous line - test distance
59 
60 		if ( nStart != nFixStart || nEnd != nFixEnd )
61 		{
62 			if ( nCount == 1 && nPos == nVarStart &&
63 					( nStart == nFixEnd ||
64 						nStart == nFixEnd + ( bVertical ? nOneY : nOneX ) ) )
65 			{
66 				//	additional optimization: extend connected lines
67 				//	keep nCount at 1
68 				nFixEnd = nEnd;
69 			}
70 			else
71 				Flush();
72 		}
73 		else if ( nCount == 1 )
74 		{
75 			nVarDiff = nPos - nVarStart;
76 			++nCount;
77 		}
78 		else if ( nPos != nVarStart + nCount * nVarDiff )		//! keep VarEnd?
79 			Flush();
80 		else
81 			++nCount;
82 	}
83 
84 	if ( !nCount )
85 	{
86 		//	first line (or flushed above) - just store
87 
88 		nFixStart = nStart;
89 		nFixEnd   = nEnd;
90 		nVarStart = nPos;
91 		nVarDiff  = 0;
92 		nCount    = 1;
93 	}
94 }
95 
AddHorLine(long nX1,long nX2,long nY)96 void ScGridMerger::AddHorLine( long nX1, long nX2, long nY )
97 {
98 	if ( bOptimize )
99 	{
100 		if ( bVertical )
101 		{
102 			Flush();
103 			bVertical = sal_False;
104 		}
105 		AddLine( nX1, nX2, nY );
106 	}
107 	else
108 		pDev->DrawLine( Point( nX1, nY ), Point( nX2, nY ) );
109 }
110 
AddVerLine(long nX,long nY1,long nY2)111 void ScGridMerger::AddVerLine( long nX, long nY1, long nY2 )
112 {
113 	if ( bOptimize )
114 	{
115 		if ( !bVertical )
116 		{
117 			Flush();
118 			bVertical = sal_True;
119 		}
120 		AddLine( nY1, nY2, nX );
121 	}
122 	else
123 		pDev->DrawLine( Point( nX, nY1 ), Point( nX, nY2 ) );
124 }
125 
Flush()126 void ScGridMerger::Flush()
127 {
128 	if (nCount)
129 	{
130 		if (bVertical)
131 		{
132 			if ( nCount == 1 )
133 				pDev->DrawLine( Point( nVarStart, nFixStart ), Point( nVarStart, nFixEnd ) );
134 			else
135 			{
136 				long nVarEnd = nVarStart + ( nCount - 1 ) * nVarDiff;
137 				if ( nVarDiff < 0 )
138 				{
139 					//	nVarDiff is negative in RTL layout mode
140 					//	Change the positions so DrawGrid is called with a positive distance
141 					//	(nVarStart / nVarDiff can be modified, aren't used after Flush)
142 
143 					nVarDiff = -nVarDiff;
144 					long nTemp = nVarStart;
145 					nVarStart = nVarEnd;
146 					nVarEnd = nTemp;
147 				}
148 				pDev->DrawGrid( Rectangle( nVarStart, nFixStart, nVarEnd, nFixEnd ),
149 								Size( nVarDiff, nFixEnd - nFixStart ),
150 								GRID_VERTLINES );
151 			}
152 		}
153 		else
154 		{
155 			if ( nCount == 1 )
156 				pDev->DrawLine( Point( nFixStart, nVarStart ), Point( nFixEnd, nVarStart ) );
157 			else
158 			{
159 				long nVarEnd = nVarStart + ( nCount - 1 ) * nVarDiff;
160 				pDev->DrawGrid( Rectangle( nFixStart, nVarStart, nFixEnd, nVarEnd ),
161 								Size( nFixEnd - nFixStart, nVarDiff ),
162 								GRID_HORZLINES );
163 			}
164 		}
165 		nCount = 0;
166 	}
167 }
168 
169 
170 
171