Credit Andrew - improve in-tree documentation
[goodguy/cinelerra.git] / cinelerra / vdevicempeg.C
1
2 /*
3  * CINELERRA
4  * Copyright (C) 2008 Adam Williams <broadcast at earthling dot net>
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
22 #include "asset.h"
23 #include "condition.h"
24 #include "file.inc"
25 #include "mwindow.h"
26 #include "record.h"
27 #include "videodevice.h"
28 #include "vdevicempeg.h"
29 #include "devicempeginput.h"
30
31
32 #include <unistd.h>
33 #include <stdint.h>
34 #include <string.h>
35
36 VDeviceMPEG::VDeviceMPEG(VideoDevice *device)
37  : VDeviceBase(device)
38 {
39         video_open = 0;
40         mpeg_input = 0;
41 }
42
43 VDeviceMPEG::~VDeviceMPEG()
44 {
45         close_all();
46 }
47
48 int VDeviceMPEG::open_input(char *name)
49 {
50         if( video_open ) return 0;
51         /* this is more like - try to open, since a broadcast signal may */
52         /*  take time to lock, or not even be there at all.  On success, */
53         /*  it updates the input config with the actual stream config. */
54         if( !mpeg_input ) {
55                 mpeg_input = get_mpeg_input();
56                 if( !mpeg_input ) return 1;
57                 device->channel->has_subchan = 1;
58                 device->channel->has_scanning = 1;
59                 device->channel->use_frequency = 1;
60                 if( name != 0 )
61                 {
62                         Channel *channel = device->new_input_source(name);
63                         channel->device_index = mpeg_input->get_device_number();
64                         channel->tuner = 0;
65                 }
66         }
67         int ret = 1;
68         if( !mpeg_input->src_stream() ) {
69                 int width = mpeg_input->video_width();
70                 int height = mpeg_input->video_height();
71                 double rate = mpeg_input->video_framerate();
72                 device->auto_update(rate, width, height);
73                 device->capturing = 1;
74                 video_open = 1;
75                 mpeg_input->src_unlock();
76                 ret = 0;
77         }
78         return ret;
79 }
80
81 int VDeviceMPEG::close_all()
82 {
83         video_open = 0;
84         if( mpeg_input ) {
85                 mpeg_input->put_mpeg_video();
86                 mpeg_input = 0;
87         }
88         return 0;
89 }
90
91 int VDeviceMPEG::read_buffer(VFrame *frame)
92 {
93         if( !video_open && open_input() ) return 1;
94         int result = mpeg_input->read_buffer(frame);
95         return result;
96 }
97
98 int VDeviceMPEG::get_best_colormodel(Asset *asset)
99 {
100         int result = mpeg_input ? mpeg_input->colormodel() : BC_YUV422P;
101         return result;
102 }
103
104 int VDeviceMPEG::drop_frames(int frames)
105 {
106         return !mpeg_input ? 1 : mpeg_input->drop_frames(frames);
107 }
108
109 double VDeviceMPEG::device_timestamp()
110 {
111         if( !video_open || !mpeg_input ) return -1.;
112         return mpeg_input->video_timestamp();
113 }
114
115 int VDeviceMPEG::start_toc(const char *path, const char *toc_path)
116 {
117         return !mpeg_input ? -1 : mpeg_input->start_toc(path, toc_path);
118 }
119
120 int VDeviceMPEG::start_record(int fd, int bsz)
121 {
122         return !mpeg_input ? -1 : mpeg_input->start_record(fd, bsz);
123 }
124
125 int VDeviceMPEG::stop_record()
126 {
127         return !mpeg_input ? -1 : mpeg_input->stop_record();
128 }
129
130 int VDeviceMPEG::total_video_streams()
131 {
132         return !mpeg_input ? -1 : mpeg_input->total_video_streams();
133 }
134
135
136 int VDeviceMPEG::set_channel(Channel *channel)
137 {
138         device->channel_changed = 0;
139         return !mpeg_input ? -1 : mpeg_input->set_channel(channel);
140 }
141
142 int VDeviceMPEG::set_captioning(int mode)
143 {
144         return !mpeg_input ? -1 : (mpeg_input->set_captioning(mode), 0);
145 }
146
147 int VDeviceMPEG::has_signal()
148 {
149         return !mpeg_input ? 0 : mpeg_input->has_signal();
150 }
151
152
153 int VDeviceMPEG::create_channeldb(ArrayList<Channel*> *channeldb)
154 {
155         return !mpeg_input ? 1 : mpeg_input->
156                 create_channeldb(channeldb);
157 }
158
159
160 int VDeviceMPEG::get_video_pid(int track)
161 {
162         return !mpeg_input ? 1 : mpeg_input->get_video_pid(track);
163 }
164
165 int VDeviceMPEG::get_video_info(int track, int &pid,
166                 double &framerate, int &width, int &height, char *title)
167 {
168         return !mpeg_input ? 1 : mpeg_input->
169                 get_video_info(track, pid, framerate, width, height, title);
170 }
171
172 int VDeviceMPEG::get_thumbnail(int stream, int64_t &position,
173                 unsigned char *&thumbnail, int &ww, int &hh)
174 {
175         return !mpeg_input ? 1 : mpeg_input->
176                 get_thumbnail(stream, position, thumbnail, ww, hh);
177 }
178
179 int VDeviceMPEG::set_skimming(int track, int skim, skim_fn fn, void *vp)
180 {
181         return !mpeg_input ? 1 : mpeg_input->
182                 set_skimming(track, skim, fn, vp);
183 }
184