著者アーカイブ 村上

村上 著者:村上

【PHP】Slim3初心者に!プロジェクトのひな型を作成できるパッケージ「slim/slim-skeleton」

昨日の記事で、Slim3の導入方法について紹介しましたが、「slim/slim-skeleton」パッケージを使った方が、特に初心者にはわかりやすいと思ったので、そのご紹介です。
私はテンプレートの導入方法で若干詰みかけていたのですが、このパッケージで作成したプロジェクトには既にテンプレートファイルが導入済みだったので、とてもありがたかったです。

参考にさせていただいた記事はこちらから。

Slim3のスケルトンプロジェクト、slim/slim-skeletonの解説 – akamist blog
https://akamist.com/blog/archives/815

主要なファイルを全て解説してあって、大変分かりやすかったです。
初心者にはおすすめの記事ですね。

GitHub のページはこちらから。

GitHub – slimphp/Slim-Skeleton: Slim Framework 3 skeleton application
https://github.com/slimphp/Slim-Skeleton

 

プロジェクトの新規作成には、下記のコマンドを実行します。

composer create-project slim/slim-skeleton [プロジェクト名]

あとは放っておけば、プロジェクトが作成されるので、コマンドが終了したら下記を実行。
なお、cd コマンドで、作成したプロジェクトのルートディレクトリに移動しておくのをお忘れなく。

php -S localhost:8080 -t public public/index.php
// または
composer start

必要なファイルは自動的に生成されるので、詳細についてはコードを参照ください。
なお、ルーティングファイルとして src/routes.php はありますが、コントローラーファイル等はなく、パスごとの処理は src/routes.php ファイルに直書きされているので、状況に応じてコントローラーファイルを作成し、処理を分けてください。

また、機能の記事にも書きましたが、Slim3 は必要最低限の機能しかないため、CSRF 対策を行いたい場合は、別途「slimphp/Slim-Csrf」を導入してください。
なお、ミドルウェアの導入は、src/middleware.php に記述します。
コメントにサンプルコードが書かれているので、参考にしてください。

 

以上、プロジェクトのひな型を作成してくれる「slim/slim-skeleton」パッケージのご紹介でした。
近いうちに「slimphp/Slim-Csrf」の紹介もしたいと思います。

なお、あまり参考になるかは分かりませんが、昨日の記事はこちらから。

【PHP】軽量フレームワーク「Slim3」の導入方法
https://cpoint-lab.co.jp/article/201901/【php】軽量フレームワーク「slim3」の導入方法/

紹介しているリンク先の記事はとても参考になりますので、ご活用ください。

村上 著者:村上

【PHP】軽量フレームワーク「Slim3」の導入方法

現在、PHPの軽量フレームワークで「Slim3」というものを試してみています。
こちらのフレームワークは必要最低限の機能しかないため軽量で、学習コストも低くて済みます。
当然、基本機能以外は開発者が実装しなければいけませんが、その分カスタマイズ性が高いという利点もあります。

ちなみに、この「Slim3」を選んだ理由は、「PHP フレームワーク 軽量」と調べたときに、候補の一番最初に表示されたからという理由です。
でも、触ってみた感じは、(今のところ)なかなか分かりやすくておすすめですね。

今回参考にさせていただいた記事はこちら。

PHP軽量FrameworkのSlim3 – Qiita
https://qiita.com/Syo_pr/items/b55e18a8361b3ff882b5

こちらの内容に沿って、実装を行いました。

 

まず、ディレクトリを作成します。
名前は任意でOKですが、私はミス防止に、サンプルの名前をそのまま使っています。

mkdir testSlim
cd testSlim/
mkdir public
cd public/

ディレクトリをつくったら、次に index.php を用意します。

vim index.php

index.php の内容はこちら。

<?php
use \Psr\Http\Message\ServerRequestInterface as Request;
use \Psr\Http\Message\ResponseInterface as Response;

require __DIR__ . '/../vendor/autoload.php';

$app = new \Slim\App;
$app->get('/hello/{name}', function (Request $request, Response $response) {
    $name = $request->getAttribute('name');
    $response->getBody()->write("Hello, $name");

    return $response;
});
$app->run();

最後に、一つ上のルートディレクトリに戻り、下記を実行します。

composer require slim/slim "^3.0"

なお、環境によっては Composer コマンドが使えないこともあるので、その場合は Composer をインストールします。
案の定、私の環境では使えなかったため、下記のサイトを参考にしてインストールを行いました。

Composer を Windows にインストールする手順|WEB ARCH LABO
https://weblabo.oscasierra.net/php-composer-windows-install/

インストール後、composer -V を実行して、バージョンが表示されれば成功です。

そして、下記のコマンドを実行し、ビルトインウェブサーバーを起動します。

php -S localhost:8080 -t public public/index.php

サンプル通りに作成した場合は、http://localhost:8080/hello/test にアクセスし、Hello, test と表示されれば成功です。

上で紹介した参考サイトでは、Routes.php とコントローラーファイルを作成し、Laravel 風のルーティングテーブルを作成する方法についても記述されていました。
こちらを導入すると、index.php や Routes.php がすっきりするため、おすすめです。

 

なお、Slim3 は最低限の機能しかないため、CSRF 対策を行う場合は、別途 slimphp/Slim-Csrf を導入する必要があります。
GitHub のページはこちらから。

GitHub – slimphp/Slim-Csrf: Slim Framework CSRF protection middleware
https://github.com/slimphp/Slim-Csrf

インストール方法から導入の手順まで載っているので、是非参考にしてください。
slimphp/Slim-Csrf の導入については、後日記事にまとめたいと思っています。

 

以上、軽量フレームワーク「Slim3」の紹介と導入方法でした。
現在は、slimphp/Slim-Csrf の導入の途中まではできたので、引き続き開発を行っていきたいです。
テンプレートを用意して、それを読み込んだりもしたいですね。
公式のドキュメントでは、slim/twig-view が紹介されていたので、こちらを導入してみたいと思います。

村上 著者:村上

【Cordova】テキストの音声読み上げ機能を実装できるプラグイン「cordova-plugin-tts」

言わずもがな、ほぼ私のための備忘録ですが…今回はテキストの音声読み上げ機能を実装するためのプラグイン「cordova-plugin-tts」のご紹介です。
読み上げの言語や、読み上げのスピードなんかも細かく設定できます。

GitHub のページはこちらから。

GitHub – vilic/cordova-plugin-tts: Cordova Text-to-Speech Plugin (Maintainer WANTED!)
https://github.com/vilic/cordova-plugin-tts

 

さて、実装方法ですが、まずインストールには下記のコマンドを実行します。

cordova plugin add cordova-plugin-tts

で、サンプルコードは下記のとおり。

TTS
    .speak({
        text: '[読み上げたいテキスト]',
        locale: 'ja-JP',  // 言語
        rate: 1  // 読み上げスピード
    }).then(function () {
        // 読み上げ成功時の処理
    }, function (reason) {
        // 読み上げ失敗時の処理
    });

なお、言語や読み上げスピードを指定しない場合は、下記のようにシンプルな書き方もできます。

TTS
    .speak('[読み上げたいテキスト]').then(function () {
        // 読み上げ成功時の処理
    }, function (reason) {
        // 読み上げ失敗時の処理
    });

音声再生を停止する場合は、.stop() を使います。
具体的には下記のとおりです。

TTS.stop();

が、調べてみると、この .stop() が正常に働かないという投稿もちらほら…。
私の環境では動いたのですが、何が原因なのでしょうか。

 

以上、テキストの音声読み上げ機能を実装するためのプラグイン「cordova-plugin-tts」のご紹介でした。
なお、こちらのプラグイン、端末によっては、漢字の読み間違えをすることもあるので、読み上げたいテキストには、All ひらがなのテキストを指定したほうが良さそうです。
とにかく、どのように再生されるかは一度チェックすることをおすすめします。

村上 著者:村上

【アプリ】iOSでビーコンの信号が受信できているかを確認できるアプリ「Beacon Scanner」

以前、Android でビーコンの情報を確認できるアプリ「Beacon Scanner」をご紹介しましたが、iOSでも良さそうなアプリを見つけたのでご紹介。
同じ名前の「Beacon Scanner」です。
が、こちらはどちらかというと、ビーコンの信号が受信できているかを調べるアプリですね。
UUID など、ビーコンの信号情報そのものを確認したい場合は不向きです。

アプリのインストールはこちらから。

Beacon Scaner on the App Store
https://itunes.apple.com/us/app/beacon-scaner/id1224905991?mt=8

ちなみに、Androidアプリの Beacon Scanner を紹介した記事はこちら。

【アプリ】AndroidでキャッチしたBeaconの情報を確認できるアプリ「Beacon Scanner」
https://cpoint-lab.co.jp/article/201809/【アプリ】androidでキャッチしたbeaconの情報を確認でき/

 

実際の画面はこんな感じ。

シンプルでわかりやすい!

ただ、使用する前に、ビーコンのUUID を登録する必要があるので要注意です。

上の画像のように、受信したい UUID を登録します。
そのため、ビーコンも ID が同じものでなければ、受信できているかどうかはわかりませんのでご注意ください。

UUID を登録後は、左のメニューから「Scan Beacon」をタップすれば、ビーコンをスキャンし、受信できたビーコンの情報を表示してくれます。

あとは、端末の Bluetooth を有効にしておくことをお忘れなく。

 

以上、iOS でビーコンの信号を受信できているかを確認できるアプリのご紹介でした。
個人的には、以前紹介した Android アプリの方が使い勝手が良いと思いますね。
ただ、アプリ開発時に「そもそも、これ本当にビーコン受信できてるの?」と心配になることがあるので、その心配を解消するためにはとても有効なアプリかと思います。
是非、ご活用ください。

村上 著者:村上

【React】React Routerで直前のページに戻るボタンを実装する

ちょっとしたことですが、コピペできると便利だろうなぁと思い、まとめ。
React Router で戻るボタンを実装する方法です。

参考にした記事はこちら。

React Routerのhistoryはどこから来るのか|TECHSCORE BLOG
http://www.techscore.com/blog/2017/12/01/where_does_react-router-history_come_from/

React 及び React Router の導入方法については割愛。
おそらく、Qiita あたりにわかりやすい記事があると思うので、そちらを参考にしてください。

 

実装方法…というか、前ページへ戻るための処理は下記の通りです。

this.props.history.goBack()

ページ遷移の時は、this.props.history.push('[遷移先]'); ですが、前のページに戻る時は最後が goBack() になります。
わかりやすいですね!

で、戻るボタン実装の際は、下記の通りです。

<button onClick={() => this.props.history.goBack()}>戻る</button>

よく、onClick に処理を書く際、最初の () => を書き忘れそうになるので、まるっとコピーできるように…。
…上記のコードはそのままコピー&ペーストで動くかと思いますので、是非ご活用ください

 

以上、React Router で戻るボタンを実装する方法でした。

村上 著者:村上

【Xcode】「An error was encountered while attempting to communicate with this device.」エラーの対処法

Xcodeでアプリ開発中に遭遇したエラーについて。
エラーは「An error was encountered while attempting to communicate with this device.」というものです。
訳すと「このデバイスと通信しようとしたときにエラーが発生しました。」とのこと。通信時のエラーのようですね。
解決方法は全く難しくなかったのですが、エラー文だけでは詳細な原因がわからなかったので、今後また遭遇した時のためにまとめます。

今回参考にさせていただいた記事はこちらから。

【Xcode9】An error was encountered while attempting to communicate with this device.のエラーが出た場合の対処方法【iOS11】|ニートに憧れるプログラム日記
http://program-life.com/227

 

さて解決策ですが、まず1つ目は、プロジェクトを Clean するというもの。
通常ですと、Build → Run の流れかと思いますが、一度 Clean してから Build を行うと解決できることがあるのだとか。
ただ、私の環境ではこの方法では解決できず。

2つ目は、Xcode の再起動です。
単にウィンドウを閉じるだけでなく、完全に終了してから、再度 Xcode を起動します。
で、再度 Build して実行します。
この方法を試したところ、問題なくアプリを実行できました!

他にも、使用しているiPhoneを再起動する方法や、最終手段として(Gitを使用している場合)一つ前のコミットに戻る方法もあるとのこと。
…とりあえず、Git 操作をしなくて済んでよかった…。
または、デバイスとの通信エラーのようなので、一度デバイスとの接続を解除してから、再接続するのも効果的かもしれませんね。

 

以上、Xcode でアプリを実機起動できなかった時の対処法でした。
今回のエラーは対処が簡単でよかったです。

村上 著者:村上

【JavaScript】JSONオブジェクトの要素数を取得する方法

若干ハマったので、備忘録としてまとめ。
JSONの要素数を取得方法についてです。
単に length だけでは取得できないんですね。今回初めて知りました。

今回参考にさせていただいた記事はこちら。

javascriptでのJSONの大きさ(サイズ)の取得 – joppot
https://joppot.info/2014/02/21/861

 

で、その方法ですが、length にプラス Object.keys を使うのだとか。
サンプルは下記のとおりです。

const length = Object.keys([要素数を知りたいJSON]).length;

単に [JSON].length だと undefined になってしまっていたのですが、上記の Object.keys を使う方法だと、問題なく要素数が取得できました。
なお、size() を使っても、正しい要素数は取得できないとのこと。
JSONオブジェクトのサイズ取得には、上記の方法が最適のようですね。

 

以上、JSON オブジェクトの要素数を取得する方法でした。

村上 著者:村上

【Xcode】アプリを実機にインストールできない「The executable was signed with invalid entitlements.」エラーの対処法

久し振りに、iOS アプリの開発を行ったところ、実機へのインストール時に、「The executable was signed with invalid entitlements.」というエラーが発生。
今回は、その対処法についてです。
以前にも、実機でアプリを起動できないことがありましたが、その時とは違うエラーでした。
原因は署名のあたりにありそう。

で、いくつかヒットした記事の中で、実際に解決策とのなったのがこちらの記事でした。

ionic framework – The executable was signed with invalid entitlements – 0xe8008016 – Stack Overflow
https://stackoverflow.com/questions/52846785/the-executable-was-signed-with-invalid-entitlements-0xe8008016

 

解決策ですが、まず Xcode のメニューバーの「File」から、「Workspace Settings…」を洗濯します。

すると次のようなウィンドウが表示されるので、「Build System」の項目を「Legacy Build System」に変更します。

操作はこれだけ!
あとは、一度 Clean してから、Build 及び Run を実行しましょう。
私の環境では、この方法で解決できました。

 

調べた時に、他にも、TARGETS の Build Settings の Code Signing Identify の Debug の値を「iOS Developer」に変更する、や、同じく TARGETS の Build Settings の Code Signing Entitlements に定義されているパスが正しいかを確認する、などの方法もありました。
が、私に環境ではこちらについては問題なしだったため、Build System を変更する方法をとりました。
個人的には、まず上の2点をお調べすることをお勧めします。

以上、iOSアプリが実機にインストールできない時の対処法でした。
この方法で解決できれば幸いです。

村上 著者:村上

【Android】ActivityのメソッドをAdapterで呼び出す方法

ちょっと悩んだので、今後のためにまとめ。
Adapter内で、Activity に記述したメソッドを呼び出す方法です。
Interface を使用しています。

なお、今回参考にしたのはこちらのサイトです。

Android – Call Activity method from adapter – Stack Overflow
https://stackoverflow.com/questions/12142255/call-activity-method-from-adapter

2つ目のアンサーに書かれている内容を参考にしました。

 

では早速コードを書いていきます。
まず、インターフェースを作成します。
で、Adapter で呼び出したい& Activity に追加するメソッドを定義します。

public interface [インターフェース名] {
    void test();
}

なお、この時指定するのは、メソッド名・引数・戻り値のみで、処理内容は記述しません。

次に、Activityに、上で作成したインターフェースを、下記のように implements で実装します。

public class [アクティビティ名] extends AppCompatActivity implements [インターフェース名] {

Android Studioを使用している場合、上記のようにインターフェースを追加すると、メソッドをオーバーライドして!というエラーになるので、Alt+Enter で言われるがままにメソッドを追加します。
なお、追加するメソッドは下記のとおりです。
最初に @Override が付くのにお気を付けください。

@Override
public void test() {
    // メソッド内で行いたい処理
}

そして Adapterに、下記を追加します。

public [アダプター名] extends BaseAdater{
    private [インターフェース名] listener;

    public [アダプター名]([インターフェース名] listener){
        this.listener = listener;
    }
}

で、あとは下記のように使いたいタイミングでメソッドを呼び出すだけです。

listener.test();

 

で、私がハマったのが、Adapterでの定義で、継承しているのが BaseAdapter ではなかったので、上記の記述では動かなかったんですよね…。
なので、下記のように修正。
まず、Adapter。

private int mResource;
private List<EntryListItem> mItems;
private LayoutInflater mInflater;
private Context mContext;
private ListViewInterface listener;

public [アダプター名](Context context, int resource, List<EntryListItem> items, [インターフェース名] listener) {
    super(context, resource, items);

    this.mContext = context;
    mResource = resource;
    mItems = items;
    mInflater = (LayoutInflater)context.getSystemService(Context.LAYOUT_INFLATER_SERVICE);
    this.listener = listener;
}

一部必要ないものも混じっていますが、それはスルーしてください。

次は、このままでは、Activitiy でエラーになるので Adapter を new している所を修正します。

[アダプター名] adapter = new [アダプター名](getBaseContext(), R.layout.[レイアウトファイル名], item, this);

最後の this がインターフェースを指しています。
ここが分からず、少し悩みました…。

 

以上、Activity内のメソッドをAdapterで呼び出す方法でした。
もしかしたら、ListViewを扱うときなどに使うことがあるかもしれませんので、その際は是非ご活用ください。

村上 著者:村上

【Android】ListView要素にボタンを追加すると要素自体のクリックイベントが呼ばれない

長いタイトルですみません。
Android アプリでカスタム ListView を利用しているとき、List の要素に Button(ImageButton)を追加したところ、要素自体のクリックイベントが呼ばれなくなったので、その対処法について。
実はこれ、以前も経験していて対処法があることは覚えていたのですが、その内容は失念していたので、備忘録としてまとめ。

なお、参考にさせていただいたサイトはこちらから。

ボタン付きのListViewを実装してみる – Qiita
https://qiita.com/maromaro3721/items/6ac3cba4f090662adabf

 

で、対処法ですが、ListViewItem のレイアウトを記述しているXMLファイルに、下記の一行を追加するだけ。

android:descendantFocusability="blocksDescendants"

具体的には下記のとおりです。

<?xml version="1.0" encoding="utf-8"?>
<RelativeLayout
    xmlns:android="http://schemas.android.com/apk/res/android"
    android:layout_width="match_parent"
    android:layout_height="match_parent"
    android:descendantFocusability="blocksDescendants">

    <TextView
        android:id="@+id/title"
        android:layout_width="match_parent"
        android:layout_height="wrap_content" />
    <ImageButton
        android:layout_width="50dp"
        android:layout_height="match_parent"
        android:src="@drawable/icon"
        android:scaleType="fitCenter"
        android:id="@+id/btn"
        android:layout_alignParentRight="true"/>
</RelativeLayout>

5行目に記述しています。
これを指定し忘れると、ListViewItem のボタンは反応するのに、ListViewItem 自体がクリックできなくなるのでご注意ください。
ちなみに、それ以外の指定等はなにもなく、これだけです。

なお、ListViewItemに指定したボタンのクリック検知は、ListAdapter の getView関数内で行います。
抜粋するとこんな感じ。

@Override
public View getView(int position, View convertView, ViewGroup parent) {
    View view;

    if (convertView != null) {
        view = convertView;
    } else {
        view = mInflater.inflate(mResource, null);
    }

    // ボタンのクリックイベント
    ImageButton btn = view.findViewById(R.id.btn);
    btn.setOnClickListener(view1 -> {
        // ボタンクリック時に行いたいたい処理
     });

     return view;
}

 

以上、カスタムしたListView にボタンを追加した際、ListViewItem自体のクリックイベントが呼ばれなくなる現象とその対処法についてでした。
同じことでお困りの方は、是非お試しください。