Merge branch 'zma_to_thread' of github.com:ConnorTechnology/ZoneMinder into zma_to_thread

This commit is contained in:
Isaac Connor 2017-12-03 11:00:52 -05:00
commit 5f01313ff6
7 changed files with 85 additions and 48 deletions

View File

@ -437,6 +437,8 @@ void Event::AddPacket( ZMPacket *packet, int score, Image *alarm_image ) {
Debug(2, "No video keyframe yet, not writing"); Debug(2, "No video keyframe yet, not writing");
} }
//FIXME if it fails, we should write a jpeg //FIXME if it fails, we should write a jpeg
} else {
Debug(2,"AddPacket but no videostore?!");
} }
if ( have_video_keyframe && ( packet->codec_type == AVMEDIA_TYPE_VIDEO ) ) { if ( have_video_keyframe && ( packet->codec_type == AVMEDIA_TYPE_VIDEO ) ) {
AddFrame( packet->image, *packet->timestamp, score, alarm_image ); AddFrame( packet->image, *packet->timestamp, score, alarm_image );

View File

@ -1919,7 +1919,6 @@ int LocalCamera::PreCapture() {
int LocalCamera::Capture( ZMPacket &zm_packet ) { int LocalCamera::Capture( ZMPacket &zm_packet ) {
// We assume that the avpacket is allocated, and just needs to be filled // We assume that the avpacket is allocated, and just needs to be filled
Debug( 3, "Capturing" );
static uint8_t* buffer = NULL; static uint8_t* buffer = NULL;
int buffer_bytesused = 0; int buffer_bytesused = 0;
int capture_frame = -1; int capture_frame = -1;
@ -1954,7 +1953,7 @@ int LocalCamera::Capture( ZMPacket &zm_packet ) {
} }
return -1; return -1;
} }
Debug(3, "Captured a frame"); Debug(5, "Captured a frame");
v4l2_data.bufptr = &vid_buf; v4l2_data.bufptr = &vid_buf;
capture_frame = v4l2_data.bufptr->index; capture_frame = v4l2_data.bufptr->index;

View File

@ -353,8 +353,10 @@ Monitor::Monitor(
event_count = 0; event_count = 0;
image_count = 0; image_count = 0;
analysis_image_count = 0; analysis_image_count = 0;
// How many frames we need to have before we start analysing
ready_count = warmup_count; ready_count = warmup_count;
first_alarm_count = 0;
last_alarm_count = 0; last_alarm_count = 0;
state = IDLE; state = IDLE;
last_signal = false; last_signal = false;
@ -411,6 +413,7 @@ Monitor::Monitor(
} }
memset( mem_ptr, 0, mem_size ); memset( mem_ptr, 0, mem_size );
shared_data->size = sizeof(SharedData); shared_data->size = sizeof(SharedData);
Debug( 1, "shared.size=%d", shared_data->size );
shared_data->active = enabled; shared_data->active = enabled;
shared_data->signal = false; shared_data->signal = false;
shared_data->state = IDLE; shared_data->state = IDLE;
@ -451,7 +454,8 @@ Monitor::Monitor(
start_time = last_fps_time = time( 0 ); start_time = last_fps_time = time( 0 );
event = 0; event = 0;
last_section_mod =0; last_section_mod = 0;
pre_event_buffer_count = pre_event_count + alarm_frame_count + warmup_count- 1;
Debug( 1, "Monitor %s\ Debug( 1, "Monitor %s\
function: %d\ function: %d\
@ -459,7 +463,9 @@ Monitor::Monitor(
IBC = %d, WUC = %d, pEC = %d, PEC = %d, EAF = %d, FRI = %d, RBP = %d, ARBP = %d, FM = %d", IBC = %d, WUC = %d, pEC = %d, PEC = %d, EAF = %d, FRI = %d, RBP = %d, ARBP = %d, FM = %d",
name, name,
function, label_format, label_coord.X(), label_coord.Y(), label_size, function, label_format, label_coord.X(), label_coord.Y(), label_size,
image_buffer_count, warmup_count, pre_event_count, post_event_count, alarm_frame_count, fps_report_interval, ref_blend_perc, alarm_ref_blend_perc, track_motion image_buffer_count, warmup_count,
pre_event_count, post_event_count, alarm_frame_count,
fps_report_interval, ref_blend_perc, alarm_ref_blend_perc, track_motion
); );
n_linked_monitors = 0; n_linked_monitors = 0;
@ -563,7 +569,6 @@ bool Monitor::connect() {
/* Allocate a buffer for the next image */ /* Allocate a buffer for the next image */
next_buffer.image = new Image( width, height, camera->Colours(), camera->SubpixelOrder()); next_buffer.image = new Image( width, height, camera->Colours(), camera->SubpixelOrder());
} }
pre_event_buffer_count = pre_event_count + alarm_frame_count - 1;
Debug(3, "Success connecting"); Debug(3, "Success connecting");
return true; return true;
@ -752,8 +757,9 @@ unsigned int Monitor::GetLastWriteIndex() const {
} }
uint32_t Monitor::GetLastEventId() const { uint32_t Monitor::GetLastEventId() const {
Debug(2, "mem_ptr(%x), State(%d) last_read_index(%d) last_read_time(%d) last_event(%d)", Debug(2, "mem_ptr(%x), size(%d) State(%d) last_read_index(%d) last_read_time(%d) last_event(%d)",
mem_ptr, mem_ptr,
shared_data->size,
shared_data->state, shared_data->state,
shared_data->last_read_index, shared_data->last_read_index,
shared_data->last_read_time, shared_data->last_read_time,
@ -777,7 +783,7 @@ double Monitor::GetFPS() const {
} }
struct timeval time1 = *snap1->timestamp; struct timeval time1 = *snap1->timestamp;
int image_count = image_buffer_count; int fps_image_count = image_buffer_count;
int index2 = (index1+1)%image_buffer_count; int index2 = (index1+1)%image_buffer_count;
Debug(2, "index2(%d)", index2); Debug(2, "index2(%d)", index2);
@ -791,7 +797,7 @@ double Monitor::GetFPS() const {
} }
index2 = (index2+1)%image_buffer_count; index2 = (index2+1)%image_buffer_count;
snap2 = &image_buffer[ index2 ]; snap2 = &image_buffer[ index2 ];
image_count--; fps_image_count--;
} }
struct timeval time2 = *snap2->timestamp; struct timeval time2 = *snap2->timestamp;
@ -799,10 +805,11 @@ double Monitor::GetFPS() const {
if ( ! time_diff ) { if ( ! time_diff ) {
return 0.0; return 0.0;
} }
double curr_fps = image_count/time_diff; double curr_fps = fps_image_count/time_diff;
if ( curr_fps < 0.0 ) { if ( curr_fps < 0.0 ) {
Error( "Negative FPS %f, time_diff = %lf (%d:%ld.%ld - %d:%ld.%ld), ibc: %d", curr_fps, time_diff, index2, time2.tv_sec, time2.tv_usec, index1, time1.tv_sec, time1.tv_usec, image_buffer_count ); Error( "Negative FPS %f, time_diff = %lf (%d:%ld.%ld - %d:%ld.%ld), ibc: %d",
curr_fps, time_diff, index2, time2.tv_sec, time2.tv_usec, index1, time1.tv_sec, time1.tv_usec, image_buffer_count );
return 0.0; return 0.0;
} }
return curr_fps; return curr_fps;
@ -1239,13 +1246,11 @@ bool Monitor::Analyse() {
// if have event, sent frames until we find a video packet, at which point do analysis. Adaptive skip should only affect which frames we do analysis on. // if have event, sent frames until we find a video packet, at which point do analysis. Adaptive skip should only affect which frames we do analysis on.
// If do have an event, then analysis_it should point to the head of the queue, because we would have emptied it on event creation.
unsigned int index = ( shared_data->last_read_index + 1 ) % image_buffer_count;
int packets_processed = 0; int packets_processed = 0;
ZMPacket *snap; ZMPacket *snap;
while ( ( snap = packetqueue->get_analysis_packet() ) && ( snap->score == -1 ) ) { while ( ( snap = packetqueue->get_analysis_packet() ) && ( snap->score == -1 ) ) {
unsigned int index = snap->image_index;
Debug(2, "Analysis index (%d), last_Write(%d)", index, shared_data->last_write_index); Debug(2, "Analysis index (%d), last_Write(%d)", index, shared_data->last_write_index);
packets_processed += 1; packets_processed += 1;
@ -1294,7 +1299,7 @@ bool Monitor::Analyse() {
if ( !signal ) { if ( !signal ) {
signalText = "Lost"; signalText = "Lost";
if ( event ) { if ( event ) {
Info( "%s: %03d - Closing event %d, signal loss", name, image_count, event->Id() ); Info( "%s: %03d - Closing event %d, signal loss", name, analysis_image_count, event->Id() );
closeEvent(); closeEvent();
last_section_mod = 0; last_section_mod = 0;
} }
@ -1374,7 +1379,7 @@ bool Monitor::Analyse() {
Debug( 3, "Section length (%d) Last Section Mod(%d), tv_sec(%d) new section mod(%d)", section_length, last_section_mod, timestamp->tv_sec, section_mod ); Debug( 3, "Section length (%d) Last Section Mod(%d), tv_sec(%d) new section mod(%d)", section_length, last_section_mod, timestamp->tv_sec, section_mod );
// This is not clear, but basically due to pauses, etc we might not get section_mod == 0 // This is not clear, but basically due to pauses, etc we might not get section_mod == 0
if ( section_mod < last_section_mod ) { if ( section_mod < last_section_mod ) {
Info( "%s: %03d - Closing event %d, section end forced ", name, image_count, event->Id() ); Info( "%s: %03d - Closing event %d, section end forced ", name, analysis_image_count, event->Id() );
closeEvent(); closeEvent();
last_section_mod = 0; last_section_mod = 0;
} else { } else {
@ -1388,7 +1393,7 @@ bool Monitor::Analyse() {
event = new Event( this, *timestamp, "Continuous", noteSetMap ); event = new Event( this, *timestamp, "Continuous", noteSetMap );
shared_data->last_event_id = event->Id(); shared_data->last_event_id = event->Id();
video_store_data->recording = event->StartTime(); video_store_data->recording = event->StartTime();
Info( "%s: %03d - Opening new event %d, section start", name, image_count, event->Id() ); Info( "%s: %03d - Opening new event %d, section start", name, analysis_image_count, event->Id() );
/* To prevent cancelling out an existing alert\prealarm\alarm state */ /* To prevent cancelling out an existing alert\prealarm\alarm state */
if ( state == IDLE ) { if ( state == IDLE ) {
shared_data->state = state = TAPE; shared_data->state = state = TAPE;
@ -1400,32 +1405,36 @@ bool Monitor::Analyse() {
Debug(9, "Score: (%d)", score ); Debug(9, "Score: (%d)", score );
if ( (state == IDLE || state == TAPE || state == PREALARM ) ) { if ( (state == IDLE || state == TAPE || state == PREALARM ) ) {
if ( Event::PreAlarmCount() >= (alarm_frame_count-1) ) { if ( Event::PreAlarmCount() >= (alarm_frame_count-1) ) {
Info( "%s: %03d - Gone into alarm state", name, image_count ); Info( "%s: %03d - Gone into alarm state", name, analysis_image_count );
shared_data->state = state = ALARM; shared_data->state = state = ALARM;
if ( (function != MOCORD && state != ALERT) ) { if ( (function != MOCORD && state != ALERT) ) {
if ( event ) {
Error("Already ahve evnet!");
} else {
event = new Event( this, *timestamp, cause, noteSetMap ); event = new Event( this, *timestamp, cause, noteSetMap );
shared_data->last_event_id = event->Id(); shared_data->last_event_id = event->Id();
}
} }
} else if ( state != PREALARM ) { } else if ( state != PREALARM ) {
Info( "%s: %03d - Gone into prealarm state", name, image_count ); Info( "%s: %03d - Gone into prealarm state", name, analysis_image_count );
shared_data->state = state = PREALARM; shared_data->state = state = PREALARM;
} }
} else if ( state == ALERT ) { } else if ( state == ALERT ) {
Info( "%s: %03d - Gone back into alarm state", name, image_count ); Info( "%s: %03d - Gone back into alarm state", name, analysis_image_count );
shared_data->state = state = ALARM; shared_data->state = state = ALARM;
} }
last_alarm_count = image_count; last_alarm_count = analysis_image_count;
} else { // no score? } else { // no score?
if ( state == ALARM ) { if ( state == ALARM ) {
Info( "%s: %03d - Gone into alert state", name, image_count ); Info( "%s: %03d - Gone into alert state", name, analysis_image_count );
shared_data->state = state = ALERT; shared_data->state = state = ALERT;
} else if ( state == ALERT ) { } else if ( state == ALERT ) {
if ( image_count-last_alarm_count > post_event_count ) { if ( analysis_image_count-last_alarm_count > post_event_count ) {
Info( "%s: %03d - Left alarm state (%d) - %d(%d) images", name, image_count, event->Id(), event->Frames(), event->AlarmFrames() ); Info( "%s: %03d - Left alarm state (%d) - %d(%d) images", name, analysis_image_count, event->Id(), event->Frames(), event->AlarmFrames() );
//if ( function != MOCORD || event_close_mode == CLOSE_ALARM || event->Cause() == SIGNAL_CAUSE ) //if ( function != MOCORD || event_close_mode == CLOSE_ALARM || event->Cause() == SIGNAL_CAUSE )
if ( function != MOCORD || event_close_mode == CLOSE_ALARM ) { if ( function != MOCORD || event_close_mode == CLOSE_ALARM ) {
shared_data->state = state = IDLE; shared_data->state = state = IDLE;
Info( "%s: %03d - Closing event %d, alarm end%s", name, image_count, event->Id(), (function==MOCORD)?", section truncated":"" ); Info( "%s: %03d - Closing event %d, alarm end%s", name, analysis_image_count, event->Id(), (function==MOCORD)?", section truncated":"" );
closeEvent(); closeEvent();
} else { } else {
shared_data->state = state = TAPE; shared_data->state = state = TAPE;
@ -1478,7 +1487,7 @@ bool Monitor::Analyse() {
if ( noteSetMap.size() > 0 ) if ( noteSetMap.size() > 0 )
event->updateNotes( noteSetMap ); event->updateNotes( noteSetMap );
} else if ( state == TAPE ) { } else if ( state == TAPE ) {
if ( !(image_count%(frame_skip+1)) ) { if ( !(analysis_image_count%(frame_skip+1)) ) {
} }
} }
if ( function == MODECT || function == MOCORD ) { if ( function == MODECT || function == MOCORD ) {
@ -1489,11 +1498,12 @@ bool Monitor::Analyse() {
} else { } else {
Debug(3,"Not ready?"); Debug(3,"Not ready?");
return false;
} }
} else { } else {
Debug(3, "trigger == off"); Debug(3, "trigger == off");
if ( event ) { if ( event ) {
Info( "%s: %03d - Closing event %d, trigger off", name, image_count, event->Id() ); Info( "%s: %03d - Closing event %d, trigger off", name, analysis_image_count, event->Id() );
closeEvent(); closeEvent();
} }
shared_data->state = state = IDLE; shared_data->state = state = IDLE;
@ -1501,24 +1511,32 @@ bool Monitor::Analyse() {
} // end if ( trigger_data->trigger_state != TRIGGER_OFF ) } // end if ( trigger_data->trigger_state != TRIGGER_OFF )
if ( event ) { if ( event ) {
int last_write = shared_data->last_write_index;
int written = 0;
ZMPacket *queued_packet; ZMPacket *queued_packet;
//popPacket will increment analysis_it if neccessary, so this will write out all packets in queue //popPacket will increment analysis_it if neccessary, so this will write out all packets in queue
// We can't just loop here forever, because we may be capturing just as fast, and never leave the loop.
// Only loop until we hit the analysis index
while ( ( queued_packet = packetqueue->popPacket() ) ) { while ( ( queued_packet = packetqueue->popPacket() ) ) {
Debug(2,"adding packet (%x) (%d)", queued_packet, queued_packet->image_index ); Debug(2,"adding packet (%d) qp lwindex(%d), written(%d)", queued_packet->image_index, last_write, written );
event->AddPacket( queued_packet ); event->AddPacket( queued_packet );
written ++;
if ( queued_packet->image_index == -1 ) { if ( queued_packet->image_index == -1 ) {
delete queued_packet; delete queued_packet;
queued_packet = NULL; } else if ( snap == queued_packet ) {
packetqueue->increment_analysis_it();
break;
} }
// encoding can take a long time, so
shared_data->last_read_time = time(NULL);
} // end while write out queued_packets } // end while write out queued_packets
queued_packet = NULL;
} else { } else {
packetqueue->increment_analysis_it(); packetqueue->increment_analysis_it();
} }
shared_data->last_read_index = snap->image_index; shared_data->last_read_index = snap->image_index;
struct timeval now; shared_data->last_read_time = time(NULL);
gettimeofday(&now, NULL);
shared_data->last_read_time = now.tv_sec;
analysis_image_count++; analysis_image_count++;
} // end while not at end of packetqueue } // end while not at end of packetqueue
if ( packets_processed > 0 ) if ( packets_processed > 0 )
@ -2736,6 +2754,7 @@ Monitor *Monitor::Load( unsigned int p_id, bool load_zones, Purpose purpose ) {
int Monitor::Capture() { int Monitor::Capture() {
static int FirstCapture = 1; // Used in de-interlacing to indicate whether this is the even or odd image static int FirstCapture = 1; // Used in de-interlacing to indicate whether this is the even or odd image
GetLastEventId();
unsigned int index = image_count % image_buffer_count; unsigned int index = image_count % image_buffer_count;
if ( (index == shared_data->last_read_index) && (function > MONITOR) ) { if ( (index == shared_data->last_read_index) && (function > MONITOR) ) {
@ -2750,7 +2769,6 @@ int Monitor::Capture() {
} }
ZMPacket *packet = &image_buffer[index]; ZMPacket *packet = &image_buffer[index];
Debug(2,"Reset index(%d) of (%d)", index, image_buffer_count );
packet->reset(); packet->reset();
Image* capture_image = packet->image; Image* capture_image = packet->image;
int captureResult = 0; int captureResult = 0;
@ -2771,7 +2789,6 @@ int Monitor::Capture() {
} }
} else { } else {
captureResult = camera->Capture(*packet); captureResult = camera->Capture(*packet);
Debug(2, "Reset timestamp");
gettimeofday( packet->timestamp, NULL ); gettimeofday( packet->timestamp, NULL );
if ( captureResult < 0 ) { if ( captureResult < 0 ) {
// Unable to capture image for temporary reason // Unable to capture image for temporary reason
@ -2804,7 +2821,6 @@ int Monitor::Capture() {
return 1; return 1;
} }
Debug(2, "Have video packet");
packet->codec_type = camera->get_VideoStream()->codecpar->codec_type; packet->codec_type = camera->get_VideoStream()->codecpar->codec_type;
if ( packet->packet.size && ! packet->in_frame ) { if ( packet->packet.size && ! packet->in_frame ) {
@ -2816,8 +2832,11 @@ int Monitor::Capture() {
// Have an av_packet, // Have an av_packet,
mutex.lock(); mutex.lock();
if ( packetqueue->video_packet_count || packet->keyframe || event ) { if ( packetqueue->video_packet_count || packet->keyframe || event ) {
Debug(2, "Have video packet for index (%d)", index );
//Debug(2, "Queueing video packet"); //Debug(2, "Queueing video packet");
packetqueue->queuePacket( packet ); packetqueue->queuePacket( packet );
} else {
Debug(2, "Not queiing video packet for index (%d)", index );
} }
mutex.unlock(); mutex.unlock();
} else { } else {
@ -3110,7 +3129,7 @@ unsigned int Monitor::DetectMotion( const Image &comp_image, Event::StringSet &z
shared_data->alarm_x = alarm_centre.X(); shared_data->alarm_x = alarm_centre.X();
shared_data->alarm_y = alarm_centre.Y(); shared_data->alarm_y = alarm_centre.Y();
Info( "Got alarm centre at %d,%d, at count %d", shared_data->alarm_x, shared_data->alarm_y, image_count ); Info( "Got alarm centre at %d,%d, at count %d", shared_data->alarm_x, shared_data->alarm_y, analysis_image_count );
} else { } else {
shared_data->alarm_x = shared_data->alarm_y = -1; shared_data->alarm_x = shared_data->alarm_y = -1;
} }
@ -3192,9 +3211,9 @@ int Monitor::PrimeCapture() {
int ret = camera->PrimeCapture(); int ret = camera->PrimeCapture();
if ( ret == 0 ) { if ( ret == 0 ) {
video_stream_id = camera->get_VideoStreamId(); video_stream_id = camera->get_VideoStreamId();
packetqueue = new zm_packetqueue( pre_event_buffer_count, video_stream_id ); packetqueue = new zm_packetqueue( image_buffer_count, video_stream_id );
} }
Debug(2, "Video stream id is (%d)", video_stream_id ); Debug(2, "Video stream id is (%d), minimum_packets to keep in buffer(%d)", video_stream_id, pre_event_buffer_count );
return ret; return ret;
} }
int Monitor::PreCapture() { int Monitor::PreCapture() {

View File

@ -100,7 +100,7 @@ protected:
typedef enum { CLOSE_TIME, CLOSE_IDLE, CLOSE_ALARM } EventCloseMode; typedef enum { CLOSE_TIME, CLOSE_IDLE, CLOSE_ALARM } EventCloseMode;
/* sizeof(SharedData) expected to be 336 bytes on 32bit and 64bit */ /* sizeof(SharedData) expected to be 344 bytes on 32bit and 64bit */
typedef struct { typedef struct {
uint32_t size; /* +0 */ uint32_t size; /* +0 */
uint32_t last_write_index; /* +4 */ uint32_t last_write_index; /* +4 */
@ -425,9 +425,15 @@ public:
return( event_prefix ); return( event_prefix );
} }
inline bool Ready() { inline bool Ready() {
if ( function <= MONITOR ) if ( function <= MONITOR ) {
Error("Should not be calling Ready if the function doesn't include motion detection");
return( false ); return( false );
return( image_count > ready_count ); }
if ( image_count > ready_count ) {
return true;
}
Debug(2, "Not ready because image_count(%d) <= ready_count(%d)", image_count, ready_count );
return false;
} }
inline bool Active() { inline bool Active() {
if ( function <= MONITOR ) if ( function <= MONITOR )

View File

@ -183,6 +183,7 @@ int RemoteCameraNVSocket::PrimeCapture() {
Disconnect(); Disconnect();
return -1; return -1;
} }
mVideoStreamId=0;
return 0; return 0;
} }
@ -207,6 +208,7 @@ int RemoteCameraNVSocket::Capture( ZMPacket &zm_packet ) {
} }
zm_packet.image->Assign( width, height, colours, subpixelorder, buffer, imagesize ); zm_packet.image->Assign( width, height, colours, subpixelorder, buffer, imagesize );
zm_packet.keyframe = 1;
return 1; return 1;
} }
@ -232,9 +234,8 @@ AVStream *RemoteCameraNVSocket::get_VideoStream() {
} else { } else {
Error("Can't create video stream"); Error("Can't create video stream");
} }
} else { } else {
Debug(2,"Have videostream"); Debug(5,"Have videostream");
} }
Debug(2,"Get videoStream");
return video_stream; return video_stream;
} }

View File

@ -46,7 +46,7 @@ VideoStore::VideoStore(
packets_written = 0; packets_written = 0;
frame_count = 0; frame_count = 0;
av_register_all(); FFMPEGInit();
Info("Opening video storage stream %s format: %s", filename, format); Info("Opening video storage stream %s format: %s", filename, format);
@ -976,7 +976,8 @@ int VideoStore::writeVideoFramePacket( ZMPacket * zm_packet ) {
} else if ( zm_packet->image ) { } else if ( zm_packet->image ) {
Debug(2,"Have an image, convert it"); Debug(2,"Have an image, convert it");
//Go straight to out frame //Go straight to out frame
swscale.Convert(zm_packet->image, swscale.Convert(
zm_packet->image,
zm_packet->buffer, zm_packet->buffer,
codec_imgsize, codec_imgsize,
(AVPixelFormat)zm_packet->image->AVPixFormat(), (AVPixelFormat)zm_packet->image->AVPixFormat(),
@ -997,10 +998,18 @@ int VideoStore::writeVideoFramePacket( ZMPacket * zm_packet ) {
if ( ! video_last_pts ) { if ( ! video_last_pts ) {
video_last_pts = zm_packet->timestamp->tv_sec*1000000 + zm_packet->timestamp->tv_usec; video_last_pts = zm_packet->timestamp->tv_sec*1000000 + zm_packet->timestamp->tv_usec;
Debug(2, "No video_lsat_pts, set to (%d)", video_last_pts );
zm_packet->out_frame->pts = 0; zm_packet->out_frame->pts = 0;
} else { } else {
zm_packet->out_frame->pts = ( zm_packet->timestamp->tv_sec*1000000 + zm_packet->timestamp->tv_usec ) - video_last_pts; zm_packet->out_frame->pts = ( zm_packet->timestamp->tv_sec*1000000 + zm_packet->timestamp->tv_usec ) - video_last_pts;
} }
if ( zm_packet->keyframe ) {
Debug(2, "Setting keyframe");
zm_packet->out_frame->key_frame =1;
Debug(2, "Setting keyframe (%d)", zm_packet->out_frame->key_frame );
} else {
Debug(2, "Not Setting keyframe");
}
// Do this to allow the encoder to choose whether to use I/P/B frame // Do this to allow the encoder to choose whether to use I/P/B frame
#if LIBAVCODEC_VERSION_CHECK(57, 64, 0, 64, 0) #if LIBAVCODEC_VERSION_CHECK(57, 64, 0, 64, 0)
@ -1040,6 +1049,7 @@ int VideoStore::writeVideoFramePacket( ZMPacket * zm_packet ) {
return 0; return 0;
} }
#endif #endif
opkt.dts = opkt.pts;
} else { } else {
AVPacket *ipkt = &zm_packet->packet; AVPacket *ipkt = &zm_packet->packet;
@ -1058,7 +1068,7 @@ int VideoStore::writeVideoFramePacket( ZMPacket * zm_packet ) {
} }
opkt.duration = 0; opkt.duration = 0;
Debug(3, "dts:%" PRId64 ", pts:%" PRId64 ", keyframe:%d", opkt.dts, opkt.pts, opkt.flags & AV_PKT_FLAG_KEY ); Debug(3, "dts:%" PRId64 ", pts:%" PRId64 ", keyframe:%d", opkt.dts, opkt.pts, opkt.flags & AV_PKT_FLAG_KEY );
write_video_packet( opkt ); write_video_packet( opkt );
zm_av_packet_unref(&opkt); zm_av_packet_unref(&opkt);

View File

@ -222,7 +222,7 @@ Warning("Not Using snapshot" . $event->Path().'/snapshot.jpg' );
$imgHtml = '<img id="thumbnail'.$event->id().'" src="'.$imgSrc.'" alt="'. validHtmlStr('Event '.$event->Id()) .'" style="width:'. validInt($thumbData['Width']) .'px;height:'. validInt( $thumbData['Height'] ).'px;" onmouseover="this.src=\''.$streamSrc.'\';" onmouseout="this.src=\''.$imgSrc.'\';"/>'; $imgHtml = '<img id="thumbnail'.$event->id().'" src="'.$imgSrc.'" alt="'. validHtmlStr('Event '.$event->Id()) .'" style="width:'. validInt($thumbData['Width']) .'px;height:'. validInt( $thumbData['Height'] ).'px;" onmouseover="this.src=\''.$streamSrc.'\';" onmouseout="this.src=\''.$imgSrc.'\';"/>';
echo makePopupLink( echo makePopupLink(
'?view=frame&amp;eid='.$event->Id().'&amp;fid='.$thumbData['FrameId'], '?view=frame&amp;eid='.$event->Id().'&amp;fid='.( isset($thumbData['FrameId']) ? $thumbData['FrameId'] : 'snapshot' ),
'zmImage', 'zmImage',
array( 'image', reScale( $event->Width(), $scale ), reScale( $event->Height(), $scale ) ), array( 'image', reScale( $event->Width(), $scale ), reScale( $event->Height(), $scale ) ),
$imgHtml $imgHtml