Filter SDK/avs2yuv
Line 112: | Line 112: | ||
avs2yuv.exe example.avs output.raw | avs2yuv.exe example.avs output.raw | ||
+ | |||
+ | === Line by line breakdown === | ||
Here's a line-by-line breakdown of avs2yuv.cpp. | Here's a line-by-line breakdown of avs2yuv.cpp. |
Revision as of 01:05, 3 January 2014
avs2yuv reads a script and outputs raw video (YUV or RGB). It's a stripped down version of the famous avs2yuv.
Here's avs2yuv.cpp:
#include <stdio.h> #include <Windows.h> #include "avisynth.h" #define MY_VERSION "Avs2YUV 0.24" const AVS_Linkage *AVS_linkage = 0; int __cdecl main(int argc, const char* argv[]) { const char* infile = NULL; const char* outfile = NULL; FILE* out_fh; if (!strcmp(argv[1], "-h")) { fprintf(stderr, MY_VERSION "\n" "Usage: avs2yuv.exe in.avs out.raw\n"); return 2; } else { infile = argv[1]; outfile = argv[2]; } try { char* colorformat; IScriptEnvironment* (__stdcall *CreateEnv)(int); HMODULE avsdll = LoadLibrary("avisynth.dll"); if (!avsdll) { fprintf(stderr, "failed to load avisynth.dll\n"); return 2; } CreateEnv = (IScriptEnvironment *(__stdcall *)(int))GetProcAddress(avsdll, "CreateScriptEnvironment"); if (!CreateEnv) { fprintf(stderr, "failed to load CreateScriptEnvironment()\n"); return 1; } IScriptEnvironment* env = CreateEnv(AVISYNTH_INTERFACE_VERSION); env->CheckVersion(5); AVS_linkage = env->GetAVSLinkage(); AVSValue arg(infile); AVSValue res = env->Invoke("Import", AVSValue(&arg, 1)); if (!res.IsClip()) { fprintf(stderr, "Error: '%s' didn't return a video clip.\n", infile); return 1; } PClip clip = res.AsClip(); VideoInfo vi = clip->GetVideoInfo(); fprintf(stderr, " %s:\n", infile); fprintf(stderr, " %dx%d,\n", vi.width, vi.height); fprintf(stderr, " %d/%d fps,\n", vi.fps_numerator, vi.fps_denominator); fprintf(stderr, " %d frames,\n", vi.num_frames); if (vi.IsYUV()) { colorformat = "YUV"; } else { colorformat = "RGB"; } fprintf(stderr, " %s color format", colorformat); out_fh = fopen(outfile, "wb"); if (!out_fh) { fprintf(stderr, "fopen(\"%s\") failed", outfile); return 1; } for (int frm = 0; frm < vi.num_frames; ++frm) { PVideoFrame f = clip->GetFrame(frm, env); static const int planes[] = {PLANAR_Y, PLANAR_U, PLANAR_V}; int wrote = 0; for (int p=0; p<3; p++) { // for interleaved formats only the first plane (being the whole frame) is written int w = vi.width >> vi.GetPlaneWidthSubsampling(planes[p]); int h = vi.height >> vi.GetPlaneHeightSubsampling(planes[p]); int pitch = f->GetPitch(planes[p]); const BYTE* data = f->GetReadPtr(planes[p]); for (int y=0; y<h; y++) { wrote += fwrite(data, 1, w, out_fh); data += pitch; } } } env->DeleteScriptEnvironment(); FreeLibrary(avsdll); } catch(AvisynthError err) { fprintf(stderr, "\nAvisynth error:\n%s\n", err.msg); return 1; } AVS_linkage = 0; fclose(out_fh); return 0; }
Compile this file into an EXE named avs2yuv.exe. See compiling instructions. Now open the command line and go to the folder where avs2yuv.exe and your script (called example.avs here) is loaded:
ColorBars() ConvertToYV12() Trim(0,4) Showframenumber()
Type the following on the command line (the name of the output clip can be arbitrary in our application):
avs2yuv.exe example.avs output.raw
Line by line breakdown
Here's a line-by-line breakdown of avs2yuv.cpp.
#include <stdio.h>
The header stdio.h contains objects like stderr (of type FILE *), and functions like [www.cplusplus.com/reference/cstdio/fprintf/ fprintf], fopen.
The standard error stream (stderr) is the default destination for error messages and other diagnostic warnings. Like stdout, it is usually also directed by default to the text console (generally, on the screen).
fprintf writes formatted data to stream.
fopen opens the file whose name is specified in the parameter filename and associates it with a stream that can be identified in future operations by the FILE pointer returned.
#include <Windows.h>
#include "avisynth.h"
This header declares all the classes and miscellaneous constants that you might need when accessing avisynth.dll.
#define MY_VERSION "Avs2YUV 0.24"
Defines the version numbers which will be printed (using the "-h" option) later on.
const AVS_Linkage *AVS_linkage = 0; int __cdecl main(int argc, const char* argv[]) { const char* infile = NULL; const char* outfile = NULL; FILE* out_fh; if (!strcmp(argv[1], "-h")) { fprintf(stderr, MY_VERSION "\n" "Usage: avs2yuv.exe in.avs out.raw\n"); return 2; } else { infile = argv[1]; outfile = argv[2]; } try { char* colorformat; IScriptEnvironment* (__stdcall *CreateEnv)(int); HMODULE avsdll = LoadLibrary("avisynth.dll"); if (!avsdll) { fprintf(stderr, "failed to load avisynth.dll\n"); return 2; } CreateEnv = (IScriptEnvironment *(__stdcall *)(int))GetProcAddress(avsdll, "CreateScriptEnvironment"); if (!CreateEnv) { fprintf(stderr, "failed to load CreateScriptEnvironment()\n"); return 1; } IScriptEnvironment* env = CreateEnv(AVISYNTH_INTERFACE_VERSION); env->CheckVersion(5); AVS_linkage = env->GetAVSLinkage(); AVSValue arg(infile); AVSValue res = env->Invoke("Import", AVSValue(&arg, 1)); if (!res.IsClip()) { fprintf(stderr, "Error: '%s' didn't return a video clip.\n", infile); return 1; } PClip clip = res.AsClip(); VideoInfo vi = clip->GetVideoInfo(); fprintf(stderr, " %s:\n", infile); fprintf(stderr, " %dx%d,\n", vi.width, vi.height); fprintf(stderr, " %d/%d fps,\n", vi.fps_numerator, vi.fps_denominator); fprintf(stderr, " %d frames,\n", vi.num_frames); if (vi.IsYUV()) { colorformat = "YUV"; } else { colorformat = "RGB"; } fprintf(stderr, " %s color format", colorformat); out_fh = fopen(outfile, "wb"); if (!out_fh) { fprintf(stderr, "fopen(\"%s\") failed", outfile); return 1; } for (int frm = 0; frm < vi.num_frames; ++frm) { PVideoFrame f = clip->GetFrame(frm, env); static const int planes[] = {PLANAR_Y, PLANAR_U, PLANAR_V}; int wrote = 0; for (int p=0; p<3; p++) { // for interleaved formats only the first plane (being the whole frame) is written int w = vi.width >> vi.GetPlaneWidthSubsampling(planes[p]); int h = vi.height >> vi.GetPlaneHeightSubsampling(planes[p]); int pitch = f->GetPitch(planes[p]); const BYTE* data = f->GetReadPtr(planes[p]); for (int y=0; y<h; y++) { wrote += fwrite(data, 1, w, out_fh); data += pitch; } } } env->DeleteScriptEnvironment(); FreeLibrary(avsdll); } catch(AvisynthError err) { fprintf(stderr, "\nAvisynth error:\n%s\n", err.msg); return 1; } AVS_linkage = 0; fclose(out_fh); return 0; }
todo - static and dynamic linking (see above) - http://msdn.microsoft.com/en-us/library/windows/desktop/ms685090%28v=vs.85%29.aspx