skia2/tools/skottie2movie.cpp
Mike Reed 5093e23de6 support assets for skottie2movie
Change-Id: Icb66c9cf4eb2db72997b566fe863dab21d2824ef
Reviewed-on: https://skia-review.googlesource.com/c/skia/+/216871
Reviewed-by: Florin Malita <fmalita@chromium.org>
Commit-Queue: Mike Reed <reed@google.com>
2019-05-30 14:37:29 +00:00

106 lines
3.2 KiB
C++

/*
* Copyright 2014 Google Inc.
*
* Use of this source code is governed by a BSD-style license that can be
* found in the LICENSE file.
*/
#include "modules/skottie/include/Skottie.h"
#include "modules/skottie/utils/SkottieUtils.h"
#include "include/core/SkStream.h"
#include "include/core/SkTime.h"
#include "src/utils/SkOSPath.h"
#include "experimental/ffmpeg/SkVideoEncoder.h"
#include "tools/flags/CommandLineFlags.h"
static DEFINE_string2(input, i, "", "skottie animation to render");
static DEFINE_string2(output, o, "", "mp4 file to create");
static DEFINE_string2(assetPath, a, "", "path to assets needed for json file");
static DEFINE_int_2(fps, f, 25, "fps");
static DEFINE_bool2(verbose, v, false, "verbose mode");
static DEFINE_bool2(loop, l, false, "loop mode for profiling");
int main(int argc, char** argv) {
CommandLineFlags::SetUsage("Converts skottie to a mp4");
CommandLineFlags::Parse(argc, argv);
if (FLAGS_input.count() == 0) {
SkDebugf("-i input_file.json argument required\n");
return -1;
}
SkString assetPath;
if (FLAGS_assetPath.count() > 0) {
assetPath.set(FLAGS_assetPath[0]);
} else {
assetPath = SkOSPath::Dirname(FLAGS_input[0]);
}
SkDebugf("assetPath %s\n", assetPath.c_str());
auto animation = skottie::Animation::Builder()
.setResourceProvider(skottie_utils::FileResourceProvider::Make(assetPath))
.makeFromFile(FLAGS_input[0]);
if (!animation) {
SkDebugf("failed to load %s\n", FLAGS_input[0]);
return -1;
}
SkISize dim = animation->size().toRound();
double duration = animation->duration();
int fps = FLAGS_fps;
if (fps < 1) {
fps = 1;
} else if (fps > 240) {
fps = 240;
}
if (FLAGS_verbose) {
SkDebugf("size %dx%d duration %g\n", dim.width(), dim.height(), duration, fps);
}
SkVideoEncoder encoder;
const int frames = SkScalarRoundToInt(duration * fps);
while (FLAGS_loop) {
double start = SkTime::GetSecs();
encoder.beginRecording(dim, fps);
for (int i = 0; i <= frames; ++i) {
animation->seek(i * 1.0 / frames); // normalized time
animation->render(encoder.beginFrame());
encoder.endFrame();
}
(void)encoder.endRecording();
if (FLAGS_verbose) {
double dur = SkTime::GetSecs() - start;
SkDebugf("%d frames, %g secs, %d fps\n",
frames, dur, (int)floor(frames / dur + 0.5));
}
}
encoder.beginRecording(dim, fps);
for (int i = 0; i <= frames; ++i) {
double ts = i * 1.0 / fps;
if (FLAGS_verbose) {
SkDebugf("rendering frame %d ts %g\n", i, ts);
}
animation->seek(i * 1.0 / frames); // normalized time
animation->render(encoder.beginFrame());
encoder.endFrame();
}
if (FLAGS_output.count() == 0) {
SkDebugf("missing -o output_file.mp4 argument\n");
return 0;
}
auto data = encoder.endRecording();
SkFILEWStream ostream(FLAGS_output[0]);
if (!ostream.isValid()) {
SkDebugf("Can't create output file %s\n", FLAGS_output[0]);
return -1;
}
ostream.write(data->data(), data->size());
return 0;
}