Line data Source code
1 : /* -*- Mode: C++; tab-width: 2; indent-tabs-mode: nil; c-basic-offset: 2 -*- */
2 : /* This Source Code Form is subject to the terms of the Mozilla Public
3 : * License, v. 2.0. If a copy of the MPL was not distributed with this file,
4 : * You can obtain one at http://mozilla.org/MPL/2.0/. */
5 :
6 : #ifndef MOZILLA_VIDEOSEGMENT_H_
7 : #define MOZILLA_VIDEOSEGMENT_H_
8 :
9 : #include "MediaSegment.h"
10 : #include "nsCOMPtr.h"
11 : #include "gfxPoint.h"
12 : #include "ImageContainer.h"
13 :
14 : namespace mozilla {
15 :
16 : namespace layers {
17 : class Image;
18 : } // namespace layers
19 :
20 0 : class VideoFrame {
21 : public:
22 : typedef mozilla::layers::Image Image;
23 :
24 : VideoFrame(already_AddRefed<Image>& aImage, const gfx::IntSize& aIntrinsicSize);
25 : VideoFrame();
26 : ~VideoFrame();
27 :
28 0 : bool operator==(const VideoFrame& aFrame) const
29 : {
30 0 : return mIntrinsicSize == aFrame.mIntrinsicSize &&
31 0 : mForceBlack == aFrame.mForceBlack &&
32 0 : ((mForceBlack && aFrame.mForceBlack) || mImage == aFrame.mImage) &&
33 0 : mPrincipalHandle == aFrame.mPrincipalHandle;
34 : }
35 : bool operator!=(const VideoFrame& aFrame) const
36 : {
37 : return !operator==(aFrame);
38 : }
39 :
40 0 : Image* GetImage() const { return mImage; }
41 0 : void SetForceBlack(bool aForceBlack) { mForceBlack = aForceBlack; }
42 0 : bool GetForceBlack() const { return mForceBlack; }
43 0 : void SetPrincipalHandle(const PrincipalHandle& aPrincipalHandle) { mPrincipalHandle = aPrincipalHandle; }
44 0 : PrincipalHandle GetPrincipalHandle() const { return mPrincipalHandle; }
45 0 : const gfx::IntSize& GetIntrinsicSize() const { return mIntrinsicSize; }
46 : void SetNull();
47 : void TakeFrom(VideoFrame* aFrame);
48 :
49 : // Create a planar YCbCr black image.
50 : static already_AddRefed<Image> CreateBlackImage(const gfx::IntSize& aSize);
51 :
52 : protected:
53 : // mImage can be null to indicate "no video" (aka "empty frame"). It can
54 : // still have an intrinsic size in this case.
55 : RefPtr<Image> mImage;
56 : // The desired size to render the video frame at.
57 : gfx::IntSize mIntrinsicSize;
58 : bool mForceBlack;
59 : // principalHandle for the image in this frame.
60 : // This can be compared to an nsIPrincipal when back on main thread.
61 : PrincipalHandle mPrincipalHandle;
62 : };
63 :
64 0 : struct VideoChunk {
65 : VideoChunk();
66 : ~VideoChunk();
67 0 : void SliceTo(StreamTime aStart, StreamTime aEnd)
68 : {
69 0 : NS_ASSERTION(aStart >= 0 && aStart < aEnd && aEnd <= mDuration,
70 : "Slice out of bounds");
71 0 : mDuration = aEnd - aStart;
72 0 : }
73 0 : StreamTime GetDuration() const { return mDuration; }
74 0 : bool CanCombineWithFollowing(const VideoChunk& aOther) const
75 : {
76 0 : return aOther.mFrame == mFrame;
77 : }
78 0 : bool IsNull() const { return !mFrame.GetImage(); }
79 0 : void SetNull(StreamTime aDuration)
80 : {
81 0 : mDuration = aDuration;
82 0 : mFrame.SetNull();
83 0 : mTimeStamp = TimeStamp();
84 0 : }
85 0 : void SetForceBlack(bool aForceBlack) { mFrame.SetForceBlack(aForceBlack); }
86 :
87 0 : size_t SizeOfExcludingThisIfUnshared(MallocSizeOf aMallocSizeOf) const
88 : {
89 : // Future:
90 : // - mFrame
91 0 : return 0;
92 : }
93 :
94 0 : PrincipalHandle GetPrincipalHandle() const { return mFrame.GetPrincipalHandle(); }
95 :
96 : StreamTime mDuration;
97 : VideoFrame mFrame;
98 : TimeStamp mTimeStamp;
99 : };
100 :
101 : class VideoSegment : public MediaSegmentBase<VideoSegment, VideoChunk> {
102 : public:
103 : typedef mozilla::layers::Image Image;
104 : typedef mozilla::gfx::IntSize IntSize;
105 :
106 : VideoSegment();
107 : ~VideoSegment();
108 :
109 : void AppendFrame(already_AddRefed<Image>&& aImage,
110 : StreamTime aDuration,
111 : const IntSize& aIntrinsicSize,
112 : const PrincipalHandle& aPrincipalHandle,
113 : bool aForceBlack = false,
114 : TimeStamp aTimeStamp = TimeStamp::Now());
115 0 : const VideoFrame* GetLastFrame(StreamTime* aStart = nullptr)
116 : {
117 0 : VideoChunk* c = GetLastChunk();
118 0 : if (!c) {
119 0 : return nullptr;
120 : }
121 0 : if (aStart) {
122 0 : *aStart = mDuration - c->mDuration;
123 : }
124 0 : return &c->mFrame;
125 : }
126 : // Override default impl
127 0 : void ReplaceWithDisabled() override {
128 0 : for (ChunkIterator i(*this);
129 0 : !i.IsEnded(); i.Next()) {
130 0 : VideoChunk& chunk = *i;
131 0 : chunk.SetForceBlack(true);
132 : }
133 0 : }
134 :
135 : // Segment-generic methods not in MediaSegmentBase
136 0 : static Type StaticType() { return VIDEO; }
137 :
138 0 : size_t SizeOfIncludingThis(MallocSizeOf aMallocSizeOf) const override
139 : {
140 0 : return aMallocSizeOf(this) + SizeOfExcludingThis(aMallocSizeOf);
141 : }
142 :
143 0 : bool IsEmpty() const
144 : {
145 0 : return mChunks.IsEmpty();
146 : }
147 :
148 : };
149 :
150 : } // namespace mozilla
151 :
152 : #endif /* MOZILLA_VIDEOSEGMENT_H_ */
|