Ejemplo n.º 1
0
        private void SplitChunk(BBTextChunk chunk, int index, string head, string tail, ref int chunksCount)
        {
            chunk.Text = head;

            if (!string.IsNullOrEmpty(tail))
            {
                var newChunk = chunk.Clone();
                newChunk.Text = tail;
                fChunks.Insert(index + 1, newChunk);
                chunksCount += 1;

                ShiftChunks(index + 1, chunksCount);
            }
        }
Ejemplo n.º 2
0
        private void ArrangeText()
        {
            try {
                fAcceptFontChange = false;
                fHeights.Clear();

                Graphics gfx = CreateGraphics();
                //gfx.TextRenderingHint = TextRenderingHint.AntiAlias;
                try {
                    int xPos       = 0;
                    int yPos       = 0;
                    int xMax       = 0;
                    int lineHeight = 0;

                    string text    = fLines.Text;
                    Font   defFont = this.Font;
                    SizeF  csz     = this.ClientSize;
                    SizeF  zerosz  = new SizeF(0f, 0f);

                    var parser = new BBTextParser(AppHost.GfxProvider, defFont.SizeInPoints,
                                                  new ColorHandler(fLinkColor), new ColorHandler(ForeColor));

                    parser.ParseText(fChunks, text);

                    int line        = -1;
                    int chunksCount = fChunks.Count;
                    int k           = 0;
                    while (k < chunksCount)
                    {
                        BBTextChunk chunk       = fChunks[k];
                        bool        recalcChunk = false;

                        if (line != chunk.Line)
                        {
                            line = chunk.Line;

                            if (line > 0)
                            {
                                yPos += lineHeight;
                                fHeights.Add(lineHeight);
                            }

                            xPos       = 0;
                            lineHeight = 0;
                        }

                        int prevX = xPos;
                        int prevY = yPos;

                        string chunkStr = chunk.Text;
                        if (!string.IsNullOrEmpty(chunkStr))
                        {
                            using (var font = new Font(defFont.Name, chunk.Size, (sdFontStyle)chunk.Style, defFont.Unit)) {
                                SizeF strSize = gfx.MeasureString(chunkStr, font, zerosz, fStrFormat);

                                if (fWordWrap)
                                {
                                    int wBound = xPos + 2 * fBorderWidth;
                                    if (wBound + strSize.Width > csz.Width)
                                    {
                                        int lastIndex = chunkStr.Length - 1;
                                        while (true)
                                        {
                                            int spPos = chunkStr.LastIndexOf(' ', lastIndex);
                                            if (spPos <= 0)
                                            {
                                                // the beginning of the chunk is reached and there are no more words to carry
                                                chunk.Text = chunkStr.Substring(0, lastIndex + 1);
                                                strSize    = gfx.MeasureString(chunkStr, font, zerosz, fStrFormat);
                                                // the current chunk still does not fit into the area
                                                if (wBound + strSize.Width > csz.Width)
                                                {
                                                    // this is not the only chunk on this line
                                                    if (k > 0 && fChunks[k - 1].Line == chunk.Line)
                                                    {
                                                        // transfer the current chunk to the next line
                                                        // and recount it again at the next iteration
                                                        ShiftChunks(k, chunksCount);
                                                        recalcChunk = true;
                                                    }
                                                }
                                                break;
                                            }

                                            string newChunk = chunkStr.Substring(0, spPos);
                                            strSize = gfx.MeasureString(newChunk, font, zerosz, fStrFormat);
                                            if (wBound + strSize.Width < csz.Width)
                                            {
                                                var secondPart = chunk.Clone();
                                                secondPart.Text  = chunkStr.Substring(spPos + 1);
                                                secondPart.Line += 1;
                                                fChunks.Insert(k + 1, secondPart);
                                                chunksCount += 1;

                                                // shift next chunks
                                                ShiftChunks(k + 2, chunksCount);

                                                chunk.Text = newChunk;
                                                break;
                                            }
                                            else
                                            {
                                                lastIndex = spPos - 1;
                                            }
                                        }
                                    }
                                }

                                chunk.Width = (int)strSize.Width;

                                xPos += chunk.Width;
                                if (xMax < xPos)
                                {
                                    xMax = xPos;
                                }

                                int h = (int)strSize.Height;
                                if (lineHeight < h)
                                {
                                    lineHeight = h;
                                }
                            }

                            if (!string.IsNullOrEmpty(chunk.URL))
                            {
                                chunk.LinkRect = ExtRect.CreateBounds(prevX, prevY, xPos - prevX, lineHeight);
                            }
                        }

                        if (!recalcChunk)
                        {
                            k++;
                        }
                    }

                    fTextSize = new ExtSize(xMax + 2 * fBorderWidth, yPos + 2 * fBorderWidth);
                } finally {
                    gfx.Dispose();
                    fAcceptFontChange = true;
                    AdjustViewport(fTextSize);
                }
            } catch (Exception ex) {
                Logger.LogWrite("HyperView.ArrangeText(): " + ex.Message);
            }
        }