Rev 433 | Rev 445 | Go to most recent revision | Details | Compare with Previous | Last modification | View Log | RSS feed
Rev | Author | Line No. | Line |
---|---|---|---|
259 | daniel-mar | 1 | /* |
2 | This file is part of Filter Foundry, a filter plugin for Adobe Photoshop |
||
3 | Copyright (C) 2003-2009 Toby Thain, toby@telegraphics.com.au |
||
4 | Copyright (C) 2018-2021 Daniel Marschall, ViaThinkSoft |
||
5 | |||
6 | This program is free software; you can redistribute it and/or modify |
||
7 | it under the terms of the GNU General Public License as published by |
||
8 | the Free Software Foundation; either version 2 of the License, or |
||
9 | (at your option) any later version. |
||
10 | |||
11 | This program is distributed in the hope that it will be useful, |
||
12 | but WITHOUT ANY WARRANTY; without even the implied warranty of |
||
13 | MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the |
||
14 | GNU General Public License for more details. |
||
15 | |||
16 | You should have received a copy of the GNU General Public License |
||
17 | along with this program; if not, write to the Free Software |
||
18 | Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA |
||
19 | */ |
||
20 | |||
21 | /* This is PLATFORM INDEPENDENT user interface code - mainly dialog logic */ |
||
22 | |||
23 | #include "ff.h" |
||
24 | #include "preview.h" |
||
25 | |||
26 | #ifdef MAC_ENV |
||
27 | #include <fp.h> |
||
28 | #endif |
||
29 | #include <math.h> |
||
30 | |||
31 | #include "PIProperties.h" |
||
32 | |||
33 | extern FilterRecordPtr gpb; |
||
34 | |||
35 | PSPixelMap preview_pmap; |
||
36 | PSPixelMask preview_pmask; |
||
37 | Handle preview_handle; |
||
38 | UIRECT preview_rect; |
||
39 | int preview_w,preview_h,previewerr = false,needall = false,needinput = true; |
||
40 | Point preview_scroll; |
||
41 | Boolean preview_complete = false; |
||
42 | double zoomfactor,fitzoom; |
||
43 | |||
44 | Boolean setup_preview(FilterRecordPtr pb, int nplanes){ |
||
45 | double zh,zv; |
||
46 | |||
47 | if(pb->displayPixels && pb->advanceState){ |
||
48 | // Possibility 1: Only the part of the preview rect is filled with background color, |
||
49 | // which can be occupied by image data if zoom factor becomes 100% |
||
50 | /* |
||
51 | if (HAS_BIG_DOC(pb)) { |
||
52 | preview_w = MIN(preview_rect.right - preview_rect.left, |
||
53 | BIGDOC_FILTER_RECT(pb).right - BIGDOC_FILTER_RECT(pb).left); |
||
54 | preview_h = MIN(preview_rect.bottom - preview_rect.top, |
||
55 | BIGDOC_FILTER_RECT(pb).bottom - BIGDOC_FILTER_RECT(pb).top); |
||
56 | } else { |
||
57 | preview_w = MIN(preview_rect.right - preview_rect.left, |
||
58 | FILTER_RECT(pb).right - FILTER_RECT(pb).left); |
||
59 | preview_h = MIN(preview_rect.bottom - preview_rect.top, |
||
60 | FILTER_RECT(pb).bottom - FILTER_RECT(pb).top); |
||
61 | } |
||
62 | */ |
||
63 | // Possibility 2: The whole preview rect is always filled with the background color, |
||
64 | // so you can easily see what is the preview area and what is not |
||
65 | preview_w = preview_rect.right - preview_rect.left; |
||
66 | preview_h = preview_rect.bottom - preview_rect.top; |
||
67 | |||
68 | if (HAS_BIG_DOC(pb)) { |
||
69 | zh = ((double)BIGDOC_FILTER_RECT(pb).right - (double)BIGDOC_FILTER_RECT(pb).left) / (double)preview_w; |
||
70 | zv = ((double)BIGDOC_FILTER_RECT(pb).bottom - (double)BIGDOC_FILTER_RECT(pb).top) / (double)preview_h; |
||
71 | } else { |
||
72 | zh = ((double)FILTER_RECT(pb).right - (double)FILTER_RECT(pb).left) / (double)preview_w; |
||
73 | zv = ((double)FILTER_RECT(pb).bottom - (double)FILTER_RECT(pb).top) / (double)preview_h; |
||
74 | } |
||
75 | fitzoom = zh > zv ? zh : zv; |
||
76 | |||
77 | preview_pmap.version = 1; |
||
78 | preview_pmap.bounds.left = preview_pmap.bounds.top = 0; |
||
79 | preview_pmap.bounds.right = preview_w; |
||
80 | preview_pmap.bounds.bottom = preview_h; |
||
81 | preview_pmap.imageMode = pb->imageMode; |
||
82 | preview_pmap.rowBytes = nplanes*preview_w; |
||
83 | preview_pmap.colBytes = nplanes; |
||
84 | preview_pmap.planeBytes = 1; /*interleaved*/ |
||
85 | // preview_pmap.baseAddr = preview_data; |
||
86 | /* baseAddr must be set before using pixelmap */ |
||
87 | |||
88 | //--------------------------------------------------------------------------- |
||
89 | // Fields new in version 1: |
||
90 | //--------------------------------------------------------------------------- |
||
91 | preview_pmap.mat = NULL; |
||
92 | |||
93 | if( (pb->imageMode == plugInModeRGBColor && nplanes == 4) |
||
94 | || (pb->imageMode == plugInModeLabColor && nplanes == 4) |
||
95 | || (pb->imageMode == plugInModeGrayScale && nplanes == 2) |
||
96 | || (pb->imageMode == plugInModeDuotone && nplanes == 2) ) |
||
97 | { |
||
98 | preview_pmask.next = NULL; |
||
99 | // preview_pmask.maskData = preview_data+3; |
||
100 | preview_pmask.rowBytes = preview_pmap.rowBytes; |
||
101 | preview_pmask.colBytes = nplanes; |
||
102 | preview_pmask.maskDescription = kSimplePSMask; |
||
103 | preview_pmap.masks = &preview_pmask; |
||
104 | }else |
||
105 | preview_pmap.masks = NULL; |
||
106 | |||
107 | preview_handle = PINEWHANDLE((long)preview_h * preview_pmap.rowBytes); |
||
108 | }else |
||
109 | preview_handle = NULL; |
||
110 | return preview_handle != NULL; |
||
111 | |||
112 | //--------------------------------------------------------------------------- |
||
113 | // Fields new in version 2: |
||
114 | //--------------------------------------------------------------------------- |
||
115 | // preview_pmap.pixelOverlays; |
||
116 | // preview_pmap.colorManagementOptions; |
||
117 | } |
||
118 | |||
119 | void dispose_preview(){ |
||
120 | if(preview_handle){ |
||
121 | PIDISPOSEHANDLE(preview_handle); |
||
122 | preview_handle = NULL; |
||
123 | } |
||
124 | } |
||
125 | |||
126 | void* memset_bgcolor(void* ptr, size_t num) { |
||
127 | int i; |
||
128 | unsigned char* p; |
||
129 | |||
130 | i = 0; |
||
131 | p = (unsigned char*)ptr; |
||
132 | for (i=0; i<(int)num; ++i) { |
||
268 | daniel-mar | 133 | #ifdef WIN_ENV |
259 | daniel-mar | 134 | DWORD color; |
135 | |||
136 | color = GetSysColor(COLOR_APPWORKSPACE); |
||
137 | |||
138 | if (gpb->imageMode == plugInModeRGBColor) { |
||
139 | if (i%nplanes == 0) p[i] = GetRValue(color); |
||
140 | if (i%nplanes == 1) p[i] = GetGValue(color); |
||
141 | if (i%nplanes == 2) p[i] = GetBValue(color); |
||
142 | if (i%nplanes == 3) p[i] = 255; // alpha channel |
||
143 | } else if (gpb->imageMode == plugInModeGrayScale) { |
||
144 | uint8_t r, g, b; |
||
145 | |||
146 | r = GetRValue(color); |
||
147 | g = GetGValue(color); |
||
148 | b = GetBValue(color); |
||
149 | |||
150 | if (i%nplanes == 0) p[i] = (uint8_t)(((299L*r)+(587L*g)+(114L*b))/1000); |
||
151 | if (i%nplanes == 1) p[i] = 255; // alpha channel |
||
152 | } else if (gpb->imageMode == plugInModeCMYKColor) { |
||
153 | uint8_t r, g, b; |
||
154 | double dmax, dr, dg, db, k, c, m, y; |
||
155 | |||
156 | r = GetRValue(color); |
||
157 | g = GetGValue(color); |
||
158 | b = GetBValue(color); |
||
159 | |||
160 | dr = (double)r / 255; |
||
161 | dg = (double)g / 255; |
||
162 | db = (double)b / 255; |
||
163 | |||
164 | dmax = dr; |
||
165 | if (dg>dmax) dmax = dg; |
||
166 | if (db>dmax) dmax = db; |
||
167 | |||
168 | k = 1 - dmax; |
||
169 | c = (1 - dr - k) / (1 - k); |
||
170 | m = (1 - dg - k) / (1 - k); |
||
171 | y = (1 - db - k) / (1 - k); |
||
172 | |||
173 | if (i%nplanes == 0) p[i] = (uint8_t)(255 - c * 255); |
||
174 | if (i%nplanes == 1) p[i] = (uint8_t)(255 - m * 255); |
||
175 | if (i%nplanes == 2) p[i] = (uint8_t)(255 - y * 255); |
||
176 | if (i%nplanes == 3) p[i] = (uint8_t)(255 - k * 255); |
||
177 | } else { |
||
178 | // FIXME: If we are in such a non supported color mode, then |
||
179 | // these color codes would be all wrong! |
||
180 | // Just to be safe use (what is probably) white |
||
181 | p[i] = 0xFF; |
||
182 | |||
183 | /* |
||
184 | #define plugInModeBitmap 0 |
||
185 | #define plugInModeGrayScale 1 supported |
||
186 | #define plugInModeIndexedColor 2 |
||
187 | #define plugInModeRGBColor 3 supported |
||
188 | #define plugInModeCMYKColor 4 supported |
||
189 | #define plugInModeHSLColor 5 |
||
190 | #define plugInModeHSBColor 6 |
||
191 | #define plugInModeMultichannel 7 |
||
192 | #define plugInModeDuotone 8 |
||
193 | #define plugInModeLabColor 9 |
||
194 | #define plugInModeGray16 10 |
||
195 | #define plugInModeRGB48 11 |
||
196 | #define plugInModeLab48 12 |
||
197 | #define plugInModeCMYK64 13 |
||
198 | #define plugInModeDeepMultichannel 14 |
||
199 | #define plugInModeDuotone16 15 |
||
200 | #define plugInModeRGB96 16 |
||
201 | #define plugInModeGray32 17 |
||
202 | */ |
||
203 | |||
204 | } |
||
268 | daniel-mar | 205 | #else |
259 | daniel-mar | 206 | // This is the behavior of FilterFoundry <1.7 was this (filled with 0xFF) |
207 | // FIXME: Should we do something fancy here, too? |
||
208 | p[i] = 0xFF; |
||
268 | daniel-mar | 209 | #endif |
259 | daniel-mar | 210 | } |
211 | return ptr; |
||
212 | } |
||
213 | |||
214 | void recalc_preview_olddoc(FilterRecordPtr pb, DIALOGREF dp) { |
||
215 | OSErr e; |
||
216 | double scaledw, scaledh; |
||
217 | int j, n, imgw, imgh; |
||
218 | Rect r, outRect; |
||
219 | Ptr outrow; |
||
220 | |||
221 | preview_complete = false; |
||
222 | |||
223 | if (preview_handle) { |
||
224 | /* size of previewed area, of source image; but no larger than filtered area (selection) */ |
||
225 | scaledw = zoomfactor * preview_w; |
||
226 | if (scaledw > ((double)FILTER_RECT(pb).right - (double)FILTER_RECT(pb).left)) |
||
227 | scaledw = (double)FILTER_RECT(pb).right - (double)FILTER_RECT(pb).left; |
||
228 | scaledh = zoomfactor * preview_h; |
||
229 | if (scaledh > ((double)FILTER_RECT(pb).bottom - (double)FILTER_RECT(pb).top)) |
||
230 | scaledh = (double)FILTER_RECT(pb).bottom - (double)FILTER_RECT(pb).top; |
||
231 | |||
232 | /* scale clipped preview area down again - this becomes the pixel size of preview */ |
||
233 | imgw = (int)ceil(scaledw / zoomfactor); |
||
234 | if (imgw > preview_w) |
||
235 | imgw = preview_w; |
||
236 | imgh = (int)ceil(scaledh / zoomfactor); |
||
237 | if (imgh > preview_h) |
||
238 | imgh = preview_h; |
||
239 | |||
240 | /* compute source data rectangle (inRect) */ |
||
241 | |||
242 | /* centre preview on filtered part of input image, adding scroll offset */ |
||
243 | r.left = (int16)(((double)FILTER_RECT(pb).left + (double)FILTER_RECT(pb).right - scaledw) / 2 + preview_scroll.h); |
||
244 | /* make sure it does not go outside the input area */ |
||
245 | if (r.left < FILTER_RECT(pb).left) { |
||
246 | preview_scroll.h += FILTER_RECT(pb).left - r.left; |
||
247 | r.left = FILTER_RECT(pb).left; |
||
248 | } |
||
249 | else if ((double)r.left + scaledw > FILTER_RECT(pb).right) { |
||
250 | preview_scroll.h += (int16)((double)FILTER_RECT(pb).right - ((double)r.left + scaledw)); |
||
251 | r.left = (int16)((double)FILTER_RECT(pb).right - scaledw); |
||
252 | } |
||
253 | r.right = (int16)((double)r.left + scaledw); |
||
254 | preview_pmap.maskPhaseCol = (int32)((preview_scroll.h) / zoomfactor); // phase of the checkerboard |
||
255 | |||
256 | /* now compute for vertical */ |
||
257 | r.top = (int16)(((double)FILTER_RECT(pb).top + (double)FILTER_RECT(pb).bottom - scaledh) / 2 + preview_scroll.v); |
||
258 | if (r.top < FILTER_RECT(pb).top) { |
||
259 | preview_scroll.v += FILTER_RECT(pb).top - r.top; |
||
260 | r.top = FILTER_RECT(pb).top; |
||
261 | } |
||
262 | else if ((double)r.top + scaledh > FILTER_RECT(pb).bottom) { |
||
263 | preview_scroll.v += (int16)(FILTER_RECT(pb).bottom - ((double)r.top + scaledh)); |
||
264 | r.top = (int16)((double)FILTER_RECT(pb).bottom - scaledh); |
||
265 | } |
||
266 | r.bottom = (int16)((double)r.top + scaledh); |
||
267 | preview_pmap.maskPhaseRow = (int32)((preview_scroll.v) / zoomfactor); // phase of the checkerboard |
||
268 | |||
269 | /* if formulae need random access to image - src(), rad() - we must request entire area: */ |
||
270 | if (needall) |
||
271 | SETRECT(IN_RECT(pb), 0, 0, IMAGE_SIZE(pb).h, IMAGE_SIZE(pb).v); |
||
272 | else |
||
273 | IN_RECT(pb) = r; |
||
274 | |||
275 | OUT_RECT(pb) = IN_RECT(pb); |
||
276 | SETRECT(MASK_RECT(pb), 0, 0, 0, 0); |
||
277 | pb->inLoPlane = pb->outLoPlane = 0; |
||
278 | pb->inHiPlane = pb->outHiPlane = nplanes - 1; |
||
279 | |||
280 | if (!needinput || !(e = pb->advanceState())) { |
||
281 | Ptr outptr = PILOCKHANDLE(preview_handle, false); |
||
282 | int blankrows = (preview_h - imgh) / 2, |
||
312 | daniel-mar | 283 | blankcols = (preview_w - imgw) / 2, |
284 | pmrb = preview_pmap.rowBytes; |
||
259 | daniel-mar | 285 | |
286 | evalinit(); |
||
287 | |||
288 | SETRECT(outRect, 0, 0, imgw, imgh); |
||
289 | |||
290 | e = process_scaled_olddoc(pb, false, r, outRect, |
||
291 | outptr + pmrb * blankrows + nplanes * blankcols, pmrb, zoomfactor); |
||
292 | if (blankrows) { |
||
293 | // blank rows on top of preview: |
||
294 | memset_bgcolor(outptr, pmrb * blankrows); |
||
295 | // blank rows below preview: |
||
296 | n = preview_h - blankrows - imgh; |
||
297 | memset_bgcolor(outptr + pmrb * (blankrows + imgh), pmrb * n); |
||
298 | } |
||
299 | if (blankcols) { |
||
300 | n = preview_w - blankcols - imgw; |
||
301 | outrow = outptr + pmrb * blankrows; |
||
302 | for (j = blankrows; j < preview_h - blankrows; ++j) { |
||
303 | // blank columns on left side of preview (if picture is smaller than the preview area): |
||
304 | memset_bgcolor(outrow, nplanes * blankcols); |
||
305 | // blank columns on right side of preview (if picture is smaller than the preview area): |
||
306 | memset_bgcolor(outrow + nplanes * (blankcols + imgw), nplanes * n); |
||
307 | outrow += pmrb; |
||
308 | } |
||
309 | } |
||
310 | |||
311 | if (!e) { |
||
312 | preview_complete = true; |
||
313 | |||
268 | daniel-mar | 314 | #ifdef WIN_ENV |
259 | daniel-mar | 315 | { |
316 | extern HWND preview_hwnd; |
||
317 | HDC hdc = GetDC(preview_hwnd); |
||
318 | |||
319 | drawpreview(dp, hdc, outptr); |
||
320 | |||
321 | ReleaseDC(preview_hwnd, hdc); |
||
322 | } |
||
268 | daniel-mar | 323 | #else |
259 | daniel-mar | 324 | { |
325 | GrafPtr saveport; |
||
326 | |||
327 | GetPort(&saveport); |
||
328 | SetPortDialogPort(dp); |
||
329 | |||
330 | drawpreview(dp, NULL, outptr); |
||
331 | |||
332 | SetPort(saveport); |
||
333 | } |
||
268 | daniel-mar | 334 | #endif |
259 | daniel-mar | 335 | } |
336 | |||
337 | PIUNLOCKHANDLE(preview_handle); |
||
338 | } |
||
339 | |||
340 | if (e && !previewerr) { |
||
444 | daniel-mar | 341 | alertuser((TCHAR*)TEXT("Could not build preview at chosen zoom level."), |
342 | e == memFullErr && !needall ? (TCHAR*)TEXT("The image is too large for available memory. Try zooming in.\nIf that does not help, cancel and retry the filter.") : (TCHAR*)TEXT("")); |
||
259 | daniel-mar | 343 | previewerr = true; |
344 | } |
||
345 | |||
346 | } |
||
347 | } |
||
348 | |||
349 | void recalc_preview_bigdoc(FilterRecordPtr pb, DIALOGREF dp) { |
||
350 | OSErr e; |
||
351 | double scaledw, scaledh; |
||
352 | int j, n, imgw, imgh; |
||
353 | VRect r, outRect; |
||
354 | Ptr outrow; |
||
355 | |||
356 | preview_complete = false; |
||
357 | |||
358 | if (preview_handle) { |
||
359 | /* size of previewed area, of source image; but no larger than filtered area (selection) */ |
||
360 | scaledw = zoomfactor * preview_w; |
||
361 | if (scaledw > ((double)BIGDOC_FILTER_RECT(pb).right - (double)BIGDOC_FILTER_RECT(pb).left)) |
||
362 | scaledw = (double)BIGDOC_FILTER_RECT(pb).right - (double)BIGDOC_FILTER_RECT(pb).left; |
||
363 | scaledh = zoomfactor * preview_h; |
||
364 | if (scaledh > ((double)BIGDOC_FILTER_RECT(pb).bottom - (double)BIGDOC_FILTER_RECT(pb).top)) |
||
365 | scaledh = (double)BIGDOC_FILTER_RECT(pb).bottom - (double)BIGDOC_FILTER_RECT(pb).top; |
||
366 | |||
367 | /* scale clipped preview area down again - this becomes the pixel size of preview */ |
||
368 | imgw = (int)ceil(scaledw / zoomfactor); |
||
369 | if (imgw > preview_w) |
||
370 | imgw = preview_w; |
||
371 | imgh = (int)ceil(scaledh / zoomfactor); |
||
372 | if (imgh > preview_h) |
||
373 | imgh = preview_h; |
||
374 | |||
375 | /* compute source data rectangle (inRect) */ |
||
376 | |||
377 | /* centre preview on filtered part of input image, adding scroll offset */ |
||
378 | r.left = (int32)(((double)BIGDOC_FILTER_RECT(pb).left + (double)BIGDOC_FILTER_RECT(pb).right - scaledw) / 2 + preview_scroll.h); |
||
379 | /* make sure it does not go outside the input area */ |
||
380 | if (r.left < BIGDOC_FILTER_RECT(pb).left) { |
||
381 | preview_scroll.h += BIGDOC_FILTER_RECT(pb).left - r.left; |
||
382 | r.left = BIGDOC_FILTER_RECT(pb).left; |
||
383 | } |
||
384 | else if ((double)r.left + scaledw > BIGDOC_FILTER_RECT(pb).right) { |
||
385 | preview_scroll.h += (int32)((double)BIGDOC_FILTER_RECT(pb).right - ((double)r.left + scaledw)); |
||
386 | r.left = (int32)((double)BIGDOC_FILTER_RECT(pb).right - scaledw); |
||
387 | } |
||
388 | r.right = (int32)((double)r.left + scaledw); |
||
389 | preview_pmap.maskPhaseCol = (int32)((preview_scroll.h) / zoomfactor); // phase of the checkerboard |
||
390 | |||
391 | /* now compute for vertical */ |
||
392 | r.top = (int32)(((double)BIGDOC_FILTER_RECT(pb).top + (double)BIGDOC_FILTER_RECT(pb).bottom - scaledh) / 2 + preview_scroll.v); |
||
393 | if (r.top < BIGDOC_FILTER_RECT(pb).top) { |
||
394 | preview_scroll.v += BIGDOC_FILTER_RECT(pb).top - r.top; |
||
395 | r.top = BIGDOC_FILTER_RECT(pb).top; |
||
396 | } |
||
397 | else if ((double)r.top + scaledh > BIGDOC_FILTER_RECT(pb).bottom) { |
||
398 | preview_scroll.v += (int32)(BIGDOC_FILTER_RECT(pb).bottom - ((double)r.top + scaledh)); |
||
399 | r.top = (int32)((double)BIGDOC_FILTER_RECT(pb).bottom - scaledh); |
||
400 | } |
||
401 | r.bottom = (int32)((double)r.top + scaledh); |
||
402 | preview_pmap.maskPhaseRow = (int32)((preview_scroll.v) / zoomfactor); // phase of the checkerboard |
||
403 | |||
404 | /* if formulae need random access to image - src(), rad() - we must request entire area: */ |
||
405 | if (needall) |
||
406 | SETRECT(BIGDOC_IN_RECT(pb), 0, 0, BIGDOC_IMAGE_SIZE(pb).h, BIGDOC_IMAGE_SIZE(pb).v); |
||
407 | else |
||
408 | BIGDOC_IN_RECT(pb) = r; |
||
409 | |||
410 | BIGDOC_OUT_RECT(pb) = BIGDOC_IN_RECT(pb); |
||
411 | SETRECT(BIGDOC_MASK_RECT(pb), 0, 0, 0, 0); |
||
412 | pb->inLoPlane = pb->outLoPlane = 0; |
||
413 | pb->inHiPlane = pb->outHiPlane = nplanes - 1; |
||
414 | |||
415 | if (!needinput || !(e = pb->advanceState())) { |
||
416 | Ptr outptr = PILOCKHANDLE(preview_handle, false); |
||
417 | int blankrows = (preview_h - imgh) / 2, |
||
312 | daniel-mar | 418 | blankcols = (preview_w - imgw) / 2, |
419 | pmrb = preview_pmap.rowBytes; |
||
259 | daniel-mar | 420 | |
421 | evalinit(); |
||
422 | |||
423 | SETRECT(outRect, 0, 0, imgw, imgh); |
||
424 | |||
425 | e = process_scaled_bigdoc(pb, false, r, outRect, |
||
426 | outptr + pmrb * blankrows + nplanes * blankcols, pmrb, zoomfactor); |
||
427 | if (blankrows) { |
||
428 | // blank rows on top of preview: |
||
429 | memset_bgcolor(outptr, pmrb * blankrows); |
||
430 | // blank rows below preview: |
||
431 | n = preview_h - blankrows - imgh; |
||
432 | memset_bgcolor(outptr + pmrb * (blankrows + imgh), pmrb * n); |
||
433 | } |
||
434 | if (blankcols) { |
||
435 | n = preview_w - blankcols - imgw; |
||
436 | outrow = outptr + pmrb * blankrows; |
||
437 | for (j = blankrows; j < preview_h - blankrows; ++j) { |
||
438 | // blank columns on left side of preview (if picture is smaller than the preview area): |
||
439 | memset_bgcolor(outrow, nplanes * blankcols); |
||
440 | // blank columns on right side of preview (if picture is smaller than the preview area): |
||
441 | memset_bgcolor(outrow + nplanes * (blankcols + imgw), nplanes * n); |
||
442 | outrow += pmrb; |
||
443 | } |
||
444 | } |
||
445 | |||
446 | if (!e) { |
||
447 | preview_complete = true; |
||
448 | |||
268 | daniel-mar | 449 | #ifdef WIN_ENV |
259 | daniel-mar | 450 | { |
451 | extern HWND preview_hwnd; |
||
452 | HDC hdc = GetDC(preview_hwnd); |
||
453 | |||
454 | drawpreview(dp, hdc, outptr); |
||
455 | |||
456 | ReleaseDC(preview_hwnd, hdc); |
||
457 | } |
||
268 | daniel-mar | 458 | #else |
259 | daniel-mar | 459 | { |
460 | GrafPtr saveport; |
||
461 | |||
462 | GetPort(&saveport); |
||
463 | SetPortDialogPort(dp); |
||
464 | |||
465 | drawpreview(dp, NULL, outptr); |
||
466 | |||
467 | SetPort(saveport); |
||
468 | } |
||
268 | daniel-mar | 469 | #endif |
259 | daniel-mar | 470 | } |
471 | |||
472 | PIUNLOCKHANDLE(preview_handle); |
||
473 | } |
||
474 | |||
475 | if (e && !previewerr) { |
||
444 | daniel-mar | 476 | alertuser((TCHAR*)TEXT("Could not build preview at chosen zoom level."), |
477 | e == memFullErr && !needall ? (TCHAR*)TEXT("The image is too large for available memory. Try zooming in.\nIf that does not help, cancel and retry the filter.") : (TCHAR*)TEXT("")); |
||
259 | daniel-mar | 478 | previewerr = true; |
479 | } |
||
480 | |||
481 | } |
||
482 | } |
||
483 | |||
484 | void recalc_preview(FilterRecordPtr pb, DIALOGREF dp) { |
||
485 | if (HAS_BIG_DOC(pb)) { |
||
486 | recalc_preview_bigdoc(pb, dp); |
||
487 | } |
||
488 | else { |
||
489 | recalc_preview_olddoc(pb, dp); |
||
490 | } |
||
491 | } |
||
492 | |||
493 | OSErr drawpreview(DIALOGREF dp,void *hdc,Ptr imageptr){ |
||
494 | intptr_t watchsusp; |
||
495 | OSErr e = noErr; |
||
496 | VRect srcRect; |
||
497 | UIRECT imagebounds; |
||
498 | |||
433 | daniel-mar | 499 | UNREFERENCED_PARAMETER(dp); |
500 | |||
259 | daniel-mar | 501 | if(preview_handle && preview_complete){ |
502 | |||
503 | srcRect = preview_pmap.bounds; |
||
504 | |||
505 | imagebounds.left = (preview_rect.left + preview_rect.right - preview_w)/2; |
||
506 | imagebounds.top = (preview_rect.top + preview_rect.bottom - preview_h)/2; |
||
507 | imagebounds.right = imagebounds.left + preview_w; |
||
508 | imagebounds.bottom = imagebounds.top + preview_h; |
||
509 | |||
510 | preview_pmap.baseAddr = imageptr; |
||
511 | preview_pmask.maskData = imageptr+3; // FIXME: is this offset correct for all modes?! |
||
512 | |||
403 | daniel-mar | 513 | if((gpb->propertyProcs != NULL) && gpb->propertyProcs->getPropertyProc){ |
259 | daniel-mar | 514 | gpb->propertyProcs->getPropertyProc(kPhotoshopSignature,propWatchSuspension,0,&watchsusp,NULL); |
515 | gpb->propertyProcs->setPropertyProc(kPhotoshopSignature,propWatchSuspension,0,watchsusp+1,NULL); |
||
516 | } |
||
517 | |||
518 | e = gpb->displayPixels(&preview_pmap,&srcRect,imagebounds.top,imagebounds.left,hdc); |
||
519 | |||
403 | daniel-mar | 520 | if((gpb->propertyProcs != NULL) && gpb->propertyProcs->getPropertyProc) |
259 | daniel-mar | 521 | gpb->propertyProcs->setPropertyProc(kPhotoshopSignature,propWatchSuspension,0,watchsusp,NULL); |
522 | } |
||
523 | return e; |
||
524 | } |