20200521のiOSに関する記事は5件です。

UILabelの三点リーダーの位置のバラツキの調査

※調査記事の為、誤りが含まれている可能性があります。

はじめに

様々なアプリでUILabelが使われていますが、UILabelにおいて指定の領域を超えた文字数を保有する場合、領域外の文字は三点リーダー以降切り捨てられます。(見た目上は)
そこで、UILabelの三点リーダーの位置のバラつきが気になったので試してみました。

試した内容

下記で試した文字列の長さに対して、UILabelのwidthは短い長さに設定しました。

文字列 三点リーダーより前の文字列の文字数 三点リーダー
aaaaaaaaaaaaaaaaaa 2 スクリーンショット 2020-05-21 22.47.53.png (下)
aaaaaaaaaaaaaaaaaaあ 2 スクリーンショット 2020-05-21 22.47.53.png (下)
あaaaaaaaaaaaaaaa 2 スクリーンショット 2020-05-21 22.47.53.png (下)
aaaaaaaaaaaaaaaaあaaaaaaaa 2 スクリーンショット 2020-05-21 22.47.53.png (下)
あaああああああああああ 1 スクリーンショット 2020-05-21 22.47.53.png (下)
あああああああああ 1 スクリーンショット 2020-05-21 22.46.29.png (中)
ああaa 1 スクリーンショット 2020-05-21 22.46.29.png (中)

仮説

文字列の末尾がマルチバイト文字か否かで三点リーダーの位置が変わると考えていました。
しかし、上記の結果を見る限りでは「三点リーダーで切り捨てられる最初の文字」がマルチバイト文字か否かで三点リーダーの位置が変わります。

  • シングルバイト文字(アルファベットや数字など):下
  • マルチバイト文字(ひらがなや漢字など):中

最後に

色々なアプリを覗いてみると、三点リーダーの位置がバラバラなことが分かるので見てみると良いかも知れません。

  • このエントリーをはてなブックマークに追加
  • Qiitaで続きを読む

UITextViewの文字を複数リンク化させる方法

はじめに

スクリーンショット 2020-05-21 19.19.21.png

iOSが意外に苦手なリンク化
HTMLみたいにタグで囲った範囲をリンク化する!みたいに出来たら便利なのですが、出来ないので

リンク化したい文字列の場所とタップした位置でゲームみたいに当たり判定でリンクをタップしたか判定します!

ViewController + Storyboardで解説

Storyboard(Xibでも可)にUITextViewを貼り付ける

スクリーンショット 2020-05-21 16.35.01.png

制約も適当に張ります。
スクリーンショット 2020-05-21 16.35.15.png

UITextViewにTapGestureを張ります!
スクリーンショット 2020-05-21 18.34.26.png

スクリーンショット 2020-05-21 18.35.34.png

こんな感じ!

スクリーンショット 2020-05-21 18.38.35.png

Storyboardとコードをつなげる

Controlキーを押しながら、TextViewをひっぱりコードに張りますー
(ちなみにエディタを分割して開くには、ファイルをoptionキーを押しながらクリックします)

スクリーンショット 2020-05-21 16.38.20.png

TapGestureもコードにつなげておきます〜

スクリーンショット 2020-05-21 18.43.36.png

以下のようになりました!

import UIKit

class ViewController: UIViewController {

    @IBOutlet weak var messageTextView: UITextView!
    override func viewDidLoad() {
        super.viewDidLoad()

    }
    @IBAction func didTapMessageView(_ sender: UITapGestureRecognizer) {
    }
}

本題

messageTextViewの初期設定をしてあげます

仕様にもよりますが、以下の制御があったほうが理想だと思います。

messageTextView.isUserInteractionEnabled = true
messageTextView.isEditable = false
messageTextView.isSelectable = false
messageTextView.isScrollEnabled = false
   @IBOutlet weak var messageTextView: UITextView! {
        didSet {
            messageTextView.isUserInteractionEnabled = true
            messageTextView.isEditable = false
            messageTextView.isSelectable = false
            messageTextView.isScrollEnabled = false
            let mutableAttributedString = NSMutableAttributedString()
            let normalAttirbutes: [NSAttributedString.Key: Any] = [
                .foregroundColor: UIColor.gray,
                .font: UIFont.monospacedSystemFont(ofSize: 18, weight: .medium)
            ]
            let linkAttributes:  [NSAttributedString.Key: Any] = [
                .foregroundColor: UIColor.link,
                .underlineStyle: NSUnderlineStyle.single.rawValue,
                .font: UIFont.monospacedSystemFont(ofSize: 22, weight: .medium)
            ]

            mutableAttributedString.append(
                NSAttributedString(
                    string: "吾輩わがはいは猫である。",
                    attributes: normalAttirbutes
                )
            )
            mutableAttributedString.append(
                NSAttributedString(
                    string: "名前",
                    attributes: linkAttributes
                )
            )
            mutableAttributedString.append(
                NSAttributedString(
                    string: "はまだ無い。",
                    attributes: normalAttirbutes
                )
            )
            mutableAttributedString.append(
                NSAttributedString(
                    string: "どこで",
                    attributes: linkAttributes
                )
            )
            mutableAttributedString.append(
                NSAttributedString(
                    string: "生れたかとんと見当けんとうがつかぬ。",
                    attributes: normalAttirbutes
                )
            )
            messageTextView.attributedText = mutableAttributedString
        }
    }

次にタップ時の挙動を記述していきます。

    @IBAction func didTapMessageView(_ sender: UITapGestureRecognizer) {
        guard let text = messageTextView.text else { return }
        let name = "名前"
        let pos = "どこで"

        let nameRange = (text as NSString).range(of: name)
        let posRange = (text as NSString).range(of: pos)

        let location = sender.location(in: messageTextView)
        let textPosition = messageTextView.closestPosition(to: location)
        let tapPosition = messageTextView.offset(from: messageTextView.beginningOfDocument, to: textPosition!)

        if NSLocationInRange(tapPosition, nameRange) {
            print("たま")
        }

        if NSLocationInRange(tapPosition, posRange) {
            print("縁側")
        }
    }

結果

3j0z2-rnaio.gif

終わり

ポイントはNSLocationInRangeで毎回当たり判定的なものを行なって毎回処理を走らせるところです!

これをUIViewControllerRepresentableすればSwiftUIでも行けるのかも?
今度試してみます!

  • このエントリーをはてなブックマークに追加
  • Qiitaで続きを読む

【Swift】@testable import no such module “xxx” というエラーが出る

Xcodeでユニットテストを実行しようとしたらタイトルのエラーが出てしまった。
そんなモジュールは存在しないよと怒られてます。

:tools: TestのTargetの「Host Application」が設定されていない

スクリーンショット 2020-05-21 16.11.08.png

上記の、タブ画面でHostApplicationが「None」になっていないか確かめる。
もしなっていたたら現在自分が開発中のアプリをターゲットにしてあげる。

:computer: プロジェクト名などを途中で変更した場合

テストファイル内の

@testable import test

上記でいう「test」の部分は自動で更新されない。。
ので自分で修正してあげる必要がある。

  • このエントリーをはてなブックマークに追加
  • Qiitaで続きを読む

AR Quick Lookで3DモデルをAR表示する

AR Quick Lookを使用すると、iOSのSafariで3DモデルをAR表示することができます。

Quick Lookギャラリー - 拡張現実 - Apple Developer

AR Quick LookではUSDZ形式の3Dモデルが必要になります。USDZ形式以外の3DモデルをUSDZファイルに変換するには上のリンク先のページ下部にある「Reality Converter」と「USDZツール」のどちらかを使用します。

Reality ConverterはGUIアプリで、USDZ形式以外の3Dモデルをアプリにドラッグ&ドロップしてメニューからExportするだけでUSDZファイルを生成することができます。

USDZツールを使用する方法も解説します。2020年5月20日現在の最新版であるUSD Python 0.64をダウンロードして、含まれているパッケージをインストールします。インストールするとアプリケーションフォルダにusdpythonというフォルダが作られます。この中にあるUSD.commandをクリックするとターミナルが開きます。そこで以下のようにすると、適当な3DファイルをUSDZ形式のファイルに変換できます。usdzconvertには多数のオプションがありusdzconvert -hで確認できます。

$ cd /Applications/usdpython/usdzconvert
$ ./usdzconvert ~/sample.obj ~/sample.usdz

作成したUSDZファイルをAR Quick Lookで表示するには、以下のようにリンクを貼るだけです。iOSのSafariでリンクをクリックするとARで表示することができます。

<a rel="ar" href="/sample.usdz">
  <img src="/sample.jpg">
</a>

AR Quick Lookを使ったモデルのプレビュー - 日本語ドキュメント - Apple Developer

  • このエントリーをはてなブックマークに追加
  • Qiitaで続きを読む

【Swift】SVProgressHUDの表示がiOS13以上だとおかしくなる

結構古くからある「SVProgressHUD」というローダーのライブラリがあります。
癖が無くて使いやすいのですが、iOS13.0で動かしてみたら画面中央では無く何故か左上の隅っこに表示されてしまいました。

72616955-f5fd9580-395d-11ea-93e3-9d0310f525bb.png

対応策

AppDelegate.swift

static var standard: AppDelegate {
  return UIApplication.shared.delegate as! AppDelegate
}

SceneDelegate.swift

func scene(_ scene: UIScene, willConnectTo session: UISceneSession, options connectionOptions: UIScene.ConnectionOptions) {
  guard let _ = (scene as? UIWindowScene) else { return }
  AppDelegate.standard.window = window
}

以上のように変更するとiOS13系でもローディングが中央に表示されるようになった。

  • このエントリーをはてなブックマークに追加
  • Qiitaで続きを読む