10
10

Delete article

Deleted articles cannot be recovered.

Draft of this article would be also deleted.

Are you sure you want to delete this article?

More than 5 years have passed since last update.

DZNEmptyDataSetでbuttonTitleに合わせてBackgroundImageのsizeを調節する

Last updated at Posted at 2016-07-17

今国際化に伴い、アプリを大幅改修しています。
こんな感じの画面を作ろうと思っていました。
ライブラリはDZNEmptyDataSetを使っています。

Screen Shot 0028-07-17 at 18.37.09.png


今まで

文言(画像のCreate New Streamの部分)を日本語で指定していた
=> 自ずと文言のサイズは一意的に決まる
=> そのLabelのサイズに合わせてpaddingを指定して、かつ、文言も含んだImageを用意していた

国際化

文言は国・地域によって変化する
=> 文言のサイズはもちろん動的に変化する
=> 背景画像だけ別で用意して、動的に変化するLabelのサイズに合わせて大きさを上手い感じに合わせる必要がある

というわけで流れとしては、

  • 背景画像の用意(Normal/Highlighted)
  • titleLabelのサイズを測って変数に格納しておく
  • backgroundImageの描画の際に、上記のサイズに合わせてimageのwidthを調節する

サクッと元のソースコードを見ながら自分でもサンプルを作ってみました。

DZNEmptyDataSetとは

TableView, collectionViewが空の時に代わりに表示するものを作成するためのライブラリ
参考

delegate method一覧

func titleForEmptyDataSet(scrollView: UIScrollView!) -> NSAttributedString! {
  // titleを指定する
}
func descriptionForEmptyDataSet(scrollView: UIScrollView!) -> NSAttributedString! {
  // 説明文を指定
 }
func imageForEmptyDataSet(scrollView: UIScrollView!) -> UIImage! {
  //  画像を指定
}
func buttonTitleForEmptyDataSet(scrollView: UIScrollView!, forState state: UIControlState) -> NSAttributedString! {
   // buttonのtitleを指定
}
func buttonImageForEmptyDataSet(scrollView: UIScrollView!, forState state: UIControlState) -> UIImage! {
   //  buttonに貼る画像を指定
}
func buttonBackgroundImageForEmptyDataSet(scrollView: UIScrollView!, forState state: UIControlState) -> UIImage! {
   // buttonの背景画像を指定
}
func backgroundColorForEmptyDataSet(scrollView: UIScrollView!) -> UIColor! {
    // 全体のviewの背景の色を指定
}
func verticalOffsetForEmptyDataSet(scrollView: UIScrollView!) -> CGFloat {
    // contentsの位置をviewの上端からどれくらいの距離離すかを指定
}
func spaceHeightForEmptyDataSet(scrollView: UIScrollView!) -> CGFloat {
    //  contentsが複数ある場合、それぞれの距離をどれくらい離すかを指定
}
func emptyDataSetShouldDisplay(scrollView: UIScrollView!) -> Bool {
    //  emptyDataSetのcontentsを表示するか否か
}
func emptyDataSetDidTapView(scrollView: UIScrollView!) {
     //  全体のviewをtapした時のアクションを指定
}
func emptyDataSetDidTapButton(scrollView: UIScrollView!) {
     //  作成したbuttonをtapした時のactionを指定
}

buttonBackgroundImageForEmptyDataSetでtitleに合わせてsizeを変える

これが面倒だったのでshareします。
やりたいことは最初に説明した通りです。

func buttonTitleForEmptyDataSet(scrollView: UIScrollView!, forState state: UIControlState) -> NSAttributedString! {
        let str = "Create New Stream"
        let font = UIFont.systemFontOfSize(14.0, weight: 2.0)
        
        
        // 文言のサイズを格納しておく
        titleSize = str.widthWithConstrainedHeight(44, font: font)

        return NSAttributedString(
            string: str,
            attributes: [
                NSFontAttributeName: font,
                NSForegroundColorAttributeName: ColorUtil.rgba(172, green: 175, blue: 189)
            ]
        )
    }


func buttonBackgroundImageForEmptyDataSet(scrollView: UIScrollView!, forState state: UIControlState) -> UIImage! {

	    // 引き伸ばされたbackgroundImageとview.bounds.size.widthとの比率。
        // どの機種でもだいたい88%でした
        let ratioViewBoundsWidthAndButton: CGFloat = 0.88

        
        //  引き伸ばされたbackgroundImageのsize
        let defaultSize = view.bounds.size.width * ratioViewBoundsWidthAndButton

        
        //  titleLabelのpadding.お好みで
        let padding: CGFloat = 20
        
        
        // 背景画像を引き伸ばしてからtitleLabelに合わせてwidthを調節してUIImageを返す
        return UIImage.makeBackgroundImage(state).shrinkImageAdjustingObject(before: defaultSize, objectSize: messageSizeForEmptyDataSet, padding: padding)
    }

        

extension UIImage {

    // 引き延ばした画像を返すメソッド
	class func makeBackgroundImage(state: UIControlState) -> UIImage {

    	let baseImage = (state == UIControlState.Highlighted) ? R.image.btn_highlight()! : R.image.btn()!
    	
    	// capInsetsは引き延ばす時に引き伸ばしたくない一部分を指定できる
        // ここでは四端5.0×5.0だけそのままのサイズで他を引き延ばすイメージ
       	let capInsets = UIEdgeInsets(top: 5.0, left: 5.0, bottom: 5.0, right: 5.0)
       	
       	
       return baseImage.resizableImageWithCapInsets(capInsets, resizingMode: UIImageResizingMode.Stretch)
    }


    //  内部のobjectのサイズとpaddingを指定すれば、imageのwidthを拡大・縮小するメソッド
    func shrinkImageAdjustingObject(before imageSize: CGFloat, objectSize: CGFloat, padding: CGFloat) -> UIImage {

        var rectInsets = UIEdgeInsetsZero
        

        // imageの端と内部のオブジェクトの端までの距離(片方ずつ)
        let widthBetweenBackgroundAndLabel = (imageSize - objectSize)/2
        

        // paddingを考慮してimageをどれくらい拡大・縮小させるか、の指定
        let shrinkWidth = widthBetweenBackgroundAndLabel - padding
        rectInsets = UIEdgeInsets(top: 0, left: -shrinkWidth, bottom: 0, right: -shrinkWidth)
        
        
        return imageWithAlignmentRectInsets(rectInsets)
    }

}

参考

10
10
0

Register as a new user and use Qiita more conveniently

  1. You get articles that match your needs
  2. You can efficiently read back useful information
  3. You can use dark theme
What you can do with signing up
10
10

Delete article

Deleted articles cannot be recovered.

Draft of this article would be also deleted.

Are you sure you want to delete this article?