pantasystem / Milktea

Misskey, MastodonのAndroidクライアント「Milktea」のソースコード
GNU General Public License v3.0
256 stars 22 forks source link

フォローボタンのデザインをわかりやすくする #1955

Closed pantasystem closed 1 year ago

pantasystem commented 1 year ago

概要

プロフィール画面、ユーザ一覧画面のフォローボタンのデザインが フォロー・非フォロー状態に関わらず同じような見た目でわかりづらいので、 状態に応じて異なるデザインのボタンが表示されるようにしたい。 また一覧画面とプロフィール画面のボタンのレイアウトの統一感を持たせるようにしたい。

sanao1006 commented 1 year ago

やりたいです🙋

sanao1006 commented 1 year ago

フォローとフォロー解除は見た目が変わる方がいいと思ったので、プロフィール画面を一覧のほうに合わせるべきかなと思ったのですがいかがでしょうか?

pantasystem commented 1 year ago

お願いします🙏

sanao1006 commented 1 year ago

すみません、質問いいですか!

ちょっと文法的なところで悩んでいます

まず方針として、フォローしてない状態ではフォローボタンをOutlinedButtonにすればいいと思いました。 https://github.com/pantasystem/Milktea/blob/33c811244e9b569209123d06dbb61e3fb93e01df/modules/features/user/src/main/res/layout/activity_user_detail.xml#L125-L135 なので、activity_user_detail.xmlの上の部分にuserViewModel.userState.followStateがUNFOLLOWINGかUNFOLLOWING_LOCKEDのときだけ@style/Widget.MaterialComponents.Button.OutlinedButtonスタイルをあてようと思ったので

...
  android:visibility="@{userViewModel.mine ? View.GONE : View.VISIBLE}"
  android:onClick="@{()-> userViewModel.changeFollow()}"
  app:cornerRadius="32dp"
  style="@{userViewModel.userState.isUnFollow ? @style/Widget.MaterialComponents.Button.OutlinedButton : ''}"
/>

みたいな感じ(isUnFollowは仮の変数)にxmlに追記したのですが、バインディング式の文法的に不可能なようで困っています(@styleは@{}のなかで使えない?)。

他にもBindingAdapterも試したのですが、 https://github.com/pantasystem/Milktea/blob/33c811244e9b569209123d06dbb61e3fb93e01df/modules/features/user/src/main/java/net/pantasystem/milktea/user/helper/FollowStateHelper.kt#L22-L24 ここにならって、

fun Button.setOutlinedStyle(state: FollowState?) {
        state?: return
        this.style = when(state) {
   //   this.setStyle = ... もダメなようでした

のように書けるかと思ったのですがこちらも不可能なようで・・・

どのように書くべきかお力添えいただけるとありがたいです🙇

pantasystem commented 1 year ago

まずstyleについてなのですが、Androidの各種Viewのコードを見てもらえると分かるのですが、 コンストラクタでstyleを経由して各種xmlに指定されたプロパティを読み取って指定しているだけなので、 直接styleというものがAndroidのViewに指定されているわけではありません。 そのためインスタンス化済みのViewからstyleを更新するには、 各種styleの値に対応するViewのプロパティを手動で一つ一つ更新する必要性があります。

pantasystem commented 1 year ago

考えられる方法としては

  1. 手動でパラメータを書き換えるコードを書く
  2. OutlinedなボタンとTextなどボタン二つをあらかじめxmlに入れておき、状態に応じてvisibilityを切り替える
  3. ViewStubなどを用いて動的にinflateする

1の方法は実現自体は可能なのですが、MaterialButtonとそれに関連するスタイルを分析し、対応するコードを書かないといけないのでそれなりに手間がかかることが考えられます。 2の方法はxmlを見た時の可読性が若干低いですが、一番容易性が高いと思います。 3の方法は確かDataBindingと相性が悪かったように思います。

sanao1006 commented 1 year ago

ありがとうございます!

とりあえず、1も気になりますが今回は2の方針で進めてみます!!

pantasystem commented 1 year ago

あとはボタンの部分をComposeViewにしてしまって ボタンの部分はComposeで表示してしまうなどでしょうか:thinkingface:

sanao1006 commented 1 year ago

部分的にjetpack composeへ移行させるっていう流行りのやつですね!

やったことはないのですが、興味があるので試してみたいですね

pantasystem commented 1 year ago

確かユーザ詳細画面(プロフィール画面)のヘッダーのロールバッジの表示にComposeを使っていたと思うので もしよければ参考にしてください🙏 https://github.com/pantasystem/Milktea/blob/59baf72a42dfef2a1c5165f686d086cf52740452/modules/features/user/src/main/res/layout/activity_user_detail.xml#L188-L197

https://github.com/pantasystem/Milktea/blob/59baf72a42dfef2a1c5165f686d086cf52740452/modules/features/user/src/main/java/net/pantasystem/milktea/user/profile/UserDetailActivity.kt#L173-L188