22
22
import com .github .barteksc .pdfviewer .util .Util ;
23
23
import com .shockwave .pdfium .util .SizeF ;
24
24
25
+ import java .util .LinkedList ;
26
+ import java .util .List ;
27
+
25
28
import static com .github .barteksc .pdfviewer .util .Constants .Cache .CACHE_SIZE ;
26
29
import static com .github .barteksc .pdfviewer .util .Constants .PRELOAD_OFFSET ;
27
30
@@ -37,21 +40,55 @@ class PagesLoader {
37
40
private float partRenderHeight ;
38
41
private final RectF thumbnailRect = new RectF (0 , 0 , 1 , 1 );
39
42
private final int preloadOffset ;
40
- private final Holder firstHolder = new Holder ();
41
- private final Holder lastHolder = new Holder ();
42
- private final GridSize firstGrid = new GridSize ();
43
- private final GridSize lastGrid = new GridSize ();
44
- private final GridSize middleGrid = new GridSize ();
45
43
46
44
private class Holder {
47
- int page ;
48
45
int row ;
49
46
int col ;
47
+
48
+ @ Override
49
+ public String toString () {
50
+ return "Holder{" +
51
+ "row=" + row +
52
+ ", col=" + col +
53
+ '}' ;
54
+ }
55
+ }
56
+
57
+ private class RenderRange {
58
+ int page ;
59
+ GridSize gridSize ;
60
+ Holder leftTop ;
61
+ Holder rightBottom ;
62
+
63
+ RenderRange () {
64
+ this .page = 0 ;
65
+ this .gridSize = new GridSize ();
66
+ this .leftTop = new Holder ();
67
+ this .rightBottom = new Holder ();
68
+ }
69
+
70
+ @ Override
71
+ public String toString () {
72
+ return "RenderRange{" +
73
+ "page=" + page +
74
+ ", gridSize=" + gridSize +
75
+ ", leftTop=" + leftTop +
76
+ ", rightBottom=" + rightBottom +
77
+ '}' ;
78
+ }
50
79
}
51
80
52
81
private class GridSize {
53
82
int rows ;
54
83
int cols ;
84
+
85
+ @ Override
86
+ public String toString () {
87
+ return "GridSize{" +
88
+ "rows=" + rows +
89
+ ", cols=" + cols +
90
+ '}' ;
91
+ }
55
92
}
56
93
57
94
PagesLoader (PDFView pdfView ) {
@@ -69,124 +106,144 @@ private void getPageColsRows(GridSize grid, int pageIndex) {
69
106
grid .cols = MathUtils .ceil (1f / partWidth );
70
107
}
71
108
72
- private Holder getPageAndCoordsByOffset (Holder holder , GridSize grid , float localXOffset ,
73
- float localYOffset , boolean endOffset ) {
74
- float fixedXOffset = -MathUtils .max (localXOffset , 0 );
75
- float fixedYOffset = -MathUtils .max (localYOffset , 0 );
76
- float offset = pdfView .isSwipeVertical () ? fixedYOffset : fixedXOffset ;
77
- holder .page = pdfView .pdfFile .getPageAtOffset (offset , pdfView .getZoom ());
78
- getPageColsRows (grid , holder .page );
79
- SizeF scaledPageSize = pdfView .pdfFile .getScaledPageSize (holder .page , pdfView .getZoom ());
80
- float rowHeight = scaledPageSize .getHeight () / grid .rows ;
81
- float colWidth = scaledPageSize .getWidth () / grid .cols ;
82
- float row , col ;
83
- float secondaryOffset = pdfView .pdfFile .getSecondaryPageOffset (holder .page , pdfView .getZoom ());
84
- if (pdfView .isSwipeVertical ()) {
85
- row = Math .abs (fixedYOffset - pdfView .pdfFile .getPageOffset (holder .page , pdfView .getZoom ())) / rowHeight ;
86
- col = MathUtils .min (fixedXOffset - secondaryOffset , 0 ) / colWidth ;
87
- } else {
88
- col = Math .abs (fixedXOffset - pdfView .pdfFile .getPageOffset (holder .page , pdfView .getZoom ())) / colWidth ;
89
- row = MathUtils .min (fixedYOffset - secondaryOffset , 0 ) / rowHeight ;
90
- }
91
-
92
- if (endOffset ) {
93
- holder .row = MathUtils .ceil (row );
94
- holder .col = MathUtils .ceil (col );
95
- } else {
96
- holder .row = MathUtils .floor (row );
97
- holder .col = MathUtils .floor (col );
98
- }
99
- return holder ;
100
- }
101
-
102
109
private void calculatePartSize (GridSize grid ) {
103
110
pageRelativePartWidth = 1f / (float ) grid .cols ;
104
111
pageRelativePartHeight = 1f / (float ) grid .rows ;
105
112
partRenderWidth = Constants .PART_SIZE / pageRelativePartWidth ;
106
113
partRenderHeight = Constants .PART_SIZE / pageRelativePartHeight ;
107
114
}
108
115
109
- private void loadVisible () {
110
- int parts = 0 ;
111
- float scaledPreloadOffset = preloadOffset * pdfView .getZoom ();
112
- float firstXOffset = -xOffset + scaledPreloadOffset ;
113
- float lastXOffset = -xOffset - pdfView .getWidth () - scaledPreloadOffset ;
114
- float firstYOffset = -yOffset + scaledPreloadOffset ;
115
- float lastYOffset = -yOffset - pdfView .getHeight () - scaledPreloadOffset ;
116
116
117
- getPageAndCoordsByOffset (firstHolder , firstGrid , firstXOffset , firstYOffset , false );
118
- getPageAndCoordsByOffset (lastHolder , lastGrid , lastXOffset , lastYOffset , true );
117
+ /**
118
+ * calculate the render range of each page
119
+ */
120
+ private List <RenderRange > getRenderRangeList (float firstXOffset , float firstYOffset , float lastXOffset , float lastYOffset ) {
121
+
122
+ float fixedFirstXOffset = -MathUtils .max (firstXOffset , 0 );
123
+ float fixedFirstYOffset = -MathUtils .max (firstYOffset , 0 );
124
+
125
+ float fixedLastXOffset = -MathUtils .max (lastXOffset , 0 );
126
+ float fixedLastYOffset = -MathUtils .max (lastYOffset , 0 );
127
+
128
+ float offsetFirst = pdfView .isSwipeVertical () ? fixedFirstYOffset : fixedFirstXOffset ;
129
+ float offsetLast = pdfView .isSwipeVertical () ? fixedLastYOffset : fixedLastXOffset ;
130
+
131
+ int firstPage = pdfView .pdfFile .getPageAtOffset (offsetFirst , pdfView .getZoom ());
132
+ int lastPage = pdfView .pdfFile .getPageAtOffset (offsetLast , pdfView .getZoom ());
133
+ int pageCount = lastPage - firstPage + 1 ;
134
+
135
+ List <RenderRange > renderRanges = new LinkedList <>();
136
+
137
+ for (int page = firstPage ; page <= lastPage ; page ++) {
138
+ RenderRange range = new RenderRange ();
139
+ range .page = page ;
140
+
141
+ float pageFirstXOffset , pageFirstYOffset , pageLastXOffset , pageLastYOffset ;
142
+ if (page == firstPage ) {
143
+ pageFirstXOffset = fixedFirstXOffset ;
144
+ pageFirstYOffset = fixedFirstYOffset ;
145
+ if (pageCount == 1 ) {
146
+ pageLastXOffset = fixedLastXOffset ;
147
+ pageLastYOffset = fixedLastYOffset ;
148
+ } else {
149
+ float pageOffset = pdfView .pdfFile .getPageOffset (page , pdfView .getZoom ());
150
+ SizeF pageSize = pdfView .pdfFile .getScaledPageSize (page , pdfView .getZoom ());
151
+ if (pdfView .isSwipeVertical ()) {
152
+ pageLastXOffset = fixedLastXOffset ;
153
+ pageLastYOffset = pageOffset + pageSize .getHeight ();
154
+ } else {
155
+ pageLastYOffset = fixedLastYOffset ;
156
+ pageLastXOffset = pageOffset + pageSize .getWidth ();
157
+ }
158
+ }
159
+ } else if (page == lastPage ) {
160
+ float pageOffset = pdfView .pdfFile .getPageOffset (page , pdfView .getZoom ());
161
+
162
+ if (pdfView .isSwipeVertical ()) {
163
+ pageFirstXOffset = fixedFirstXOffset ;
164
+ pageFirstYOffset = pageOffset ;
165
+ } else {
166
+ pageFirstYOffset = fixedFirstYOffset ;
167
+ pageFirstXOffset = pageOffset ;
168
+ }
119
169
120
- for (int i = firstHolder .page ; i <= lastHolder .page ; i ++) {
121
- loadThumbnail (i );
122
- }
170
+ pageLastXOffset = fixedLastXOffset ;
171
+ pageLastYOffset = fixedLastYOffset ;
123
172
124
- int pagesCount = lastHolder .page - firstHolder .page + 1 ;
125
- for (int page = firstHolder .page ; page <= lastHolder .page && parts < CACHE_SIZE ; page ++) {
173
+ } else {
174
+ float pageOffset = pdfView .pdfFile .getPageOffset (page , pdfView .getZoom ());
175
+ SizeF pageSize = pdfView .pdfFile .getScaledPageSize (page , pdfView .getZoom ());
176
+ if (pdfView .isSwipeVertical ()) {
177
+ pageFirstXOffset = fixedFirstXOffset ;
178
+ pageFirstYOffset = pageOffset ;
179
+
180
+ pageLastXOffset = fixedLastXOffset ;
181
+ pageLastYOffset = pageOffset + pageSize .getHeight ();
182
+ } else {
183
+ pageFirstXOffset = pageOffset ;
184
+ pageFirstYOffset = fixedFirstYOffset ;
185
+
186
+ pageLastXOffset = pageOffset + pageSize .getWidth ();
187
+ pageLastYOffset = fixedLastYOffset ;
188
+ }
189
+ }
190
+
191
+ getPageColsRows (range .gridSize , range .page ); // get the page's grid size that rows and cols
192
+ SizeF scaledPageSize = pdfView .pdfFile .getScaledPageSize (range .page , pdfView .getZoom ());
193
+ float rowHeight = scaledPageSize .getHeight () / range .gridSize .rows ;
194
+ float colWidth = scaledPageSize .getWidth () / range .gridSize .cols ;
195
+
196
+
197
+ // get the page offset int the whole file
198
+ // ---------------------------------------
199
+ // | | | |
200
+ // |<--offset-->| (page) |<--offset-->|
201
+ // | | | |
202
+ // | | | |
203
+ // ---------------------------------------
204
+ float secondaryOffset = pdfView .pdfFile .getSecondaryPageOffset (page , pdfView .getZoom ());
205
+
206
+ // calculate the row,col of the point in the leftTop and rightBottom
207
+ if (pdfView .isSwipeVertical ()) {
208
+ range .leftTop .row = MathUtils .floor (Math .abs (pageFirstYOffset - pdfView .pdfFile .getPageOffset (range .page , pdfView .getZoom ())) / rowHeight );
209
+ range .leftTop .col = MathUtils .floor (MathUtils .min (pageFirstXOffset - secondaryOffset , 0 ) / colWidth );
126
210
127
- if (page == firstHolder .page && pagesCount > 1 ) {
128
- parts += loadPageEnd (firstHolder , firstGrid , CACHE_SIZE - parts );
129
- } else if (page == lastHolder .page && pagesCount > 1 ) {
130
- parts += loadPageStart (lastHolder , lastGrid , CACHE_SIZE - parts );
131
- } else if (pagesCount == 1 ) {
132
- parts += loadPageCenter (firstHolder , lastHolder , firstGrid , CACHE_SIZE - parts );
211
+ range .rightBottom .row = MathUtils .ceil (Math .abs (pageLastYOffset - pdfView .pdfFile .getPageOffset (range .page , pdfView .getZoom ())) / rowHeight );
212
+ range .rightBottom .col = MathUtils .floor (MathUtils .min (pageLastXOffset - secondaryOffset , 0 ) / colWidth );
133
213
} else {
134
- getPageColsRows (middleGrid , page );
135
- parts += loadWholePage (page , middleGrid , CACHE_SIZE - parts );
214
+ range .leftTop .col = MathUtils .floor (Math .abs (pageFirstXOffset - pdfView .pdfFile .getPageOffset (range .page , pdfView .getZoom ())) / colWidth );
215
+ range .leftTop .row = MathUtils .floor (MathUtils .min (pageFirstYOffset - secondaryOffset , 0 ) / rowHeight );
216
+
217
+ range .rightBottom .col = MathUtils .floor (Math .abs (pageLastXOffset - pdfView .pdfFile .getPageOffset (range .page , pdfView .getZoom ())) / colWidth );
218
+ range .rightBottom .row = MathUtils .floor (MathUtils .min (pageLastYOffset - secondaryOffset , 0 ) / rowHeight );
136
219
}
220
+
221
+ renderRanges .add (range );
137
222
}
138
223
224
+ return renderRanges ;
139
225
}
140
226
141
- /**
142
- * When whole page is visible
143
- *
144
- * @return loaded parts count
145
- */
146
- private int loadWholePage (int page , GridSize grid , int nbOfPartsLoadable ) {
147
- calculatePartSize (grid );
148
- return loadPage (page , 0 , grid .rows - 1 , 0 , grid .cols - 1 , nbOfPartsLoadable );
149
- }
227
+ private void loadVisible () {
228
+ int parts = 0 ;
229
+ float scaledPreloadOffset = preloadOffset ;
230
+ float firstXOffset = -xOffset + scaledPreloadOffset ;
231
+ float lastXOffset = -xOffset - pdfView .getWidth () - scaledPreloadOffset ;
232
+ float firstYOffset = -yOffset + scaledPreloadOffset ;
233
+ float lastYOffset = -yOffset - pdfView .getHeight () - scaledPreloadOffset ;
150
234
151
- /**
152
- * When only part of one page is visible
153
- *
154
- * @return loaded parts count
155
- */
156
- private int loadPageCenter (Holder firstHolder , Holder lastHolder , GridSize grid , int nbOfPartsLoadable ) {
157
- calculatePartSize (grid );
158
- return loadPage (firstHolder .page , firstHolder .row , lastHolder .row , firstHolder .col , lastHolder .col , nbOfPartsLoadable );
159
- }
235
+ List <RenderRange > rangeList = getRenderRangeList (firstXOffset , firstYOffset , lastXOffset , lastYOffset );
160
236
161
- /**
162
- * When only end of page is visible
163
- *
164
- * @return loaded parts count
165
- */
166
- private int loadPageEnd (Holder holder , GridSize grid , int nbOfPartsLoadable ) {
167
- calculatePartSize (grid );
168
- if (pdfView .isSwipeVertical ()) {
169
- int firstRow = holder .row ;
170
- return loadPage (holder .page , firstRow , grid .rows - 1 , 0 , grid .cols - 1 , nbOfPartsLoadable );
171
- } else {
172
- int firstCol = holder .col ;
173
- return loadPage (holder .page , 0 , grid .rows - 1 , firstCol , grid .cols - 1 , nbOfPartsLoadable );
237
+ for (RenderRange range : rangeList ) {
238
+ loadThumbnail (range .page );
174
239
}
175
- }
176
240
177
- /**
178
- * If only start of the page is visible
179
- *
180
- * @return loaded parts count
181
- */
182
- private int loadPageStart (Holder holder , GridSize grid , int nbOfPartsLoadable ) {
183
- calculatePartSize (grid );
184
- if (pdfView .isSwipeVertical ()) {
185
- int lastRow = holder .row ;
186
- return loadPage (holder .page , 0 , lastRow , 0 , grid .cols - 1 , nbOfPartsLoadable );
187
- } else {
188
- int lastCol = holder .col ;
189
- return loadPage (holder .page , 0 , grid .rows - 1 , 0 , lastCol , nbOfPartsLoadable );
241
+ for (RenderRange range : rangeList ) {
242
+ calculatePartSize (range .gridSize );
243
+ parts += loadPage (range .page , range .leftTop .row , range .rightBottom .row , range .leftTop .col , range .rightBottom .col , CACHE_SIZE - parts );
244
+ if (parts >= CACHE_SIZE ) {
245
+ break ;
246
+ }
190
247
}
191
248
192
249
}
0 commit comments