Android Studioのビューアニメーションの罠
仕事が忙しくずっと放置してしまってました・・・。
本日はタイトル通りの内容です。
仕事でアニメーション作成の際の記述で沼ったので解説を・・・。
皆さんがアニメーションを制作するときに、記述を調べたくてネット検索を行うかと思います。
その際に「移動 アニメ」などとして結果上位に表示されるのは大体がビューアニメーションです。
でもこのビューアニメーション・・・便利ですがとある罠があります。
ビューアニメーションのはビューの見た目を変えるという機能です。
「いや、何を当たり前なことを」
と思ったそこのあなた!
悲報です。
こいつは見た目が動くだけで、座標情報を保持していないんです。
どういうことかというと、
プログラム上はもともとの座標のままで、見た目のみが移動しているということです。
そのため、一度移動を終えたビューに対して再度移動をさせようとすると初期値(xmlで指定した位置)からの開始になります。
私自身この仕様に気が付かずに色々な記述を試し、時間を浪費してしまいました。
移動さきの座標情報がない以上相対的な移動は不可能なんです・・・。無理やり連続させるなら親の左上起点の絶対値での移動になります。
さて、ここで朗報です。
私のもとにObjectAnimatorという神が降臨しました。
こいつは・・・このお方は、見た目ではなくオブジェクト本体の座標情報を変更します。
ObjectAnimato様で移動した時には移動先の情報が保持されます。
故にアニメ終了後に移動した位置から再度動かすことが可能となります。
基本的な記述は以下のようになります。
ObjectAnimator.ofFloat(ビュー, "プロパティ名前", Float型移動数値)
少し実用的にすると以下のような感じ
//引数でビューオブジェクトと移動距離を取得 fun xAnimation(v:View,xNum){ //オブジェクトアニメーターにビューとプロパティを設定し、移動距離を突っ込んで実行 val anime = ObjectAnimator.ofFloat(v, "translationX", xNum).apply{ dulation = 1000 start() } } //関数にビューオブジェクトと移動距離を渡す xAnimation(binding.view,400f)
はい。これで座標の罠にかかることがなくなりましたね。
次回は円軌道でオブジェクトを動かす方法についてアウトプットしようかと思います。
資料が公式リファレンスくらいなもので、実際にブログなどで上げている方がほとんどいなかったので・・・。
プログラミングの学習方法やモチベーションの維持に関して
本日はタイトル通り
学習方法やモチベーションの維持に関してです。
この部分に関してはスクールなどの利用をお勧めします。
理由としては大きく2点です。
1 : 独学での学習では挫折する可能性が高い
2 : 一人での学習はモチベーションの維持が難しい
1に関しては、わからない部分をわからないまま進めてしまって
基礎の構築ができず挫折してしまう可能性があります。
そもそも環境構築がわからず諦めてしまったという話もよく聞きます。
2に関しては、同じ志を持つ仲間と学習することでモチベーションを高く保つことができます。
また、専属でカウンセラーやライフコート、アドバイザーなどが付くことが多いので、
相談しながら学習プランを考えていけるなどの利点もあります。
私は学習にテックキャンプを利用しました。
生徒一人一人に
メンター(技術面の相談相手)
ライフコート(生活面の相談相手)
キャリアアドバイザー(就職活動支援)
がつくので学習から転職までがスムーズです。
また、専門実践教育訓練給付金制度が利用でき学習費用が最大で70%戻ります。
転職保証制度もあり、内定が決まらなかった場合には全額返金などの制度もあります。
未経験からのエンジニア転職にどれだけの自信を持っているかがわかりますね。
転職用
教養としての学習用
紹介欄にコード「urip70」を入力するとそれぞれ
エンジニア転職では10000円分のAmazonギフト券がもらえる
プログラミング教養では受講料が5%割引になる
という特典があります。
実際に受講した感想
受講を開始して最初に私が躓いたのは環境構築です。
MacのOSのバージョンによって手順や導入するフレームワークのバージョンなどが変わってしまうため、学習するにあたりターミナルのバージョンをダウングレードしました。
この作業に関して、私一人では解決不可能だったと思います。
技術面の相談に乗ってくれるメンターの方に相談しながらなんとか解決できたとと言った感じです。
メンターの方は実力のあるプログラマーの方々なので、原因等を説明しながらどうすればいいのかを教えてくれました。
学習に入っていって躓いたのはクラスやメソッドと言った部分の理解です。
最初は本当に訳が分からず頭が混乱しました。
なのでメンターを質問攻めにして少しずつ理解していきました。
理解しようと努力する人に対しては真摯に向き合って学習の手助けをしてくれるので本当に助かりました。
学習するにあたってのポイントは楽しむことです!
実際に学んだプログラムを改造して遊んだりしているうちに徐々に理解できるようになってきます。
フレームワークはRuby on Railsを使って学習を進めていきました。
この部分に関しても覚える部分が多く大変でしたが、メンターに助けてもらったり、
基本の講座とは別にRailsの勉強会のようなものを開催してくれたので、非常に助かりました。
その後JavaScriptやデプロイの仕組みや手順などを学習し、一通りカリキュラムが終わった後には就職活動のポートフォリオとしてオリジナルアプリケーションの作成を行いました。
この頃にはRailsの扱いにも慣れてだいぶ思い通りに作成できるようになっていました。
就職活動が始まるとキャリアアドバイザーがついて一緒に履歴書、職務経歴書の作成を行いました。
面接が決まった企業の面接対策や、個人の履歴の部分でプッシュすべき部分などを事細かにアドバイスしていただけたので安心して就職活動に取り組めました。
キャリアアドバイザーの助けもあって、就職を始めて2週間ほどで第一志望の企業から内定をもらうことができました。
私の履歴に関してですが、大きな欠点は3点。
・ジョブホッパーであること。
・有用な資格を有していたいこと。
・年齢が30オーバーであること
があげられます。
しかしながらテックキャンプで学習し努力を重ね、キャリアアドバイザーに手助けしていただいた結果、すぐに内定を獲得できました。
30代からでもしっかりとしたスクールで学習し、
努力を重ねることでエンジニアになれるのです!
学習してきたのはRubyとRails、JavaScriptとWeb系ではありますが、現在はKotlinを使いAndroidアプリケーションの制作を行っています。
テックキャンプは30代からのエンジニア転職に非常に強いので、
30オーバーでスクール利用ならテックキャンプをお勧めします!
転職用
教養としての学習用
紹介欄にコード「urip70」を入力するとそれぞれ
エンジニア転職では10000円分のAmazonギフト券がもらえる
プログラミング教養では受講料が5%割引になる
という特典があります。
Ruby(10) クラスとインスタンスとは?
今回はクラスとインスタンスについてです。
ただ、学習にあたってオブジェクト指向とは何か
という部分を知らなければいけないので
まずはオブジェクト指向について学習しましょう。
オブジェクト指向というのは
データの集合体(属性)とそのデータに対する動作(メソッド)を一つの設計図(クラス)として作成し、
設計図から作成したモノ(インスタンス)とモノを組み合わせることによってプログラムを作っていく手法です。
人間で説明するとわかりやすいので人間に例えて説明します。
まずモノを作るためには設計図が必要になります。
人間の設計図を作るために何が必要でしょうか?
人間の特徴の部分と、人間が行う動作を設計図に記述する必要があります。
まずは人間の設計図を作ってみましょう。
# Humanクラスを作成 class Human # initializeはインスタンス作成時に自動実行される処理 # 今回は人物の名前と年齢の情報を格納 # 変数の頭に@をつけることでインスタンス変数というものになり、クラス内の他のメソッドでも使用できるようになる。 def initialize(human_name, human_age) @human_state = {} # 情報を格納するためのハッシュを作成 @human_state[:name] = human_name # nameというキーを作りバリューとして引数を指定 @human_state[:age] = human_age # ageというキーを作りバリューとして引数を指定 # この一つ目のインスタンスの段階でのハッシュの中身 {:name=>"taro", :age=>18} end # 食べるものの情報 def eat(food) puts "#{@human_state[:name]}は#{food}を食べる" end #歩く場所の情報 def walk(place) puts "#{@human_state[:name]}は#{place}を歩く" end end
ちゃんと記述すると情報量が多すぎるので年齢と名前しか入れてないです!
イメージは掴めたでしょうか?
人物の情報を定義した上でその人物に特定の動作をさせます。
次はクラスのインスタンス化(設計図をモノとして実体化させる)と動きをつけるための記述です。
taro = Human.new("太郎", 18) # taroという変数にHumanクラスを.newによりインスタンス化して格納 ここで指定した引数がinitializeに送られる。 taro.eat("家系ラーメン") # taroにeatメソッドを実行するように指示 taro.walk("東白楽") # taroにwalkメソッドを実行するように指示 hanako = Human.new("花子", 15) hanako.eat("カレー") hanako.walk("横須賀")
少しずつイメージが固まってきたでしょうか?
一度プログラム全体を見てみましょう。
class Human def initialize(human_name, human_age) @human_state = {} @human_state[:name] = human_name @human_state[:age] = human_age end def eat(food) puts "#{@human_state[:name]}は#{food}を食べる" end def walk(place) puts "#{@human_state[:name]}は#{place}を歩く" end end taro = Human.new("太郎", 18) taro.eat("家系ラーメン") taro.walk("東白楽") hanako = Human.new("花子", 15) hanako.eat("カレー") hanako.walk("横須賀")
難しいことをやっているように見えますが、
考え方一つで簡単に捉えることができます。
まず主役となるモノを設計図に基づいて作り上げます。
その後そのモノに対して「〜を食べて」「〜を歩いて」と言ったような指令を出します。
オブジェクト指向のプログラミングはプログラムとプログラマの対話です。
難しく考えすぎる必要はありません。
今回の例(太郎君)では
まず変数taroに設計図に基づいて太郎君をインスタンス化して代入します。
その際に太郎君の人物情報をinitializeメソッドに送りハッシュに格納しています。
その後taroに対してeatメソッドを実行してという指令を出したりwalkメソッドを実行してという指令を出しています。
難しく考えすぎるとドツボにハマるので
シンプルに自分がわかりやすいように考えていくようにしましょう。
では今回はこの辺りで!
Ruby(9) メソッドとは?
今回はメソッドについて学習しましょう。
まずそもそもメソッドってなに?というところですが、
メソッドというのは処理に名前をつけて使いまわせるようにするものです。
例えばですが、コンビニのレジで生産をするときに
一つ一つの商品に対して税率の計算をしていくと時間がかかりますし大変ですよね。
そこでメソッドの出番です。
予め税率を計算するための処理をメソッドとして名前をつけて登録しておきます。
すると商品を登録スキャンしてメソッドの名前を入れるだけで自動で計算して結果を出してくれるようになります。
これがメソッドです。
Rubyではdef〜endまでをメソッドとして扱います。
では基本的な記述を見てみましょう。
// メソッドの定義 def メソッド名(仮引数) end // メソッドの呼び出し メソッド名(引数)
これが基本形です。
引数というのはメソッドなどに渡したい値です。
仮引数というのは外部から受け取った値を仮引数に入れてメソッド内で扱うために必要になります。
例を見てみましょう。
def num_put(num) puts num end number = 10 num_put(number)
プログラムは上から順に進んでいくのになぜこれでエラーが出ないの?
と思った方はなかなか目の付け所がシャープです。
これはプログラムが読み込まれるときにメソッド部分は読み飛ばされるためです。
具体的にいうとメソッドは呼び出されて初めて機能するものだからです。
それを踏まえた上で処理の流れを追ってみましょう。
プログラムが読み込まれてメソッドはスルーされ
最初に変数numerの宣言が行われます。
次に引数として変数numberをメソッドnum_putに送ります。
メソッドは受け取った変数numberを仮引数numとして扱い処理を行います。
puts numが実行され、結果として10という数値が出力されます。
ではもう一つ例を
def num_put(num) return num += (num * 0.1).floor //floorメソッドによって計算結果を小数点以下切り捨て end number = 100 puts num_put(number) # 結果 # 110
早速プログラムの流れを見ていきましょう。
まず最初に変数宣言し、putsメソッド処理として宣言した変数を引数としてメソッドに送ります。
メソッド内では受け取った変数をnumとして扱い、記述された計算を行います。
ここで出てきたreturnというのはメソッド呼び出しもとに返す値を指定する文です。
呼び出しもとに返す値を返り値や戻り値と言います。
今回は計算式の結果を呼び出しもとに返します。
メソッド内で処理した値を呼び出しもとが受け取り、putsメソッドに従い結果を出力します。
上記のような流れとなります。
returnに関しては省略することができます。
省略した場合には最後の処理の結果を戻り値として渡します。
このあたりは概念的なものなので慣れるしかないです。
一緒に頑張っていきましょう!
Ruby(8) メソッドを用いた繰り返し
今回はメソッドを用いた繰り返し処理についてです。
まずはeachメソッドからです。
このメソッドは前回学習したfor文と動きが似ています。
基本的な記述は以下のように行います。
オブジェクト.each do |変数| 処理 end
では前回使った例と同じような記述をeachメソッドを使って行ってみましょう。
ary = ["スギ","ヒノキ","イネ"] ary.each do |allergies| puts "今年は#{allergies}の花粉がやばい" end end # 出力結果 # 今年はスギの花粉がやばい # 今年はヒノキの花粉がやばい # 今年はイネの花粉がやばい
処理の流れとしてはeachメソッドを使って配列aryを変数allergiesに一つずつ入れて処理を行います。
パイプ||の中で宣言している変数はブロック変数(ブロックパラメーターとも)と呼ばれるもので、
対象ブロック(do~endまで)のみで有効な変数です。
繰り返し処理はオブジェクトの中に格納されている要素数回行います。
次はtimesメソッドです。
こちらは指定した回数繰り返し処理を行うというものになります。
integer.times do |変数| 処理 end
上記が基本的な記述です。
変数には自動的に0が代入されます。
10.times do |i| puts i end # 結果は0~9までの数値が出力されます(0からカウントして10回処理を行うため)
次はuptoメソッドです。
指定した値が最大値に達するまでの間処理を継続します。
integer.upto(最大値) do |変数| 処理 end
上記が基本的な記述です。
実際に使ってみましょう。
i = 1 5.upto(10) do |num| puts "#{i}回目、数値は#{num}" i += 1 end # 結果 # 1回目、数値は5 # 2回目、数値は6 # 3回目、数値は7 # 4回目、数値は8 # 5回目、数値は9 # 6回目、数値は10
例からわかるようにオブジェクトに指定したintegerの値がブロック変数に入っています。
そしてブロック変数が繰り返しとともにカウントアップしていき、最大値に指定した値に達したときに処理が終了します。
次はdowntoメソッドです。
こちらはuptoとは逆で開始値から繰り返す度にカウントダウンしていき最小値まで処理を繰り返します。
integer.downto(最小値) do |変数| 処理 end
上記が基本的な記述の仕方です。
i = 1 10.downto(5) do |num| puts "#{i}回目、数値は#{num}" i += 1 end # 結果 # 1回目、数値は10 # 2回目、数値は9 # 3回目、数値は8 # 4回目、数値は7 # 5回目、数値は6 # 6回目、数値は5
例を見てわかるようにuptoとは逆の処理になっていますね。
では次はstepメソッドです。
こちらはuptoと似ているのですが、大きな違いとしては小数点以下の値を扱えることです。
オブジェクト.step(最大値,1ループごとのカウントアップ数) do |変数| 処理 end
となります。
通常1ずつ上昇するカウントアップの値の指定することで小数点以下のカウントアップが可能です。
i = 1 5.0.step(5.5,0.1) do |num| puts "#{i}回目、数値は#{num}" i += 1 end # 結果 # 1回目、数値は5.0 # 2回目、数値は5.1 # 3回目、数値は5.2 # 4回目、数値は5.3 # 5回目、数値は5.4 # 6回目、数値は5.5
上記の処理は開始値を5.0として変数numに代入して出力。
1回繰り返すごとにブロック変数に0.1加算していき、5.5より大きくなったら終了という処理です。
次はloopメソッドです
こちらは一言で言ってしまうと
無限ループを作るメソッドです。
記述はとてもシンプルで
loop do 処理 end
これだけです。
ただこの状態だと処理が永遠に終わらないのでループを抜ける処理を記述する必要があります。
そこで使うのがbreak文というものです。
今は一番内側のループ処理を中断して抜けるために使用します。
では実際に使ってみましょう。
i = 0 loop do puts i i += 1 if i > 5 puts "条件を満たしたのでbreak実行" break end end puts "ループ処理終了" # 結果 # 0 # 1 # 2 # 3 # 4 # 5 # 条件を満たしたのでbreak実行 # ループ処理終了
上記のようにbreak文は強制的に処理を終了させます。
繰り返し処理ではたくさんの文やメソッドが出てきましたがそれぞれ性質が違うので
しっかりと性質を理解した上で使うようにしましょう。
では今回はこの辺りで。
Ruby(7) 構文を用いた繰り返し
今回は繰り返し処理、その中でも構文を用いた繰り返しについてです。
繰り返し処理とは指定した回数または、条件を満たすまで処理を継続し続けることです。
今回扱う繰り返し構文はwhile文、until文、for文の三種類です。
while文は条件式がtrueである限り繰り返しを継続します。
while 条件式 実行内容 end
上記が基本的なwhile文の作り方です。
実際に使ってみましょう。
num = 0 while num < 10 # numが10より小さい場合に処理を継続 num += 2 # numにnum + 2したものを再代入 puts num end puts "条件を満たさなくなるため(条件がfalseになるため)処理が終了" # 出力結果 # 2 # 4 # 6 # 8 # 10 # 条件を満たさなくなるため(条件がfalseになるため)処理が終了
条件がtrueの場合に処理を継続するので、
条件式にtrueを入れた場合は無限ループになります。
また、上記例の処理内容を num -= 2 とした場合も条件から外れることがなくなるので
無限ループになります。
コンソールで試して無限ループになってしまったら慌てずにcontrol + c で処理を強制終了しましょう。
次はuntil文です。
こちらも基本的な記述の仕方はwhile文と変わりません。
ただ、whileとは逆で条件がfalseの間処理を継続します。
実際に例を見てみましょう。
num = 0 until num > 10 # numが10より大きくない場合に処理を継続(比較演算子を変更) num += 2 # numにnum + 2したものを再代入 puts num end puts "条件を満たしたため(条件がtrueになるため)処理が終了" # 出力結果 # 2 # 4 # 6 # 8 # 10 # 12 # 条件を満たしたため(条件がtrueになるため)処理が終了
while文の例と変えたのは比較演算子と出力用の文字列だけです。
しかし数字の出力結果が異なっています。
これは条件を10より〜という記述にしている為です。
whileは10より小さい場合に継続、つまりは9以下なら継続ということです。
その為値が10になった時に条件を満たします。
一方untilでは10より大きくない場合としているので11以上にならない限り継続ということです。
その為10になった時点では11以上という条件式から外れるための条件を満たせないので
12まで出力されています。
両方の例でwhileとuntilの記述だけ入れ替えた場合はどうでしょうか?
そもそもループ脱出条件を既に満たしているのでループに入ることはありません。
では最後にfor文を。
for 変数 in オブジェクト 処理 end
上記がfor文の基本形となります。
オブジェクトから取り出したものを順番に変数に入れて処理をしていきます。
for num in 1..5 puts num end # 出力結果 # 1 # 2 # 3 # 4 # 5
1..5という記述は範囲オブジェクトというものです。
数字の1~5までをオブジェクト(一つのモノ)として扱いますよということです。
処理の流れとしては
1~5までの値を順番に変数であるnumに入れてputsメソッドで出力しています。
もっと具体的な使い方にしてみましょう。
ary = ["スギ","ヒノキ","イネ"] for allergies in ary puts "今年は#{allergies}の花粉がやばい" end # 出力結果 # 今年はスギの花粉がやばい # 今年はヒノキの花粉がやばい # 今年はイネの花粉がやばい
オブジェクトの中身を一つずつ変数に入れて、その変数に対して処理を行う
といった具合ですね。
似たような処理を行うものにeachメソッドというものがありますが、それはまた次の機会に。
Ruby (6) 条件分岐 case文,unless文
今回はcase文とunless文について学びましょう。
まずはcase文から!
case文は最初に対象となるオブジェクト(変数など)を指定して
その後にwhenの横に記述された値によって条件分岐します。
早速例を見ていきましょう。
num = 10 case num # numの比較対象として指定 when 1 # numが1の時に実行 when 2 # numが2の時に実行 when 3 # numが3の時に実行 when "ダー!" # numが文字列 ”ダー!” の時に実行 when 10 # numが10の時に実行 else # どの条件にも当てはまらない時に実行。
上記のようにif文よりもシンプルに記述することができます。
分岐が多くなる場合にはcase文が使えそうならこちらの方がすっきりしますね。
また、whenで複数の値に当てはまるときの記述をすることもできます。
name = チョコボール case name when "きのこの山", "たけのこの里", "すぎのこ村" # きのこの山、たけのこの里、すぎのこ村のいずれかに該当すれば実行 when "チョコボール", "大玉チョコボール" # チョコボール、大玉チョコボールのいずれかに該当すれば実行 else # どの条件も満たさない場合に実行
上記のように一気に比較できるようになりました。
便利ですねー。
ちなみにif文と同じように最初に当てはまった分岐が実行されるので、
同じ内容を条件に入れる場合には明確に条件を指定できるif文の方がいいです。
では次にunless文についてです。
こやつはif文とは逆で条件が偽(false)の時に処理を実行します。
例を見てみましょう。
num = 10 unless num = 10 # numが10ではない時に実行 else # numが10以外の時に実行
このようになります。
もし当てはまらない場合のみに実行したいといった場合には
if文で条件にノット演算子を使うよりも
unlessを使ってあげた方がスマートです。
では本日はこの辺りで。