aboutsummaryrefslogtreecommitdiff
path: root/Src/h264/nsv_h264_decoder.cpp
diff options
context:
space:
mode:
authorJean-Francois Mauguit <jfmauguit@mac.com>2024-09-24 09:03:25 -0400
committerGitHub <noreply@github.com>2024-09-24 09:03:25 -0400
commitbab614c421ed7ae329d26bf028c4a3b1d2450f5a (patch)
tree12f17f78986871dd2cfb0a56e5e93b545c1ae0d0 /Src/h264/nsv_h264_decoder.cpp
parent4bde6044fddf053f31795b9eaccdd2a5a527d21f (diff)
parent20d28e80a5c861a9d5f449ea911ab75b4f37ad0d (diff)
downloadwinamp-bab614c421ed7ae329d26bf028c4a3b1d2450f5a.tar.gz
Merge pull request #5 from WinampDesktop/community
Merge to main
Diffstat (limited to 'Src/h264/nsv_h264_decoder.cpp')
-rw-r--r--Src/h264/nsv_h264_decoder.cpp77
1 files changed, 77 insertions, 0 deletions
diff --git a/Src/h264/nsv_h264_decoder.cpp b/Src/h264/nsv_h264_decoder.cpp
new file mode 100644
index 00000000..3fa781ff
--- /dev/null
+++ b/Src/h264/nsv_h264_decoder.cpp
@@ -0,0 +1,77 @@
+#include "nsv_h264_decoder.h"
+#include "../nsv/nsvlib.h"
+#include "../nsv/dec_if.h"
+#include <assert.h>
+#include <Mferror.h>
+
+H264_Decoder::H264_Decoder()
+{
+ vidbufdec=0;
+ last_pic = 0;
+ decoder.Open();
+}
+
+H264_Decoder::~H264_Decoder()
+{
+ for (size_t i=0;i<buffered_frames.size();i++) {
+ nullsoft_h264_frame_data frame_data = buffered_frames[i];
+ decoder.FreeFrame((YV12_PLANES *)frame_data.data, frame_data.decoder_data);
+ }
+
+ decoder.FreeFrame(vidbufdec, last_pic);
+}
+
+int H264_Decoder::decode(int need_kf,
+ void *_in, int _in_len,
+ void **out, // out is set to a pointer to data
+ unsigned int *out_type, // 'Y','V','1','2' is currently defined
+ int *is_kf)
+{
+ *out_type=NSV_MAKETYPE('Y','V','1','2');
+
+ if (last_pic)
+ {
+ decoder.FreeFrame(vidbufdec, last_pic);
+ vidbufdec=0;
+ last_pic=0;
+ }
+
+ if (_in_len) {
+ for (;;) {
+ HRESULT hr = decoder.FeedRaw(_in, _in_len, 0);
+ if (hr == MF_E_NOTACCEPTING) {
+ nullsoft_h264_frame_data frame_data;
+ if (FAILED(decoder.GetFrame((YV12_PLANES **)&frame_data.data, &frame_data.decoder_data, &frame_data.local_timestamp))) {
+ continue;
+ }
+ buffered_frames.push_back(frame_data);
+ } else if (FAILED(hr)) {
+ return -1;
+ } else {
+ break;
+ }
+ }
+ } else {
+ decoder.Drain();
+ }
+
+ if (SUCCEEDED(decoder.GetFrame(&vidbufdec, &last_pic, 0))) {
+ *out = vidbufdec;
+ *is_kf = 1;
+ } else {
+ *out = 0;
+ }
+
+ return 0;
+}
+
+void H264_Decoder::flush()
+{
+ for ( size_t i = 0; i < buffered_frames.size(); i++ )
+ {
+ nullsoft_h264_frame_data frame_data = buffered_frames[ i ];
+ decoder.FreeFrame( (YV12_PLANES *)frame_data.data, frame_data.decoder_data );
+ }
+
+ decoder.Flush();
+}