File indexing completed on 2024-05-12 04:44:37

0001 /*
0002     Copyright (C) 2012-2021 Harald Sitter <sitter@kde.org>
0003 
0004     This library is free software; you can redistribute it and/or
0005     modify it under the terms of the GNU Lesser General Public
0006     License as published by the Free Software Foundation; either
0007     version 2.1 of the License, or (at your option) any later version.
0008 
0009     This library is distributed in the hope that it will be useful,
0010     but WITHOUT ANY WARRANTY; without even the implied warranty of
0011     MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
0012     Lesser General Public License for more details.
0013 
0014     You should have received a copy of the GNU Lesser General Public
0015     License along with this library.  If not, see <http://www.gnu.org/licenses/>.
0016 */
0017 
0018 #include "videomemorystream.h"
0019 
0020 #include <vlc/plugins/vlc_picture.h>
0021 
0022 #include "mediaplayer.h"
0023 #include "utils/debug.h"
0024 
0025 namespace Phonon {
0026 namespace VLC {
0027 
0028 static inline VideoMemoryStream *p_this(void *opaque) { return static_cast<VideoMemoryStream *>(opaque); }
0029 static inline VideoMemoryStream *p_this(void **opaque) { return static_cast<VideoMemoryStream *>(*opaque); }
0030 #define P_THIS p_this(opaque)
0031 
0032 VideoMemoryStream::VideoMemoryStream()
0033 {
0034 }
0035 
0036 VideoMemoryStream::~VideoMemoryStream()
0037 {
0038 }
0039 
0040 unsigned VideoMemoryStream::setPitchAndLines(uint32_t fourcc,
0041                                              unsigned width, unsigned height,
0042                                              unsigned *pitches, unsigned *lines)
0043 {
0044     // Fairly unclear what the last two arguments do, they seem to make no diff for the planes though, so I guess they can be anything in our case.
0045     const auto picture = picture_New(fourcc, width, height, 0, 1);
0046 
0047     unsigned bufferSize = 0;
0048 
0049     for (auto i = 0; i < picture->i_planes; ++i) {
0050         const auto plane = picture->p[i];
0051         pitches[i] = plane.i_visible_pitch;
0052         lines[i] = plane.i_visible_lines;
0053         bufferSize += (pitches[i] * lines[i]);
0054     }
0055 
0056     return bufferSize;
0057 }
0058 
0059 void VideoMemoryStream::setCallbacks(MediaPlayer *player)
0060 {
0061     libvlc_video_set_callbacks(player->libvlc_media_player(),
0062                                lockCallbackInternal,
0063                                unlockCallbackInternal,
0064                                displayCallbackInternal,
0065                                this);
0066     libvlc_video_set_format_callbacks(player->libvlc_media_player(),
0067                                       formatCallbackInternal,
0068                                       formatCleanUpCallbackInternal);
0069 }
0070 
0071 void VideoMemoryStream::unsetCallbacks(MediaPlayer *player)
0072 {
0073     libvlc_video_set_callbacks(player->libvlc_media_player(),
0074                                0,
0075                                0,
0076                                0,
0077                                0);
0078     libvlc_video_set_format_callbacks(player->libvlc_media_player(),
0079                                       0,
0080                                       0);
0081 }
0082 
0083 
0084 void *VideoMemoryStream::lockCallbackInternal(void *opaque, void **planes)
0085 {
0086     return P_THIS->lockCallback(planes);
0087 }
0088 
0089 void VideoMemoryStream::unlockCallbackInternal(void *opaque, void *picture, void *const*planes)
0090 {
0091     P_THIS->unlockCallback(picture, planes);
0092 }
0093 
0094 void VideoMemoryStream::displayCallbackInternal(void *opaque, void *picture)
0095 {
0096     P_THIS->displayCallback(picture);
0097 }
0098 
0099 unsigned VideoMemoryStream::formatCallbackInternal(void **opaque, char *chroma,
0100                                                    unsigned *width, unsigned *height,
0101                                                    unsigned *pitches, unsigned *lines)
0102 {
0103     auto ret = P_THIS->formatCallback(chroma, width, height, pitches, lines);
0104 
0105     if (Debug::debugEnabled()) {
0106         QStringList pitchValues;
0107         QStringList lineValues;
0108         unsigned *pitch = pitches;
0109         unsigned *line = lines;
0110         for (; *pitch != 0; ++pitch) {
0111             Q_ASSERT(lines != 0); // pitch and line tables ought to be the same size
0112             pitchValues << QString::number(*pitch);
0113             lineValues << QString::number(*line);
0114         }
0115         const QString separator = QStringLiteral(", ");
0116         debug() << "vmem-format[chroma:" << chroma << "w:" << *width << "h:" << *height
0117                 << "pitches:" << pitchValues.join(separator) << "lines:" << lineValues.join(separator)
0118                 << "size:" << ret << "]";
0119     }
0120 
0121     return ret;
0122 }
0123 
0124 void VideoMemoryStream::formatCleanUpCallbackInternal(void *opaque)
0125 {
0126     P_THIS->formatCleanUpCallback();
0127 }
0128 
0129 } // namespace VLC
0130 } // namespace Phonon