示例#1
0
        static NSFont _ToNativeFont(string family, float size, FontAttributes attributes)
        {
            NSFont           defaultFont = NSFont.SystemFontOfSize(size);
            NSFont           font        = null;
            NSFontDescriptor descriptor  = null;
            var bold   = (attributes & FontAttributes.Bold) != 0;
            var italic = (attributes & FontAttributes.Italic) != 0;

            if (family != null && family != DefaultFontName)
            {
                try
                {
                    descriptor = new NSFontDescriptor().FontDescriptorWithFamily(family);
                    font       = NSFont.FromDescription(descriptor, size);

                    if (font == null)
                    {
                        var cleansedFont = CleanseFontName(family);
                        font = NSFont.FromFontName(cleansedFont, size);
                    }
                }
                catch
                {
                    Debug.WriteLine("Could not load font named: {0}", family);
                }
            }

            //if we didn't found a Font or Descriptor for the FontFamily use the default one
            if (font == null)
            {
                font       = defaultFont;
                descriptor = defaultFont.FontDescriptor;
            }

            if (descriptor == null)
            {
                descriptor = defaultFont.FontDescriptor;
            }


            if (bold || italic)
            {
                var traits = (NSFontSymbolicTraits)0;
                if (bold)
                {
                    traits |= NSFontSymbolicTraits.BoldTrait;
                }
                if (italic)
                {
                    traits |= NSFontSymbolicTraits.ItalicTrait;
                }

                var fontDescriptorWithTraits = descriptor.FontDescriptorWithSymbolicTraits(traits);

                font = NSFont.FromDescription(fontDescriptorWithTraits, size);
            }

            return(font.ScreenFontWithRenderingMode(NSFontRenderingMode.AntialiasedIntegerAdvancements));
        }
示例#2
0
        private PlatformFont GetFont()
        {
            if (_native == null)
            {
#if __MACOS__
                using (var descriptor = !string.IsNullOrEmpty(FontFamily)
                                        ? NSFontDescriptor.FromNameSize(FontFamily, FontSize)
                                        : new NSFontDescriptor())
                {
                    if (IsItalic)
                    {
                        using (var descriptor2 = descriptor.FontDescriptorWithSymbolicTraits(NSFontSymbolicTraits.ItalicTrait))
                        {
                            _native = NSFont.FromDescription(descriptor2, FontSize);
                        }
                    }
                    else
                    {
                        _native = NSFont.FromDescription(descriptor, FontSize);
                    }
                }
#else
                using (var descriptor = !string.IsNullOrEmpty(FontFamily)
                                        ? UIFontDescriptor.FromName(FontFamily, FontSize)
                                        : new UIFontDescriptor())
                {
                    if (IsItalic)
                    {
                        using (var descriptor2 = descriptor.CreateWithTraits(UIFontDescriptorSymbolicTraits.Italic))
                        {
                            _native = UIFont.FromDescriptor(descriptor2, FontSize);
                        }
                    }
                    else
                    {
                        _native = UIFont.FromDescriptor(descriptor, FontSize);
                    }
                }
#endif
            }
            return(_native);
        }
示例#3
0
        public static UIFont ToNSFont(this Font self)
#endif
        {
            var size = (float)self.FontSize;

            if (self.UseNamedSize)
            {
                switch (self.NamedSize)
                {
                case NamedSize.Micro:
                    size = 12;
                    break;

                case NamedSize.Small:
                    size = 14;
                    break;

                case NamedSize.Medium:
                    size = 17;                             // as defined by iOS documentation
                    break;

                case NamedSize.Large:
                    size = 22;
                    break;

                default:
                    size = 17;
                    break;
                }
            }

            var bold   = self.FontAttributes.HasFlag(FontAttributes.Bold);
            var italic = self.FontAttributes.HasFlag(FontAttributes.Italic);

            if (self.FontFamily != null && self.FontFamily != DefaultFontName)
            {
                try
                {
#if __MOBILE__
                    if (UIFont.FamilyNames.Contains(self.FontFamily))
                    {
                        var descriptor = new UIFontDescriptor().CreateWithFamily(self.FontFamily);

                        if (bold || italic)
                        {
                            var traits = (UIFontDescriptorSymbolicTraits)0;
                            if (bold)
                            {
                                traits = traits | UIFontDescriptorSymbolicTraits.Bold;
                            }
                            if (italic)
                            {
                                traits = traits | UIFontDescriptorSymbolicTraits.Italic;
                            }

                            descriptor = descriptor.CreateWithTraits(traits);
                            return(UIFont.FromDescriptor(descriptor, size));
                        }
                    }

                    return(UIFont.FromName(self.FontFamily, size));
#else
                    var descriptor = new NSFontDescriptor().FontDescriptorWithFamily(self.FontFamily);

                    if (bold || italic)
                    {
                        var traits = (NSFontSymbolicTraits)0;
                        if (bold)
                        {
                            traits = traits | NSFontSymbolicTraits.BoldTrait;
                        }
                        if (italic)
                        {
                            traits = traits | NSFontSymbolicTraits.ItalicTrait;
                        }

                        descriptor = descriptor.FontDescriptorWithSymbolicTraits(traits);
                        return(NSFont.FromDescription(descriptor, size));
                    }

                    return(NSFont.FromFontName(self.FontFamily, size));
#endif
                }
                catch
                {
                    Debug.WriteLine("Could not load font named: {0}", self.FontFamily);
                }
            }
            if (bold && italic)
            {
                var defaultFont = UIFont.SystemFontOfSize(size);
#if __MOBILE__
                var descriptor = defaultFont.FontDescriptor.CreateWithTraits(UIFontDescriptorSymbolicTraits.Bold | UIFontDescriptorSymbolicTraits.Italic);
                return(UIFont.FromDescriptor(descriptor, 0));
            }
            if (italic)
            {
                return(UIFont.ItalicSystemFontOfSize(size));
            }
#else
                var descriptor = defaultFont.FontDescriptor.FontDescriptorWithSymbolicTraits(
                    NSFontSymbolicTraits.BoldTrait |
                    NSFontSymbolicTraits.ItalicTrait);

                return(NSFont.FromDescription(descriptor, 0));
            }
示例#4
0
        public static NSFont FromDescription(NSFontDescriptor fontDescriptor, NSAffineTransform textTransform)
        {
            var ptr = _FromDescription(fontDescriptor, textTransform);

            return(ptr == IntPtr.Zero ? null : new NSFont(ptr));
        }
示例#5
0
        public static NSFont FromDescription(NSFontDescriptor fontDescriptor, nfloat fontSize)
        {
            var ptr = _FromDescription(fontDescriptor, fontSize);

            return(ptr == IntPtr.Zero ? null : new NSFont(ptr));
        }
示例#6
0
        public override void DrawRect(CGRect dirtyRect)
        {
            // Don't draw if we don't have a font or a title.
            if (Font == null || Title == string.Empty)
            {
                return;
            }

            // Initialize the text matrix to a known value
            CGContext context = NSGraphicsContext.CurrentContext.GraphicsPort;

            context.TextMatrix = CGAffineTransform.MakeIdentity();

            // Draw a white background
            NSColor.White.Set();
            context.FillRect(dirtyRect);
            CTLine line = new CTLine(AttributedString);

            int glyphCount = (int)line.GlyphCount;

            if (glyphCount == 0)
            {
                return;
            }

            GlyphArcInfo[] glyphArcInfo = new GlyphArcInfo[glyphCount];
            PrepareGlyphArcInfo(line, glyphCount, glyphArcInfo);

            // Move the origin from the lower left of the view nearer to its center.
            context.SaveState();
            context.TranslateCTM(dirtyRect.GetMidX(), dirtyRect.GetMidY() - Radius / 2);

            // Stroke the arc in red for verification.
            context.BeginPath();
            context.AddArc(0, 0, Radius, (float)Math.PI, 0, true);
            context.SetStrokeColor(1, 0, 0, 1);
            context.StrokePath();

            // Rotate the context 90 degrees counterclockwise.
            context.RotateCTM((float)PI_2);

            /*
             *      Now for the actual drawing. The angle offset for each glyph relative to the previous
             *      glyph has already been calculated; with that information in hand, draw those glyphs
             *      overstruck and centered over one another, making sure to rotate the context after each
             *      glyph so the glyphs are spread along a semicircular path.
             */
            CGPoint textPosition = new CGPoint(0, Radius);

            context.TextPosition = textPosition;
            var runArray = line.GetGlyphRuns();
            var runCount = runArray.Count();

            var glyphOffset = 0;
            var runIndex    = 0;

            for (; runIndex < runCount; runIndex++)
            {
                var    run           = runArray [runIndex];
                var    runGlyphCount = run.GlyphCount;
                bool   drawSubstitutedGlyphsManually = false;
                CTFont runFont = run.GetAttributes().Font;

                // Determine if we need to draw substituted glyphs manually. Do so if the runFont is not
                //      the same as the overall font.
                var    description = NSFontDescriptor.FromNameSize(runFont.FamilyName, runFont.Size);
                NSFont rrunFont    = NSFont.FromDescription(description, runFont.Size);
                // used for comparison
                if (DimsSubstitutedGlyphs && Font != rrunFont)
                {
                    drawSubstitutedGlyphsManually = true;
                }

                var runGlyphIndex = 0;
                for (; runGlyphIndex < runGlyphCount; runGlyphIndex++)
                {
                    var glyphRange = new NSRange(runGlyphIndex, 1);
                    context.RotateCTM(-(glyphArcInfo [runGlyphIndex + glyphOffset].angle));

                    // Center this glyph by moving left by half its width.
                    var glyphWidth           = glyphArcInfo [runGlyphIndex + glyphOffset].width;
                    var halfGlyphWidth       = glyphWidth / 2.0;
                    var positionForThisGlyph = new CGPoint(textPosition.X - (float)halfGlyphWidth, textPosition.Y);

                    // Glyphs are positioned relative to the text position for the line, so offset text position leftwards by this glyph's
                    //      width in preparation for the next glyph.
                    textPosition.X -= glyphWidth;

                    CGAffineTransform textMatrix = run.TextMatrix;
                    textMatrix.x0      = positionForThisGlyph.X;
                    textMatrix.y0      = positionForThisGlyph.Y;
                    context.TextMatrix = textMatrix;

                    if (!drawSubstitutedGlyphsManually)
                    {
                        run.Draw(context, glyphRange);
                    }
                    else
                    {
                        // We need to draw the glyphs manually in this case because we are effectively applying a graphics operation by
                        //      setting the context fill color. Normally we would use kCTForegroundColorAttributeName, but this does not apply
                        // as we don't know the ranges for the colors in advance, and we wanted demonstrate how to manually draw.
                        var cgFont   = runFont.ToCGFont();
                        var glyph    = run.GetGlyphs(glyphRange);
                        var position = run.GetPositions(glyphRange);
                        context.SetFont(cgFont);
                        context.SetFontSize(runFont.Size);
                        context.SetFillColor(0.25f, 0.25f, 0.25f, 1);
                        context.ShowGlyphsAtPositions(glyph, position, 1);
                    }

                    // Draw the glyph bounds
                    if (ShowsGlyphBounds)
                    {
                        var glyphBounds = run.GetImageBounds(context, glyphRange);
                        context.SetStrokeColor(0, 0, 1, 1);
                        context.StrokeRect(glyphBounds);
                    }

                    // Draw the bounding boxes defined by the line metrics
                    if (ShowsLineMetrics)
                    {
                        var    lineMetrics = new CGRect();
                        nfloat ascent      = 0;
                        nfloat descent     = 0;
                        nfloat leading     = 0;

                        run.GetTypographicBounds(glyphRange, out ascent, out descent, out leading);

                        // The glyph is centered around the y-axis
                        lineMetrics.Location = new CGPoint(-(float)halfGlyphWidth, positionForThisGlyph.Y - descent);
                        lineMetrics.Size     = new CGSize(glyphWidth, ascent + descent);
                        context.SetStrokeColor(0, 1, 0, 1);
                        context.StrokeRect(lineMetrics);
                    }
                }

                glyphOffset += (int)runGlyphCount;
            }

            context.RestoreState();
        }
示例#7
0
 public static NSFont FromDescriptor(NSFontDescriptor fontDescriptor, nfloat fontSize)
 => WrappedNSFont.Wrap(IntPtr_objc_msgSend_IntPtr_nfloat(
        public static NSFont GetFont(
            this ResourceDictionary resourceDictionary,
            bool respectScale = true)
        {
            NSFontDescriptor fontDescriptor = null;
            nfloat           fontSize       = 0;

            switch (resourceDictionary[TypefaceId])
            {
            case NSFontDescriptor fd:
                fontDescriptor = fd;
                break;

            case NSFont rdFont:
                fontDescriptor = rdFont.FontDescriptor;
                fontSize       = rdFont.PointSize;
                break;

            case string fontName:
                fontDescriptor = NSFontWorkarounds
                                 .FromFontName(fontName, 0)
                                 .FontDescriptor;
                break;
            }

            switch (resourceDictionary[FontRenderingSizeId])
            {
            case double d:
                fontSize = (nfloat)d;
                break;

            case float f:
                fontSize = f;
                break;

            case nfloat nf:
                fontSize = nf;
                break;

            case int i:
                fontSize = i;
                break;
            }

            if (fontSize <= 0)
            {
                fontSize = NSFont.SystemFontSize;
            }

            if (respectScale && resourceDictionary[FontRenderingScaleId] is double scale)
            {
                fontSize *= (nfloat)scale;
            }

            var font = fontDescriptor == null
                ? NSFontWorkarounds.UserFixedPitchFontOfSize(fontSize)
                : NSFontWorkarounds.FromDescriptor(fontDescriptor, fontSize);

            NSFontTraitMask convertFontTraits = 0;

            if (resourceDictionary.Contains(IsBoldId) &&
                resourceDictionary[IsBoldId] is bool isBold &&
                isBold)
            {
                convertFontTraits |= NSFontTraitMask.Bold;
            }

            if (resourceDictionary.Contains(IsItalicId) &&
                resourceDictionary[IsItalicId] is bool isItalic &&
                isItalic)
            {
                convertFontTraits |= NSFontTraitMask.Italic;
            }

            if (convertFontTraits != 0)
            {
                font = NSFontManager.SharedFontManager.ConvertFontWorkaround(
                    font,
                    convertFontTraits);
            }

            return(font);
        }