1/*
2 * Copyright 2013, The Android Open Source Project
3 *
4 * Licensed under the Apache License, Version 2.0 (the "License");
5 * you may not use this file except in compliance with the License.
6 * You may obtain a copy of the License at
7 *
8 *     http://www.apache.org/licenses/LICENSE-2.0
9 *
10 * Unless required by applicable law or agreed to in writing, software
11 * distributed under the License is distributed on an "AS IS" BASIS,
12 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13 * See the License for the specific language governing permissions and
14 * limitations under the License.
15 */
16
17#ifndef MEDIA_MUXER_H_
18#define MEDIA_MUXER_H_
19
20#include <utils/Errors.h>
21#include <utils/RefBase.h>
22#include <utils/Vector.h>
23#include <utils/threads.h>
24
25#include "foundation/ABase.h"
26
27namespace android {
28
29struct ABuffer;
30struct AMessage;
31struct MediaAdapter;
32class MediaBuffer;
33struct MediaSource;
34class MetaData;
35struct MediaWriter;
36
37// MediaMuxer is used to mux multiple tracks into a video. Currently, we only
38// support a mp4 file as the output.
39// The expected calling order of the functions is:
40// Constructor -> addTrack+ -> start -> writeSampleData+ -> stop
41// If muxing operation need to be cancelled, the app is responsible for
42// deleting the output file after stop.
43struct MediaMuxer : public RefBase {
44public:
45    // Please update media/java/android/media/MediaMuxer.java if the
46    // OutputFormat is updated.
47    enum OutputFormat {
48        OUTPUT_FORMAT_MPEG_4      = 0,
49        OUTPUT_FORMAT_WEBM        = 1,
50        OUTPUT_FORMAT_THREE_GPP   = 2,
51        OUTPUT_FORMAT_HEIF        = 3,
52        OUTPUT_FORMAT_LIST_END // must be last - used to validate format type
53    };
54
55    // Construct the muxer with the file descriptor. Note that the MediaMuxer
56    // will close this file at stop().
57    MediaMuxer(int fd, OutputFormat format);
58
59    virtual ~MediaMuxer();
60
61    /**
62     * Add a track with its format information. This should be
63     * called before start().
64     * @param format the track's format.
65     * @return the track's index or negative number if error.
66     */
67    ssize_t addTrack(const sp<AMessage> &format);
68
69    /**
70     * Start muxing. Make sure all the tracks have been added before
71     * calling this.
72     */
73    status_t start();
74
75    /**
76     * Set the orientation hint.
77     * @param degrees The rotation degrees. It has to be either 0,
78     *                90, 180 or 270.
79     * @return OK if no error.
80     */
81    status_t setOrientationHint(int degrees);
82
83    /**
84     * Set the location.
85     * @param latitude The latitude in degree x 1000. Its value must be in the range
86     * [-900000, 900000].
87     * @param longitude The longitude in degree x 1000. Its value must be in the range
88     * [-1800000, 1800000].
89     * @return OK if no error.
90     */
91    status_t setLocation(int latitude, int longitude);
92
93    /**
94     * Stop muxing.
95     * This method is a blocking call. Depending on how
96     * much data is bufferred internally, the time needed for stopping
97     * the muxer may be time consuming. UI thread is
98     * not recommended for launching this call.
99     * @return OK if no error.
100     */
101    status_t stop();
102
103    /**
104     * Send a sample buffer for muxing.
105     * The buffer can be reused once this method returns. Typically,
106     * this function won't be blocked for very long, and thus there
107     * is no need to use a separate thread calling this method to
108     * push a buffer.
109     * @param buffer the incoming sample buffer.
110     * @param trackIndex the buffer's track index number.
111     * @param timeUs the buffer's time stamp.
112     * @param flags the only supported flag for now is
113     *              MediaCodec::BUFFER_FLAG_SYNCFRAME.
114     * @return OK if no error.
115     */
116    status_t writeSampleData(const sp<ABuffer> &buffer, size_t trackIndex,
117                             int64_t timeUs, uint32_t flags) ;
118
119private:
120    const OutputFormat mFormat;
121    sp<MediaWriter> mWriter;
122    Vector< sp<MediaAdapter> > mTrackList;  // Each track has its MediaAdapter.
123    sp<MetaData> mFileMeta;  // Metadata for the whole file.
124
125    Mutex mMuxerLock;
126
127    enum State {
128        UNINITIALIZED,
129        INITIALIZED,
130        STARTED,
131        STOPPED
132    };
133    State mState;
134
135    DISALLOW_EVIL_CONSTRUCTORS(MediaMuxer);
136};
137
138}  // namespace android
139
140#endif  // MEDIA_MUXER_H_
141
142