1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 105 106 107 108 109 110 111 112 113 114 115 116 117 118 119 120 121 122 123 124 125 126 127 128 129 130 131 132 133 134 135 136 137 138 139 140 141 142 143 144 145 146 147 148 149 150 151 152 153 154 155 156 157 158 159 160 161 162 163 164 165 166 167 168 169 170 171 172 173 174 175 176 177 178 179 180 181 182 183 184 185 186 187 188 189 190 191 192 193 194 195 196 197 198 199 200 201 202 203 204 205 206
|
#include <opencv/cv.h>
#include <opencv/highgui.h>
#include <stdio.h>
// Create a string
using namespace std;
// Image to capture the frame from video
IplImage* image = NULL; // original image
IplImage* lastImage = NULL; // last image
IplImage* diffImage = NULL; // differences between images
IplImage* threshImage = NULL; // threshold image
IplImage* mjpegImage = NULL;
// Function protoype for characteristics about a video
void showCaptureProperties(CvCapture* capture)
{
// Read the video's frame size out of the avi
int width, height, framePerSecond;
width = (int)cvGetCaptureProperty(capture,CV_CAP_PROP_FRAME_WIDTH);
height = (int)cvGetCaptureProperty(capture,CV_CAP_PROP_FRAME_HEIGHT);
framePerSecond = (int)cvGetCaptureProperty(capture,CV_CAP_PROP_FPS);
printf("Video properties ( width*height - frame per seconde ): %d*%d - %d\n", width, height, framePerSecond);
}
// Main function, defines the entry point for the program
int main(int argc, char** argv)
{
// Structure for getting video from avi
CvCapture* capture = 0;
// Image to capture the frame from video
IplImage* frame = NULL;
// Check for the correct usage of the command line
if(argc > 1)
capture = cvCaptureFromAVI(argv[1]);
if(!capture)
{
fprintf(stderr,"Could not initialize capturing...\n");
return -1;
}
// The Linux version of OpenCV has a bug. You need to read a frame before an AVI's properties can be queried.
cvQueryFrame(capture);
// Read the video's frame size out of the avi
if(cvSetCaptureProperty(capture, CV_CAP_PROP_FRAME_WIDTH,320))
printf("Cant set width property\n");
if(cvSetCaptureProperty(capture, CV_CAP_PROP_FRAME_HEIGHT, 240))
printf("Cant set height property\n");
// Threshold value
int thresh = 40;
// Create window object (use flag=0 to allow resize, 1 to auto fix size)
cvNamedWindow("Live video display", 1);
cvNamedWindow("Difference between subsequence image frames",1);
cvNamedWindow("Difference between subsequence image frames with threshold", 1);
cvCreateTrackbar("Threshold", "Difference between subsequence image frames with threshold", &thresh, 255, NULL);
// Call the function showCaptureProperties
showCaptureProperties(capture);
char key; // user input
int EVENT_LOOP_DELAY = 40; // delay for GUI window
// 40 ms equates to 1000ms/25fps = 40ms per frame
int numberScenes = 1;
int idScene = 0;
int framePerSecond;
char filename[256];
CvVideoWriter* writer = NULL;
int frameId = 0;
if (argc > 2)
thresh = atoi(argv[2]);
printf(">>>> scene detection : %s\n",argv[1]);
for(;;)
{
// Capture the frame and load it in IplImage
frame = cvQueryFrame(capture);
if(!frame)
break;
frameId++;
// Create image header same as frame but with 1 channel to gray
if(!image)
{
image = cvCreateImage(cvSize(frame->width, frame->height), frame->depth,1);
image->origin = frame->origin;
threshImage = cvCreateImage(cvSize(frame->width, frame->height), frame->depth,1);
threshImage->origin = frame->origin;
}
// Convert frame to gray and store in image
cvCvtColor(frame, image, CV_BGR2GRAY);
// Create lastImage clone actual image
if(!lastImage)
{
lastImage = cvCloneImage(image);
}
// Create image header same as frame but with 1 channel to gray
if(!diffImage)
{
diffImage = cvCreateImage(cvSize(frame->width, frame->height), frame->depth,1);
diffImage->origin = frame->origin;
}
// Display movie in window
cvShowImage("Live video display", frame);
// Differences with actual and last image
cvAbsDiff(image, lastImage, diffImage);
cvShowImage("Difference between subsequence image frames", diffImage);
//Threshold image
cvThreshold(diffImage, threshImage, thresh, 255, CV_THRESH_BINARY);
cvShowImage("Difference between subsequence image frames with threshold", threshImage);
// Percentage of white pixels on the image
int counterWhitePixels = 0;
int percentageWhitePixels = 0;
int numberPixels = threshImage->width*threshImage->height;
for(int i=0; i<threshImage->width; i++)
{
for(int j=0; j<threshImage->height; j++)
{
CvScalar pixel = cvGet2D(threshImage, j, i);
if(pixel.val[0] == 255)
counterWhitePixels++;
}
}
percentageWhitePixels = counterWhitePixels * 100 / numberPixels;
// detect movie scenes
if (percentageWhitePixels > thresh)
{
numberScenes++;
cvReleaseVideoWriter(&writer);
}
// Split movie into scenes
framePerSecond = (int)cvGetCaptureProperty(capture,CV_CAP_PROP_FPS);
CvSize size = cvSize((int)cvGetCaptureProperty(capture,CV_CAP_PROP_FRAME_WIDTH),
(int)cvGetCaptureProperty(capture,CV_CAP_PROP_FRAME_HEIGHT));
if (idScene != numberScenes)
{
idScene = numberScenes;
printf("Shot detected #%d at frame #%d\n",idScene,frameId);
sprintf(filename,"shot-%d.avi",idScene);
writer = cvCreateVideoWriter(filename, CV_FOURCC('M','J','P','G'), framePerSecond, size);
//writer = cvCreateVideoWriter(filename, -1, 25, cvSize(320,240));
printf("--- seq #%d frame id #%d threshold = %d \n",idScene,frameId,percentageWhitePixels);
printf("w=%d,h=%d\n",frame->width,frame->height);
mjpegImage = cvCreateImage(size, IPL_DEPTH_8U, 3);
//mjpegImage = cvCloneImage(frame);
cvWriteFrame(writer, frame);
}
// Change datas
lastImage = cvCloneImage(image);
// Start event processing loop (very important,in fact essential for GUI)
// 40 ms roughly equates to 1000ms/25fps = 4ms per frame
key = cvWaitKey(EVENT_LOOP_DELAY);
if (key == 'x')
{
// If user presses "x" then exit
printf("Keyboard exit requested : exiting now - bye!\n");
break;
}
}
printf("<<<< scene detection : %s\n",argv[1]);
// Destroy capture object
cvReleaseVideoWriter(&writer);
// Destroy capture object
cvReleaseCapture(&capture);
// Destroys images created
cvReleaseImage(&frame);
cvReleaseImage(&image);
cvReleaseImage(&lastImage);
cvReleaseImage(&threshImage);
cvReleaseImage(&diffImage);
cvReleaseImage(&mjpegImage);
// Destroy window objects
cvDestroyAllWindows();
// All OK : main returns 0
return 0;
} |
Partager