BlinkenLibJava v.0.1.1 (200...
Christian Heimke authored 13 years ago
|
18) import org.blinkenarea.BlinkenLib.*;
19)
20) public class BlinkenMovie
21) {
22)
23) private int height;
24) private int width;
25) private int channels;
26) private int maxval;
27) private int infoCnt;
28) private String[][] infos;
29) private int frameCnt;
30) private BlinkenFrame[] frames;
31)
32) public BlinkenMovie( int height, int width, int channels, int maxval )
33) {
34) if( height < BlinkenConstants.BlinkenHeightMin ) height = BlinkenConstants.BlinkenHeightMin;
35) if( height > BlinkenConstants.BlinkenHeightMax ) height = BlinkenConstants.BlinkenHeightMax;
36) if( width < BlinkenConstants.BlinkenWidthMin ) width = BlinkenConstants.BlinkenWidthMin;
37) if( width > BlinkenConstants.BlinkenWidthMax ) width = BlinkenConstants.BlinkenWidthMax;
38) if( channels < BlinkenConstants.BlinkenChannelsMin ) channels = BlinkenConstants.BlinkenChannelsMin;
39) if( channels > BlinkenConstants.BlinkenChannelsMax ) channels = BlinkenConstants.BlinkenChannelsMax;
40) if( maxval < BlinkenConstants.BlinkenMaxvalMin ) maxval = BlinkenConstants.BlinkenMaxvalMin;
41) if( maxval > BlinkenConstants.BlinkenMaxvalMax ) maxval = BlinkenConstants.BlinkenMaxvalMax;
42)
43) this.height = height;
44) this.width = width;
45) this.channels = channels;
46) this.maxval = maxval;
47) infoCnt = 0;
48) infos = new String[0][2];
49) frameCnt = 0;
50) frames = new BlinkenFrame[0];
51) }
52)
53) public BlinkenMovie( BlinkenMovie movie )
54) {
55) int i;
56)
57) height = movie.height;
58) width = movie.width;
59) channels = movie.channels;
60) maxval = movie.maxval;
61) infoCnt = 0;
62) infos = new String[0][2];
63) frameCnt = 0;
64) frames = new BlinkenFrame[0];
65)
66) for( i = 0; i < movie.infoCnt; i++ )
67) appendInfo( new String( movie.infos[i][0] ), new String( movie.infos[i][1] ) );
68)
69) for( i = 0; i < movie.frameCnt; i++ )
70) appendFrame( new BlinkenFrame( movie.frames[i] ) );
71) }
72)
73) public int getHeight( )
74) {
75) return height;
76) }
77)
78) public int getWidth( )
79) {
80) return width;
81) }
82)
83) public int getChannels( )
84) {
85) return channels;
86) }
87)
88) public int getMaxval( )
89) {
90) return maxval;
91) }
92)
93) public int getDuration( )
94) {
95) int duration, i;
96) duration = 0;
97) for( i = 0; i < frameCnt; i++ )
98) duration += frames[i].getDuration( );
99) return duration;
100) }
101)
102) public int getInfoCnt( )
103) {
104) return infoCnt;
105) }
106)
107) public String getInfoType( int infoNo )
108) {
109) if( infoCnt < 1 ) return "";
110) if( infoNo < 0 ) infoNo = 0;
111) if( infoNo >= infoCnt ) infoNo = infoCnt - 1;
112) return infos[infoNo][0];
113) }
114)
115) public String getInfoData( int infoNo )
116) {
117) if( infoCnt < 1 ) return "";
118) if( infoNo < 0 ) infoNo = 0;
119) if( infoNo >= infoCnt ) infoNo = infoCnt - 1;
120) return infos[infoNo][1];
121) }
122)
123) public void setInfo( int infoNo, String infoType, String infoData )
124) {
125) if( infoNo < 0 || infoNo >= infoCnt )
126) return;
127) infos[infoNo][0] = infoType;
128) infos[infoNo][1] = infoData;
129) }
130)
131) public void insertInfo( int infoNo, String infoType, String infoData )
132) {
133) String[][] new_infos;
134) int i;
135)
136) if( infoNo < 0 || infoNo > infoCnt )
137) return;
138)
139) new_infos = new String[infoCnt+1][2];
140)
141) for( i = 0; i < infoNo; i++ )
142) {
143) new_infos[i][0] = infos[i][0];
144) new_infos[i][1] = infos[i][1];
145) }
146)
147) new_infos[infoNo][0] = infoType;
148) new_infos[infoNo][1] = infoData;
149)
150) for( i = infoNo; i < infoCnt; i++ )
151) {
152) new_infos[i+1][0] = infos[i][0];
153) new_infos[i+1][1] = infos[i][1];
154) }
155)
156) infos = new_infos;
157) infoCnt++;
158) }
159)
160) public void appendInfo( String infoType, String infoData )
161) {
162) insertInfo( infoCnt, infoType, infoData );
163) }
164)
165) public void deleteInfo( int infoNo )
166) {
167) String[][] new_infos;
168) int i;
169)
170) if( infoNo < 0 || infoNo >= infoCnt )
171) return;
172)
173) new_infos = new String[infoCnt-1][2];
174)
175) for( i = 0; i < infoNo; i++ )
176) {
177) new_infos[i][0] = infos[i][0];
178) new_infos[i][1] = infos[i][1];
179) }
180)
181) for( i = infoNo; i < infoCnt-1; i++ )
182) {
183) new_infos[i][0] = infos[i+1][0];
184) new_infos[i][1] = infos[i+1][1];
185) }
186)
187) infos = new_infos;
188) infoCnt--;
189) }
190)
191) public void deleteInfos( )
192) {
193) infos = new String[0][2];
194) infoCnt = 0;
195) }
196)
197) public int getFrameCnt( )
198) {
199) return frameCnt;
200) }
201)
202) public BlinkenFrame getFrame( int frameNo )
203) {
204) BlinkenFrame frame;
205) if( frameCnt < 1 )
206) {
207) frame = new BlinkenFrame( height, width, channels, maxval, 0 );
208) frame.clear( );
209) return frame;
210) }
211) if( frameNo < 0 ) frameNo = 0;
212) if( frameNo >= frameCnt ) frameNo = frameCnt - 1;
213) return frames[frameNo];
214) }
215)
216) public void setFrame( int frameNo, BlinkenFrame frame )
217) {
218) if( frameNo < 0 || frameNo >= frameCnt )
219) return;
220) frame.resize( height, width, channels, maxval );
221) frames[frameNo] = frame;
222) }
223)
224) public void insertFrame( int frameNo, BlinkenFrame frame )
225) {
226) BlinkenFrame[] new_frames;
227) int i;
228)
229) if( frameNo < 0 || frameNo > frameCnt )
230) return;
231)
232) new_frames = new BlinkenFrame[frameCnt+1];
233)
234) for( i = 0; i < frameNo; i++ )
235) new_frames[i] = frames[i];
236)
237) frame.resize( height, width, channels, maxval );
238) new_frames[frameNo] = frame;
239)
240) for( i = frameNo; i < frameCnt; i++ )
241) new_frames[i+1] = frames[i];
242)
243) frames = new_frames;
244) frameCnt++;
245) }
246)
247) public void appendFrame( BlinkenFrame frame )
248) {
249) insertFrame( frameCnt, frame );
250) }
251)
252) public void deleteFrame( int frameNo )
253) {
254) BlinkenFrame[] new_frames;
255) int i;
256)
257) if( frameNo < 0 || frameNo >= frameCnt )
258) return;
259)
260) new_frames = new BlinkenFrame[frameCnt-1];
261)
262) for( i = 0; i < frameNo; i++ )
263) new_frames[i] = frames[i];
264)
265) for( i = frameNo; i < frameCnt-1; i++ )
266) new_frames[i] = frames[i+1];
267)
268) frames = new_frames;
269) frameCnt--;
270) }
271)
272) public void deleteFrames( )
273) {
274) frames = new BlinkenFrame[0];
275) frameCnt = 0;
276) }
277)
278) public void resize( int height, int width, int channels, int maxval )
279) {
280) int i;
281)
282) if( height < BlinkenConstants.BlinkenHeightMin ) height = BlinkenConstants.BlinkenHeightMin;
283) if( height > BlinkenConstants.BlinkenHeightMax ) height = BlinkenConstants.BlinkenHeightMax;
284) if( width < BlinkenConstants.BlinkenWidthMin ) width = BlinkenConstants.BlinkenWidthMin;
285) if( width > BlinkenConstants.BlinkenWidthMax ) width = BlinkenConstants.BlinkenWidthMax;
286) if( channels < BlinkenConstants.BlinkenChannelsMin ) channels = BlinkenConstants.BlinkenChannelsMin;
287) if( channels > BlinkenConstants.BlinkenChannelsMax ) channels = BlinkenConstants.BlinkenChannelsMax;
288) if( maxval < BlinkenConstants.BlinkenMaxvalMin ) maxval = BlinkenConstants.BlinkenMaxvalMin;
289) if( maxval > BlinkenConstants.BlinkenMaxvalMax ) maxval = BlinkenConstants.BlinkenMaxvalMax;
290)
291) this.height = height;
292) this.width = width;
293) this.channels = channels;
294) this.maxval = maxval;
295)
296) for( i = 0; i < frameCnt; i++ )
297) frames[i].resize( height, width, channels, maxval );
298) }
299)
300) public void scale( int height, int width )
301) {
302) int i;
303)
304) if( height < BlinkenConstants.BlinkenHeightMin ) height = BlinkenConstants.BlinkenHeightMin;
305) if( height > BlinkenConstants.BlinkenHeightMax ) height = BlinkenConstants.BlinkenHeightMax;
306) if( width < BlinkenConstants.BlinkenWidthMin ) width = BlinkenConstants.BlinkenWidthMin;
307) if( width > BlinkenConstants.BlinkenWidthMax ) width = BlinkenConstants.BlinkenWidthMax;
308)
309) this.height = height;
310) this.width = width;
311)
312) for( i = 0; i < frameCnt; i++ )
313) frames[i].scale( height, width );
314) }
315)
316) public String toString( )
317) {
318) String str = "BlinkenMovie " + width + "x" + height + "-" + channels + "/" + (maxval + 1) + "\n";
319) int i;
320) for( i = 0; i < infoCnt; i++ )
321) str += infos[i][0] + " = " + infos[i][1] + "\n";
322) for( i = 0; i < frameCnt; i++ )
323) str += "frame " + i + "\n" + frames[i].toString( );
324) return str;
325) }
326)
327) public boolean loadBlm( BufferedReader reader )
328) {
329) Pattern header, infoLine, startOfFrame, dataLine;
330) String line, pixel;
331) Matcher matcher;
332) int new_width, new_height, new_duration, y, x, val;
333) BlinkenFrame frame;
334)
335) //initialize needed regexp patterns
336) header = Pattern.compile( "^ *# BlinkenLights Movie ([0-9]+)x([0-9]+)" );
337) infoLine = Pattern.compile( "^ *# ?([A-Za-z0-9]+)(?: *= *|: *)(.*)" );
338) startOfFrame = Pattern.compile( "^ *@([0-9]+)" );
339) dataLine = Pattern.compile( " *([01])" );
340)
341) //delete all frames
342) deleteInfos( );
343) deleteFrames( );
344) resize( 0, 0, 0, 0 );
345)
346) //try to read from buffered reader
347) try
348) {
349) //read magic and size
350) if( (line = reader.readLine( )) != null )
351) {
352) if( (matcher = header.matcher( line )).find( ) )
353) {
354) new_width = Integer.parseInt( matcher.group( 1 ) );
355) new_height = Integer.parseInt( matcher.group( 2 ) );
356) resize( new_height, new_width, 1, 1 );
357)
358) //create unused dummy frame for beginning
359) frame = new BlinkenFrame( height, width, 1, 1, 0 );
360) y = 0;
361)
362) //read frames
363) while( (line = reader.readLine( )) != null )
364) {
365)
366) //info line
367) if( (matcher = infoLine.matcher( line )).find( ) )
368) {
369) appendInfo( matcher.group( 1 ), matcher.group( 2 ) );
370) }
371)
372) //start of frame
373) else if( (matcher = startOfFrame.matcher( line )).find( ) )
374) {
375) new_duration = Integer.parseInt( matcher.group( 1 ) );
376) //create new frame and append it to movie
377) frame = new BlinkenFrame( height, width, 1, 1, new_duration );
378) frame.clear( );
379) appendFrame( frame );
380) y = 0;
381) }
382)
383) //data line
384) else if( (matcher = dataLine.matcher( line )).find( ) )
385) {
386) x = 0;
387) while( true )
388) {
389) pixel = matcher.group( 1 );
390) val = Integer.parseInt( pixel );
391) frame.setPixel( y, x, 0, (byte)val ); //set pixel
392) if( ! matcher.find( ) ) //get next pixel
393) break;
394) x++; //next pixel
395) }
396) y++; //next row
397) }
398)
399) } //while( (line = ...
400) } //if( matcher = header..matcher( ...
401) } //if( (line = ...
402)
403) //success
404) return true;
405) }
406) catch( IOException e ) { }
407)
408) //some error
409) return false;
410) }
411)
412) public boolean loadBlm( String filename )
413) {
414) try
415) {
416) BufferedReader file = new BufferedReader( new FileReader( filename ) );
417) boolean ret = loadBlm( file );
418) file.close( );
419) return ret;
420) }
421) catch( IOException e )
422) {
423) return false;
424) }
425) }
426)
427) public boolean loadBmm( BufferedReader reader )
428) {
429) Pattern header, infoLine, startOfFrame, dataLine;
430) String line, pixel;
431) Matcher matcher;
432) int new_width, new_height, new_duration, y, x, val;
433) BlinkenFrame frame;
434)
435) //initialize needed regexp patterns
436) header = Pattern.compile( "^ *# BlinkenMini Movie ([0-9]+)x([0-9]+)" );
437) infoLine = Pattern.compile( "^ *# ?([A-Za-z0-9]+)(?: *= *|: *)(.*)" );
438) startOfFrame = Pattern.compile( "^ *@([0-9]+)" );
439) dataLine = Pattern.compile( " *(0x[0-9A-Fa-f]+|[0-9]+)" );
440)
441) //delete all frames
442) deleteInfos( );
443) deleteFrames( );
444) resize( 0, 0, 0, 0 );
445)
446) //try to read from buffered reader
447) try
448) {
449) //read magic and size
450) if( (line = reader.readLine( )) != null )
451) {
452) if( (matcher = header.matcher( line )).find( ) )
453) {
454) new_width = Integer.parseInt( matcher.group( 1 ) );
455) new_height = Integer.parseInt( matcher.group( 2 ) );
456) resize( new_height, new_width, 1, 255 );
457)
458) //create unused dummy frame for beginning
459) frame = new BlinkenFrame( height, width, 1, 255, 0 );
460) y = 0;
461)
462) //read frames
463) while( (line = reader.readLine( )) != null )
464) {
465)
466) //info line
467) if( (matcher = infoLine.matcher( line )).find( ) )
468) {
469) appendInfo( matcher.group( 1 ), matcher.group( 2 ) );
470) }
471)
472) //start of frame
473) else if( (matcher = startOfFrame.matcher( line )).find( ) )
474) {
475) new_duration = Integer.parseInt( matcher.group( 1 ) );
476) //create new frame and append it to movie
477) frame = new BlinkenFrame( height, width, 1, 255, new_duration );
478) frame.clear( );
479) appendFrame( frame );
480) y = 0;
481) }
482)
483) //data line
484) else if( (matcher = dataLine.matcher( line )).find( ) )
485) {
486) x = 0;
487) while( true )
488) {
489) pixel = matcher.group( 1 );
490) if( pixel.length( ) >= 2 && pixel.substring( 0, 2 ).equals( "0x" ) )
491) val = Integer.parseInt( pixel.substring( 2 ), 0x10 );
492) else
493) val = Integer.parseInt( pixel );
494) frame.setPixel( y, x, 0, (byte)val ); //set pixel
495) if( ! matcher.find( ) ) //get next pixel
496) break;
497) x++; //next pixel
498) }
499) y++; //next row
500) }
501)
502) } //while( (line = ...
503) } //if( matcher = header..matcher( ...
504) } //if( (line = ...
505)
506) //success
507) return true;
508) }
509) catch( IOException e ) { }
510)
511) //some error
512) return false;
513) }
514)
515) public boolean loadBmm( String filename )
516) {
517) try
518) {
519) BufferedReader file = new BufferedReader( new FileReader( filename ) );
520) boolean ret = loadBmm( file );
521) file.close( );
522) return ret;
523) }
524) catch( IOException e )
525) {
526) return false;
527) }
528) }
529)
530) public boolean loadBml( BufferedReader reader )
531) {
532) Pattern blmTag, blmHeight, blmWidth, blmChannels, blmBits;
533) Pattern infoTitle, infoDescription, infoGeneric, infoCreator, infoAuthor, infoEmail, infoUrl;
534) Pattern frameTag, frameDuration, rowTag, tag;
535) String line, data, row;
536) boolean blmTagFound;
537) Matcher matcher, submatcher;
538) int new_height, new_width, new_channels, bits, new_maxval, chrs, duration, y, x, c, len, i, val;
539) BlinkenFrame frame;
540)
541) //initialize needed regexp patterns
542) blmTag = Pattern.compile( "^[^<]*<blm([^>]*)>" );
543) blmHeight = Pattern.compile( "height=\"?([0-9]*)\"?" );
544) blmWidth = Pattern.compile( "width=\"?([0-9]*)\"?" );
545) blmChannels = Pattern.compile( "channels=\"?([0-9]*)\"?" );
546) blmBits = Pattern.compile( "bits=\"?([0-9]*)\"?" );
547) infoTitle = Pattern.compile( "^[^<]*<title>([^<]*)</title>" );
548) infoDescription = Pattern.compile( "[^<]*<description>([^<]*)</description>" );
549) infoGeneric = Pattern.compile( "^([A-Za-z0-9]+)(?: *= *|: *)(.*)" );
550) infoCreator = Pattern.compile( "^[^<]*<creator>([^<]*)</creator>" );
551) infoAuthor = Pattern.compile( "^[^<]*<author>([^<]*)</author>" );
552) infoEmail = Pattern.compile( "^[^<]*<email>([^<]*)</email>" );
553) infoUrl = Pattern.compile( "^[^<]*<url>([^<]*)</url>" );
554) frameTag = Pattern.compile( "^[^<]*<frame([^>]*)>" );
555) frameDuration = Pattern.compile( "duration=\"?([0-9]*)\"?" );
556) rowTag = Pattern.compile( "^[^<]*<row>([0-9A-Fa-f]*)</row>" );
557) tag = Pattern.compile( "^[^<]*<[^>]*>" );
558)
559) //delete all frames
560) deleteInfos( );
561) deleteFrames( );
562) resize( 0, 0, 0, 0 );
563)
564) //try to read from buffered reader
565) try
566) {
567) //create unused dummy frame for beginning
568) frame = new BlinkenFrame( 0, 0, 0, 0, 0 );
569) y = 0;
570) chrs = 1;
571)
572) //read
573) data = "";
574) blmTagFound = false;
575) while( (line = reader.readLine( )) != null )
576) {
577) data += " " + line; //add new line to data
578)
579) //match tags
580) while( true )
581) {
582)
583) //no blm tag yet
584) if( ! blmTagFound )
585) {
586)
587) //blm tag
588) if( (matcher = blmTag.matcher( data )).find( ) )
589) {
590) //remove matched part
591) data = data.substring( matcher.end( ) );
592) //get attributes
593) new_width = 0;
594) new_height = 0;
595) new_channels = 1;
596) bits = 4;
597) new_maxval = 15;
598) if( (submatcher = blmHeight.matcher( matcher.group( 1 ) )).find( ) ) //height
599) new_height = Integer.parseInt( submatcher.group( 1 ) );
600) if( (submatcher = blmWidth.matcher( matcher.group( 1 ) )).find( ) ) //width
601) new_width = Integer.parseInt( submatcher.group( 1 ) );
602) if( (submatcher = blmChannels.matcher( matcher.group( 1 ) )).find( ) ) //channels
603) new_channels = Integer.parseInt( submatcher.group( 1 ) );
604) if( (submatcher = blmBits.matcher( matcher.group( 1 ) )).find( ) ) //bits
605) new_maxval = (1 << (bits = Integer.parseInt( submatcher.group( 1 ) ))) - 1;
606) //remember that blm tag was found
607) blmTagFound = true;
608) //set movie size
609) resize( new_height, new_width, new_channels, new_maxval );
610) //get number of characters per channel
611) chrs = (bits + 3) >> 2;
612) }
613)
614) //unknown tag
615) else if( (matcher = tag.matcher( data )).find( ) )
616) //remove matched part
617) data = data.substring( matcher.end( ) );
618)
619) //nothing matches
620) else
621) //end loop
622) break;
623)
624) } //if( ! blmTagFound )
625)
626) //blm tag was already found
627) else
628) {
629)
630) //title tag
631) if( (matcher = infoTitle.matcher( data )).find( ) )
632) {
633) //remove matched part
634) data = data.substring( matcher.end( ) );
635) //add info to movie
636) appendInfo( "title", matcher.group( 1 ) );
637) }
638)
639) //description tag
640) else if( (matcher = infoDescription.matcher( data )).find( ) )
641) {
642) //remove matched part
643) data = data.substring( matcher.end( ) );
644) //check if generic info
645) if( (submatcher = infoGeneric.matcher( matcher.group( 1 ) )).find( ) )
646) //add info to movie
647) appendInfo( submatcher.group( 1 ), submatcher.group( 2 ) );
648) else
649) //add info to movie
650) appendInfo( "description", matcher.group( 1 ) );
651) }
652)
653) //creator tag
654) else if( (matcher = infoCreator.matcher( data )).find( ) )
655) {
656) //remove matched part
657) data = data.substring( matcher.end( ) );
658) //add info to movie
659) appendInfo( "creator", matcher.group( 1 ) );
660) }
661)
662) //author tag
663) else if( (matcher = infoAuthor.matcher( data )).find( ) )
664) {
665) //remove matched part
666) data = data.substring( matcher.end( ) );
667) //add info to movie
668) appendInfo( "author", matcher.group( 1 ) );
669) }
670)
671) //email tag
672) else if( (matcher = infoEmail.matcher( data )).find( ) )
673) {
674) //remove matched part
675) data = data.substring( matcher.end( ) );
676) //add info to movie
677) appendInfo( "email", matcher.group( 1 ) );
678) }
679)
680) //url tag
681) else if( (matcher = infoUrl.matcher( data )).find( ) )
682) {
683) //remove matched part
684) data = data.substring( matcher.end( ) );
685) //add info to movie
686) appendInfo( "url", matcher.group( 1 ) );
687) }
688)
689) //frame tag
690) else if( (matcher = frameTag.matcher( data )).find( ) )
691) {
692) //remove matched part
693) data = data.substring( matcher.end( ) );
694) //get attributes
695) duration = 0;
696) if( (submatcher = frameDuration.matcher( matcher.group( 1 ) )).find( ) ) //duration
697) duration = Integer.parseInt( submatcher.group( 1 ) );
698) //create new frame and append it to movie
699) frame = new BlinkenFrame( height, width, channels, maxval, duration );
700) frame.clear( );
701) appendFrame( frame );
702) y = 0;
703) }
704)
705) //row tag
706) else if( (matcher = rowTag.matcher( data )).find( ) )
707) {
708) //remove matched part
709) data = data.substring( matcher.end( ) );
710) //parse row
711) row = matcher.group( 1 );
712) len = row.length( );
713) i = 0;
714) for( x = 0; x < this.width && i + chrs <= len; x++ )
715) {
716) for( c = 0; c < this.channels && i + chrs <= len; c++, i += chrs )
717) {
718) val = Integer.parseInt( row.substring( i, i + chrs ), 0x10 );
719) frame.setPixel( y, x, c, (byte)val ); //set pixel
720) }
721) }
722) y++; //next row
723) }
724)
725) //unknown tag
726) else if( (matcher = tag.matcher( data )).find( ) )
727) //remove matched part
728) data = data.substring( matcher.end( ) );
729)
730) //nothing matches
731) else
732) //end loop
733) break;
734)
735) } //if( ! blmTagFound ) ... else
736)
737) } //while( true )
738)
739) } //while( (line = ...
740)
741) //success
742) return true;
743) }
744) catch( IOException e ) { }
745)
746) //some error
747) return false;
748) }
749)
750) public boolean loadBml( String filename )
751) {
752) try
753) {
754) BufferedReader file = new BufferedReader( new FileReader( filename ) );
755) boolean ret = loadBml( file );
756) file.close( );
757) return ret;
758) }
759) catch( IOException e )
760) {
761) return false;
762) }
763) }
764)
765) public boolean loadBbm( String filename )
766) {
767) RandomAccessFile file;
768) byte[] header, subHeader, infoHeader, frameStartMarker, frameData;
769) int headerMagic, headerHeight, headerWidth, headerChannels, headerMaxval;
770) int headerFrameCnt, headerDuration, headerFramePtr;
771) int subHeaderMagic, subHeaderSize;
772) int frameStartMarkerMagic;
773) StringTokenizer tokenizer;
774) String infoType, infoData;
775) int fileLength, frameLength;
776) int duration, i, y, x, c;
777) BlinkenFrame frame;
778)
779) //delete all frames
780) deleteInfos( );
781) deleteFrames( );
782) resize( 0, 0, 0, 0 );
783)
784) //try to read file
785) try
786) {
787) //open file
788) file = new RandomAccessFile( filename, "r" );
789)
790) //read header
791) header = new byte[24];
792) file.readFully( header );
793) headerMagic = ((int)header[0] & 0xFF) << 24 | ((int)header[1] & 0xFF) << 16 | ((int)header[2] & 0xFF) << 8 | ((int)header[3] & 0xFF);
794) headerHeight = ((int)header[4] & 0xFF) << 8 | ((int)header[5] & 0xFF);
795) headerWidth = ((int)header[6] & 0xFF) << 8 | ((int)header[7] & 0xFF);
796) headerChannels = ((int)header[8] & 0xFF) << 8 | ((int)header[9] & 0xFF);
797) headerMaxval = ((int)header[10] & 0xFF) << 8 | ((int)header[11] & 0xFF);
798) headerFrameCnt = ((int)header[12] & 0xFF) << 24 | ((int)header[13] & 0xFF) << 16 | ((int)header[14] & 0xFF) << 8 | ((int)header[15] & 0xFF);
799) headerDuration = ((int)header[16] & 0xFF) << 24 | ((int)header[17] & 0xFF) << 16 | ((int)header[18] & 0xFF) << 8 | ((int)header[19] & 0xFF);
800) headerFramePtr = ((int)header[20] & 0xFF) << 24 | ((int)header[21] & 0xFF) << 16 | ((int)header[22] & 0xFF) << 8 | ((int)header[23] & 0xFF);
801) //check magic
802) if( headerMagic == 0x23542666 )
803) {
804)
805) //adapt movie format
806) resize( headerHeight, headerWidth, headerChannels, headerMaxval );
807)
808) //read subheaders
809) subHeader = new byte[6];
810) while( file.getFilePointer( ) + 6 <= headerFramePtr )
811) {
812) file.readFully( subHeader );
813) subHeaderMagic = ((int)subHeader[0] & 0xFF) << 24 | ((int)subHeader[1] & 0xFF) << 16 | ((int)subHeader[2] & 0xFF) << 8 | ((int)subHeader[3] & 0xFF);
814) subHeaderSize = ((int)subHeader[4] & 0xFF) << 8 | ((int)subHeader[5] & 0xFF);
815)
816) //header fits into gap to frame start
817) if( subHeaderSize >= 6 && file.getFilePointer( ) + subHeaderSize - 6 <= headerFramePtr )
818) {
819) //info header
820) if( subHeaderMagic == 0x696E666F ) //'i' 'n' 'f' 'o'
821) {
822) //read rest of info header
823) infoHeader = new byte[subHeaderSize - 6];
824) file.readFully( infoHeader );
825) //parse information
826) tokenizer = new StringTokenizer( new String( infoHeader ), "\000" );
827) if( tokenizer.countTokens( ) >= 2 )
828) {
829) infoType = tokenizer.nextToken();
830) infoData = tokenizer.nextToken();
831) appendInfo( infoType, infoData );
832) }
833) }
834)
835) //unknown subHeader
836) else
837) //skip
838) file.skipBytes( subHeaderSize - 6 );
839)
840) } //if( file.getFilePointer( ) ...
841) } //while( file.getFilePointer( ) ...
842)
843) //seek to start of frames
844) file.seek( headerFramePtr );
845)
846) //read frame start marker
847) frameStartMarker = new byte[4];
848) file.readFully( frameStartMarker );
849) frameStartMarkerMagic = ((int)frameStartMarker[0] & 0xFF) << 24 | ((int)frameStartMarker[1] & 0xFF) << 16 | ((int)frameStartMarker[2] & 0xFF) << 8 | ((int)frameStartMarker[3] & 0xFF);
850) if( frameStartMarkerMagic == 0x66726D73 ) //'f' 'r' 'm' 's'
851) {
852)
853) //read frames
854) fileLength = (int)file.length( );
855) frameLength = 2 + headerHeight * headerWidth * headerChannels;
856) frameData = new byte[frameLength];
857) while( file.getFilePointer( ) + frameLength <= fileLength )
858) {
859) //read frame
860) file.readFully( frameData );
861) duration = ((int)frameData[0] & 0xFF) << 8 | ((int)frameData[1] & 0xFF);
862) //build frame and append it to movie
863) frame = new BlinkenFrame( height, width, channels, maxval, duration );
864) i = 2;
865) for( y = 0; y < headerHeight; y++ )
866) for( x = 0; x < headerWidth; x++ )
867) for( c = 0; c < headerChannels; c++, i++ )
868) frame.setPixel( y, x, c, frameData[i] );
869) appendFrame( frame );
870)
871) } //while( file.getFilePointer ...
872)
873) } //if( frameStartMarkerMagic ...
874)
875) } //if( headerMagic ...
876)
877) //close file
878) file.close( );
879)
880) //success
881) return true;
882) }
883) catch( IOException e ) { }
884)
885) //some error
886) return false;
887) }
888)
|
first version fo GIF read s...
Stefan Schuermans authored 6 years ago
|
889) public boolean loadGif( String filename )
890) {
891) //delete all frames
892) deleteInfos( );
893) deleteFrames( );
894) resize( 0, 0, 0, 0 );
895)
896) //try to read file
897) try
898) {
899) //load file
900) ImageReader reader = (ImageReader)ImageIO.getImageReadersByFormatName( "gif").next( );
901) ImageInputStream inStrm = ImageIO.createImageInputStream( new File( filename ) );
902) reader.setInput( inStrm, false );
903)
904) //get global metadata
905) IIOMetadata meta = reader.getStreamMetadata( );
906) Node tree = meta.getAsTree( "javax_imageio_gif_stream_1.0" );
907) NodeList children = tree.getChildNodes( );
908)
909) //parse global metadata
910) Color bgColor = Color.BLACK;
911) for( int chi = 0; chi < children.getLength(); ++chi )
912) {
913) Node child = children.item( chi );
914)
915) if( child.getNodeName( ).equals( "GlobalColorTable" ) )
916) {
917) NamedNodeMap attr = child.getAttributes();
918) Node bgIdxNode = attr.getNamedItem( "backgroundColorIndex" );
919) if( bgIdxNode != null )
920) {
921) int bgIdx = Integer.valueOf( bgIdxNode.getNodeValue( ) );
922)
923) NodeList entries = child.getChildNodes( );
924) for( int ent = 0; ent < entries.getLength( ); ++ent )
925) {
926) Node entry = entries.item( ent );
927) if( entry.getNodeName( ).equals( "ColorTableEntry" ) )
928) {
929) NamedNodeMap entryAttr = entry.getAttributes();
930) int index = Integer.valueOf( entryAttr.getNamedItem(
931) "index" ).getNodeValue( ) );
932) if( index == bgIdx )
933) {
934) int red = Integer.valueOf( entryAttr.getNamedItem(
935) "red" ).getNodeValue( ) );
936) int green = Integer.valueOf( entryAttr.getNamedItem(
937) "green" ).getNodeValue( ) );
938) int blue = Integer.valueOf( entryAttr.getNamedItem(
939) "blue" ).getNodeValue( ) );
940) bgColor = new Color(red, green, blue);
941) break;
942) } //if index
943) } //if entry
944) } //for ent
945) } //if bgIdxNode
946) } //if child
947) } //for chi
948)
949) //iterate through all frames
950) int frameCnt = reader.getNumImages( true );
951) int movieWidth = 0;
952) int movieHeight = 0;
953) BufferedImage canvas = null, backup = null;
954) for( int frame = 0; frame < frameCnt; ++frame )
955) {
956) //get image
957) BufferedImage img = reader.read( frame );
958)
959) //get image metadata
960) meta = reader.getImageMetadata( frame );
961) tree = meta.getAsTree( "javax_imageio_gif_image_1.0" );
962) children = tree.getChildNodes( );
963)
964) //parse metadata for this image
965) int left = -1, top = -1, width = -1, height = -1;
966) int duration = 100;
967) boolean restoreToPrevious = false;
968) boolean restoreToBackgroundColor = false;
969) for( int chi = 0; chi < children.getLength( ); ++chi )
970) {
971) Node child = children.item( chi );
972)
973) if( child.getNodeName( ).equals( "ImageDescriptor" ) )
974) {
975) NamedNodeMap attr = child.getAttributes();
976) left = Integer.valueOf( attr.getNamedItem(
977) "imageLeftPosition" ).getNodeValue( ) );
978) top = Integer.valueOf( attr.getNamedItem(
979) "imageTopPosition" ).getNodeValue( ) );
980) width = Integer.valueOf( attr.getNamedItem(
981) "imageWidth" ).getNodeValue( ) );
982) height = Integer.valueOf( attr.getNamedItem(
983) "imageHeight" ).getNodeValue( ) );
984) } //if ImageDescriptor
985) if( child.getNodeName( ).equals( "GraphicControlExtension" ) )
986) {
987) NamedNodeMap attr = child.getAttributes();
988) Node disposalMethod = attr.getNamedItem( "disposalMethod" );
989) if( disposalMethod != null )
990) {
991) String disposalMethodStr = disposalMethod.getNodeValue( );
992) if( disposalMethodStr.equals( "restoreToPrevious" ) )
993) restoreToPrevious = true;
994) else if( disposalMethodStr.equals( "restoreToBackgroundColor" ) )
995) restoreToBackgroundColor = true;
996) }
997) Node durationNode = attr.getNamedItem( "delayTime" );
998) if( durationNode != null )
999) duration = Integer.valueOf( durationNode.getNodeValue( ) ) * 10;
1000) } //if GraphicControlExtension
1001) } //for chi
1002)
1003) //no position -> ignore this frame
1004) if (left < 0 || top < 0 || width < 0 || height < 0)
1005) continue;
1006)
1007) //first frame determines movie size
1008) if( canvas == null )
1009) {
1010) movieWidth = width;
1011) movieHeight = height;
1012) resize( movieHeight, movieWidth, 3, 255 );
1013) canvas = new BufferedImage( movieWidth, movieHeight,
1014) BufferedImage.TYPE_INT_ARGB );
1015) backup = new BufferedImage( movieWidth, movieHeight,
1016) BufferedImage.TYPE_INT_ARGB );
1017) }
1018)
1019) // keep backup if needed
1020) if( restoreToPrevious )
1021) {
1022) Graphics g = backup.getGraphics();
1023) g.drawImage(canvas, 0, 0, null);
1024) g.dispose();
1025) }
1026)
1027) // draw new image to canvas
1028) Graphics g = canvas.getGraphics( );
1029) g.drawImage( img, left, top, null );
1030) g.dispose();
1031)
1032) // convert canvas to new frame and append to movie
1033) BlinkenFrame newFrame = new BlinkenFrame( movieHeight, movieWidth,
1034) 3, 255, duration );
1035) for( int y = 0; y < movieHeight; y++ )
1036) for( int x = 0; x < movieWidth; x++ )
1037) newFrame.setColor( y, x, new Color( canvas.getRGB( x, y ) ) );
1038) appendFrame( newFrame );
1039)
1040) // disposal of image on canvas
1041) if( restoreToPrevious )
1042) {
1043) g = canvas.getGraphics();
1044) g.drawImage(backup, 0, 0, null);
1045) g.dispose();
1046) }
1047) if( restoreToBackgroundColor )
1048) {
1049) Graphics2D g2d = canvas.createGraphics();
1050) g2d.setColor(bgColor);
1051) g2d.fill(new Rectangle(left, top, width, height));
1052) g2d.dispose();
1053) }
1054)
1055) } //for frame
1056)
1057) //success
1058) return true;
1059) }
1060) catch( IOException e ) { }
1061)
1062) //some error
1063) return false;
1064) }
1065)
|
BlinkenLibJava v.0.1.1 (200...
Christian Heimke authored 13 years ago
|
1078) deleteFrames( );
1079) return false;
1080) }
1081)
1082) public boolean saveBlm( BufferedWriter writer )
1083) {
1084) BlinkenMovie movie;
1085) int cnt, i, y, x;
1086) String line;
1087)
1088) //convert movie to suitable format
1089) movie = new BlinkenMovie( this );
1090) movie.resize( movie.height, movie.width, 1, 1 );
1091)
1092) try
1093) {
1094) //write header line
1095) writer.write( "# BlinkenLights Movie " + movie.width + "x" + movie.height + "\n" );
1096)
1097) //write information lines
1098) cnt = movie.getInfoCnt( );
1099) for( i = 0; i < cnt; i++ )
1100) writer.write( "# " + movie.getInfoType( i ) + " = " + movie.getInfoData( i ) + "\n" );
1101)
1102) //write frames
1103) cnt = movie.getFrameCnt( );
1104) for( i = 0; i < cnt; i++ )
1105) {
1106) writer.write( "\n@" + movie.frames[i].getDuration( ) + "\n" );
1107) for( y = 0; y < movie.height; y++ )
1108) {
1109) line = "";
1110) for( x = 0; x < movie.width; x++ )
1111) {
1112) if( movie.frames[i].getPixel( y, x, 0 ) != 0 )
1113) line = line + "1";
1114) else
1115) line = line + "0";
1116) }
1117) writer.write( line + "\n" );
1118) }
1119) }
1120)
1121) //success
1122) return true;
1123) }
1124) catch( IOException e ) { }
1125)
1126) //some error
1127) return false;
1128) }
1129)
1130) public boolean saveBlm( String filename )
1131) {
1132) try
1133) {
1134) BufferedWriter file = new BufferedWriter( new FileWriter( filename ) );
1135) boolean ret = saveBlm( file );
1136) file.close( );
1137) return ret;
1138) }
1139) catch( IOException e )
1140) {
1141) return false;
1142) }
1143) }
1144)
1145) public boolean saveBmm( BufferedWriter writer )
1146) {
1147) BlinkenMovie movie;
1148) int cnt, i, y, x, val;
1149) String line;
1150)
1151) //convert movie to suitable format
1152) movie = new BlinkenMovie( this );
1153) movie.resize( movie.height, movie.width, 1, 255 );
1154)
1155) try
1156) {
1157) //write header line
1158) writer.write( "# BlinkenMini Movie " + movie.width + "x" + movie.height + "\n" );
1159)
1160) //write information lines
1161) cnt = movie.getInfoCnt( );
1162) for( i = 0; i < cnt; i++ )
1163) writer.write( "# " + movie.getInfoType( i ) + " = " + movie.getInfoData( i ) + "\n" );
1164)
1165) //write frames
1166) cnt = movie.getFrameCnt( );
1167) for( i = 0; i < cnt; i++ )
1168) {
1169) writer.write( "\n@" + movie.frames[i].getDuration( ) + "\n" );
1170) for( y = 0; y < movie.height; y++ )
1171) {
1172) line = "";
1173) for( x = 0; x < movie.width; x++ )
1174) {
1175) val = (int)movie.frames[i].getPixel( y, x, 0 ) & 0xFF;
1176) if( val < 0x10 )
1177) line = line + " 0x0" + Integer.toHexString( val ).toUpperCase( );
1178) else
1179) line = line + " 0x" + Integer.toHexString( val ).toUpperCase( );
1180) }
1181) writer.write( line.substring( 1 ) + "\n" );
1182) }
1183) }
1184)
1185) //success
1186) return true;
1187) }
1188) catch( IOException e ) { }
1189)
1190) //some error
1191) return false;
1192) }
1193)
1194) public boolean saveBmm( String filename )
1195) {
1196) try
1197) {
1198) BufferedWriter file = new BufferedWriter( new FileWriter( filename ) );
1199) boolean ret = saveBmm( file );
1200) file.close( );
1201) return ret;
1202) }
1203) catch( IOException e )
1204) {
1205) return false;
1206) }
1207) }
1208)
1209) public boolean saveBml( BufferedWriter writer )
1210) {
1211) BlinkenMovie movie;
1212) int bits, cnt, i, y, x, c, val;
1213) String infoType, infoData, line;
1214)
1215) //convert movie to suitable format
1216) movie = new BlinkenMovie( this );
1217) val = movie.maxval; //get number of bits
1218) for( bits = 0; val != 0; val >>= 1, bits++ );
1219) movie.resize( movie.height, movie.width, movie.channels, (1 << bits) - 1 );
1220)
1221) try
1222) {
1223) //write header line
1224) writer.write( "<?xml version=\"1.0\" encoding=\"UTF-8\"?>\n" );
1225)
1226) //write blm start tag
1227) writer.write( "<blm width=\"" + movie.width + "\" height=\"" + movie.height
1228) + "\" bits=\"" + bits + "\" channels=\"" + movie.channels + "\">\n" );
1229)
1230) //write information lines
1231) writer.write( "\t<header>\n" );
1232) cnt = movie.getInfoCnt( );
1233) for( i = 0; i < cnt; i++ )
1234) {
1235) infoType = movie.getInfoType( i );
1236) infoData = movie.getInfoData( i );
1237) if( infoType.equals( "title" ) )
1238) writer.write( "\t\t<title>" + infoData + "</title>\n" );
1239) else if( infoType.equals( "description" ) )
1240) writer.write( "\t\t<description>" + infoData + "</description>\n" );
1241) else if( infoType.equals( "creator" ) )
1242) writer.write( "\t\t<creator>" + infoData + "</creator>\n" );
1243) else if( infoType.equals( "author" ) )
1244) writer.write( "\t\t<author>" + infoData + "</author>\n" );
1245) else if( infoType.equals( "email" ) )
1246) writer.write( "\t\t<email>" + infoData + "</email>\n" );
1247) else if( infoType.equals( "url" ) )
1248) writer.write( "\t\t<url>" + infoData + "</url>\n" );
1249) else
1250) writer.write( "\t\t<description>" + infoType + ": " + infoData + "</description>\n" );
1251) }
1252) writer.write( "\t</header>\n" );
1253)
1254) //write frames
1255) cnt = movie.getFrameCnt( );
1256) for( i = 0; i < cnt; i++ )
1257) {
1258) writer.write( "\n\t<frame duration=\"" + movie.frames[i].getDuration( ) + "\">\n" );
1259) for( y = 0; y < movie.height; y++ )
1260) {
1261) line = "";
1262) for( x = 0; x < movie.width; x++ )
1263) {
1264) for( c = 0; c < movie.channels; c++ )
1265) {
1266) val = (int)movie.frames[i].getPixel( y, x, c ) & 0xFF;
1267) if( bits > 4 && val < 0x10 )
1268) line = line + "0" + Integer.toHexString( val ).toUpperCase( );
1269) else
1270) line = line + Integer.toHexString( val ).toUpperCase( );
1271) }
1272) }
1273) writer.write( "\t\t<row>" + line + "</row>\n" );
1274) }
1275) writer.write( "\t</frame>\n" );
1276) }
1277)
1278) //write blm end tag
1279) writer.write( "</blm>\n" );
1280)
1281) //success
1282) return true;
1283) }
1284) catch( IOException e ) { }
1285)
1286) //some error
1287) return false;
1288) }
1289)
1290) public boolean saveBml( String filename )
1291) {
1292) try
1293) {
1294) BufferedWriter file = new BufferedWriter( new FileWriter( filename ) );
1295) boolean ret = saveBml( file );
1296) file.close( );
1297) return ret;
1298) }
1299) catch( IOException e )
1300) {
1301) return false;
1302) }
1303) }
1304)
1305) public boolean saveBbm( String filename )
1306) {
1307) RandomAccessFile file;
1308) byte[] header, infoHeader, framePointer, frameStartMarker, frameData;
1309) int cnt, duration, i, j, len, y, x, c, val;
1310) String infoType, infoData, line;
1311)
1312) try
1313) {
1314) //open file
1315) file = new RandomAccessFile( filename, "rw" );
1316)
|