Objective-CでCSSでよく使うようなABCDEFFFのようなHex encodeされた形式の文字列からUIColorを生成する方法の紹介です。

   1  @interface UIColor (HexEncoding)
   2  + (UIColor*)colorFromString:(NSString*)string;
   3  - (NSString*)encodeToString;
   4  @end
   5  
   6  @implementation UIColor (HexEncoding)
   7  
   8  + (UIColor*)
   9  colorFromString:(NSString*)string
  10  {
  11    NSScanner *scanner = [NSScanner scannerWithString:string];
  12    NSUInteger value;
  13    [scanner scanHexInt:&value];
  14    CGFloat red   = ((value & 0xFF000000) >> 24) / 255.0f;
  15    CGFloat green = ((value & 0x00FF0000) >> 16) / 255.0f;
  16    CGFloat blue  = ((value & 0x0000FF00) >>  8) / 255.0f;
  17    CGFloat alpha = ((value & 0x000000FF) >>  0) / 255.0f;
  18    return [UIColor colorWithRed:red green:green blue:blue alpha:alpha];
  19  }
  20  
  21  - (NSString*)encodeToString
  22  {
  23    const CGFloat *components = CGColorGetComponents(self.CGColor);
  24    return [NSString stringWithFormat:@"%02x%02x%02x%02x",
  25            (int)(components[0]*255 + 0.5f),
  26            (int)(components[1]*255 + 0.5f),
  27            (int)(components[2]*255 + 0.5f),
  28            (int)(components[3]*255 + 0.5f)];
  29  }
  30  
  31  @end

わかりやすいように、UIColorにメソッドカテゴリを追加しています。 encodeToStringのほうでは、0.5を足してroundをかけていますが、 状況に応じてfloorにしたりceilにしたりしてください。

また、この例ではComponentsのサイズが4である事を期待しています。 そうではない色を扱うときには問題が発生しますので、ご注意ください。

posted by Png genki on Fri 7 Nov 2008 at 12:20

Objective-Cは、Rubyのようにメソッドの定義を書き換えたりする事ができます。

   1  #import <objc/runtime.h>
   2  
   3  id (*foo_without_bar)(id, SEL);
   4  id foo_with_bar(id self, SEL selector)
   5  {
   6    /* do your work here */
   7    return foo_without_bar(self, selector);
   8  }
   9  
  10  // exchange method implementation
  11  SEL fooSelector = @selector(foo);
  12  Method method = class_getInstanceMethod(class, fooSelector);
  13  *(IMP*)&foo_without_bar =
  14    method_getImplementation(method);
  15  method_setImplementation(method, (IMP)foo_with_bar);

この例では、IMPの定義と同じプロトタイプのメソッドを書き換えてるので不要ですが、IMPの定義と異なるプロトタイプのメソッドを書き換える場合は、 IMPにキャストする必要があります。

また、戻り値が浮動小数型であったり、サイズが大きい構造体を返すメソッドの場合は、上記の例とは異なる方法を使う必要があるので、注意が必要です。(NSInvocationを使う必要があります)

See Also

posted by Png genki on Fri 7 Nov 2008 at 12:00 with 2 comments

UIScrollViewのscrollRectToVisible:animated:の挙動についてのメモです。

これは名前の通り、第一引数で指定したCGRectをViewの可視領域に 持って行くためのメソッドなのですが、 可視領域からはみ出すような大きなCGRectを指定した場合は、CGRectの下端が優先的に表示されるような挙動になるようです。 また、CGRectがemptyの場合は何もおこりません。

上端を優先して表示させたい場合は、 可視領域のCGRectを求めて、あらかじめ可視領域に収まるようにしてから呼び出せばOkです。

ところで、このメソッドはcontentInsetを意識してくれないようなので、 contentInsetを使っている場合は、contentInsetの分だけ広げたrectを指定してあげると良い感じになるようです。

posted by Png genki on Fri 7 Nov 2008 at 11:14
Contents
Objective-CでABCDEFFFのような文字列をparseする方法
Objective-Cでalias_method_chain
UIScrollView#scrollRectToVisible:animated:の挙動に関するメモ
Comments
dsjf: https://gist.github.com/6bf1bf2c3cbb5eb6e7a7 これ... '13-1
瀧内元気: おお、チェックしてみます。thx! '11-12
overisland: Reeder for iPhone もこの UI を実装していますね。 '11-12
瀧内元気: その情報は見たのですが、以下のサイトによると、現在はまた必要になってるっぽいんですよね。 ... '11-12
tkawa: http://devcenter.heroku.com/articles/rails31_he... '11-12
Services from s21g
twpro(ツイプロ)
Twitterプロフィールを快適検索
地価2009
土地の値段を調べてみよう
MyRestaurant
自分だけのレストラン手帳
Formula
ブログに数式を埋め込める数式コミュニティ