wiretap 0.1 → 0.1.2

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (91) hide show
  1. data/README +2 -1
  2. data/ext/Makefile +27 -24
  3. data/ext/audio_format.cpp +10 -8
  4. data/ext/charstream.h +41 -0
  5. data/ext/extconf.rb +8 -10
  6. data/ext/frame_io.cpp +120 -0
  7. data/ext/frame_io.h +45 -0
  8. data/ext/image_format.cpp +49 -169
  9. data/ext/image_io.cpp +466 -0
  10. data/ext/image_io.h +73 -0
  11. data/ext/node.cpp +71 -48
  12. data/ext/nodeframes.cpp +36 -34
  13. data/ext/nodemetadata.cpp +21 -3
  14. data/ext/server.cpp +2 -2
  15. data/ext/serverlist.cpp +20 -8
  16. data/ext/wiretap.cpp +11 -8
  17. data/ext/wiretap.h +17 -13
  18. data/lib/wiretap.rb +65 -5
  19. data/test_new/common.rb +8 -0
  20. data/{test/wiretap-images → test_new/fixtures/img/ppm-8bit}/01.ppm +0 -0
  21. data/test_new/fixtures/raw/cube_2k_12bitP_1f/0.stoneimage +0 -0
  22. data/test_new/fixtures/raw/cube_2k_8bit_1f/0.stoneimage +0 -0
  23. data/test_new/fixtures/raw/cube_SD_10bit_5f/0.stoneimage +0 -0
  24. data/test_new/fixtures/raw/cube_SD_10bit_5f/1.stoneimage +0 -0
  25. data/test_new/fixtures/raw/cube_SD_10bit_5f/2.stoneimage +0 -0
  26. data/test_new/fixtures/raw/cube_SD_10bit_5f/3.stoneimage +0 -0
  27. data/test_new/fixtures/raw/cube_SD_10bit_5f/4.stoneimage +0 -0
  28. data/test_new/fixtures/raw/cube_SD_12bitP_5f/0.stoneimage +0 -0
  29. data/test_new/fixtures/raw/cube_SD_12bitP_5f/1.stoneimage +0 -0
  30. data/test_new/fixtures/raw/cube_SD_12bitP_5f/2.stoneimage +0 -0
  31. data/test_new/fixtures/raw/cube_SD_12bitP_5f/3.stoneimage +0 -0
  32. data/test_new/fixtures/raw/cube_SD_12bitP_5f/4.stoneimage +0 -0
  33. data/test_new/fixtures/raw/cube_SD_12bitU_5f/0.stoneimage +0 -0
  34. data/test_new/fixtures/raw/cube_SD_12bitU_5f/1.stoneimage +0 -0
  35. data/test_new/fixtures/raw/cube_SD_12bitU_5f/2.stoneimage +0 -0
  36. data/test_new/fixtures/raw/cube_SD_12bitU_5f/3.stoneimage +0 -0
  37. data/test_new/fixtures/raw/cube_SD_12bitU_5f/4.stoneimage +0 -0
  38. data/test_new/fixtures/raw/cube_SD_8bit_8f/0.stoneimage +0 -0
  39. data/test_new/fixtures/raw/cube_SD_8bit_8f/1.stoneimage +0 -0
  40. data/test_new/fixtures/raw/cube_SD_8bit_8f/2.stoneimage +0 -0
  41. data/test_new/fixtures/raw/cube_SD_8bit_8f/3.stoneimage +0 -0
  42. data/test_new/fixtures/raw/cube_SD_8bit_8f/4.stoneimage +0 -0
  43. data/test_new/fixtures/raw/cube_SD_8bit_8f/5.stoneimage +0 -0
  44. data/test_new/fixtures/raw/cube_SD_8bit_8f/6.stoneimage +0 -0
  45. data/test_new/fixtures/raw/cube_SD_8bit_8f/7.stoneimage +0 -0
  46. data/{test/wiretap-images/b1.stonesound → test_new/fixtures/raw-snd/simple.stonesound} +0 -0
  47. data/{test/wiretap-images/output.wav → test_new/fixtures/snd/simple-wave.wav} +0 -0
  48. data/test_new/test_audio_conversions.rb +28 -0
  49. data/test_new/test_image_conversions.rb +132 -0
  50. data/test_new/test_parts/connect_to_test_host.rb +27 -0
  51. data/test_new/test_parts/constants.rb +7 -0
  52. data/test_new/test_parts/create_test_project.rb +37 -0
  53. data/test_new/test_parts/raw_formats_and_uploads.rb +170 -0
  54. data/test_new/test_parts/server_list.rb +20 -0
  55. data/test_new/test_parts/simple_node_lookup_and_browsing.rb +76 -0
  56. data/test_new/test_suite.rb +70 -0
  57. data/{test/convert.rb → test_new/test_thread_worker.rb} +2 -3
  58. metadata +71 -61
  59. data/ext/bmp.cpp +0 -65
  60. data/ext/image.h +0 -27
  61. data/ext/ppm.cpp +0 -132
  62. data/ext/sgi.cpp +0 -69
  63. data/test/audio.rb +0 -27
  64. data/test/image.rb +0 -101
  65. data/test/read_frames.rb +0 -142
  66. data/test/wiretap-images/32bit.stoneimage +0 -621
  67. data/test/wiretap-images/36bit.stoneimage +0 -1036
  68. data/test/wiretap-images/48bit.stoneimage +1 -800
  69. data/test/wiretap-images/a.stoneimage +0 -0
  70. data/test/wiretap-images/a0.stoneimage +0 -0
  71. data/test/wiretap-images/a1.stoneimage +0 -0
  72. data/test/wiretap-images/a2.stoneimage +0 -0
  73. data/test/wiretap-images/a3.stoneimage +0 -0
  74. data/test/wiretap-images/a4.stoneimage +0 -0
  75. data/test/wiretap-images/importable-seq/00000001.ppm +0 -0
  76. data/test/wiretap-images/importable-seq/00000002.ppm +0 -0
  77. data/test/wiretap-images/importable-seq/00000003.ppm +0 -0
  78. data/test/wiretap-images/importable-seq/00000004.ppm +0 -0
  79. data/test/wiretap-images/importable-seq/00000005.ppm +0 -0
  80. data/test/wiretap-images/importable-seq/00000006.ppm +0 -0
  81. data/test/wiretap-images/importable-seq/00000007.ppm +0 -0
  82. data/test/wiretap-images/importable-seq/00000008.ppm +0 -0
  83. data/test/wiretap-images/importable-seq/00000009.ppm +0 -0
  84. data/test/wiretap-images/importable-seq/00000010.ppm +0 -0
  85. data/test/wiretap-images/importable-seq/00000011.ppm +0 -0
  86. data/test/wiretap-images/importable-seq/00000012.ppm +0 -0
  87. data/test/wiretap-images/monsters_001.tif +0 -0
  88. data/test/wiretap-images/monsters_002.tif +0 -0
  89. data/test/wiretap-images/monsters_003.tif +0 -0
  90. data/test/wiretap-images/output.mov +0 -0
  91. data/test/write_frames.rb +0 -82
data/README CHANGED
@@ -24,7 +24,8 @@ For sound files:
24
24
  === Running the unit tests
25
25
 
26
26
  Define a RUBY_WIRETAP_TEST_HOST environment variable that will contain the hostname or IP address
27
- of your IFFS system. Make a PAL 720x576 8-bit project on the system and name it "RubyWiretapTest".
27
+ of your IFFS system. If you are running versions EARLIER than 2007 you will also have to
28
+ make a PAL 720x576 8-bit project on the system and name it "RubyWiretapTest".
28
29
 
29
30
  Run rake.
30
31
 
data/ext/Makefile CHANGED
@@ -4,55 +4,58 @@ SHELL = /bin/sh
4
4
  #### Start of system configuration section. ####
5
5
 
6
6
  srcdir = .
7
- topdir = /opt/local/lib/ruby/1.8/i686-darwin8.8.3
7
+ topdir = /usr/local/lib/ruby/1.8/powerpc-darwin8.8.0
8
8
  hdrdir = $(topdir)
9
9
  VPATH = $(srcdir):$(topdir):$(hdrdir)
10
- prefix = $(DESTDIR)/opt/local
11
- exec_prefix = $(DESTDIR)/opt/local
10
+ prefix = $(DESTDIR)/usr/local
11
+ exec_prefix = $(DESTDIR)/usr/local
12
12
  sitedir = $(prefix)/lib/ruby/site_ruby
13
13
  rubylibdir = $(libdir)/ruby/$(ruby_version)
14
+ docdir = $(datarootdir)/doc/$(PACKAGE)
15
+ dvidir = $(docdir)
16
+ datarootdir = $(prefix)/share
14
17
  archdir = $(rubylibdir)/$(arch)
15
18
  sbindir = $(exec_prefix)/sbin
16
- vendordir = $(prefix)/lib/ruby/vendor_ruby
17
- datadir = $(prefix)/share
19
+ psdir = $(docdir)
20
+ localedir = $(datarootdir)/locale
21
+ htmldir = $(docdir)
22
+ datadir = $(datarootdir)
18
23
  includedir = $(prefix)/include
19
- infodir = $(prefix)/info
24
+ infodir = $(datarootdir)/info
20
25
  sysconfdir = $(prefix)/etc
21
- mandir = $(DESTDIR)/opt/local/share/man
22
- libdir = $(DESTDIR)/opt/local/lib
26
+ mandir = $(datarootdir)/man
27
+ libdir = $(DESTDIR)/usr/local/lib
23
28
  sharedstatedir = $(prefix)/com
24
29
  oldincludedir = $(DESTDIR)/usr/include
30
+ pdfdir = $(docdir)
25
31
  sitearchdir = $(sitelibdir)/$(sitearch)
26
- vendorarchdir = $(vendorlibdir)/$(vendorarch)
27
32
  bindir = $(exec_prefix)/bin
28
33
  localstatedir = $(prefix)/var
29
- vendorlibdir = $(vendordir)/$(ruby_version)
30
34
  sitelibdir = $(sitedir)/$(ruby_version)
31
35
  libexecdir = $(exec_prefix)/libexec
32
36
 
33
37
  CC = g++
34
- LIBRUBY = $(LIBRUBY_SO)
38
+ LIBRUBY = $(LIBRUBY_A)
35
39
  LIBRUBY_A = lib$(RUBY_SO_NAME)-static.a
36
- LIBRUBYARG_SHARED = -l$(RUBY_SO_NAME)
40
+ LIBRUBYARG_SHARED =
37
41
  LIBRUBYARG_STATIC = -l$(RUBY_SO_NAME)-static
38
42
 
39
43
  RUBY_EXTCONF_H =
40
- CFLAGS = -fno-common -O -pipe -I/opt/local/include -fno-common -pipe -fno-common -I../../wiretap_api//api -Wall
41
- INCFLAGS = -I. -I. -I/opt/local/lib/ruby/1.8/i686-darwin8.8.3 -I.
42
- CPPFLAGS = -DHAVE_WIRETAPCLIENTAPI_H -DHAVE_SNDFILE_H -O -pipe -I/opt/local/include
44
+ CFLAGS = -fno-common -g -O2 -pipe -fno-common -I/Code/wiretap-api-stable/api -I/opt/local/include -I/opt/local/lib -Wall
45
+ INCFLAGS = -I. -I. -I/usr/local/lib/ruby/1.8/powerpc-darwin8.8.0 -I.
46
+ CPPFLAGS = -DHAVE_WIRETAPCLIENTAPI_H -DHAVE_SNDFILE_H
43
47
  CXXFLAGS = $(CFLAGS)
44
- DLDFLAGS = -L/opt/local/lib -L../../wiretap_api//lib/dbg/MACOSX/fat/Darwin_8_3_0/GCC_4_0_1/
45
- LDSHARED = cc -dynamic -bundle -undefined suppress -flat_namespace
48
+ DLDFLAGS = -L/Code/wiretap-api-stable/libs/Mac/OSX/gcc_3.3/dbg -L/usr/local/lib -L/opt/local/lib
49
+ LDSHARED = g++ -dynamic -bundle -undefined suppress -flat_namespace
46
50
  AR = ar
47
51
  EXEEXT =
48
52
 
49
53
  RUBY_INSTALL_NAME = ruby
50
54
  RUBY_SO_NAME = ruby
51
- arch = i686-darwin8.8.3
52
- sitearch = i686-darwin8.8.3
53
- vendorarch = i686-darwin8.8.3
55
+ arch = powerpc-darwin8.8.0
56
+ sitearch = powerpc-darwin8.8.0
54
57
  ruby_version = 1.8
55
- ruby = /opt/local/bin/ruby
58
+ ruby = /usr/local/bin/ruby
56
59
  RUBY = $(ruby)
57
60
  RM = rm -f
58
61
  MAKEDIRS = mkdir -p
@@ -76,9 +79,9 @@ extout =
76
79
  extout_prefix =
77
80
  target_prefix =
78
81
  LOCAL_LIBS =
79
- LIBS = $(LIBRUBYARG_SHARED) -lwiretapClientAPI -lsndfile -lpthread -ldl -lobjc
80
- SRCS = audio_format.cpp bmp.cpp format.cpp image_format.cpp node.cpp nodechildren.cpp nodeframes.cpp nodemetadata.cpp ppm.cpp server.cpp serverlist.cpp sgi.cpp thread_worker.cpp wiretap.cpp
81
- OBJS = audio_format.o bmp.o format.o image_format.o node.o nodechildren.o nodeframes.o nodemetadata.o ppm.o server.o serverlist.o sgi.o thread_worker.o wiretap.o
82
+ LIBS = -lwiretapClientAPI -lsndfile -lpthread -ldl -lobjc
83
+ SRCS = audio_format.cpp format.cpp frame_io.cpp image_format.cpp image_io.cpp node.cpp nodechildren.cpp nodeframes.cpp nodemetadata.cpp server.cpp serverlist.cpp thread_worker.cpp wiretap.cpp
84
+ OBJS = audio_format.o format.o frame_io.o image_format.o image_io.o node.o nodechildren.o nodeframes.o nodemetadata.o server.o serverlist.o thread_worker.o wiretap.o
82
85
  TARGET = wiretap_bin
83
86
  DLLIB = $(TARGET).bundle
84
87
  EXTSTATIC =
data/ext/audio_format.cpp CHANGED
@@ -94,7 +94,7 @@ int wiretap_write_audio_frame(int samples, int rate, int bps, ID type, unsigned
94
94
  SNDFILE *input = sf_open_virtual(&v_io, SFM_READ, &info, &vf);
95
95
 
96
96
  if(!input) {
97
- THROW("Couldn't open frame for reading");
97
+ THROW("Couldn't open audio frame for reading");
98
98
  }
99
99
 
100
100
  std::auto_ptr<float> output_items(new float[item_count]);
@@ -106,20 +106,20 @@ int wiretap_write_audio_frame(int samples, int rate, int bps, ID type, unsigned
106
106
  sf_close(input);
107
107
  if(error) {
108
108
  output_items.release();
109
- THROW("Waited to read %d frames, got %d: %s", item_count, size, error);
109
+ THROW("Did not reach %d frames, got %d: %s", item_count, size, error);
110
110
  }
111
111
 
112
112
  SF_INFO out_info = info;
113
113
  out_info.format = SF_FORMAT_AIFF | SF_FORMAT_PCM_16;
114
114
  if(!sf_format_check(&out_info)) {
115
115
  output_items.release();
116
- THROW("Invalid format provided for output file");
116
+ THROW("Invalid format provided for audio output file");
117
117
  }
118
118
 
119
119
  SNDFILE *output = sf_open(filename, SFM_RDWR, &out_info);
120
120
  if(!output) {
121
121
  output_items.release();
122
- THROW("Couldn't open file %s for write", filename);
122
+ THROW("Couldn't open file %s for writing", filename);
123
123
  }
124
124
  int out_size = sf_write_float(output, output_items.get(), item_count);
125
125
  output_items.release();
@@ -158,7 +158,10 @@ static VALUE wiretap_get_audio_format(VALUE self, VALUE filename) {
158
158
  return Data_Wrap_Struct(cAudioFormat, 0, wiretap_format_free, new WireTapAudioFormat(audio_format));
159
159
  }
160
160
 
161
- static VALUE wiretap_audio_import_music(VALUE self, VALUE filename) {
161
+ /*
162
+ * Importing music is possible on Audio clips
163
+ */
164
+ static VALUE wiretap_audio_import_audio_file(VALUE self, VALUE filename) {
162
165
  Check_Type(filename, T_STRING);
163
166
 
164
167
  SF_INFO sfinfo;
@@ -181,7 +184,7 @@ static VALUE wiretap_audio_import_music(VALUE self, VALUE filename) {
181
184
  return self;
182
185
  }
183
186
 
184
- /* This is called on node. Not on NodeFrames */
187
+ /* This is called on the node itself, but not on NodeFrames */
185
188
 
186
189
  static VALUE wiretap_audio_dump(VALUE self, VALUE file) {
187
190
  WireTapNodeHandle* node;
@@ -212,13 +215,12 @@ static VALUE wiretap_audio_dump(VALUE self, VALUE file) {
212
215
 
213
216
  #endif /* HAVE_SNDFILE_H */
214
217
 
215
-
216
218
  void Init_audio_format() {
217
219
  #ifdef HAVE_SNDFILE_H
218
220
  rb_define_singleton_method(mWiretap, "dump_audio_data", VALUEFUNC(wiretap_dump_audio_data), 6);
219
221
  rb_define_singleton_method(mWiretap, "audio_format", VALUEFUNC(wiretap_get_audio_format), 1);
220
222
 
221
- rb_define_method(cAudio, "import_music", VALUEFUNC(wiretap_audio_import_music), 1);
223
+ rb_define_method(cAudio, "import_audio!", VALUEFUNC(wiretap_audio_import_audio_file), 1);
222
224
  rb_define_method(cAudio, "dump", VALUEFUNC(wiretap_audio_dump), 1);
223
225
  #endif /* HAVE_SNDFILE_H */
224
226
  }
data/ext/charstream.h ADDED
@@ -0,0 +1,41 @@
1
+ #ifndef _CHARSTREAM_H_
2
+ #define _CHARSTREAM_H_
3
+ #include <stdio.h>
4
+
5
+ class charstream {
6
+ public:
7
+ charstream();
8
+ virtual void write_char(unsigned char channel);
9
+ virtual ~charstream();
10
+
11
+ void write_int32_le(int value);
12
+ void write_int32_be(int value);
13
+ void write_int16_le(short value);
14
+ void write_int16_be(short value);
15
+ void write_string(char* value);
16
+ };
17
+
18
+ class memstream : public charstream {
19
+ unsigned char* ptr;
20
+ public:
21
+ memstream(unsigned char* _ptr);
22
+ void write_char(unsigned char channel);
23
+ };
24
+
25
+ class filestream : public charstream {
26
+ FILE* f;
27
+ public:
28
+ filestream(FILE* _f);
29
+ void write_char(unsigned char channel);
30
+ };
31
+
32
+ class filestream_bgr : public charstream {
33
+ int count;
34
+ unsigned char buffer[3];
35
+ FILE* f;
36
+ public:
37
+ filestream_bgr(FILE* _f);
38
+ void write_char(unsigned char channel);
39
+ };
40
+
41
+ #endif /* _CHARSTREAM_H_ */
data/ext/extconf.rb CHANGED
@@ -6,11 +6,10 @@ CONFIG["CPP"] = "g++ -E "
6
6
  CONFIG["CC"] = "g++ "
7
7
  CONFIG["LDSHARED"].gsub!(/^cc /,"g++ ")
8
8
 
9
- #@wiretap_placements = [ "../../wiretap_api", "/Code/wiretap-api"]
10
9
  @wiretap_placements = []
11
-
12
- @includes = []
13
- @libraries = []
10
+ @includes = ["/opt/local/include", "/opt/local/lib", ]
11
+ @libraries = ["/usr/local/lib", "/opt/local/lib"]
12
+ @wiretap_placements << ENV['WIRETAP_INSTALL_DIR'] if ENV['WIRETAP_INSTALL_DIR']
14
13
 
15
14
  OptionParser.new do |opts|
16
15
  opts.on("-S PATH", "--sndfile-dir=PATH", "Prefix, where libsndfile is installed: /usr/local or /opt/local") do |path|
@@ -67,12 +66,12 @@ end
67
66
  $CFLAGS << include_flags
68
67
  $LDFLAGS << library_flags
69
68
 
70
- have_header "WireTapClientAPI.h"
69
+ have_header "WireTapClientAPI.h" or raise "We must have the Wiretap client header. Check the --wiretap-dir parameter"
71
70
  unless have_header("sndfile.h") && have_library("sndfile")
72
71
  puts "*********************"
73
- puts "You don't have libsndfile installed. You can use wiretap ruby binding without it,"
74
- puts "but You will not have support of audio."
75
- puts "If You install libsndfile, reinstall gem after it."
72
+ puts "You don't have libsndfile installed. You can use wiretap ruby bindings without it,"
73
+ puts "but without audio support. If you will be installing libsndfile, recompile the gem afterwards."
74
+ puts "Verify if you have audio by calling Wiretap::supports_audio?"
76
75
  end
77
76
  have_library "wiretapClientAPI", "WireTapClientInit" do <<-SRC
78
77
  #include <WireTapClientAPI.h>
@@ -81,5 +80,4 @@ int main(void) {
81
80
  }
82
81
  SRC
83
82
  end
84
- create_makefile "wiretap_bin"
85
-
83
+ create_makefile "wiretap_bin"
data/ext/frame_io.cpp ADDED
@@ -0,0 +1,120 @@
1
+ #include "frame_io.h"
2
+
3
+ FrameIO::FrameIO(unsigned char* _frame, int _width, int _height) {
4
+ frame = _frame;
5
+ width = _width;
6
+ height = _height;
7
+ length = 0;
8
+ }
9
+
10
+ FrameIO::~FrameIO() {}
11
+
12
+ FrameIO* FrameIO::decoder(unsigned char* frame, int width, int height, int bpp) {
13
+ switch(bpp) {
14
+ case 24: return new FrameIO_24(frame, width, height);
15
+ case 30:
16
+ case 32: return new FrameIO_32(frame, width, height);
17
+ case 36: return new FrameIO_36(frame, width, height);
18
+ case 48: return new FrameIO_48(frame, width, height);
19
+ }
20
+ return NULL;
21
+ }
22
+
23
+ unsigned char* FrameIO::get_frame() { return frame; }
24
+
25
+
26
+ FrameIO_24::FrameIO_24(unsigned char* _frame, int _width, int _height) : FrameIO(_frame, _width, _height) {
27
+ length = width*height*3;
28
+ }
29
+
30
+ void FrameIO_24::decode(charstream& writer, bool bit16) {
31
+ for(size_t index = 0; index < length; index++) {
32
+ writer.write_char(frame[index]);
33
+ // TODO: Here is only bigendian encoding
34
+ if(bit16) writer.write_char(0);
35
+ }
36
+ }
37
+
38
+ FrameIO_32::FrameIO_32(unsigned char* _frame, int _width, int _height) : FrameIO(_frame, _width, _height) {
39
+ length = width*height*4;
40
+ }
41
+
42
+ void FrameIO_32::decode(charstream& writer, bool bit16) {
43
+ unsigned char* frame = get_frame();
44
+ for(size_t index = 0; index < length; index += 4) {
45
+ short r = (short(frame[0]) << 2) + (frame[1] >> 6);
46
+ short g = (short(frame[1]) << 2) + (frame[2] >> 6);
47
+ short b = (short(frame[2]) << 4) + (frame[3] >> 4);
48
+ if(bit16) {
49
+ writer.write_int16_be(r);
50
+ writer.write_int16_be(g);
51
+ writer.write_int16_be(b);
52
+ } else {
53
+ writer.write_char((r >> 2) & 0xFF);
54
+ writer.write_char((g >> 2) & 0xFF);
55
+ writer.write_char((b >> 2) & 0xFF);
56
+ }
57
+ frame += 4;
58
+ }
59
+ }
60
+
61
+ FrameIO_36::FrameIO_36(unsigned char* _frame, int _width, int _height) : FrameIO(_frame, _width, _height) {
62
+ length = width*height*9/2;
63
+ }
64
+ void FrameIO_36::decode(charstream& writer, bool bit16) {
65
+ unsigned char* frame = get_frame();
66
+ int orphan_index = 0;
67
+ int orphan[3*6]; //куски, которые пропускаем
68
+
69
+ int pixelnum = 0;
70
+
71
+ for(size_t index = 0; index < length*2/9; index++) {
72
+ if (pixelnum == 6) //7й пиксель собираем и пропущеных кусков
73
+ {
74
+ writer.write_char(((orphan[4] & 0xF) << 4) + (orphan[2] & 0xF)); // R
75
+ writer.write_char(((orphan[5] & 0xF) << 4) + (orphan[3] & 0xF)); // G
76
+ writer.write_char(((orphan[10] & 0xF) << 4) + (orphan[8] & 0xF));// B
77
+
78
+ pixelnum++;
79
+ continue;
80
+ }
81
+
82
+ if (pixelnum == 7) //8й пиксель тоже собираем из пропущеных кусков
83
+ {
84
+ writer.write_char(((orphan[11] & 0xF) << 4) + (orphan[9] & 0xF)); // R
85
+ writer.write_char(((orphan[16] & 0xF) << 4) + (orphan[14] & 0xF));// G
86
+ writer.write_char(((orphan[17] & 0xF) << 4) + (orphan[15] & 0xF));// B
87
+
88
+ pixelnum = 0;
89
+ orphan_index = 0;
90
+
91
+ continue;
92
+ }
93
+
94
+ writer.write_char(*frame++); // R
95
+ orphan[orphan_index++] = *frame++;
96
+
97
+ writer.write_char(*frame++); // G
98
+ orphan[orphan_index++] = *frame++;
99
+
100
+ writer.write_char(*frame++); // B
101
+ orphan[orphan_index++] = *frame++;
102
+
103
+ pixelnum++;
104
+ }
105
+ }
106
+
107
+ FrameIO_48::FrameIO_48(unsigned char* _frame, int _width, int _height) : FrameIO(_frame, _width, _height) {
108
+ length = width*height*6;
109
+ }
110
+ void FrameIO_48::decode(charstream& writer, bool bit16) {
111
+ for(size_t index = 0; index < length / 6; index++) {
112
+ writer.write_char(frame[index*6 + 0]);
113
+ if(bit16) writer.write_char(frame[index*6 + 1]);
114
+ writer.write_char(frame[index*6 + 2]);
115
+ if(bit16) writer.write_char(frame[index*6 + 3]);
116
+ writer.write_char(frame[index*6 + 4]);
117
+ if(bit16) writer.write_char(frame[index*6 + 5]);
118
+ }
119
+ }
120
+
data/ext/frame_io.h ADDED
@@ -0,0 +1,45 @@
1
+ #ifndef _FRAME_IO_H_
2
+ #define _FRAME_IO_H_
3
+ #include "charstream.h"
4
+ #include "wiretap.h"
5
+
6
+
7
+ class FrameIO {
8
+ public:
9
+ FrameIO(unsigned char* _frame, int width, int height);
10
+ virtual void decode(charstream& writer, bool bit16 = false) = 0;
11
+ virtual ~FrameIO();
12
+ static FrameIO* decoder(unsigned char* frame, int width, int height, int bpp);
13
+ unsigned char* get_frame();
14
+ protected:
15
+ unsigned char* frame;
16
+ size_t length;
17
+ int width;
18
+ int height;
19
+ };
20
+
21
+ class FrameIO_24 : public FrameIO {
22
+ public:
23
+ FrameIO_24(unsigned char* _frame, int width, int height);
24
+ virtual void decode(charstream& writer, bool bit16 = false);
25
+ };
26
+
27
+ class FrameIO_32 : public FrameIO {
28
+ public:
29
+ FrameIO_32(unsigned char* _frame, int width, int height);
30
+ virtual void decode(charstream& writer, bool bit16 = false);
31
+ };
32
+
33
+ class FrameIO_36 : public FrameIO {
34
+ public:
35
+ FrameIO_36(unsigned char* _frame, int width, int height);
36
+ virtual void decode(charstream& writer, bool bit16 = false);
37
+ };
38
+
39
+ class FrameIO_48 : public FrameIO {
40
+ public:
41
+ FrameIO_48(unsigned char* _frame, int width, int height);
42
+ virtual void decode(charstream& writer, bool bit16 = false);
43
+ };
44
+
45
+ #endif /* _FRAME_IO_H_ */
data/ext/image_format.cpp CHANGED
@@ -1,194 +1,74 @@
1
1
  #include "wiretap.h"
2
2
 
3
- enum {IMAGE_BMP, IMAGE_SGI};
4
- int img_format = IMAGE_SGI;
5
-
6
-
7
-
8
- static int wiretap_reduce_frame_bits24(const unsigned char* frame, int byte_length, bitstream_writer writer, void *data) {
9
- for(int index = 0; index < byte_length; index++) {
10
- writer(data, frame[index]);
11
- }
12
- return 0;
13
- }
14
-
15
-
16
- static int wiretap_reduce_frame_bits32(const unsigned char* frame, int byte_length, bitstream_writer writer, void *data) {
17
- for(int index = 0; index < byte_length; index += 4) {
18
- writer(data, frame[0]);
19
-
20
- writer(data, frame[1] << 2 | frame[2] >> 6);
21
-
22
- writer(data, frame[2] << 4 | frame[3] >> 4);
23
- frame += 4;
24
- }
25
- return 0;
26
- }
27
-
28
-
29
-
30
- static int wiretap_reduce_frame_bits36(const unsigned char* frame, int byte_length, bitstream_writer writer, void *data) {
31
-
32
- int orphan_index = 0;
33
- int orphan[3*6]; //куски, которые пропускаем
34
-
35
- int pixelnum = 0;
36
-
37
- for(int index = 0; index < byte_length*2/9; index++) {
38
- if (pixelnum == 6) //7й пиксель собираем и пропущеных кусков
39
- {
40
- writer(data, ((orphan[4] & 0xF) << 4) + (orphan[2] & 0xF)); // R
41
- writer(data, ((orphan[5] & 0xF) << 4) + (orphan[3] & 0xF)); // G
42
- writer(data, ((orphan[10] & 0xF) << 4) + (orphan[8] & 0xF));// B
43
-
44
- pixelnum++;
45
- continue;
46
- }
47
-
48
- if (pixelnum == 7) //8й пиксель тоже собираем из пропущеных кусков
49
- {
50
- writer(data, ((orphan[11] & 0xF) << 4) + (orphan[9] & 0xF)); // R
51
- writer(data, ((orphan[16] & 0xF) << 4) + (orphan[14] & 0xF));// G
52
- writer(data, ((orphan[17] & 0xF) << 4) + (orphan[15] & 0xF));// B
53
-
54
- pixelnum = 0;
55
- orphan_index = 0;
56
-
57
- continue;
58
- }
59
-
60
- writer(data, *frame++); // R
61
- orphan[orphan_index++] = *frame++;
62
-
63
- writer(data, *frame++); // G
64
- orphan[orphan_index++] = *frame++;
65
-
66
- writer(data, *frame++); // B
67
- orphan[orphan_index++] = *frame++;
68
-
69
- pixelnum++;
70
- }
71
- return 0;
72
- }
73
-
74
- static int wiretap_reduce_frame_bits48(const unsigned char* frame, int byte_length, bitstream_writer writer, void* data) {
75
- for(int index = 0; index < byte_length / 6; index++) {
76
- writer(data, frame[index*6 + 0]);
77
- writer(data, frame[index*6 + 2]);
78
- writer(data, frame[index*6 + 4]);
79
- }
80
- return 0;
81
- }
82
3
 
83
4
  bool wiretap_write_image_frame(int width, int height, int bpp, unsigned char* frame, const char* filename) {
84
- FILE *f = fopen(filename, "w+");
85
- if(!f) {
86
- THROW("Couldn't open file for dump: %s", filename);
87
- }
5
+ WireTapClipFormat format;
6
+ format.setWidth(width);
7
+ format.setHeight(height);
8
+ format.setBitsPerPixel(bpp);
88
9
 
89
- switch(img_format) {
90
- case IMAGE_SGI: {
91
- wiretap_write_frame_sgi(width, height, bpp, frame, f);
92
- break;
93
- }
94
- case IMAGE_BMP: {
95
- wiretap_write_frame_bmp(width, height, bpp, frame, f);
96
- break;
97
- }
98
- default: {
99
- fclose(f);
100
- THROW("Error. Wrong internal format provided: %d", img_format);
101
- }
10
+ std::auto_ptr<ImageIO> image(ImageIO::open(filename, format, false));
11
+ if(!image.get()) {
12
+ THROW("Couldn't guess image format for file: %s", filename);
102
13
  }
103
- fclose(f);
14
+ image->write_data(frame);
104
15
  return true;
105
16
  }
106
17
 
107
18
 
108
- void write_to_memory(void *stream, unsigned char channel) {
109
- memstream* data = (memstream *)stream;
110
- *data->ptr++ = channel;
111
- }
112
-
113
- void write_to_file(void *stream, unsigned char channel) {
114
- filestream* data = (filestream *)stream;
115
- fwrite(&channel, sizeof(channel), 1, data->f);
116
- }
117
-
118
-
119
-
120
- int reduced_frame_length(int byte_length, int bpp) {
121
- const int bits_in_byte = 8;
122
- const int bytes_in_pixel = 3;
123
- // bpp/bits_in_byte - number of bytes per pixel in income frame. Maybe 3 (in case of 24bpp) or 4.5 (in case of 36bpp)
124
- // byte_length/bytes_per_pixel - number of pixels in income frame
125
- // number_pixels * 3 - number of pixels in outgoing frame
126
- // 3 * byte_length/bpp * bits_in_byte
127
- return (bytes_in_pixel * byte_length * bits_in_byte) / bpp;
128
- }
129
-
130
-
131
-
132
- int wiretap_write_image_data(int width, int height, int bpp, const unsigned char* frame, bitstream_writer writer, void *data) {
133
- switch(bpp) {
134
- case 24: {
135
- wiretap_reduce_frame_bits24(frame, width*height*3, writer, data);
136
- break;
137
- }
138
- case 30:
139
- case 32: {
140
- wiretap_reduce_frame_bits32(frame, width*height*4, writer, data);
141
- break;
142
- }
143
- case 36: {
144
- wiretap_reduce_frame_bits36(frame, width*height*9/2, writer, data);
145
- break;
146
- }
147
- case 48: {
148
- wiretap_reduce_frame_bits48(frame, width*height*6, writer, data);
149
- break;
150
- }
151
- default: {
152
- THROW("Unsupported color depth: %d", bpp);
153
- }
154
- }
155
- return 0;
156
- }
157
-
158
-
159
19
  VALUE wiretap_dump_image_data(VALUE self, VALUE width, VALUE height, VALUE bpp, VALUE raw, VALUE filename) {
160
20
  wiretap_write_image_frame(NUM2INT(width), NUM2INT(height), NUM2INT(bpp), (unsigned char* )STR(raw), CSTR(filename));
161
21
  return Qtrue;
162
22
  }
163
23
 
164
- VALUE wiretap_set_dump_image_format(VALUE self, VALUE format) {
165
- ID bmp, sgi, format_id;
166
- bmp = rb_intern("bmp");
167
- sgi = rb_intern("sgi");
168
- Check_Type(format, T_SYMBOL);
169
- format_id = SYM2ID(format);
170
-
171
- if(format_id == bmp ) {
172
- img_format = IMAGE_BMP;
173
- } else if(format_id == sgi) {
174
- img_format = IMAGE_SGI;
175
- } else {
176
- THROW("Unknown format");
24
+ /*
25
+ * Extract Wiretap clip format from image file. The format will inherit the bit depths of the image and allocate
26
+ * the framebuffer size into which the imported image will fit
27
+ *
28
+ * @clipformat = Wiretap::image_format("test/wiretap-images/01.ppm")
29
+ */
30
+ static VALUE wiretap_get_format(VALUE self, VALUE input) {
31
+ WireTapClipFormat format;
32
+ std::auto_ptr<ImageIO> image(ImageIO::open(CSTR(input), format));
33
+ if(!image.get()) {
34
+ THROW("Couldn't open file %s for reading", CSTR(input));
177
35
  }
178
- return self;
36
+ image->read_format();
37
+ VALUE clip_format = rb_funcall(cClipFormat, rb_intern("new"), 0);
38
+ DATA_PTR(clip_format) = new WireTapClipFormat(format);
39
+ return clip_format;
179
40
  }
180
41
 
181
- VALUE wiretap_get_dump_image_format(VALUE self) {
182
- switch(img_format) {
183
- case IMAGE_SGI: return ID2SYM(rb_intern("sgi"));
184
- case IMAGE_BMP: return ID2SYM(rb_intern("bmp"));
42
+ /*
43
+ * Convert a PPM file to an SGI file
44
+ *
45
+ * Wiretap::convert_image("test/wiretap-images/01.ppm", "/tmp/a.sgi")
46
+ */
47
+ static VALUE wiretap_convert_image(VALUE self, VALUE input, VALUE output) {
48
+ Check_Type(input, T_STRING);
49
+ Check_Type(output, T_STRING);
50
+
51
+ WireTapClipFormat format;
52
+ std::auto_ptr<ImageIO> image(ImageIO::open(CSTR(input), format));
53
+ if(!image.get()) {
54
+ image.release();
55
+ THROW("Couldn't open file %s for read", CSTR(input));
56
+ }
57
+ image->read_format();
58
+ std::auto_ptr<unsigned char> frame(image->read_data());
59
+
60
+ if(!wiretap_write_image_frame(format.width(), format.height(), format.bitsPerPixel(), frame.get(), CSTR(output))) {
61
+ rb_warn("Couldn't dump image to file %s", CSTR(output));
62
+ return Qfalse;
185
63
  }
186
- return Qnil;
64
+ return Qtrue;
187
65
  }
188
66
 
189
67
 
68
+
190
69
  void Init_image_format() {
70
+ rb_define_singleton_method(mWiretap, "convert_image", VALUEFUNC(wiretap_convert_image), 2);
71
+ rb_define_singleton_method(mWiretap, "image_format", VALUEFUNC(wiretap_get_format), 1);
191
72
  rb_define_singleton_method(mWiretap, "dump_image_data", VALUEFUNC(wiretap_dump_image_data), 5);
192
- rb_define_singleton_method(mWiretap, "dump_image_format=", VALUEFUNC(wiretap_set_dump_image_format), 1);
193
- rb_define_singleton_method(mWiretap, "dump_image_format", VALUEFUNC(wiretap_get_dump_image_format), 0);
73
+ rb_define_singleton_method(mWiretap, "convert_image", VALUEFUNC(wiretap_convert_image), 2);
194
74
  }