1.3.2
by Teis Dreijer (NOT the hoff)
Import upstream version 1.0.0 |
1 |
/*
|
1.1.18
by Scott Evans
Import upstream version 1.3.6 |
2 |
* Copyright (C) 2011 Michael Lamothe
|
1.3.2
by Teis Dreijer (NOT the hoff)
Import upstream version 1.0.0 |
3 |
*
|
4 |
* This file is part of Me TV
|
|
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 Library 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., 51 Franklin Street, Fifth Floor Boston, MA 02110-1301, USA
|
|
19 |
*/
|
|
20 |
||
21 |
#include "scheduled_recording_manager.h" |
|
22 |
#include "application.h" |
|
23 |
||
1.1.14
by Scott Evans
Import upstream version 1.3.0 |
24 |
void ScheduledRecordingManager::initialise() |
1.3.2
by Teis Dreijer (NOT the hoff)
Import upstream version 1.0.0 |
25 |
{
|
26 |
g_static_rec_mutex_init(mutex.gobj()); |
|
27 |
}
|
|
28 |
||
29 |
void ScheduledRecordingManager::load(Data::Connection& connection) |
|
30 |
{
|
|
31 |
Glib::RecMutex::Lock lock(mutex); |
|
32 |
||
33 |
g_debug("Loading scheduled recordings"); |
|
1.1.15
by Scott Evans
Import upstream version 1.3.1 |
34 |
|
1.3.2
by Teis Dreijer (NOT the hoff)
Import upstream version 1.0.0 |
35 |
Data::Table table = get_application().get_schema().tables["scheduled_recording"]; |
36 |
Data::TableAdapter adapter(connection, table); |
|
37 |
||
38 |
Glib::ustring where = Glib::ustring::compose( |
|
1.1.12
by Michael Lamothe
Import upstream version 1.2.4 |
39 |
"((start_time + duration) > %1 OR recurring_type != 0)", time(NULL)); |
1.3.2
by Teis Dreijer (NOT the hoff)
Import upstream version 1.0.0 |
40 |
Data::DataTable data_table = adapter.select_rows(where, "start_time"); |
1.1.16
by Scott Evans
Import upstream version 1.3.4 |
41 |
|
42 |
dirty = false; |
|
1.3.2
by Teis Dreijer (NOT the hoff)
Import upstream version 1.0.0 |
43 |
|
44 |
scheduled_recordings.clear(); |
|
45 |
for (Data::Rows::iterator i = data_table.rows.begin(); i != data_table.rows.end(); i++) |
|
46 |
{
|
|
47 |
ScheduledRecording scheduled_recording; |
|
48 |
Data::Row& row = *i; |
|
49 |
||
50 |
scheduled_recording.scheduled_recording_id = row["scheduled_recording_id"].int_value; |
|
51 |
scheduled_recording.channel_id = row["channel_id"].int_value; |
|
52 |
scheduled_recording.description = row["description"].string_value; |
|
1.1.12
by Michael Lamothe
Import upstream version 1.2.4 |
53 |
scheduled_recording.recurring_type = row["recurring_type"].int_value; |
54 |
scheduled_recording.action_after = row["action_after"].int_value; |
|
1.3.2
by Teis Dreijer (NOT the hoff)
Import upstream version 1.0.0 |
55 |
scheduled_recording.start_time = row["start_time"].int_value; |
56 |
scheduled_recording.duration = row["duration"].int_value; |
|
57 |
scheduled_recording.device = row["device"].string_value; |
|
58 |
||
59 |
scheduled_recordings.push_back(scheduled_recording); |
|
1.1.16
by Scott Evans
Import upstream version 1.3.4 |
60 |
|
61 |
guint now = time(NULL); |
|
62 |
if(scheduled_recording.start_time + scheduled_recording.duration < now) |
|
63 |
dirty = true; |
|
1.3.2
by Teis Dreijer (NOT the hoff)
Import upstream version 1.0.0 |
64 |
}
|
1.1.15
by Scott Evans
Import upstream version 1.3.1 |
65 |
|
1.3.2
by Teis Dreijer (NOT the hoff)
Import upstream version 1.0.0 |
66 |
g_debug("Scheduled recordings loaded"); |
67 |
}
|
|
68 |
||
69 |
void ScheduledRecordingManager::save(Data::Connection& connection) |
|
70 |
{
|
|
1.1.15
by Scott Evans
Import upstream version 1.3.1 |
71 |
if (!dirty) |
72 |
{
|
|
73 |
g_debug("Scheduled recordings are not dirty, not saving"); |
|
74 |
return; |
|
75 |
}
|
|
1.1.16
by Scott Evans
Import upstream version 1.3.4 |
76 |
g_debug("Scheduled recordings are dirty, saving"); |
1.1.15
by Scott Evans
Import upstream version 1.3.1 |
77 |
|
1.3.2
by Teis Dreijer (NOT the hoff)
Import upstream version 1.0.0 |
78 |
Glib::RecMutex::Lock lock(mutex); |
79 |
||
1.1.8
by Teis Dreijer
Import upstream version 1.0.1 |
80 |
g_debug("Saving %d scheduled recordings", (int)scheduled_recordings.size()); |
1.3.2
by Teis Dreijer (NOT the hoff)
Import upstream version 1.0.0 |
81 |
|
82 |
Data::Table table = get_application().get_schema().tables["scheduled_recording"]; |
|
83 |
Data::DataTable data_table(table); |
|
84 |
for (ScheduledRecordingList::iterator i = scheduled_recordings.begin(); i != scheduled_recordings.end(); i++) |
|
85 |
{
|
|
86 |
ScheduledRecording& scheduled_recording = *i; |
|
1.1.16
by Scott Evans
Import upstream version 1.3.4 |
87 |
time_t now = time(NULL); |
1.1.12
by Michael Lamothe
Import upstream version 1.2.4 |
88 |
if (scheduled_recording.get_end_time() > now || scheduled_recording.recurring_type != 0) |
1.3.2
by Teis Dreijer (NOT the hoff)
Import upstream version 1.0.0 |
89 |
{
|
90 |
Data::Row row; |
|
1.1.12
by Michael Lamothe
Import upstream version 1.2.4 |
91 |
row.auto_increment = &(scheduled_recording.scheduled_recording_id); |
1.3.2
by Teis Dreijer (NOT the hoff)
Import upstream version 1.0.0 |
92 |
row["scheduled_recording_id"].int_value = scheduled_recording.scheduled_recording_id; |
93 |
row["channel_id"].int_value = scheduled_recording.channel_id; |
|
94 |
row["description"].string_value = scheduled_recording.description; |
|
1.1.12
by Michael Lamothe
Import upstream version 1.2.4 |
95 |
row["recurring_type"].int_value = scheduled_recording.recurring_type; |
96 |
row["action_after"].int_value = scheduled_recording.action_after; |
|
1.3.2
by Teis Dreijer (NOT the hoff)
Import upstream version 1.0.0 |
97 |
row["start_time"].int_value = scheduled_recording.start_time; |
98 |
row["duration"].int_value = scheduled_recording.duration; |
|
99 |
row["device"].string_value = scheduled_recording.device; |
|
1.1.12
by Michael Lamothe
Import upstream version 1.2.4 |
100 |
|
1.3.2
by Teis Dreijer (NOT the hoff)
Import upstream version 1.0.0 |
101 |
data_table.rows.add(row); |
102 |
}
|
|
1.1.12
by Michael Lamothe
Import upstream version 1.2.4 |
103 |
|
1.3.2
by Teis Dreijer (NOT the hoff)
Import upstream version 1.0.0 |
104 |
g_debug("Scheduled recording '%s' (%d) saved", scheduled_recording.description.c_str(), scheduled_recording.scheduled_recording_id); |
105 |
}
|
|
106 |
||
107 |
Data::TableAdapter adapter(connection, table); |
|
108 |
adapter.replace_rows(data_table); |
|
109 |
||
110 |
guint now = time(NULL); |
|
111 |
g_debug("Deleting old scheduled recordings ending before %d", now); |
|
1.1.12
by Michael Lamothe
Import upstream version 1.2.4 |
112 |
Glib::ustring where = Glib::ustring::compose("recurring_type != %1 AND (start_time + duration) < %2", SCHEDULED_RECORDING_RECURRING_TYPE_ONCE, now); |
113 |
data_table = adapter.select_rows(where, "start_time"); |
|
114 |
||
115 |
gboolean updated = false; |
|
116 |
for (Data::Rows::iterator i = data_table.rows.begin(); i != data_table.rows.end(); i++) |
|
117 |
{
|
|
118 |
Data::Row& row = *i; |
|
1.1.16
by Scott Evans
Import upstream version 1.3.4 |
119 |
g_debug("ScheduledRecordingManager::save/clear ID: %d", row["scheduled_recording_id"].int_value); |
1.1.12
by Michael Lamothe
Import upstream version 1.2.4 |
120 |
|
121 |
if(row["recurring_type"].int_value == SCHEDULED_RECORDING_RECURRING_TYPE_EVERYDAY) |
|
122 |
{
|
|
123 |
row["start_time"].int_value += 86400; |
|
124 |
}
|
|
125 |
else if(row["recurring_type"].int_value == SCHEDULED_RECORDING_RECURRING_TYPE_EVERYWEEK) |
|
126 |
{
|
|
127 |
row["start_time"].int_value += 604800; |
|
128 |
}
|
|
129 |
else if(row["recurring_type"].int_value == SCHEDULED_RECORDING_RECURRING_TYPE_EVERYWEEKDAY) |
|
130 |
{
|
|
131 |
time_t tim = row["start_time"].int_value; |
|
132 |
struct tm *ts; |
|
133 |
char buf[80]; |
|
134 |
ts = localtime(&tim); |
|
135 |
strftime(buf, sizeof(buf), "%w", ts); |
|
136 |
switch(atoi(buf)) |
|
137 |
{
|
|
138 |
case 5 : row["start_time"].int_value += 259200; break; |
|
139 |
case 6 : row["start_time"].int_value += 172800; break; |
|
140 |
default: row["start_time"].int_value += 86400; break; |
|
141 |
}
|
|
142 |
}
|
|
143 |
updated = true; |
|
144 |
}
|
|
145 |
if(updated) |
|
146 |
{
|
|
147 |
adapter.replace_rows(data_table); |
|
148 |
load(connection); |
|
149 |
}
|
|
150 |
Glib::ustring clause = Glib::ustring::compose("(start_time + duration) < %1 AND recurring_type = %2", now, SCHEDULED_RECORDING_RECURRING_TYPE_ONCE); |
|
1.3.2
by Teis Dreijer (NOT the hoff)
Import upstream version 1.0.0 |
151 |
adapter.delete_rows(clause); |
152 |
||
1.1.15
by Scott Evans
Import upstream version 1.3.1 |
153 |
dirty = false; |
154 |
||
1.3.2
by Teis Dreijer (NOT the hoff)
Import upstream version 1.0.0 |
155 |
g_debug("Scheduled recordings saved"); |
156 |
}
|
|
157 |
||
1.1.12
by Michael Lamothe
Import upstream version 1.2.4 |
158 |
void ScheduledRecordingManager::set_scheduled_recording(EpgEvent& epg_event) |
159 |
{
|
|
160 |
ScheduledRecording scheduled_recording; |
|
161 |
||
162 |
Application& application = get_application(); |
|
1.1.14
by Scott Evans
Import upstream version 1.3.0 |
163 |
guint before = configuration_manager.get_int_value("record_extra_before"); |
164 |
guint after = configuration_manager.get_int_value("record_extra_after"); |
|
1.1.16
by Scott Evans
Import upstream version 1.3.4 |
165 |
|
166 |
guint now = get_local_time(); |
|
1.1.12
by Michael Lamothe
Import upstream version 1.2.4 |
167 |
|
1.1.16
by Scott Evans
Import upstream version 1.3.4 |
168 |
scheduled_recording.channel_id = epg_event.channel_id; |
169 |
scheduled_recording.description = epg_event.get_title(); |
|
170 |
scheduled_recording.recurring_type = SCHEDULED_RECORDING_RECURRING_TYPE_ONCE; |
|
171 |
scheduled_recording.action_after = SCHEDULED_RECORDING_ACTION_AFTER_NONE; |
|
172 |
scheduled_recording.start_time = convert_to_utc_time(epg_event.start_time - (before * 60)); |
|
173 |
scheduled_recording.duration = epg_event.duration + ((before + after) * 60); |
|
174 |
scheduled_recording.device = ""; |
|
1.1.12
by Michael Lamothe
Import upstream version 1.2.4 |
175 |
|
176 |
set_scheduled_recording(scheduled_recording); |
|
177 |
}
|
|
178 |
||
1.1.15
by Scott Evans
Import upstream version 1.3.1 |
179 |
gboolean ScheduledRecordingManager::is_device_available(const Glib::ustring& device, const ScheduledRecording& scheduled_recording) |
180 |
{
|
|
181 |
Channel& channel = channel_manager.get_channel_by_id(scheduled_recording.channel_id); |
|
182 |
||
183 |
for (ScheduledRecordingList::iterator i = scheduled_recordings.begin(); i != scheduled_recordings.end(); i++) |
|
184 |
{
|
|
185 |
ScheduledRecording& current = *i; |
|
186 |
||
187 |
Channel& current_channel = channel_manager.get_channel_by_id(current.channel_id); |
|
188 |
||
189 |
if ( |
|
190 |
channel.transponder != current_channel.transponder && |
|
191 |
scheduled_recording.overlaps(current) && |
|
192 |
device == current.device |
|
193 |
)
|
|
194 |
{
|
|
1.1.18
by Scott Evans
Import upstream version 1.3.6 |
195 |
g_debug("Frontend '%s' is busy recording '%s'", device.c_str(), current.description.c_str()); |
1.1.15
by Scott Evans
Import upstream version 1.3.1 |
196 |
return false; |
197 |
}
|
|
198 |
}
|
|
199 |
||
200 |
g_debug("Found available frontend '%s'", device.c_str()); |
|
201 |
||
202 |
return true; |
|
203 |
}
|
|
204 |
||
205 |
void ScheduledRecordingManager::select_device(ScheduledRecording& scheduled_recording) |
|
206 |
{
|
|
207 |
g_debug("Looking for an available device for scheduled recording"); |
|
208 |
||
209 |
Channel& channel = channel_manager.get_channel_by_id(scheduled_recording.channel_id); |
|
210 |
||
211 |
FrontendList& frontends = device_manager.get_frontends(); |
|
212 |
for (FrontendList::iterator j = frontends.begin(); j != frontends.end(); j++) |
|
213 |
{
|
|
1.1.18
by Scott Evans
Import upstream version 1.3.6 |
214 |
Dvb::Frontend* device = (*j); |
215 |
const Glib::ustring& device_path = device->get_path(); |
|
216 |
||
217 |
if (device->get_frontend_type() != channel.transponder.frontend_type) |
|
218 |
{
|
|
219 |
g_debug("Device %s is the wrong type", device_path.c_str()); |
|
220 |
}
|
|
221 |
else
|
|
222 |
{
|
|
223 |
if (is_device_available(device_path, scheduled_recording)) |
|
1.1.15
by Scott Evans
Import upstream version 1.3.1 |
224 |
{
|
1.1.18
by Scott Evans
Import upstream version 1.3.6 |
225 |
scheduled_recording.device = device_path; |
226 |
||
227 |
if (stream_manager.has_display_stream()) |
|
228 |
{
|
|
229 |
Channel& display_channel = stream_manager.get_display_channel(); |
|
230 |
if (channel.transponder == display_channel.transponder) |
|
231 |
{
|
|
232 |
return; |
|
233 |
}
|
|
234 |
}
|
|
235 |
else
|
|
1.1.15
by Scott Evans
Import upstream version 1.3.1 |
236 |
{
|
237 |
return; |
|
238 |
}
|
|
239 |
||
1.1.18
by Scott Evans
Import upstream version 1.3.6 |
240 |
g_debug("Display channel is on a different transponder for '%s', looking for something better", device_path.c_str()); |
241 |
}
|
|
1.1.15
by Scott Evans
Import upstream version 1.3.1 |
242 |
}
|
243 |
}
|
|
244 |
}
|
|
245 |
||
1.3.2
by Teis Dreijer (NOT the hoff)
Import upstream version 1.0.0 |
246 |
void ScheduledRecordingManager::set_scheduled_recording(ScheduledRecording& scheduled_recording) |
247 |
{
|
|
248 |
Glib::RecMutex::Lock lock(mutex); |
|
1.1.12
by Michael Lamothe
Import upstream version 1.2.4 |
249 |
ScheduledRecordingList::iterator iupdated; |
250 |
gboolean updated = false; |
|
251 |
gboolean is_same = false; |
|
252 |
gboolean conflict = false; |
|
1.1.10
by Teis Dreijer
Import upstream version 1.1.2 |
253 |
|
254 |
g_debug("Setting scheduled recording"); |
|
255 |
||
1.1.14
by Scott Evans
Import upstream version 1.3.0 |
256 |
Channel& channel = channel_manager.get_channel_by_id(scheduled_recording.channel_id); |
1.1.12
by Michael Lamothe
Import upstream version 1.2.4 |
257 |
|
258 |
if (scheduled_recording.device.empty()) |
|
259 |
{
|
|
1.1.15
by Scott Evans
Import upstream version 1.3.1 |
260 |
select_device(scheduled_recording); |
261 |
||
262 |
if (scheduled_recording.device.empty()) |
|
1.1.12
by Michael Lamothe
Import upstream version 1.2.4 |
263 |
{
|
1.1.16
by Scott Evans
Import upstream version 1.3.4 |
264 |
Glib::ustring message = Glib::ustring::compose(_( |
265 |
"Failed to set scheduled recording for '%1' at %2: There are no devices available at that time"), |
|
266 |
scheduled_recording.description, scheduled_recording.get_start_time_text()); |
|
267 |
throw Exception(message); |
|
1.1.12
by Michael Lamothe
Import upstream version 1.2.4 |
268 |
}
|
269 |
||
1.1.15
by Scott Evans
Import upstream version 1.3.1 |
270 |
g_debug("Device selected: '%s'", scheduled_recording.device.c_str()); |
1.1.12
by Michael Lamothe
Import upstream version 1.2.4 |
271 |
}
|
272 |
||
273 |
for (ScheduledRecordingList::iterator i = scheduled_recordings.begin(); i != scheduled_recordings.end(); i++) |
|
1.3.2
by Teis Dreijer (NOT the hoff)
Import upstream version 1.0.0 |
274 |
{
|
275 |
ScheduledRecording& current = *i; |
|
276 |
||
1.1.14
by Scott Evans
Import upstream version 1.3.0 |
277 |
Channel& current_channel = channel_manager.get_channel_by_id(current.channel_id); |
1.1.10
by Teis Dreijer
Import upstream version 1.1.2 |
278 |
|
1.3.2
by Teis Dreijer (NOT the hoff)
Import upstream version 1.0.0 |
279 |
// Check for conflict
|
1.1.8
by Teis Dreijer
Import upstream version 1.0.1 |
280 |
if (current.scheduled_recording_id != scheduled_recording.scheduled_recording_id && |
1.1.10
by Teis Dreijer
Import upstream version 1.1.2 |
281 |
current_channel.transponder != channel.transponder && |
1.1.12
by Michael Lamothe
Import upstream version 1.2.4 |
282 |
scheduled_recording.device == current.device && |
1.1.8
by Teis Dreijer
Import upstream version 1.0.1 |
283 |
scheduled_recording.overlaps(current)) |
1.3.2
by Teis Dreijer (NOT the hoff)
Import upstream version 1.0.0 |
284 |
{
|
1.1.12
by Michael Lamothe
Import upstream version 1.2.4 |
285 |
conflict = true; |
1.3.2
by Teis Dreijer (NOT the hoff)
Import upstream version 1.0.0 |
286 |
Glib::ustring message = Glib::ustring::compose( |
287 |
_("Failed to save scheduled recording because it conflicts with another scheduled recording called '%1'."), |
|
288 |
current.description); |
|
289 |
throw Exception(message); |
|
290 |
}
|
|
291 |
||
1.1.12
by Michael Lamothe
Import upstream version 1.2.4 |
292 |
// Check if its an existing scheduled recording
|
1.3.2
by Teis Dreijer (NOT the hoff)
Import upstream version 1.0.0 |
293 |
if (scheduled_recording.scheduled_recording_id != 0 && |
294 |
scheduled_recording.scheduled_recording_id == current.scheduled_recording_id) |
|
295 |
{
|
|
296 |
g_debug("Updating scheduled recording"); |
|
297 |
updated = true; |
|
1.1.12
by Michael Lamothe
Import upstream version 1.2.4 |
298 |
iupdated = i; |
1.3.2
by Teis Dreijer (NOT the hoff)
Import upstream version 1.0.0 |
299 |
}
|
300 |
||
301 |
// Check if we are scheduling the same program
|
|
302 |
if (scheduled_recording.scheduled_recording_id == 0 && |
|
1.1.12
by Michael Lamothe
Import upstream version 1.2.4 |
303 |
current.channel_id == scheduled_recording.channel_id && |
304 |
current.start_time == scheduled_recording.start_time && |
|
305 |
current.duration == scheduled_recording.duration) |
|
1.3.2
by Teis Dreijer (NOT the hoff)
Import upstream version 1.0.0 |
306 |
{
|
307 |
Glib::ustring message = Glib::ustring::compose( |
|
308 |
_("Failed to save scheduled recording because you have already have a scheduled recording called '%1' which is scheduled for the same time on the same channel."), |
|
309 |
current.description); |
|
310 |
throw Exception(message); |
|
311 |
}
|
|
1.1.12
by Michael Lamothe
Import upstream version 1.2.4 |
312 |
|
313 |
if (current.scheduled_recording_id == scheduled_recording.scheduled_recording_id && |
|
314 |
current.recurring_type == scheduled_recording.recurring_type && |
|
315 |
current.action_after == scheduled_recording.action_after && |
|
316 |
current.channel_id == scheduled_recording.channel_id && |
|
317 |
current.start_time == scheduled_recording.start_time && |
|
318 |
current.duration == scheduled_recording.duration) |
|
319 |
{
|
|
320 |
is_same = true; |
|
321 |
}
|
|
322 |
}
|
|
323 |
||
324 |
// If there is an update an not conflict on scheduled recording, update it.
|
|
325 |
if (updated && !conflict && !is_same) |
|
326 |
{
|
|
327 |
ScheduledRecording& current = *iupdated; |
|
328 |
||
329 |
current.device = scheduled_recording.device; |
|
330 |
current.recurring_type = scheduled_recording.recurring_type; |
|
331 |
current.action_after = scheduled_recording.action_after; |
|
332 |
current.description = scheduled_recording.description; |
|
333 |
current.channel_id = scheduled_recording.channel_id; |
|
334 |
current.start_time = scheduled_recording.start_time; |
|
335 |
current.duration = scheduled_recording.duration; |
|
1.1.16
by Scott Evans
Import upstream version 1.3.4 |
336 |
dirty = true; |
1.3.2
by Teis Dreijer (NOT the hoff)
Import upstream version 1.0.0 |
337 |
}
|
338 |
||
339 |
// If the scheduled recording is new then add it
|
|
340 |
if (scheduled_recording.scheduled_recording_id == 0) |
|
341 |
{
|
|
342 |
g_debug("Adding scheduled recording"); |
|
343 |
scheduled_recordings.push_back(scheduled_recording); |
|
1.1.15
by Scott Evans
Import upstream version 1.3.1 |
344 |
dirty = true; |
1.3.2
by Teis Dreijer (NOT the hoff)
Import upstream version 1.0.0 |
345 |
}
|
346 |
||
347 |
// Have to save to update the scheduled recording ID
|
|
348 |
Application& application = get_application(); |
|
349 |
Data::Connection connection(application.get_database_filename()); |
|
350 |
save(connection); |
|
351 |
application.check_scheduled_recordings(); |
|
352 |
}
|
|
353 |
||
354 |
void ScheduledRecordingManager::remove_scheduled_recording(guint scheduled_recording_id) |
|
355 |
{
|
|
356 |
Glib::RecMutex::Lock lock(mutex); |
|
357 |
||
358 |
g_debug("Deleting scheduled recording %d", scheduled_recording_id); |
|
359 |
||
360 |
gboolean found = false; |
|
361 |
for (ScheduledRecordingList::iterator i = scheduled_recordings.begin(); i != scheduled_recordings.end() && !found; i++) |
|
362 |
{
|
|
363 |
ScheduledRecording& scheduled_recording = *i; |
|
364 |
if (scheduled_recording_id == scheduled_recording.scheduled_recording_id) |
|
365 |
{
|
|
366 |
g_debug("Deleting scheduled recording '%s' (%d)", |
|
367 |
scheduled_recording.description.c_str(), |
|
368 |
scheduled_recording.scheduled_recording_id); |
|
369 |
scheduled_recordings.erase(i); |
|
370 |
||
371 |
Data::Connection connection(get_application().get_database_filename()); |
|
372 |
Data::Table table = get_application().get_schema().tables["scheduled_recording"]; |
|
373 |
Data::TableAdapter adapter(connection, table); |
|
374 |
adapter.delete_row(scheduled_recording_id); |
|
375 |
||
376 |
found = true; |
|
1.1.15
by Scott Evans
Import upstream version 1.3.1 |
377 |
dirty = true; |
1.3.2
by Teis Dreijer (NOT the hoff)
Import upstream version 1.0.0 |
378 |
}
|
379 |
}
|
|
380 |
g_debug("Scheduled recording deleted"); |
|
381 |
||
382 |
get_application().check_scheduled_recordings(); |
|
383 |
}
|
|
384 |
||
1.1.12
by Michael Lamothe
Import upstream version 1.2.4 |
385 |
void ScheduledRecordingManager::remove_scheduled_recording(EpgEvent& epg_event) |
386 |
{
|
|
387 |
Glib::RecMutex::Lock lock(mutex); |
|
388 |
||
389 |
for (ScheduledRecordingList::iterator i = scheduled_recordings.begin(); i != scheduled_recordings.end(); i++) |
|
390 |
{
|
|
391 |
ScheduledRecording& scheduled_recording = *i; |
|
392 |
if (scheduled_recording.channel_id == epg_event.channel_id && |
|
393 |
scheduled_recording.is_in( |
|
394 |
convert_to_utc_time(epg_event.start_time), |
|
395 |
convert_to_utc_time(epg_event.get_end_time()))) |
|
396 |
{
|
|
397 |
remove_scheduled_recording(scheduled_recording.scheduled_recording_id); |
|
398 |
return; |
|
399 |
}
|
|
400 |
}
|
|
401 |
}
|
|
402 |
||
1.1.10
by Teis Dreijer
Import upstream version 1.1.2 |
403 |
ScheduledRecordingList ScheduledRecordingManager::check_scheduled_recordings() |
1.3.2
by Teis Dreijer (NOT the hoff)
Import upstream version 1.0.0 |
404 |
{
|
1.1.10
by Teis Dreijer
Import upstream version 1.1.2 |
405 |
ScheduledRecordingList results; |
406 |
||
1.1.16
by Scott Evans
Import upstream version 1.3.4 |
407 |
time_t now = time(NULL); |
408 |
||
1.3.2
by Teis Dreijer (NOT the hoff)
Import upstream version 1.0.0 |
409 |
g_debug("Checking scheduled recordings"); |
410 |
Glib::RecMutex::Lock lock(mutex); |
|
411 |
||
1.1.16
by Scott Evans
Import upstream version 1.3.4 |
412 |
g_debug("Now: %u", (guint)now); |
413 |
g_debug("Removing scheduled recordings older than %u", (guint)now); |
|
414 |
||
415 |
ScheduledRecordingList::iterator i = scheduled_recordings.begin(); |
|
416 |
while (i != scheduled_recordings.end()) |
|
417 |
{
|
|
418 |
if ((*i).is_old(now)) |
|
419 |
{
|
|
420 |
guint action = (*i).action_after; |
|
1.1.17
by Scott Evans
Import upstream version 1.3.5 |
421 |
remove_scheduled_recording((*i).scheduled_recording_id); |
1.1.16
by Scott Evans
Import upstream version 1.3.4 |
422 |
action_after(action); |
1.1.17
by Scott Evans
Import upstream version 1.3.5 |
423 |
|
424 |
i = scheduled_recordings.begin(); |
|
1.1.16
by Scott Evans
Import upstream version 1.3.4 |
425 |
}
|
426 |
else
|
|
427 |
{
|
|
428 |
i++; |
|
429 |
}
|
|
430 |
}
|
|
431 |
||
1.3.2
by Teis Dreijer (NOT the hoff)
Import upstream version 1.0.0 |
432 |
if (!scheduled_recordings.empty()) |
433 |
{
|
|
434 |
g_debug("============================================================================================="); |
|
435 |
g_debug("#ID | Start Time | Duration | Record | Channel | Device | Description"); |
|
436 |
g_debug("============================================================================================="); |
|
437 |
for (ScheduledRecordingList::iterator i = scheduled_recordings.begin(); i != scheduled_recordings.end(); i++) |
|
438 |
{
|
|
439 |
ScheduledRecording& scheduled_recording = *i; |
|
440 |
||
441 |
gboolean record = scheduled_recording.is_in(now); |
|
1.1.16
by Scott Evans
Import upstream version 1.3.4 |
442 |
g_debug("%3d | %u | %8d | %s | %10s | %27s | %s", |
1.3.2
by Teis Dreijer (NOT the hoff)
Import upstream version 1.0.0 |
443 |
scheduled_recording.scheduled_recording_id, |
1.1.16
by Scott Evans
Import upstream version 1.3.4 |
444 |
(guint)scheduled_recording.start_time, |
1.3.2
by Teis Dreijer (NOT the hoff)
Import upstream version 1.0.0 |
445 |
scheduled_recording.duration, |
446 |
record ? "true " : "false ", |
|
1.1.14
by Scott Evans
Import upstream version 1.3.0 |
447 |
channel_manager.get_channel_by_id(scheduled_recording.channel_id).name.c_str(), |
1.3.2
by Teis Dreijer (NOT the hoff)
Import upstream version 1.0.0 |
448 |
scheduled_recording.device.c_str(), |
449 |
scheduled_recording.description.c_str()); |
|
450 |
||
451 |
if (record) |
|
452 |
{
|
|
1.1.13
by Michael Lamothe
Import upstream version 1.2.6 |
453 |
results.push_back(scheduled_recording); |
1.3.2
by Teis Dreijer (NOT the hoff)
Import upstream version 1.0.0 |
454 |
}
|
1.1.16
by Scott Evans
Import upstream version 1.3.4 |
455 |
|
456 |
if (scheduled_recording.get_end_time() < now) |
|
457 |
{
|
|
458 |
dirty = true; |
|
459 |
}
|
|
1.3.2
by Teis Dreijer (NOT the hoff)
Import upstream version 1.0.0 |
460 |
}
|
461 |
}
|
|
462 |
||
1.1.10
by Teis Dreijer
Import upstream version 1.1.2 |
463 |
return results; |
1.3.2
by Teis Dreijer (NOT the hoff)
Import upstream version 1.0.0 |
464 |
}
|
465 |
||
466 |
ScheduledRecording ScheduledRecordingManager::get_scheduled_recording(guint scheduled_recording_id) |
|
467 |
{
|
|
468 |
Glib::RecMutex::Lock lock(mutex); |
|
469 |
||
470 |
ScheduledRecording* result = NULL; |
|
471 |
for (ScheduledRecordingList::iterator i = scheduled_recordings.begin(); i != scheduled_recordings.end() && result == NULL; i++) |
|
472 |
{
|
|
473 |
ScheduledRecording& scheduled_recording = *i; |
|
474 |
if (scheduled_recording.scheduled_recording_id == scheduled_recording_id) |
|
475 |
{
|
|
476 |
result = &scheduled_recording; |
|
477 |
}
|
|
478 |
}
|
|
479 |
||
480 |
if (result == NULL) |
|
481 |
{
|
|
482 |
Glib::ustring message = Glib::ustring::compose( |
|
483 |
_("Scheduled recording '%1' not found"), scheduled_recording_id); |
|
484 |
throw Exception(message); |
|
485 |
}
|
|
486 |
||
487 |
return *result; |
|
488 |
}
|
|
1.1.10
by Teis Dreijer
Import upstream version 1.1.2 |
489 |
|
1.1.12
by Michael Lamothe
Import upstream version 1.2.4 |
490 |
guint ScheduledRecordingManager::is_recording(const Channel& channel) |
1.1.10
by Teis Dreijer
Import upstream version 1.1.2 |
491 |
{
|
492 |
Glib::RecMutex::Lock lock(mutex); |
|
493 |
||
494 |
guint now = time(NULL); |
|
495 |
for (ScheduledRecordingList::iterator i = scheduled_recordings.begin(); i != scheduled_recordings.end(); i++) |
|
496 |
{
|
|
497 |
ScheduledRecording& scheduled_recording = *i; |
|
498 |
if (scheduled_recording.is_in(now) && scheduled_recording.channel_id == channel.channel_id) |
|
499 |
{
|
|
1.1.16
by Scott Evans
Import upstream version 1.3.4 |
500 |
return scheduled_recording.scheduled_recording_id; |
1.1.10
by Teis Dreijer
Import upstream version 1.1.2 |
501 |
}
|
502 |
}
|
|
1.1.12
by Michael Lamothe
Import upstream version 1.2.4 |
503 |
return 0; |
1.1.10
by Teis Dreijer
Import upstream version 1.1.2 |
504 |
}
|
505 |
||
506 |
gboolean ScheduledRecordingManager::is_recording(const EpgEvent& epg_event) |
|
507 |
{
|
|
508 |
Glib::RecMutex::Lock lock(mutex); |
|
509 |
||
510 |
for (ScheduledRecordingList::iterator i = scheduled_recordings.begin(); i != scheduled_recordings.end(); i++) |
|
511 |
{
|
|
512 |
ScheduledRecording& scheduled_recording = *i; |
|
513 |
if (scheduled_recording.channel_id == epg_event.channel_id && |
|
514 |
scheduled_recording.is_in( |
|
515 |
convert_to_utc_time(epg_event.start_time), |
|
516 |
convert_to_utc_time(epg_event.get_end_time()))) |
|
517 |
{
|
|
518 |
return true; |
|
519 |
}
|
|
520 |
}
|
|
521 |
||
522 |
return false; |
|
523 |
}
|
|
1.1.16
by Scott Evans
Import upstream version 1.3.4 |
524 |
|
525 |
void ScheduledRecordingManager::action_after(guint action) |
|
526 |
{
|
|
527 |
if (action == SCHEDULED_RECORDING_ACTION_AFTER_CLOSE) |
|
528 |
{
|
|
529 |
g_message("Me TV closed by Scheduled Recording"); |
|
530 |
action_quit->activate(); |
|
531 |
}
|
|
532 |
else if (action == SCHEDULED_RECORDING_ACTION_AFTER_SHUTDOWN) |
|
533 |
{
|
|
534 |
DBusGConnection* dbus_connection = get_application().get_dbus_connection(); |
|
535 |
if (dbus_connection == NULL) |
|
536 |
{
|
|
537 |
throw Exception(_("DBus connection not available")); |
|
538 |
}
|
|
539 |
||
540 |
g_message("Computer shutdown by scheduled recording"); |
|
541 |
||
542 |
DBusGProxy* proxy = dbus_g_proxy_new_for_name(dbus_connection, |
|
543 |
"org.gnome.SessionManager", |
|
544 |
"/org/gnome/SessionManager", |
|
545 |
"org.gnome.SessionManager"); |
|
546 |
if (proxy == NULL) |
|
547 |
{
|
|
548 |
throw Exception(_("Failed to get org.gnome.SessionManager proxy")); |
|
549 |
}
|
|
550 |
||
551 |
GError* error = NULL; |
|
552 |
if (!dbus_g_proxy_call(proxy, "Shutdown", &error, G_TYPE_INVALID, G_TYPE_INVALID)) |
|
553 |
{
|
|
554 |
throw Exception(_("Failed to call Shutdown method")); |
|
555 |
}
|
|
556 |
||
557 |
g_message("Shutdown requested"); |
|
558 |
}
|
|
559 |
}
|