Пример #1
0
        public void WriteParagraph(Paragraph p, Bitmap bmp, ContentAlignment alignment) // inspired by code from SubtitleCreator
        {
            // timestamp: 00:00:33:900, filepos: 000000000
            _idx.AppendLine(string.Format("timestamp: {0:00}:{1:00}:{2:00}:{3:000}, filepos: {4}", p.StartTime.Hours, p.StartTime.Minutes, p.StartTime.Seconds, p.StartTime.Milliseconds, _subFile.Position.ToString("X").PadLeft(9, '0').ToLower()));

            var nbmp = new NikseBitmap(bmp);

            _emphasis2 = nbmp.ConverToFourColors(_background, _pattern, _emphasis1, _useInnerAntialiasing);
            var twoPartBuffer = nbmp.RunLengthEncodeForDvd(_background, _pattern, _emphasis1, _emphasis2);
            var imageBuffer   = GetSubImageBuffer(twoPartBuffer, nbmp, p, alignment);

            int  bufferIndex = 0;
            byte vobSubId    = (byte)_languageStreamId;
            var  mwsub       = new MemWriter(200000);

            byte[] subHeader = new byte[30];
            byte[] ts        = new byte[4];

            // Lended from "Son2VobSub" by Alain Vielle and Petr Vyskocil
            // And also from Sup2VobSub by Emmel
            subHeader[0]  = 0x00; // MPEG 2 PACK HEADER
            subHeader[1]  = 0x00;
            subHeader[2]  = 0x01;
            subHeader[3]  = 0xba;
            subHeader[4]  = 0x44;
            subHeader[5]  = 0x02;
            subHeader[6]  = 0xc4;
            subHeader[7]  = 0x82;
            subHeader[8]  = 0x04;
            subHeader[9]  = 0xa9;
            subHeader[10] = 0x01;
            subHeader[11] = 0x89;
            subHeader[12] = 0xc3;
            subHeader[13] = 0xf8;

            subHeader[14] = 0x00; // PES
            subHeader[15] = 0x00;
            subHeader[16] = 0x01;
            subHeader[17] = 0xbd;

            int  packetSize = imageBuffer.Length;
            long toWrite    = packetSize; // Image buffer + control sequence length
            bool header0    = true;

            while (toWrite > 0)
            {
                long headerSize;
                if (header0)
                {
                    header0 = false;

                    // This is only for first packet
                    subHeader[20] = 0x81;   // mark as original
                    subHeader[21] = 0x80;   // first packet: PTS
                    subHeader[22] = 0x05;   // PES header data length

                    // PTS (90kHz):
                    //--------------
                    subHeader[23] = (byte)((ts[3] & 0xc0) >> 5 | 0x21);
                    subHeader[24] = (byte)((ts[3] & 0x3f) << 2 | (ts[2] & 0xc0) >> 6);
                    subHeader[25] = (byte)((ts[2] & 0x3f) << 2 | (ts[1] & 0x80) >> 6 | 0x01);
                    subHeader[26] = (byte)((ts[1] & 0x7f) << 1 | (ts[0] & 0x80) >> 7);
                    subHeader[27] = (byte)((ts[0] & 0x7f) << 1 | 0x01);

                    const string pre             = "0010"; // 0011 or 0010 ? (KMPlayer will not understand 0011!!!)
                    long         newPts          = (long)(p.StartTime.TotalSeconds * 90000.0 + 0.5);
                    string       bString         = Convert.ToString(newPts, 2).PadLeft(33, '0');
                    string       fiveBytesString = pre + bString.Substring(0, 3) + "1" + bString.Substring(3, 15) + "1" + bString.Substring(18, 15) + "1";
                    for (int i = 0; i < 5; i++)
                    {
                        subHeader[23 + i] = Convert.ToByte(fiveBytesString.Substring((i * 8), 8), 2);
                    }
                    subHeader[28] = vobSubId;
                    headerSize    = 29;
                }
                else
                {
                    subHeader[20] = 0x81; // mark as original
                    subHeader[21] = 0x00; // no PTS
                    subHeader[22] = 0x00; // header data length
                    subHeader[23] = vobSubId;
                    headerSize    = 24;
                }

                if ((toWrite + headerSize) <= 0x800)
                {
                    // write whole image in one 0x800 part

                    long j = (headerSize - 20) + toWrite;
                    subHeader[18] = (byte)(j / 0x100);
                    subHeader[19] = (byte)(j % 0x100);

                    // First Write header
                    for (int x = 0; x < headerSize; x++)
                    {
                        mwsub.WriteByte(subHeader[x]);
                    }

                    // Write Image Data
                    for (int x = 0; x < toWrite; x++)
                    {
                        mwsub.WriteByte(imageBuffer[bufferIndex++]);
                    }

                    // Pad remaining space
                    long paddingSize = 0x800 - headerSize - toWrite;
                    for (int x = 0; x < paddingSize; x++)
                    {
                        mwsub.WriteByte(0xff);
                    }

                    toWrite = 0;
                }
                else
                {
                    // write multiple parts

                    long blockSize = 0x800 - headerSize;
                    long j         = (headerSize - 20) + blockSize;
                    subHeader[18] = (byte)(j / 0x100);
                    subHeader[19] = (byte)(j % 0x100);

                    // First Write header
                    for (int x = 0; x < headerSize; x++)
                    {
                        mwsub.WriteByte(subHeader[x]);
                    }

                    // Write Image Data
                    for (int x = 0; x < blockSize; x++)
                    {
                        mwsub.WriteByte(imageBuffer[bufferIndex++]);
                    }

                    toWrite -= blockSize;
                }
            }

            // Write whole memory stream to file
            long endPosition = mwsub.GetPosition();

            mwsub.GotoBegin();
            _subFile.Write(mwsub.GetBuf(), 0, (int)endPosition);
        }
Пример #2
0
        // inspired by code from SubtitleCreator
        public void WriteParagraph(Paragraph p, Bitmap bmp, ContentAlignment alignment)
        {
            // timestamp: 00:00:33:900, filepos: 000000000
            _idx.AppendLine(string.Format("timestamp: {0:00}:{1:00}:{2:00}:{3:000}, filepos: {4}", p.StartTime.Hours, p.StartTime.Minutes, p.StartTime.Seconds, p.StartTime.Milliseconds, _subFile.Position.ToString("X").PadLeft(9, '0').ToLower()));

            var nbmp = new NikseBitmap(bmp);
            _emphasis2 = nbmp.ConverToFourColors(_background, _pattern, _emphasis1, _useInnerAntialiasing);
            var twoPartBuffer = nbmp.RunLengthEncodeForDvd(_background, _pattern, _emphasis1, _emphasis2);
            var imageBuffer = GetSubImageBuffer(twoPartBuffer, nbmp, p, alignment);

            int bufferIndex = 0;
            byte vobSubId = (byte)_languageStreamId;
            var mwsub = new MemWriter(200000);
            byte[] subHeader = new byte[30];
            byte[] ts = new byte[4];

            // Lended from "Son2VobSub" by Alain Vielle and Petr Vyskocil
            // And also from Sup2VobSub by Emmel
            subHeader[0] = 0x00; // MPEG 2 PACK HEADER
            subHeader[1] = 0x00;
            subHeader[2] = 0x01;
            subHeader[3] = 0xba;
            subHeader[4] = 0x44;
            subHeader[5] = 0x02;
            subHeader[6] = 0xc4;
            subHeader[7] = 0x82;
            subHeader[8] = 0x04;
            subHeader[9] = 0xa9;
            subHeader[10] = 0x01;
            subHeader[11] = 0x89;
            subHeader[12] = 0xc3;
            subHeader[13] = 0xf8;

            subHeader[14] = 0x00; // PES
            subHeader[15] = 0x00;
            subHeader[16] = 0x01;
            subHeader[17] = 0xbd;

            int packetSize = imageBuffer.Length;
            long toWrite = packetSize;  // Image buffer + control sequence length
            bool header0 = true;

            while (toWrite > 0)
            {
                long headerSize;
                if (header0)
                {
                    header0 = false;

                    // This is only for first packet
                    subHeader[20] = 0x81;   // mark as original
                    subHeader[21] = 0x80;   // first packet: PTS
                    subHeader[22] = 0x05;   // PES header data length

                    // PTS (90kHz):
                    //--------------
                    subHeader[23] = (byte)((ts[3] & 0xc0) >> 5 | 0x21);
                    subHeader[24] = (byte)((ts[3] & 0x3f) << 2 | (ts[2] & 0xc0) >> 6);
                    subHeader[25] = (byte)((ts[2] & 0x3f) << 2 | (ts[1] & 0x80) >> 6 | 0x01);
                    subHeader[26] = (byte)((ts[1] & 0x7f) << 1 | (ts[0] & 0x80) >> 7);
                    subHeader[27] = (byte)((ts[0] & 0x7f) << 1 | 0x01);

                    const string pre = "0010"; // 0011 or 0010 ? (KMPlayer will not understand 0011!!!)
                    long newPts = (long)(p.StartTime.TotalSeconds * 90000.0 + 0.5);
                    string bString = Convert.ToString(newPts, 2).PadLeft(33, '0');
                    string fiveBytesString = pre + bString.Substring(0, 3) + "1" + bString.Substring(3, 15) + "1" + bString.Substring(18, 15) + "1";
                    for (int i = 0; i < 5; i++)
                    {
                        subHeader[23 + i] = Convert.ToByte(fiveBytesString.Substring((i * 8), 8), 2);
                    }
                    subHeader[28] = vobSubId;
                    headerSize = 29;
                }
                else
                {
                    subHeader[20] = 0x81; // mark as original
                    subHeader[21] = 0x00; // no PTS
                    subHeader[22] = 0x00; // header data length
                    subHeader[23] = vobSubId;
                    headerSize = 24;
                }

                if ((toWrite + headerSize) <= 0x800)
                {
                    // write whole image in one 0x800 part

                    long j = (headerSize - 20) + toWrite;
                    subHeader[18] = (byte)(j / 0x100);
                    subHeader[19] = (byte)(j % 0x100);

                    // First Write header
                    for (int x = 0; x < headerSize; x++)
                        mwsub.WriteByte(subHeader[x]);

                    // Write Image Data
                    for (int x = 0; x < toWrite; x++)
                        mwsub.WriteByte(imageBuffer[bufferIndex++]);

                    // Pad remaining space
                    long paddingSize = 0x800 - headerSize - toWrite;
                    for (int x = 0; x < paddingSize; x++)
                        mwsub.WriteByte(0xff);

                    toWrite = 0;
                }
                else
                {
                    // write multiple parts

                    long blockSize = 0x800 - headerSize;
                    long j = (headerSize - 20) + blockSize;
                    subHeader[18] = (byte)(j / 0x100);
                    subHeader[19] = (byte)(j % 0x100);

                    // First Write header
                    for (int x = 0; x < headerSize; x++)
                        mwsub.WriteByte(subHeader[x]);

                    // Write Image Data
                    for (int x = 0; x < blockSize; x++)
                        mwsub.WriteByte(imageBuffer[bufferIndex++]);

                    toWrite -= blockSize;
                }
            }

            // Write whole memory stream to file
            long endPosition = mwsub.GetPosition();
            mwsub.GotoBegin();
            _subFile.Write(mwsub.GetBuf(), 0, (int)endPosition);
        }
        /// <summary>
        /// The generate image from text with style.
        /// </summary>
        /// <param name="p">
        /// The p.
        /// </param>
        /// <param name="mbp">
        /// The mbp.
        /// </param>
        /// <returns>
        /// The <see cref="Bitmap"/>.
        /// </returns>
        private Bitmap GenerateImageFromTextWithStyle(Paragraph p, out MakeBitmapParameter mbp)
        {
            mbp = new MakeBitmapParameter();
            mbp.P = p;

            if (this._vobSubOcr != null)
            {
                var index = this._subtitle.GetIndex(p);
                if (index >= 0)
                {
                    return this._vobSubOcr.GetSubtitleBitmap(index);
                }
            }

            mbp.AlignLeft = this.comboBoxHAlign.SelectedIndex == 0;
            mbp.AlignRight = this.comboBoxHAlign.SelectedIndex == 2;
            mbp.SimpleRendering = this.checkBoxSimpleRender.Checked;
            mbp.BorderWidth = this._borderWidth;
            mbp.BorderColor = this._borderColor;
            mbp.SubtitleFontName = this._subtitleFontName;
            mbp.SubtitleColor = this._subtitleColor;
            mbp.SubtitleFontSize = this._subtitleFontSize;
            mbp.SubtitleFontBold = this._subtitleFontBold;
            mbp.LineHeight = (int)this.numericUpDownLineSpacing.Value;
            mbp.FullFrame = this.checkBoxFullFrameImage.Checked;
            mbp.FullFrameBackgroundcolor = this.panelFullFrameBackground.BackColor;

            if (this._format.HasStyleSupport && !string.IsNullOrEmpty(p.Extra))
            {
                if (this._format.GetType() == typeof(SubStationAlpha))
                {
                    var style = AdvancedSubStationAlpha.GetSsaStyle(p.Extra, this._subtitle.Header);
                    mbp.SubtitleColor = style.Primary;
                    mbp.SubtitleFontBold = style.Bold;
                    mbp.SubtitleFontSize = style.FontSize;
                    if (style.BorderStyle == "3")
                    {
                        mbp.BackgroundColor = style.Background;
                    }
                }
                else if (this._format.GetType() == typeof(AdvancedSubStationAlpha))
                {
                    var style = AdvancedSubStationAlpha.GetSsaStyle(p.Extra, this._subtitle.Header);
                    mbp.SubtitleColor = style.Primary;
                    mbp.SubtitleFontBold = style.Bold;
                    mbp.SubtitleFontSize = style.FontSize;
                    if (style.BorderStyle == "3")
                    {
                        mbp.BackgroundColor = style.Outline;
                    }
                }
            }

            if (this.comboBoxBorderWidth.SelectedItem.ToString() == Configuration.Settings.Language.ExportPngXml.BorderStyleBoxForEachLine)
            {
                this._borderWidth = 0;
                mbp.BackgroundColor = this.panelBorderColor.BackColor;
                mbp.BoxSingleLine = true;
            }
            else if (this.comboBoxBorderWidth.SelectedItem.ToString() == Configuration.Settings.Language.ExportPngXml.BorderStyleOneBox)
            {
                this._borderWidth = 0;
                mbp.BackgroundColor = this.panelBorderColor.BackColor;
            }

            int width;
            int height;
            this.GetResolution(out width, out height);
            mbp.ScreenWidth = width;
            mbp.ScreenHeight = height;
            mbp.VideoResolution = this.comboBoxResolution.Text;
            mbp.Type3D = this.comboBox3D.SelectedIndex;
            mbp.Depth3D = (int)this.numericUpDownDepth3D.Value;
            mbp.BottomMargin = this.comboBoxBottomMargin.SelectedIndex;
            mbp.ShadowWidth = this.comboBoxShadowWidth.SelectedIndex;
            mbp.ShadowAlpha = (int)this.numericUpDownShadowTransparency.Value;
            mbp.ShadowColor = this.panelShadowColor.BackColor;
            mbp.LineHeight = (int)this.numericUpDownLineSpacing.Value;
            mbp.Forced = this.subtitleListView1.Items[this._subtitle.GetIndex(p)].Checked;
            mbp.LineJoin = Configuration.Settings.Tools.ExportPenLineJoin;
            var bmp = GenerateImageFromTextWithStyle(mbp);
            if (this._exportType == "VOBSUB" || this._exportType == "STL" || this._exportType == "SPUMUX")
            {
                var nbmp = new NikseBitmap(bmp);
                nbmp.ConverToFourColors(Color.Transparent, this._subtitleColor, this._borderColor, !this.checkBoxTransAntiAliase.Checked);
                var temp = nbmp.GetBitmap();
                bmp.Dispose();
                return temp;
            }

            return bmp;
        }
Пример #4
0
        public void WriteParagraph(Paragraph p, Bitmap bmp)
        {
            // timestamp: 00:00:33:900, filepos: 000000000
            _idx.AppendLine(string.Format("timestamp: {0:00}:{1:00}:{2:00}:{3:000}, filepos: {4}", p.StartTime.Hours, p.StartTime.Minutes, p.StartTime.Seconds, p.StartTime.Milliseconds, _subFile.Position.ToString("X").PadLeft(9, '0')));


            // write binary vobsub file (duration + image)
            long start = _subFile.Position;

            _subFile.Write(Mpeg2PackHeaderBuffer, 0, Mpeg2PackHeaderBuffer.Length);

            NikseBitmap nbmp = new NikseBitmap(bmp);

            nbmp.ConverToFourColors(Color.Transparent, Color.White, Color.FromArgb(200, 0, 0, 0), Color.FromArgb(200, 25, 25, 25));

            var outBmp = nbmp.GetBitmap();

            outBmp.Save(@"D:\download\-_-" + p.Number.ToString() + ".bmp");
            bmp.Save(@"D:\download\-__" + p.Number.ToString() + ".bmp");
            outBmp.Dispose();

            var twoPartBuffer = nbmp.RunLengthEncodeForDvd(Color.Transparent, Color.White, Color.FromArgb(200, 0, 0, 0), Color.FromArgb(200, 25, 25, 25));

            // PES size
            int length = Mpeg2PackHeaderBuffer.Length + PacketizedElementaryStreamHeaderBufferFirst.Length + 10 + twoPartBuffer.Length;

            //block_size = 0x800 - header_size;
            //long j = (header_size - 20) + block_size;
            //SubHeader[18] = (byte)(j / 0x100);
            //SubHeader[19] = (byte)(j % 0x100);

            PacketizedElementaryStreamHeaderBufferFirst[4] = (byte)(length / 256);
            PacketizedElementaryStreamHeaderBufferFirst[5] = (byte)(length % 256);
            _subFile.Write(PacketizedElementaryStreamHeaderBufferFirst, 0, PacketizedElementaryStreamHeaderBufferFirst.Length);

            // PTS (timestamp)
            FillPTS(p.StartTime);
            _subFile.Write(PresentationTimeStampBuffer, 0, PresentationTimeStampBuffer.Length);

            _subFile.WriteByte(0x32); //sub-stream number

            if (twoPartBuffer.Length < 0x800 - (_subFile.Position - start))
            {
                _subFile.Write(twoPartBuffer.Buffer1, 0, twoPartBuffer.Buffer1.Length);
                _subFile.Write(twoPartBuffer.Buffer2, 0, twoPartBuffer.Buffer2.Length);
            }
            else
            {
                System.Windows.Forms.MessageBox.Show("Too long for payload!!!");
            }

//            HeaderDataLength = buffer[index + 8];

            // language id
            //    int id = buffer[9 + HeaderDataLength];
            //    if (id >= 0x20 && id <= 0x40) // x3f 0r x40 ?
            //        SubPictureStreamId = id;
            //}


            for (long i = _subFile.Position - start; i < 0x800; i++) // 2048 packet size - pad with 0xff
            {
                _subFile.WriteByte(0xff);
            }
        }