I want to create bezier path with dynamically changing line's width. I need spending the same amount of color on each part of line. So, longer line should be thinner. And shorter line should be bold. Or, at least, line should change it's width from beginning to the end.
Any ideas how to achieve it?
Thank you.
the only way to achieve this is with multiple UIBezierPaths of different thickness and colour.
Related
please see the image below for two examples of what is to be achived
the alignment should be on the Center Y of the first lines of each UILabels and should work regardless of font size or font. currently we have implemented this with different constraints to the top of the super view for different font and font size combinations.
the constraint to align the center of the two UILabels does not work since the text of the second UILabel is not fixed and can have several lines.
also the text is dynamic, so it is not known where the text will wrap to create the first line, thus it cannot be shown in an one line UILabel with the rest of the text in another one below.
currently this is implemented using UIKit, but if there is an easy solution in SwiftUI we can put these two labels in a SwiftUI component. so a SwiftUI solution would also be welcomed.
Your comments said "it should be on the glyphs" ... but, without additional information, my guess is that "real world" usage would not really need that level of precision.
For example:
While the glyphs are not perfectly center-Y aligned, it seems unlikely you'd run into a case where the first line of the "rightLabel" is " ' " ' " or . , . , ..
This layout can be easily done with only a few constraints - no need to do any calculations:
The "Positioning" label would, of course, be set .hidden = true so it would never be seen.
If you really, really want glyph-precision, you'll need to calculate
the Glyph bounding box for the left-label
the Glyph bounding box for first line of the right-label
calculate the "character box" offsets to align the Glyph Y-centers
and then position the two labels accordingly, or use Core Text to draw the text (instead of using UILabel).
Probably more work than necessary -- unless your actual use-case demands it.
That's an interesting problem! You can try using the centerYAnchor for the label on the left, and the firstBaselineAnchor for the label on the right... that will align the center Y with the text baseline, which isn't quite what you want.
To find the correct offset to apply, you can use the information from UIFont about the size of the characters. I'd probably start with capHeight * 0.5 and see if that looks or feels right. Something like:
leftLabel.centerYAnchor.constraint(equalTo: rightLabel.firstBaseLineAnchor, constant: rightFont.capHeight * 0.5)
This is a more difficult problem in SwiftUI, I think, because resolved font metrics aren't directly available to you.
I've a weird problem that faces me. I've a UILabel contains text of multiple lines and I'm using bullet in the first line "•".
But my problem is that the second line is not aligned with first character after the bullet.
I measured it and found that width of the bullet is a little bit bigger tan width of normal space.
Is there any trick for that?
the issue is concerning font attributes. Get into the difference of monospaced fonts and proportional fonts, then you will know why there's a difference between space and bullet in your font
https://en.wikipedia.org/wiki/Monospaced_font
easy solution and maybe really an option for you is to use a monospaced font.
Okay, I found a powerful answer by using NSParagraphStyle.
https://wingoodharry.wordpress.com/2016/04/10/bullet-point-list-ios-swift/
I'm trying to develop a drawing application, and I need to change the width of the path according to the speed of the hand.
I tried to use moveToPoint to start another subpath
myPath.moveToPoint(myPath.currentPoint)
myPath.lineWidth = myPath.lineWidth + 1
but it doesn't work, it changes the width of the entire path.
Do you know if there's a way to change only a subpath's width?
That is not possible. All UIBezierPath properties (lineWidth, flatness, ...) apply to the entire path with all its subpaths.
To draw curves with different line widths you have to create multiple bezier paths.
I would like to implement karaoke-like progress highlight for iOS.
I know I could use NSAttributedString and highlight the text character by character. However, I would like the highlight to progress pixel by pixel, not character by character.
Any ideas?
P.S. No need for sample code, just point me to the right direction.
Here is an example:
I can't think of any automatic way to do that. There would be several problems to solve. It would be pretty hard, I think.
The hardest would probably be figuring out the pixel position of each word so you can pace the coloring to match the timing within the music. With text and attributed layout, you could probably get the text engine to give you the boundaries of each word and then apply the color attribute to each word as it's spoken/sung. You'd have to have data about the time offset for the beginning and end of each word's being sung.
You might have to use Core Text to get layout information about the bounding rectangles of each word.
Once you get that you could build a path (UIBezierPath or CGPath; they're pretty interchangeable) that follows the flow of the text, and then install that path in to a shape layer. You could then make the text transparent, make the shape layer a colored background that shows through, and animate the shape layer's strokeStart and/or strokeEnd properties to make it fill the text. You might need to do it word by word with a short animation that interpolates between one word and the next to get the timing right.
You probably want to have a look at Core Text, which is the lower level framework used for laying out text, using this you can obtain necessary paths that you need to render said effect (I suggest starting from answers similar to this)
There are plenty of answers for alternative, perhaps simpler answers, for example character by character or word-by-word, which may be easier to implement.
Is there a property that will apply the proper character spacing to have all the text on each line in an NSAttributedString butt up against the bounds like in a book, (including the final line which I know isn't done in books)? I know kerning can be adjusted, but that won't dynamically adjust on a per line basis. Any help would be appreciated. Also NSTextAlignmentJustified and NSTextAlignmentNatural get close, but won't apply the effect to the last line of text.
The only option is to use NSTextAlignmentJustified. Last line is never justified, because NSTextAlignmentJustified refers to Left Justification mode, as it is the standard case.
For more information you can take a look at Typographic Alignment on wikipedia : http://en.wikipedia.org/wiki/Typographic_alignment