Exemplo n.º 1
0
        public void ParseText(string text, List <ProjectAsset> assets)
        {
            text = PreProcLine(text);

            // preprocessor to make linewraping more convenient
            text = text.Replace(@"\wrap", @"\\\wrap\\")
                   .Replace(@"\break", @"\\\break\\")
                   //.Replace(@"\reading", @"\\\reading")
                   //.Replace(@"\sermon", @"\\\sermon")
                   //.Replace(@"\image", @"\\\image")
                   //.Replace(@"\fullimage", @"\\\fullimage")
                   //.Replace(@"\fitimage", @"\\\fitimage")
                   .Replace(@"\apostlescreed", @"\\\apostlescreed\\")
                   .Replace(@"\nicenecreed", @"\\\nicenecreed")
                   .Replace(@"\lordsprayer", @"\\\lordsprayer\\")
                   .Replace(@"\morningprayer", @"\\\morningprayer")
                   .Replace(@"\copyright", @"\\\copyright\\")
                   .Replace(@"\viewseries", @"\\\viewseries\\")
                   .Replace(@"\viewservices", @"\\\viewservices\\")
                   .Replace(@"\hymn", @"\\\hymn");

            // replace functions
            text = Regex.Replace(text, @"(?<funct>\\\w+\(.*\))", @"\\\\${funct}\\\\", RegexOptions.Multiline);

            var lines = text.Split(new[] { @"\\" }, StringSplitOptions.RemoveEmptyEntries).ToList();

            // try to intelligently split lines by newlines after punctuation

            // remove 'empty' lines (new lines)
            //lines = lines.Where(s => s != "\n")
            //.Where(s => s != "\r\n")
            //.Where(s => s != Environment.NewLine).ToList();

            lines = lines.Where(s => !Regex.Match(s, @"^\s$", RegexOptions.None).Success).ToList();
            lines = lines.Where(s => s.Trim() != string.Empty).Select(s => s.Trim()).ToList();



            foreach (var line in lines)
            {
                string tl = line.Trim().Replace(Environment.NewLine, " ").Replace("\n", " ").Replace("\r", " ").Replace("\r\n", " ");

                if (tl.StartsWith(@"\break"))
                {
                    TypesetCommand cmd = new TypesetCommand()
                    {
                        Command = Command.NewSlide
                    };
                    LineData.Add(cmd);
                    continue;
                }

                if (tl.StartsWith(@"\wrap"))
                {
                    TypesetCommand cmd = new TypesetCommand()
                    {
                        Command = Command.WrapSpeakerText
                    };
                    LineData.Add(cmd);
                    continue;
                }

                if (tl.StartsWith(@"\video"))
                {
                    try
                    {
                        // add a non-rendered slide to copy video output to slides
                        var         matches = Regex.Match(tl, @"\\video\((?<name>.*)\)");
                        RenderVideo rc      = new RenderVideo();
                        rc.Asset = assets.First(s => s.Name == matches.Groups["name"].Value);
                        LineData.Add(rc);
                    }
                    catch (Exception)
                    {
                    }
                    continue;
                }

                // typeset the reading on a new slide
                // expected params are comma delimited
                // eg. \reading(<Title>,<Reference>)
                if (tl.StartsWith(@"\reading"))
                {
                    //var contents = tl.Split(new char[] { '(', ',', ')' }, 4, StringSplitOptions.RemoveEmptyEntries);
                    var a        = tl.Split('(')[1];
                    var b        = a.Split(')')[0];
                    var contents = b.Split(new char[] { ',' }, 2, StringSplitOptions.RemoveEmptyEntries);


                    ReadingLine rl = new ReadingLine()
                    {
                        Title = contents[0].Trim(), Reference = contents[1].Trim()
                    };
                    LineData.Add(rl);
                    continue;
                }

                if (tl.StartsWith(@"\sermon"))
                {
                    var         matches     = Regex.Match(tl, @"\\sermon\((?<title>.*),(?<source>.*)\)");
                    SermonTitle sermonTitle = new SermonTitle()
                    {
                        Title = "Sermon", SermonName = matches.Groups["title"].Value, SermonText = matches.Groups["source"].Value
                    };
                    LineData.Add(sermonTitle);
                    continue;
                }

                if (tl.StartsWith(@"\image"))
                {
                    var         args        = tl.Split('(', ',', ')');
                    InlineImage inlineImage = new InlineImage();
                    inlineImage.ImageAsset = assets.Find(a => a.Name == args[1]);
                    inlineImage.AutoScale  = args[2] == "fill";
                    LineData.Add(inlineImage);
                    continue;
                }

                if (tl.StartsWith(@"\fullimage"))
                {
                    var       args = tl.Split('(', ')');
                    Fullimage img  = new Fullimage();
                    img.ImageAsset = assets.Find(a => a.Name == args[1]);
                    LineData.Add(img);
                    continue;
                }

                if (tl.StartsWith(@"\fitimage"))
                {
                    var       args = tl.Split('(', ')');
                    Fullimage img  = new Fullimage();
                    img.ImageAsset = assets.Find(a => a.Name == args[1]);
                    img.Streach    = false;
                    LineData.Add(img);
                    continue;
                }

                if (tl.StartsWith(@"\apostlescreed"))
                {
                    Fullimage ac = new Fullimage();
                    ac.ImageAsset       = new ProjectAsset();
                    ac.ImageAsset.Image = Properties.Resources.apostlescreed;
                    ac.ImageAsset.Name  = "Apostle Creed - Prerendered";
                    ac.Streach          = true;
                    LineData.Add(ac);
                    continue;
                }
                if (tl.StartsWith(@"\nicenecreed"))
                {
                    TypesetCommand cmd = new TypesetCommand()
                    {
                        Command = Command.NewSlide
                    };
                    LineData.Add(cmd);
                    continue;
                }
                if (tl.StartsWith(@"\lordsprayer"))
                {
                    Fullimage ac = new Fullimage();
                    ac.ImageAsset       = new ProjectAsset();
                    ac.ImageAsset.Image = Properties.Resources.lordsprayer;
                    ac.ImageAsset.Name  = "Lords Prayer - Prerendered";
                    ac.Streach          = true;
                    LineData.Add(ac);
                    continue;
                }
                if (tl.StartsWith(@"\viewseries"))
                {
                    Fullimage ac = new Fullimage();
                    ac.ImageAsset       = new ProjectAsset();
                    ac.ImageAsset.Image = Properties.Resources.sessions;
                    ac.ImageAsset.Name  = "View Series - Prerendered";
                    ac.Streach          = true;
                    LineData.Add(ac);
                    continue;
                }
                if (tl.StartsWith(@"\viewservices"))
                {
                    Fullimage ac = new Fullimage();
                    ac.ImageAsset       = new ProjectAsset();
                    ac.ImageAsset.Image = Properties.Resources.services;
                    ac.ImageAsset.Name  = "View Services - Prerendered";
                    ac.Streach          = true;
                    LineData.Add(ac);
                    continue;
                }
                if (tl.StartsWith(@"\copyright"))
                {
                    Fullimage ac = new Fullimage();
                    ac.ImageAsset       = new ProjectAsset();
                    ac.ImageAsset.Image = Properties.Resources.copyright;
                    ac.ImageAsset.Name  = "Copyright1 - Prerendered";
                    ac.Streach          = true;
                    LineData.Add(ac);
                    continue;
                }
                if (tl.StartsWith(@"\morningprayer"))
                {
                    TypesetCommand cmd = new TypesetCommand()
                    {
                        Command = Command.NewSlide
                    };
                    LineData.Add(cmd);
                    continue;
                }
                if (tl.StartsWith(@"\hymn"))
                {
                    TypesetCommand cmd = new TypesetCommand()
                    {
                        Command = Command.NewSlide
                    };
                    LineData.Add(cmd);
                    continue;
                }

                LiturgyLine l = new LiturgyLine();
                if (tl.StartsWith("P"))
                {
                    l.Text    = tl.Replace(" T ", " + ").Substring(1).Trim();
                    l.Speaker = Speaker.Pastor;
                }
                else if (tl.StartsWith("L"))
                {
                    l.Text    = tl.Replace(" T ", " + ").Substring(1).Trim();
                    l.Speaker = Speaker.Leader;
                }
                else if (tl.StartsWith("C"))
                {
                    l.Text    = tl.Replace(" T ", " + ").Substring(1).Trim();
                    l.Speaker = Speaker.Congregation;
                }
                else if (tl.StartsWith("A"))
                {
                    l.Text    = tl.Replace(" T ", " + ").Substring(1).Trim();
                    l.Speaker = Speaker.Assistant;
                }
                else
                {
                    l.Text    = tl.Trim();
                    l.Speaker = Speaker.None;
                }
                l.IsSubsplit = false;
                LineData.Add(l);
            }
        }
        public RenderSlide TypesetSlide(RenderSlide slide, TextRenderer r)
        {
            LiturgyLine line = this;


            // update state if not in wrapmode
            if (!r.LLState.SpeakerWrap)
            {
                r.LLState.LastSpeaker = line.Speaker;
            }
            else
            {
                line.Speaker = r.LLState.LastSpeaker;
            }

            // try to fit to current slide
            int lineheight = (int)Math.Ceiling(slide.gfx.MeasureString("CPALTgy", r.SpeakerFonts.TryGetVal(line.Speaker, r.Font)).Height);

            // check if whole line will fit

            SizeF s = slide.gfx.MeasureString(line.Text, r.SpeakerFonts.TryGetVal(line.Speaker, r.Font), r.TextboxRect.Width);

            if (slide.YOffset + s.Height <= r.TextboxRect.Height)
            {
                // it fits, add this line at position and compute
                RenderLine rl = new RenderLine()
                {
                    Height = (int)s.Height, Width = (int)s.Width, ShowSpeaker = line.SubSplit == 0 || slide.Lines == 0, Speaker = line.Speaker, Text = line.Text, RenderX = 0, RenderY = 0, RenderLayoutMode = LayoutMode.Auto, LineNum = slide.Lines++, Font = r.SpeakerFonts.TryGetVal(line.Speaker, r.Font)
                };
                slide.RenderLines.Add(rl);
                slide.YOffset += (int)s.Height;
                // wrap only works for one line
                r.LLState.SpeakerWrap = false;
                return(slide);
            }
            // if slide isn't blank, then try it on a blank slide
            if (!slide.Blank)
            {
                r.Slides.Add(r.FinalizeSlide(slide));
                // wrap only works for one line
                r.LLState.SpeakerWrap = false;
                return(line.TypesetSlide(new RenderSlide()
                {
                    Order = slide.Order + 1
                }, r));
            }
            // if doesn't fit on a blank slide
            // try to split into sentences. put as many sentences as fit on one slide until done


            // If have already split into sentences... split into chunks of words?
            if (line.IsSubsplit)
            {
                RenderSlide errorslide;
                if (!slide.Blank)
                {
                    r.Slides.Add(r.FinalizeSlide(slide));
                    errorslide = new RenderSlide()
                    {
                        Order = slide.Order + 1
                    };
                }
                else
                {
                    errorslide = slide;
                }
                // for now abandon
                string     emsg      = "ERROR";
                Size       esize     = slide.gfx.MeasureString(emsg, r.Font).ToSize();
                RenderLine errorline = new RenderLine()
                {
                    Height = esize.Height, Width = esize.Width, ShowSpeaker = r.LLState.SpeakerWrap, Speaker = Speaker.None, Text = emsg, RenderX = 0, RenderY = 0, RenderLayoutMode = LayoutMode.Auto, LineNum = 0, Font = r.Font, TextBrush = Brushes.Red
                };
                errorslide.RenderLines.Add(errorline);
                r.Slides.Add(r.FinalizeSlide(errorslide));
                // wrap only works for one line
                r.LLState.SpeakerWrap = false;
                return(new RenderSlide()
                {
                    Order = errorslide.Order + 1
                });
            }


            // split line text into sentences
            var sentences = line.Text.Split(new string[] { "." }, StringSplitOptions.RemoveEmptyEntries);

            var tmp = Regex.Matches(line.Text, @"((?<sentence>[^\.;!?]+)(?<delimiter>[\.;!?])+)");



            // keep trying to stuff a sentence
            List <LiturgyLine> sublines = new List <LiturgyLine>();
            int splitnum = 0;

            foreach (var sentence in tmp)
            {
                // create a bunch of sub-liturgy-lines and try to typeset them all
                string t = sentence.ToString();
                sublines.Add(new LiturgyLine()
                {
                    Speaker = line.Speaker, Text = t.Trim(), SubSplit = splitnum++, IsSubsplit = true
                });
            }

            foreach (var sl in sublines)
            {
                slide = sl.TypesetSlide(slide, r);
            }


            // wrap only works for one line
            r.LLState.SpeakerWrap = false;
            return(slide);
        }