CATextLayer and CAConstraint

  • I've been pulling my hair out trying to get a CATextLayer to work with
    a couple of CAConstraints. The following is a method implemented in a
    layer backed view and the following call is made in the view's
    awakeFromNib:
    self.layer.layoutManager = [CAConstraintLayoutManager layoutManager];

    The method is as follows:

    -(void)addFileNameLayer:(NSString *)fileName
    {
    CATextLayer * fileNameLayer = [CATextLayer layer];
    fileNameLayer.string = fileName;
    fileNameLayer.name = @"fileNameLayer";
    fileNameLayer.fontSize = 14.0;
    fileNameLayer.alignmentMode = kCAAlignmentCenter;
    fileNameLayer.wrapped = YES;
    fileNameLayer.anchorPoint = CGPointMake(0.5, 0.5);
    fileNameLayer.bounds = CGRectMake(0, 0, 320, 50);
    [fileNameLayer addConstraint:[CAConstraint
    constraintWithAttribute:kCAConstraintMidX relativeTo:@"superlayer"
    attribute:kCAConstraintMidX]];
    [fileNameLayer addConstraint:[CAConstraint
    constraintWithAttribute:kCAConstraintMidY relativeTo:@"superlayer"
    attribute:kCAConstraintMidY offset:-100]];
    [self.layer addSublayer:fileNameLayer];
    }

    When the code executes, it displays nothing. I also add another plain
    old CALayer before I call this method with similar constraints and it
    works out fine. Anyone help would be appreciated.

    -Aaron
  • Hi Aaron,

    When trying to manipulate layers like this its best if you use a layer
    hosting view rather than a layer backed view. If you rely on the layer
    the view creates for you its often the case that you get weird
    behavior like this.

    Instead in your awakeFromNib method you can make your view layer
    hosting;
    myLayer = [CALayer layer];
    // other myLayer initilization
    [myView setLayer:myLayer];
    [myView setWantsLayer:YES];

    then you can add sublayers as in your addFileNameLayer: below and
    everything should work.

    As an alternative you could simply create a text field as a label and
    add it as a subview of your current setup and it will become layer
    backed since you are adding it to a view that is layer backed.

    HTH,

    -bd-
    http://bill.dudney.net/roller/objc

    On Nov 18, 2007, at 1:00 AM, Aaron Tait wrote:

    > I've been pulling my hair out trying to get a CATextLayer to work
    > with a couple of CAConstraints. The following is a method
    > implemented in a layer backed view and the following call is made in
    > the view's awakeFromNib:
    > self.layer.layoutManager = [CAConstraintLayoutManager layoutManager];
    >
    > The method is as follows:
    >
    > -(void)addFileNameLayer:(NSString *)fileName
    > {
    > CATextLayer * fileNameLayer = [CATextLayer layer];
    > fileNameLayer.string = fileName;
    > fileNameLayer.name = @"fileNameLayer";
    > fileNameLayer.fontSize = 14.0;
    > fileNameLayer.alignmentMode = kCAAlignmentCenter;
    > fileNameLayer.wrapped = YES;
    > fileNameLayer.anchorPoint = CGPointMake(0.5, 0.5);
    > fileNameLayer.bounds = CGRectMake(0, 0, 320, 50);
    > [fileNameLayer addConstraint:[CAConstraint
    > constraintWithAttribute:kCAConstraintMidX relativeTo:@"superlayer"
    > attribute:kCAConstraintMidX]];
    > [fileNameLayer addConstraint:[CAConstraint
    > constraintWithAttribute:kCAConstraintMidY relativeTo:@"superlayer"
    > attribute:kCAConstraintMidY offset:-100]];
    > [self.layer addSublayer:fileNameLayer];
    > }
    >
    > When the code executes, it displays nothing. I also add another
    > plain old CALayer before I call this method with similar constraints
    > and it works out fine. Anyone help would be appreciated.
    >
    > -Aaron
  • Bill, I tried your solution but it did not help. Fortunately however,
    I have found a working solution. It looks like the constraints mess
    with the sizing and bounds of my CATextLayer making it only 1 unit in
    size. I have added the following constraint and it produces a
    desirable result:
    [fileNameLayer addConstraint:[CAConstraint
    constraintWithAttribute:kCAConstraintWidth relativeTo:@"superlayer"
    attribute:kCAConstraintWidth]];

    -Aaron

    On 18-Nov-07, at 8:26 AM, Bill Dudney wrote:

    > Hi Aaron,
    >
    > When trying to manipulate layers like this its best if you use a
    > layer hosting view rather than a layer backed view. If you rely on
    > the layer the view creates for you its often the case that you get
    > weird behavior like this.
    >
    > Instead in your awakeFromNib method you can make your view layer
    > hosting;
    > myLayer = [CALayer layer];
    > // other myLayer initilization
    > [myView setLayer:myLayer];
    > [myView setWantsLayer:YES];
    >
    > then you can add sublayers as in your addFileNameLayer: below and
    > everything should work.
    >
    > As an alternative you could simply create a text field as a label
    > and add it as a subview of your current setup and it will become
    > layer backed since you are adding it to a view that is layer backed.
    >
    > HTH,
    >
    > -bd-
    > http://bill.dudney.net/roller/objc
    >
    > On Nov 18, 2007, at 1:00 AM, Aaron Tait wrote:
    >
    >> I've been pulling my hair out trying to get a CATextLayer to work
    >> with a couple of CAConstraints. The following is a method
    >> implemented in a layer backed view and the following call is made
    >> in the view's awakeFromNib:
    >> self.layer.layoutManager = [CAConstraintLayoutManager layoutManager];
    >>
    >> The method is as follows:
    >>
    >> -(void)addFileNameLayer:(NSString *)fileName
    >> {
    >> CATextLayer * fileNameLayer = [CATextLayer layer];
    >> fileNameLayer.string = fileName;
    >> fileNameLayer.name = @"fileNameLayer";
    >> fileNameLayer.fontSize = 14.0;
    >> fileNameLayer.alignmentMode = kCAAlignmentCenter;
    >> fileNameLayer.wrapped = YES;
    >> fileNameLayer.anchorPoint = CGPointMake(0.5, 0.5);
    >> fileNameLayer.bounds = CGRectMake(0, 0, 320, 50);
    >> [fileNameLayer addConstraint:[CAConstraint
    >> constraintWithAttribute:kCAConstraintMidX relativeTo:@"superlayer"
    >> attribute:kCAConstraintMidX]];
    >> [fileNameLayer addConstraint:[CAConstraint
    >> constraintWithAttribute:kCAConstraintMidY relativeTo:@"superlayer"
    >> attribute:kCAConstraintMidY offset:-100]];
    >> [self.layer addSublayer:fileNameLayer];
    >> }
    >>
    >> When the code executes, it displays nothing. I also add another
    >> plain old CALayer before I call this method with similar
    >> constraints and it works out fine. Anyone help would be appreciated.
    >>
    >> -Aaron
    >
  • On Nov 18, 2007, at 1:02 PM, Aaron Tait wrote:

    > Bill, I tried your solution but it did not help. Fortunately
    > however, I have found a working solution. It looks like the
    > constraints mess with the sizing and bounds of my CATextLayer making
    > it only 1 unit in size.

    If this is the case, it may be a bug. might be worth reporting

    are you notifying the superlayer that it needs to layout its
    sublayers when the string changes?  I don't believe that simply
    changing the string of the textlayer will do that.

    CATextLayer does alter its bounds to fit the text exactly when using
    constraints. (this is mentioned in the reference)
  • As it's been said by Apple Documentation the CATextLayer only
    automatically resizes when a default CAConstraintLayoutManager is on.

    So Aaron, instead of constraining the layer's width just set its
    layoutManager to [CAConstraintLayoutManager defaultManager] and it'll
    resize to fit your text.

    By the way, I'd like to play with my CATextLayer's constraints, but it
    does not work properly: I want my layer width to be constraint but not
    its height and, whenever the string prompted in my layer is too large,
    I want the layer height to increase in order to fit the whole
    phrase... I don't know if you get me, my english is not that correct
    (I'm Frog powered huhu).

    Maybe a small schema could help: (I'm sorry if you cannot see it
    properly — font and font size issue — :'/)
    + First:                                      ___________
    This is my CATextLayer --> | Hey Apple Li |  st people, how you doin'?

    ¨¨¨¨¨¨¨¨¨¨¨¨¨¨¨¨¨¨¨¨          /\
                                                                                            |
                                                                      This
    is hidden because it does not fit the layer (too large)

    + Then it resizes as I want:  ___________
    This is my CATextLayer --> | Hey Apple    |
                                                      | List people,  |
    No more hidden text
    The layer width stay un-      | how you        |
    -changed but the height      | doin'?            |
    got bigger.                              ¨¨¨¨¨¨¨¨¨¨¨¨¨¨¨¨¨¨¨¨

    I've tried a couple techniques (like telling layer and / or superlayer
    to layout, playing with the autoresizing mask, manually setting the
    layer height, etc.) but it never does want I want.

    If anyone has an idea, it would be very appreciated :')

    Thanks,

    Paul

    On , Mon Nov 19 10:12:19 2007 Scott Anguish wrote:
    > If this is the case, it may be a bug. might be worth reporting
    >
    > are you notifying the superlayer that it needs to layout its
    > sublayers when the string changes?  I don't believe that simply
    > changing the string of the textlayer will do that.
    >
    > CATextLayer does alter its bounds to fit the text exactly when using
    > constraints. (this is mentioned in the reference)
    >
    > On  Sun Nov 18 19:02:15 2007 Aaron Tait wrote:
    >> Bill, I tried your solution but it did not help. Fortunately however,
    >> I have found a working solution. It looks like the constraints mess
    >> with the sizing and bounds of my CATextLayer making it only 1 unit in
    >> size. I have added the following constraint and it produces a
    >> desirable result:
    >> [fileNameLayer addConstraint:[CAConstraint
    >> constraintWithAttribute:kCAConstraintWidth relativeTo:@"superlayer"
    >> attribute:kCAConstraintWidth]];
    >>
    >> -Aaron
    >>
    >>
    >> On 18-Nov-07, at 8:26 AM, Bill Dudney wrote:
    >>> Hi Aaron,
    >>>
    >>> When trying to manipulate layers like this its best if you use a
    >>> layer hosting view rather than a layer backed view. If you rely on
    >>> the layer the view creates for you its often the case that you get
    >>> weird behavior like this.
    >>>
    >>> Instead in your awakeFromNib method you can make your view layer
    >>> hosting;
    >>> myLayer = [CALayer layer];
    >>> // other myLayer initilization
    >>> [myView setLayer:myLayer];
    >>> [myView setWantsLayer:YES];
    >>>
    >>> then you can add sublayers as in your addFileNameLayer: below and
    >>> everything should work.
    >>>
    >>> As an alternative you could simply create a text field as a label
    >>> and add it as a subview of your current setup and it will become
    >>> layer backed since you are adding it to a view that is layer backed.
    >>>
    >>> HTH,
    >>>
    >>> -bd-
    >>> http://bill.dudney.net/roller/objc
    >>>
    >>> On Nov 18, 2007, at 1:00 AM, Aaron Tait wrote:
    >>>> I've been pulling my hair out trying to get a CATextLayer to work
    >>>> with a couple of CAConstraints. The following is a method
    >>>> implemented in a layer backed view and the following call is made
    >>>> in the view's awakeFromNib:
    >>>> self.layer.layoutManager = [CAConstraintLayoutManager
    >>>> layoutManager];
    >>>>
    >>>> The method is as follows:
    >>>>
    >>>> -(void)addFileNameLayer:(NSString *)fileName
    >>>> {
    >>>> CATextLayer * fileNameLayer = [CATextLayer layer];
    >>>> fileNameLayer.string = fileName;
    >>>> fileNameLayer.name = @"fileNameLayer";
    >>>> fileNameLayer.fontSize = 14.0;
    >>>> fileNameLayer.alignmentMode = kCAAlignmentCenter;
    >>>> fileNameLayer.wrapped = YES;
    >>>> fileNameLayer.anchorPoint = CGPointMake(0.5, 0.5);
    >>>> fileNameLayer.bounds = CGRectMake(0, 0, 320, 50);
    >>>> [fileNameLayer addConstraint:[CAConstraint
    >>>> constraintWithAttribute:kCAConstraintMidX relativeTo:@"superlayer"
    >>>> attribute:kCAConstraintMidX]];
    >>>> [fileNameLayer addConstraint:[CAConstraint
    >>>> constraintWithAttribute:kCAConstraintMidY relativeTo:@"superlayer"
    >>>> attribute:kCAConstraintMidY offset:-100]];
    >>>> [self.layer addSublayer:fileNameLayer];
    >>>> }
    >>>>
    >>>> When the code executes, it displays nothing. I also add another
    >>>> plain old CALayer before I call this method with similar
    >>>> constraints and it works out fine. Anyone help would be
    >>>> appreciated.
    >>>>
    >>>> -Aaron
previous month november 2007 next month
MTWTFSS
      1 2 3 4
5 6 7 8 9 10 11
12 13 14 15 16 17 18
19 20 21 22 23 24 25
26 27 28 29 30    
Go to today