1 /*
2 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
3 % %
4 % %
5 % %
6 % SSSSS CCCC RRRR %
7 % SS C R R %
8 % SSS C RRRR %
9 % SS C R R %
10 % SSSSS CCCC R R %
11 % %
12 % %
13 % Read ZX-Spectrum SCREEN$ Format %
14 % %
15 % Software Design %
16 % Catalin Mihaila %
17 % October 2003 %
18 % %
19 % %
20 % Copyright 1999-2016 ImageMagick Studio LLC, a non-profit organization %
21 % dedicated to making software imaging solutions freely available. %
22 % %
23 % You may not use this file except in compliance with the License. You may %
24 % obtain a copy of the License at %
25 % %
26 % http://www.imagemagick.org/script/license.php %
27 % %
28 % Unless required by applicable law or agreed to in writing, software %
29 % distributed under the License is distributed on an "AS IS" BASIS, %
30 % WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. %
31 % See the License for the specific language governing permissions and %
32 % limitations under the License. %
33 % %
34 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
35 %
36 %
37 */
38
39 /*
40 Include declarations.
41 */
42 #include "MagickCore/studio.h"
43 #include "MagickCore/blob.h"
44 #include "MagickCore/blob-private.h"
45 #include "MagickCore/cache.h"
46 #include "MagickCore/exception.h"
47 #include "MagickCore/exception-private.h"
48 #include "MagickCore/image.h"
49 #include "MagickCore/image-private.h"
50 #include "MagickCore/list.h"
51 #include "MagickCore/magick.h"
52 #include "MagickCore/memory_.h"
53 #include "MagickCore/monitor.h"
54 #include "MagickCore/monitor-private.h"
55 #include "MagickCore/pixel-accessor.h"
56 #include "MagickCore/quantum-private.h"
57 #include "MagickCore/static.h"
58 #include "MagickCore/string_.h"
59 #include "MagickCore/module.h"
60
61 /*
62 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
63 % %
64 % %
65 % %
66 % R e a d S C R I m a g e %
67 % %
68 % %
69 % %
70 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
71 %
72 % ReadSCRImage() reads a Scitex image file and returns it. It allocates
73 % the memory necessary for the new Image structure and returns a pointer to
74 % the new image.
75 %
76 % The format of the ReadSCRImage method is:
77 %
78 % Image *ReadSCRImage(const ImageInfo *image_info,ExceptionInfo *exception)
79 %
80 % A description of each parameter follows:
81 %
82 % o image_info: the image info.
83 %
84 % o exception: return any errors or warnings in this structure.
85 %
86 */
ReadSCRImage(const ImageInfo * image_info,ExceptionInfo * exception)87 static Image *ReadSCRImage(const ImageInfo *image_info,ExceptionInfo *exception)
88 {
89 char zxscr[6144];
90 char zxattr[768];
91 int octetnr;
92 int octetline;
93 int zoneline;
94 int zonenr;
95 int octet_val;
96 int attr_nr;
97 int pix;
98 int piy;
99 int binar[8];
100 int attrbin[8];
101 int *pbin;
102 int *abin;
103 int z;
104 int one_nr;
105 int ink;
106 int paper;
107 int bright;
108
109 unsigned char colour_palette[] = {
110 0, 0, 0,
111 0, 0,192,
112 192, 0, 0,
113 192, 0,192,
114 0,192, 0,
115 0,192,192,
116 192,192, 0,
117 192,192,192,
118 0, 0, 0,
119 0, 0,255,
120 255, 0, 0,
121 255, 0,255,
122 0,255, 0,
123 0,255,255,
124 255,255, 0,
125 255,255,255
126 };
127
128 Image
129 *image;
130
131 MagickBooleanType
132 status;
133
134 register Quantum
135 *q;
136
137 ssize_t
138 count;
139
140 /*
141 Open image file.
142 */
143 assert(image_info != (const ImageInfo *) NULL);
144 assert(image_info->signature == MagickCoreSignature);
145 if (image_info->debug != MagickFalse)
146 (void) LogMagickEvent(TraceEvent,GetMagickModule(),"%s",
147 image_info->filename);
148 assert(exception != (ExceptionInfo *) NULL);
149 assert(exception->signature == MagickCoreSignature);
150 image=AcquireImage(image_info,exception);
151 status=OpenBlob(image_info,image,ReadBinaryBlobMode,exception);
152 if (status == MagickFalse)
153 {
154 image=DestroyImageList(image);
155 return((Image *) NULL);
156 }
157 image->columns = 256;
158 image->rows = 192;
159 status=SetImageExtent(image,image->columns,image->rows,exception);
160 if (status == MagickFalse)
161 return(DestroyImageList(image));
162 count=ReadBlob(image,6144,(unsigned char *) zxscr);
163 (void) count;
164 count=ReadBlob(image,768,(unsigned char *) zxattr);
165 for(zonenr=0;zonenr<3;zonenr++)
166 {
167 for(zoneline=0;zoneline<8;zoneline++)
168 {
169 for(octetline=0;octetline<8;octetline++)
170 {
171 for(octetnr=(zoneline*32);octetnr<((zoneline*32)+32);octetnr++)
172 {
173 octet_val = zxscr[octetnr+(256*octetline)+(zonenr*2048)];
174 attr_nr = zxattr[octetnr+(256*zonenr)];
175
176 pix = (((8*octetnr)-(256*zoneline)));
177 piy = ((octetline+(8*zoneline)+(zonenr*64)));
178
179 pbin = binar;
180 abin = attrbin;
181
182 one_nr=1;
183
184 for(z=0;z<8;z++)
185 {
186 if(octet_val&one_nr)
187 {
188 *pbin = 1;
189 } else {
190 *pbin = 0;
191 }
192 one_nr=one_nr*2;
193 pbin++;
194 }
195
196 one_nr = 1;
197
198 for(z=0;z<8;z++)
199 {
200 if(attr_nr&one_nr)
201 {
202 *abin = 1;
203 } else {
204 *abin = 0;
205 }
206 one_nr=one_nr*2;
207 abin++;
208 }
209
210 ink = (attrbin[0]+(2*attrbin[1])+(4*attrbin[2]));
211 paper = (attrbin[3]+(2*attrbin[4])+(4*attrbin[5]));
212 bright = attrbin[6];
213
214 if(bright) { ink=ink+8; paper=paper+8; }
215
216 for(z=7;z>-1;z--)
217 {
218 q=QueueAuthenticPixels(image,pix,piy,1,1,exception);
219 if (q == (Quantum *) NULL)
220 break;
221
222 if(binar[z])
223 {
224 SetPixelRed(image,ScaleCharToQuantum(
225 colour_palette[3*ink]),q);
226 SetPixelGreen(image,ScaleCharToQuantum(
227 colour_palette[1+(3*ink)]),q);
228 SetPixelBlue(image,ScaleCharToQuantum(
229 colour_palette[2+(3*ink)]),q);
230 } else {
231 SetPixelRed(image,ScaleCharToQuantum(
232 colour_palette[3*paper]),q);
233 SetPixelGreen(image,ScaleCharToQuantum(
234 colour_palette[1+(3*paper)]),q);
235 SetPixelBlue(image,ScaleCharToQuantum(
236 colour_palette[2+(3*paper)]),q);
237 }
238
239 pix++;
240 }
241 }
242 }
243 }
244 }
245 (void) CloseBlob(image);
246 return(GetFirstImageInList(image));
247 }
248
249 /*
250 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
251 % %
252 % %
253 % %
254 % R e g i s t e r S C R I m a g e %
255 % %
256 % %
257 % %
258 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
259 %
260 % RegisterSCRImage() adds attributes for the SCR image format to
261 % the list of supported formats. The attributes include the image format
262 % tag, a method to read and/or write the format, whether the format
263 % supports the saving of more than one frame to the same file or blob,
264 % whether the format supports native in-memory I/O, and a brief
265 % description of the format.
266 %
267 % The format of the RegisterSCRImage method is:
268 %
269 % size_t RegisterSCRImage(void)
270 %
271 */
RegisterSCRImage(void)272 ModuleExport size_t RegisterSCRImage(void)
273 {
274 MagickInfo
275 *entry;
276
277 entry=AcquireMagickInfo("SCR","SCR","ZX-Spectrum SCREEN$");
278 entry->decoder=(DecodeImageHandler *) ReadSCRImage;
279 entry->flags^=CoderAdjoinFlag;
280 (void) RegisterMagickInfo(entry);
281 return(MagickImageCoderSignature);
282 }
283
284 /*
285 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
286 % %
287 % %
288 % %
289 % U n r e g i s t e r S C R I m a g e %
290 % %
291 % %
292 % %
293 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
294 %
295 % UnregisterSCRImage() removes format registrations made by the
296 % SCR module from the list of supported formats.
297 %
298 % The format of the UnregisterSCRImage method is:
299 %
300 % UnregisterSCRImage(void)
301 %
302 */
UnregisterSCRImage(void)303 ModuleExport void UnregisterSCRImage(void)
304 {
305 (void) UnregisterMagickInfo("SCR");
306 }
307