예제 #1
0
        public static int DrawString(this WriteableBitmap bmp, int x0, int y0, IntRect cliprect, Color fontColor, PortableFontDesc typeface, string text)
        {
            var font = GetFont(typeface);

            return(bmp.DrawString(x0, y0, cliprect, fontColor, font, text));
        }
예제 #2
0
        public static unsafe void DrawLetterVertical(this BitmapContext context, int x0, int y0, IntRect cliprect, Color fontColor, GrayScaleLetterGlyph glyph, Boolean topToBottom)
        {
            if (glyph.Items == null)
            {
                return;
            }

            // Use refs for faster access (really important!) speeds up a lot!
            int w      = context.Width;
            int h      = context.Height;
            var pixels = context.Pixels;

            int fr = fontColor.R;
            int fg = fontColor.G;
            int fb = fontColor.B;

            int xmin = cliprect.Left;
            int ymin = cliprect.Top;
            int xmax = cliprect.Right;
            int ymax = cliprect.Bottom;

            if (xmin < 0)
            {
                xmin = 0;
            }
            if (ymin < 0)
            {
                ymin = 0;
            }
            if (xmax >= w)
            {
                xmax = w - 1;
            }
            if (ymax >= h)
            {
                ymax = h - 1;

                fixed(GrayScaleLetterGlyph.Item *items = glyph.Items)
                {
                    int itemCount = glyph.Items.Length;

                    GrayScaleLetterGlyph.Item *currentItem = items;
                    for (int i = 0; i < itemCount; i++, currentItem++)
                    {
                        int x;
                        int y;
                        if (topToBottom)
                        {
                            x = x0 - currentItem->Y;
                            y = y0 + currentItem->X;
                        }
                        else
                        {
                            x = x0 + currentItem->Y;
                            y = y0 - currentItem->X;
                        }

                        int alpha = currentItem->Alpha;
                        if (x < xmin || y < ymin || x > xmax || y > ymax)
                        {
                            continue;
                        }

                        int color = pixels[y * w + x];
                        int r     = ((color >> 16) & 0xFF);
                        int g     = ((color >> 8) & 0xFF);
                        int b     = ((color) & 0xFF);

                        r = (((r << 12) + (fr - r) * alpha) >> 12) & 0xFF;
                        g = (((g << 12) + (fg - g) * alpha) >> 12) & 0xFF;
                        b = (((b << 12) + (fb - b) * alpha) >> 12) & 0xFF;

                        pixels[y * w + x] = (0xFF << 24) | (r << 16) | (g << 8) | (b);
                    }
                }
        }
예제 #3
0
        public static unsafe void DrawLetter(this BitmapContext context, int x0, int y0, IntRect cliprect, ClearTypeLetterGlyph glyph)
        {
            //if (glyph.Instructions == null) return;
            if (glyph.Items == null)
            {
                return;
            }

            // Use refs for faster access (really important!) speeds up a lot!
            int w      = context.Width;
            int h      = context.Height;
            var pixels = context.Pixels;

            int xmin = cliprect.Left;
            int ymin = cliprect.Top;
            int xmax = cliprect.Right;
            int ymax = cliprect.Bottom;

            if (xmin < 0)
            {
                xmin = 0;
            }
            if (ymin < 0)
            {
                ymin = 0;
            }
            if (xmax >= w)
            {
                xmax = w - 1;
            }
            if (ymax >= h)
            {
                ymax = h - 1;

                fixed(ClearTypeLetterGlyph.Item *items = glyph.Items)
                {
                    int itemCount = glyph.Items.Length;

                    ClearTypeLetterGlyph.Item *currentItem = items;
                    for (int i = 0; i < itemCount; i++, currentItem++)
                    {
                        int x     = x0 + currentItem->X;
                        int y     = y0 + currentItem->Y;
                        int color = currentItem->Color;
                        if (x < xmin || y < ymin || x > xmax || y > ymax)
                        {
                            continue;
                        }

                        pixels[y * w + x] = color;
                    }
                }
        }
예제 #4
0
 public static int DrawString(this WriteableBitmap bmp, int x0, int y0, IntRect cliprect, Color fontColor, GlyphFont font, string text)
 {
     return(DrawString(bmp, x0, y0, cliprect, fontColor, null, font, text));
 }
예제 #5
0
        public static unsafe void DrawLetter(this BitmapContext context, int x0, int y0, IntRect cliprect, ClearTypeLetterGlyph glyph)
        {
            // if (glyph.Instructions == null) return;
            if (glyph.Items == null)
            {
                return;
            }

            // Use refs for faster access (really important!) speeds up a lot!
            int w      = context.Width;
            int h      = context.Height;
            var pixels = context.Pixels;

            int xmin = cliprect.Left;
            int ymin = cliprect.Top;
            int xmax = cliprect.Right;
            int ymax = cliprect.Bottom;

            if (xmin < 0)
            {
                xmin = 0;
            }

            if (ymin < 0)
            {
                ymin = 0;
            }

            if (xmax >= w)
            {
                xmax = w - 1;
            }

            if (ymax >= h)
            {
                ymax = h - 1;
            }

            fixed(ClearTypeLetterGlyph.Item *items = glyph.Items)
            {
                int itemCount = glyph.Items.Length;

                ClearTypeLetterGlyph.Item *currentItem = items;

                // if (x0 >= xmin && y0 >= ymin && x0 + glyph.Width < xmax && y0 + glyph.Height < ymax)
                // {
                //    for (int i = 0; i < itemCount; i++, currentItem++)
                //    {
                //        pixels[(y0 + currentItem->Y) * w + x0 + currentItem->X] = currentItem->Color;
                //    }
                // }
                // else
                // {
                for (int i = 0; i < itemCount; i++, currentItem++)
                {
                    int x     = x0 + currentItem->X;
                    int y     = y0 + currentItem->Y;
                    int color = currentItem->Color;
                    if (x < xmin || y < ymin || x > xmax || y > ymax)
                    {
                        continue;
                    }

                    pixels[(y * w) + x] = color;
                }

                // }
            }

            // fixed (int *instructions = glyph.Instructions)
            // {
            //    int* current = instructions;
            //    while (*current != -1)
            //    {
            //        int dy = *current++;
            //        int dx = *current++;
            //        int count0 = *current++;

            // int y = y0 + dy;
            //        if (y >= ymin && y <= ymax)
            //        {
            //            int x = x0 + dx;
            //            int* dst = pixels + y*w + x;
            //            int* src = current;
            //            int count = count0;

            // if (x < xmin)
            //            {
            //                int dmin = xmin - x;
            //                x += dmin;
            //                dst += dmin;
            //                src += dmin;
            //                count -= dmin;
            //            }

            // if (x + count - 1 > xmax)
            //            {
            //                int dmax = x + count - 1 - xmax;
            //                count -= dmax;
            //            }

            // if (count > 0)
            //            {
            //                NativeMethods.memcpy(dst, src, count * 4);

            // //if (count < 10)
            //                //{
            //                //    while (count > 0)
            //                //    {
            //                //        *dst++ = *src++;
            //                //        count--;
            //                //    }
            //                //}
            //                //else
            //                //{
            //                //    NativeMethods.memcpy(dst, src, count*4);
            //                //}
            //            }
            //        }

            // current += count0;
            //    }
            // }
        }
예제 #6
0
        public static int DrawString(this WriteableBitmap bmp, int x0, int y0, IntRect cliprect, Color fontColor, Color?bgColor, GlyphFont font, string text)
        {
            if (text == null)
            {
                return(0);
            }

            int dx = 0, dy = 0;
            int textwi = 0;

            using (var context = bmp.GetBitmapContext())
            {
                foreach (char ch in text)
                {
                    if (ch == '\n')
                    {
                        if (dx > textwi)
                        {
                            textwi = dx;
                        }

                        dx  = 0;
                        dy += font.TextHeight;
                    }

                    if (x0 + dx <= cliprect.Right)
                    {
                        if (font.IsClearType)
                        {
                            if (!bgColor.HasValue)
                            {
                                throw new Exception("Clear type fonts must have background specified");
                            }

                            var letter = font.GetClearTypeLetter(ch, fontColor, bgColor.Value);
                            if (letter == null)
                            {
                                continue;
                            }

                            context.DrawLetter(x0 + dx, y0 + dy, cliprect, letter);
                            dx += letter.Width;
                        }
                        else
                        {
                            var letter = font.GetGrayScaleLetter(ch);
                            if (letter == null)
                            {
                                continue;
                            }

                            context.DrawLetter(x0 + dx, y0 + dy, cliprect, fontColor, letter);
                            dx += letter.Width;
                        }
                    }
                }
            }

            if (dx > textwi)
            {
                textwi = dx;
            }

            return(textwi);
        }
예제 #7
0
        /// <summary>
        /// scrolls content of given rectangle
        /// </summary>
        /// <param name="bmp"></param>
        /// <param name="dy">if greater than 0, scrolls down, else scrolls up</param>
        /// <param name="rect"></param>
        public static unsafe void ScrollY(this WriteableBitmap bmp, int dy, IntRect rect, Color?background = null)
        {
            int bgcolor = WriteableBitmapExtensions.ConvertColor(background ?? Colors.White);

            using (var context = bmp.GetBitmapContext())
            {
                // Use refs for faster access (really important!) speeds up a lot!
                int w      = context.Width;
                int h      = context.Height;
                var pixels = context.Pixels;
                int xmin   = rect.Left;
                int ymin   = rect.Top;
                int xmax   = rect.Right;
                int ymax   = rect.Bottom;

                if (xmin < 0)
                {
                    xmin = 0;
                }

                if (ymin < 0)
                {
                    ymin = 0;
                }

                if (xmax >= w)
                {
                    xmax = w - 1;
                }

                if (ymax >= h)
                {
                    ymax = h - 1;
                }

                int xcnt = xmax - xmin + 1;
                int ycnt = ymax - ymin + 1;
                if (xcnt <= 0)
                {
                    return;
                }

                if (dy > 0)
                {
                    for (int y = ymax; y >= ymin + dy; y--)
                    {
                        int ydstidex  = y;
                        int ysrcindex = y - dy;
                        if (ysrcindex < ymin || ysrcindex > ymax)
                        {
                            continue;
                        }

                        NativeMethods.memcpy(pixels + (ydstidex * w) + xmin, pixels + (ysrcindex * w) + xmin, xcnt * 4);
                    }
                }

                if (dy < 0)
                {
                    for (int y = ymin; y <= ymax - dy; y++)
                    {
                        int ysrcindex = y - dy;
                        int ydstidex  = y;
                        if (ysrcindex < ymin || ysrcindex > ymax)
                        {
                            continue;
                        }

                        NativeMethods.memcpy(pixels + (ydstidex * w) + xmin, pixels + (ysrcindex * w) + xmin, xcnt * 4);
                    }
                }

                if (dy < 0)
                {
                    bmp.FillRectangle(xmin, ymax + dy + 1, xmax, ymax, bgcolor);
                }

                if (dy > 0)
                {
                    bmp.FillRectangle(xmin, ymin, xmax, ymin + dy - 1, bgcolor);
                }
            }
        }
예제 #8
0
        /// <summary>
        /// scrolls content of given rectangle
        /// </summary>
        /// <param name="bmp"></param>
        /// <param name="dx">if greater than 0, scrolls right, else scrolls left</param>
        /// <param name="rect"></param>
        public static unsafe void ScrollX(this WriteableBitmap bmp, int dx, IntRect rect, Color?background = null)
        {
            int bgcolor = WriteableBitmapExtensions.ConvertColor(background ?? Colors.White);

            using (var context = bmp.GetBitmapContext())
            {
                // Use refs for faster access (really important!) speeds up a lot!
                int w      = context.Width;
                int h      = context.Height;
                var pixels = context.Pixels;
                int xmin   = rect.Left;
                int ymin   = rect.Top;
                int xmax   = rect.Right;
                int ymax   = rect.Bottom;

                if (xmin < 0)
                {
                    xmin = 0;
                }

                if (ymin < 0)
                {
                    ymin = 0;
                }

                if (xmax >= w)
                {
                    xmax = w - 1;
                }

                if (ymax >= h)
                {
                    ymax = h - 1;
                }

                int xcnt = xmax - xmin + 1;
                int ycnt = ymax - ymin + 1;

                int srcx = xmin, dstx = xmin;
                if (dx < 0)
                {
                    xcnt += dx;
                    dstx  = xmin;
                    srcx  = xmin - dx;
                }

                if (dx > 0)
                {
                    xcnt -= dx;
                    srcx  = xmin;
                    dstx  = xmin + dx;
                }

                if (xcnt <= 0)
                {
                    return;
                }

                int *yptr = pixels + (w * ymin);
                for (int y = ymin; y <= ymax; y++, yptr += w)
                {
                    NativeMethods.memcpy(yptr + dstx, yptr + srcx, xcnt * 4);
                }

                if (dx < 0)
                {
                    bmp.FillRectangle(xmax + dx + 1, ymin, xmax, ymax, bgcolor);
                }

                if (dx > 0)
                {
                    bmp.FillRectangle(xmin, ymin, xmin + dx - 1, ymax, bgcolor);
                }
            }
        }
예제 #9
0
        public static void DrawRectangle(this WriteableBitmap bmp, IntRect rect, Color color)
        {
            var col = ConvertColor(color);

            bmp.DrawRectangle(rect.Left, rect.Top, rect.Right, rect.Bottom, col);
        }