Esempio n. 1
0
    /// <summary>
    /// Opens and reads the data for the specified file.
    /// </summary>
    /// <param name="fileName">The full path and file name of the MP4 file to open.</param>
    /// <returns>An <see cref="Mp4File"/> object you can use to manipulate file.</returns>
    /// <exception cref="ArgumentException">
    /// Thrown if the specified file name is <see langword="null"/> or the empty string.
    /// </exception>
    public static Mp4File Open(string fileName)
    {
        var file = new Mp4File(fileName);

        file.Load();
        return(file);
    }
Esempio n. 2
0
    /// <inheritdoc/>
    public Video ReadVideo(string path)
    {
        var file = Mp4File.Open(path);
        var tags = file.Tags;

        if (tags is null)
        {
            throw new ArgumentException(default, nameof(path));
Esempio n. 3
0
        /// <summary>
        /// Read Mfra box.
        /// </summary>
        /// <param name="stream">Mp4 stream.</param>
        /// <returns>Mfra box.</returns>
        private Mp4MfraBox GetMfra(Mp4Stream stream)
        {
            stream.Position = stream.Length - 4;
            uint mfraSize = stream.ReadUInt32();

            stream.Position = stream.Length - mfraSize;
            var file = new Mp4File(stream);

            return((Mp4MfraBox)file.Boxes[0]);
        }
Esempio n. 4
0
        public void ShowFile(Mp4File file)
        {
            RemoveViews();

            if (file != null)
            {
                IMainView view = _Container.Resolve <IMainView>();
                view.File = file;
                IRegion mainRegion = _RegionManager.Regions[RegionNames.MainRegion];
                mainRegion.Add(view);
                mainRegion.Activate(view);
            }
        }
Esempio n. 5
0
        private void Open(object obj)
        {
            try
            {
                var openFileDialog = new OpenFileDialog
                {
                    Filter      = "MP4 Files (*.mp4,*.m4a,*.ismv,*.mov)|*.mp4;*.m4a;*.ismv;*.mov|All Files (*.*)|*.*",
                    FilterIndex = 1
                };

                if (openFileDialog.ShowDialog() == true)
                {
                    _Stream?.Close();
                    var       backgroundWorker = new BackgroundWorker();
                    Exception exceptionError   = null;
                    backgroundWorker.DoWork += (object s, DoWorkEventArgs args) =>
                    {
                        try
                        {
                            _Stream = new Mp4Stream(openFileDialog.OpenFile());
                            _File   = new Mp4File(_Stream);
                            List <Mp4Box> unknowBoxes = _File.Boxes.FindAll(b => b is Mp4UnknownBox);
                            if (unknowBoxes.Count > 1)
                            {
                                throw new Exception("Too many unknown boxes.");
                            }
                            View.Dispatcher.Invoke(new Action(() =>
                            {
                                View.RootNode = BuildTree(_File, Path.GetFileName(openFileDialog.FileName));
                                _Controller.RemoveViews();
                            }));
                        }
                        catch (Exception ex)
                        {
                            exceptionError = ex;
                        }
                    };
                    var progressWindow = new ProgressWindow(backgroundWorker);
                    progressWindow.ShowDialog();
                    if (exceptionError != null)
                    {
                        throw exceptionError;
                    }
                }
            }
            catch
            {
                MessageBox.Show("Error loading mp4 file", "Error", MessageBoxButton.OK, MessageBoxImage.Error);
            }
        }
Esempio n. 6
0
        /// <summary>
        ///
        /// </summary>
        /// <param name="file"></param>
        /// <param name="name"></param>
        /// <returns></returns>
        private TreeViewItem BuildTree(Mp4File file, string name)
        {
            ImageTreeViewItem root = new ImageTreeViewItem()
            {
                Text = name, ImageSource = "/Mp4Explorer;component/Images/movie_16.ico"
            };

            foreach (Mp4Box box in file.Boxes)
            {
                root.Items.Add(new Mp4TreeNode(box));
            }

            return(root);
        }
Esempio n. 7
0
        private void ReadMp4File(Stream fileStream, string fileName)
        {
            if (stream != null)
            {
                stream.Close();
            }

            BackgroundWorker backgroundWorker = new BackgroundWorker();
            Exception        exceptionError   = null;

            backgroundWorker.DoWork += delegate
            {
                try
                {
                    stream = new Mp4Stream(fileStream);
                    file   = new Mp4File(stream);

                    List <Mp4Box> unknowBoxes = file.Boxes.FindAll(b => b is Mp4UnknownBox);

                    if (unknowBoxes.Count > 1)
                    {
                        throw new Exception("Too many unknow boxes.");
                    }

                    View.Dispatcher.Invoke(new Action(delegate
                    {
                        this.View.RootNode = BuildTree(file, new FileInfo(fileName).Name);

                        controller.RemoveViews();
                    }));
                }
                catch (Exception ex)
                {
                    exceptionError = ex;
                }
            };

            ProgressWindow progressWindow = new ProgressWindow();

            progressWindow.Worker = backgroundWorker;

            progressWindow.ShowDialog();

            if (exceptionError != null)
            {
                throw exceptionError;
            }
        }
Esempio n. 8
0
    /// <inheritdoc/>
    public void UpdateEpisode(string fileName, Episode episode, IDictionary <MediaTrackType, string>?languages = default)
    {
        var file = Mp4File.Open(fileName);

        Update(file, episode, MediaKind.TVShow, languages);
        if (file.Tags is not null)
        {
            // episode
            file.Tags.EpisodeNumber = ValueOrNull(episode.Number);
            file.Tags.SeasonNumber  = ValueOrNull(episode.Season);
            file.Tags.TVShow        = episode.Show;
            file.Tags.EpisodeId     = episode.Id;
            file.Tags.TVNetwork     = episode.Network;
            file.Tags.ContentId     = episode.Part;
        }

        file.Save();
Esempio n. 9
0
        public override async Task <StatusHandler> ProcessAsync(LibraryBook libraryBook)
        {
            OnBegin(libraryBook);

            OnStreamingBegin($"Begin converting {libraryBook} to mp3");

            try
            {
                var m4bPath = AudibleFileStorage.Audio.GetPath(libraryBook.Book.AudibleProductId);
                m4bBook = new Mp4File(m4bPath, FileAccess.Read);
                m4bBook.ConversionProgressUpdate += M4bBook_ConversionProgressUpdate;

                fileSize = m4bBook.InputStream.Length;

                OnTitleDiscovered(m4bBook.AppleTags.Title);
                OnAuthorsDiscovered(m4bBook.AppleTags.FirstAuthor);
                OnNarratorsDiscovered(m4bBook.AppleTags.Narrator);
                OnCoverImageDiscovered(m4bBook.AppleTags.Cover);

                using var mp3File = File.OpenWrite(Path.GetTempFileName());

                var result = await Task.Run(() => m4bBook.ConvertToMp3(mp3File));

                m4bBook.InputStream.Close();
                mp3File.Close();

                var proposedMp3Path = Mp3FileName(m4bPath);
                var realMp3Path     = FileUtility.SaferMoveToValidPath(mp3File.Name, proposedMp3Path);
                OnFileCreated(libraryBook, realMp3Path);

                var statusHandler = new StatusHandler();

                if (result == ConversionResult.Failed)
                {
                    statusHandler.AddError("Conversion failed");
                }

                return(statusHandler);
            }
            finally
            {
                OnStreamingCompleted($"Completed converting to mp3: {libraryBook.Book.Title}");
                OnCompleted(libraryBook);
            }
        }
Esempio n. 10
0
 /// <inheritdoc/>
 public void UpdateVideo(string fileName, Video video, IDictionary <MediaTrackType, string>?languages = default)
 {
     if (video is Episode episode)
     {
         this.UpdateEpisode(fileName, episode, languages);
     }
     else if (video is Movie movie)
     {
         this.UpdateMovie(fileName, movie, languages);
     }
     else
     {
         var file      = Mp4File.Open(fileName);
         var mediaType = file.Tags is null
             ? MediaKind.NotSet
             : file.Tags.MediaType;
         Update(file, video, mediaType, languages);
         file.Save();
     }
 }
Esempio n. 11
0
        internal TrackInfo(Mp4File mp4)
        {
            var       sam = mp4.audioTrackSample;
            MediaInfo in4 = mp4.audioTrack.info;

            maxBytesInFrame = in4.mediaInformation.sampleTable.maxBytesInFrame;
            sampleRate      = (int)(sam.sampleRateInt >> 16);
            bitsPerSample   = sam.bitsPerSample;
            channelsCount   = sam.channelCount;

            if (sam is MP4AudioSampleEntry)
            {
                audioCodec = eAudioCodec.AAC;
                uint sampleDelta = in4.mediaInformation.sampleTable.timeToSample[0].sampleDelta;
                uint timeScale   = in4.timeScale;
                long samples     = ((long)sampleDelta * sampleRate) / timeScale;
                samplesPerFrame = checked ((int)samples);
                if (16 != bitsPerSample)
                {
                    throw new NotSupportedException("Currently, the library only supports 16-bit samples");
                }

                decoderConfigBlob = mp4.audioTrackSample.audioSpecificConfig;
                strippedHeader    = null;
                return;
            }
            if (sam is Ac3AudioSampleEntry)
            {
                audioCodec        = eAudioCodec.AC3;
                decoderConfigBlob = null;
                strippedHeader    = null;
                if (maxBytesInFrame > IO.Dolby.liba52.maxEncodedBuffer)
                {
                    throw new ArgumentException($"Sample entry specified { maxBytesInFrame } bytes / frame, this exceeds the codec limit of { IO.Dolby.liba52.maxEncodedBuffer }");
                }
                samplesPerFrame = IO.Dolby.liba52.samplesPerFrame;
                return;
            }

            throw new ApplicationException("Unrecognized audio codec");
        }
Esempio n. 12
0
        public bool Step2_DownloadAndCombine()
        {
            DecryptProgressUpdate?.Invoke(this, 0);

            if (File.Exists(OutputFileName))
            {
                FileExt.SafeDelete(OutputFileName);
            }

            FileStream outFile = File.OpenWrite(OutputFileName);

            aaxFile.SetDecryptionKey(downloadLicense.AudibleKey, downloadLicense.AudibleIV);

            aaxFile.ConversionProgressUpdate += AaxFile_ConversionProgressUpdate;

            var decryptionResult = OutputFormat == OutputFormat.Mp4a ? aaxFile.ConvertToMp4a(outFile, downloadLicense.ChapterInfo) : aaxFile.ConvertToMp3(outFile);

            aaxFile.ConversionProgressUpdate -= AaxFile_ConversionProgressUpdate;

            aaxFile.Close();

            downloadLicense.ChapterInfo = aaxFile.Chapters;

            if (decryptionResult == ConversionResult.NoErrorsDetected &&
                coverArt is not null &&
                OutputFormat == OutputFormat.Mp4a)
            {
                //This handles a special case where the aaxc file doesn't contain cover art and
                //Libation downloaded it instead (Animal Farm). Currently only works for Mp4a files.
                using var decryptedBook = new Mp4File(OutputFileName, FileAccess.ReadWrite);
                decryptedBook.AppleTags?.SetCoverArt(coverArt);
                decryptedBook.Save();
                decryptedBook.Close();
            }

            nfsPersister.Dispose();

            DecryptProgressUpdate?.Invoke(this, 0);

            return(decryptionResult == ConversionResult.NoErrorsDetected && !isCanceled);
        }
Esempio n. 13
0
        public static VideoSampleReader create(Mp4File mp4)
        {
            TrackMetadata track = mp4.videoTrack;

            if (null == track)
            {
                throw new ApplicationException("The MP4 doesn’t have a video track");
            }

            VideoSampleEntry vse = mp4.videoTrackSample;

            switch (vse.naluLengthSize)
            {
            case 4:
                return(new VideoSampleReader4(mp4));

            case 3:
                return(new VideoSampleReader3(mp4));
            }
            // The specs also defines 1 and 2 bytes versions.
            // Slightly harder to handle as we need to expand the samples, 3 bytes is the minimum length of NALU start code in Annex B bitstream.
            throw new NotImplementedException();
        }
Esempio n. 14
0
        /// <summary>
        ///
        /// </summary>
        /// <param name="obj"></param>
        private void Open(object obj)
        {
            try
            {
                OpenFileDialog openFileDialog = new OpenFileDialog();

                //openFileDialog.Filter = "MP4 Files (*.mp4,*.m4a,*.ismv,*.mov,*.qlv)|*.mp4;*.m4a;*.ismv;*.mov;*.qlv|All Files (*.*)|*.*";
                openFileDialog.Filter      = "MP4 Files (*.mp4,*.m4a,*.ismv,*.mov)|*.mp4;*.m4a;*.ismv;*.mov|All Files (*.*)|*.*";
                openFileDialog.FilterIndex = 1;

                if (openFileDialog.ShowDialog() == true)
                {
                    if (stream != null)
                    {
                        stream.Close();
                    }

                    BackgroundWorker backgroundWorker = new BackgroundWorker();

                    Exception exceptionError = null;

                    backgroundWorker.DoWork += delegate(object s, DoWorkEventArgs args)
                    {
                        try
                        {
                            stream = new Mp4Stream(openFileDialog.OpenFile());
                            file   = new Mp4File(stream);

                            List <Mp4Box> unknowBoxes = file.Boxes.FindAll(b => b is Mp4UnknownBox);

                            //if (unknowBoxes.Count > 1)
                            //    throw new Exception("Too many unknow boxes.");

                            View.Dispatcher.Invoke(new Action(delegate
                            {
                                this.View.RootNode = BuildTree(file, new FileInfo(openFileDialog.FileName).Name);

                                controller.RemoveViews();
                            }));
                        }
                        catch (Exception ex)
                        {
                            exceptionError = ex;
                        }
                    };

                    ProgressWindow progressWindow = new ProgressWindow();

                    progressWindow.Worker = backgroundWorker;

                    progressWindow.ShowDialog();

                    if (exceptionError != null)
                    {
                        throw exceptionError;
                    }
                }
            }
            catch
            {
                MessageBox.Show("Error loading mp4 file", "Error", MessageBoxButton.OK, MessageBoxImage.Error);
            }
        }
Esempio n. 15
0
 public Reader(Mp4File mp4)
 {
     stream       = mp4.reader.stream;
     sampleReader = new SampleReader(mp4.audioTrack);
 }
Esempio n. 16
0
 public VideoSampleReader3(Mp4File mp4) : base(mp4)
 {
 }
Esempio n. 17
0
 public VideoSampleReader(Mp4File mp4)
 {
     stream       = mp4.reader.stream;
     sampleReader = new SampleReader(mp4.videoTrack);
 }