結果だけでなく過程も見てください

たい焼きさんの日々の奮闘を綴る日記です。

サマータイム(夏時間)について勉強する

※整理しきれていないため、修正・加筆予定です。

サマータイム(夏時間、Daylight saving time)は、日本ではあまり馴染みがありませんが、欧米で採用されている仕組みです。

簡単に言うと、地域全体で時計をずらし、太陽が出ている時間帯を有効に使おうというものです。

この仕組み自体はコンピューターの仕組みというわけではなく、地域全体で時計をずらすため、その地域で動作するコンピューターでもその仕組みに合わせて時計を動かさなきゃね、というものになります。

ここにものすごくわかりやすい説明がありましたのでリンクを貼っておきます。
http://gakusyu.shizuoka-c.ed.jp/shakai/jisa/009%20sama-taimutte.htm

さらに詳細を知りたい方はWikipediaなんかを参照してください。

OSの夏時間の設定

Windowsでの夏時間の設定方法

コントロールパネルで「日付と時刻」→「タイム ゾーンの設定」と選択します。

日本に住んでいる人は、地域が「東京、大阪」などになると思いますが、ここを、サマータイムを採用している国に変更します。イギリスや、アメリカの特定に地域等ですね。

ここでは「(UTC+00:00) ダブリン、エジンバラリスボン、ロンドン」とします。
また「自動的に夏時間の調整をする」といった設定にはチェックを入れます。

Linuxでの夏時間の設定方法

環境変数TZを設定します。あとで書きます。

プログラム(C/C++)で夏時間を扱う

ここでは年月日や時刻(YYYYMMDD等)、人が通常使う表記のことをISO 8601形式と呼ぶことにします。

UNIX時間からISO 8601形式への変換

注意書きだらけですみません。

UNIX時間(UNIX時刻,POSIX時刻)というのは1970年1月1日午前0時0分0秒からの経過秒数です。
うるう秒は加味せず、8時59分59秒→8時59分60秒といった瞬間も+1されています。
現在時刻から、UNIX時間を算出してくれるWebシステムがありますが、
そのWebシステムが「現在時刻」をローカル時刻とみなすかどうかを意識してください。

例えば
https://url-c.com/tc/
こちらのサイトでは、現在時刻がローカル時刻になっています。

https://www.epochconverter.com/
こちらのサイトでは、現在時刻をGMTかLocal timeから選択できるようになっています。

ここを間違えると、日本の場合9時間分がズレてしまいますのでご注意ください。
夏時間がいつから開始(時計が一定時間スキップされます0:59:59→2:00:00)され、
終了(時計が一定時間同じ時間を繰り返します1:59:59→1:00:00)するかは、地域によって異なります。
2019年の「(UTC+00:00) ダブリン、エジンバラ、リスボン、ロンドン」では以下の通り。

開始:2019/03/31(日) 02:00 (OS上は03/31 0:59:59→1秒後 03/31 2:00:00)
終了:2019/10/27(日) 01:00 (OS上は10/27 1:59:59→1秒後 10/27 1:00:00)

このあたりから確認できます。
https://www.jisakeisan.com/summertime/london/

以下のようなソースコードで検証を行ってみます。
夏時間が有効な地域かどうかわからないため、夏時間フラグは手動で入力しています。

#include <stdio.h>
#include <stdlib.h>
#include <time.h>
#include <errno.h>

void settm(struct tm* ptm, int year, int mon, int day, int hour, int min, int sec, int isdst)
{
	ptm->tm_year = year - 1900;
	ptm->tm_mon = mon - 1;
	ptm->tm_mday = day;
	ptm->tm_hour = hour;
	ptm->tm_min = min;
	ptm->tm_sec = sec;
	ptm->tm_isdst = isdst;
}

int main()
{
    struct tm  tmp = {0};
    time_t     tt  = 0;

    // TODO:ここでtmpに年月日と時刻を入れます。夏時間が有効であればisdstに1、そうでなければ0を入れます。
    // 例 settm(&tmp, 2019, 12, 15, 3, 0, 0, 1);

    tt = mktime(&tmp);
    printf("%lld  %d/%d/%d %d:%d:%d\n", tt, tmp.tm_year + 1900, tmp.tm_mon + 1, tmp.tm_mday, tmp.tm_hour, tmp.tm_min, tmp.tm_sec);
}

自分が検証したかったのは、OSの「自動的に夏時間を調整する」の設定有無と、プログラム上のtm_isdstフラグの組み合わせで、サマータイム開始・終了時間帯を指定した場合どういう結果になるのか?ということです。

今回の入力は「2019/03/31 01:30(UNIX時間:1553995800)」です。
この2019/03/31 01:30は日本時間(ローカル時刻)ではなく、GMTであることを意識してください。
間違えると日本時間はGMTから+9時間のズレがあるので、その分UNIX時間もズレてしまいます。

結果。

# OSの夏時間設定 struct tmのtm_isdst mktimeの結果 mktimeの結果のISO 8601形式表記
なし 0 1553995800 2019/03/31 01:30:00
あり 0 1553995800 2019/03/31 02:30:00
なし 1 1553995800 2019/03/31 01:30:00
あり 1 1553992200 2019/03/31 00:30:00

で、なぜこの結果になるのかを考えてみました。

①のケース(OSの夏時間設定:なし tm_isdst:0)

夏時間に合わせて時刻を合わせないし、サマータイム影響中でもない。つまり渡された時刻をそのまま処理する。だから結果は3/31 1:30のままとなる。

②のケース(OSの夏時間設定:あり tm_isdst:0)

このケースは、OSは夏時間に合わせて時刻をずらす気まんまんだが、tm_isdstではサマータイム影響中でないことになっている。
そう言われたらOSはそれを信じるしかないので、純粋に3/31 1:30を処理しようとする。
しかし夏時間としては、3/31 1:30は存在しない時刻なので、夏時間の定義に従って2:30に補正する。
重要なのは見た目の時間が変わっているだけであって、通算秒は変わっていない点。

③のケース(OSの夏時間設定:なし tm_isdst:1)

3/31 1:30はサマータイム影響中と主張しているが、OSとしては夏時間に合わせて時刻をずらさないので、渡されたものをそのまま処理する。夏時間影響であれば本当は存在しない時間だが、OSは夏時間を認識してないので、そのまま表示できる。ということで3/31 1:30のまま処理をしている。

④のケース(OSの夏時間設定:あり tm_isdst:1)

このケースは時刻がすでにサマータイム影響下である。
OSは夏時間に合わせて時刻を調整しなければならないので、3/31 1:30は1時間進められた時間と認識するため、(ここの理解が曖昧です…)まず時間を1時間戻す。
戻した時間が本来の時間であり、ここは実際に1時間前の時刻としてみなされるので、実際にUNIX時間が1時間ずれる。
3/31 0:30は、夏時間としてはそのまま表示できる時間なので、そのまま出力されている。


ちなみに、2019/03/31 2:30(UNIX時間:1553999400)で、上記④のケースを適用してみると、結果はUNIX時間1553995800、ISO 8601形式では2019/03/31 02:30:00だった。
動作としては、まず03/31 2:30が渡される。これはサマータイム影響中であり本当の時間は1時間前である。だから1時間ずらす(3/31 1:30)。実際UNIX時間が戻されている。
3/31 1:30は夏時間としては存在しない時間であり、夏時間表示としては2:30になる。

ドラゴンクエストウォーク(DQW)の情報メモ

ドラゴンクエストウォークを始めました。
個人的に疑問に思ったことをどんどんメモしていきたいと思います(情報が分散してわかりづらいので…)

モンスターについて

モンスターの頭に出るビックリマークの数

モンスターの総合戦力を表しており、ビックリマークの数が多いほど強敵ということになります。

これは相対的な戦力を表しており、例えば全員LV30のパーティならビックリマーク1つの場合でも、転職してLV1のキャラクターがいるとビックリマークの数が3つになったりします。

キラキラ光っているモンスターは何?

倒すと宝箱を確定で落とします。

「かくてい」とふきだしがあるモンスターは何?

倒すと確定で「こころ」を落とします。
はぐれメタルなどのモンスターにも「かくてい」が出ることがあるようですが、逃げられると入手できないので注意です。

丸いマーク(こころ)のふきだしがあるモンスターは何?

倒すと高確率(約50%とのウワサ)で「こころ」を落とします。

範囲外に出現したモンスターと戦いたい

タップするとこちらに寄ってきてくれます

モンスターの強さはどうやって決まる?図鑑を埋めるときなど、弱いモンスターと戦いたいのだが。

現在進行中のクエストに依存するようです。
ですのでクリア済の昔のクエストを開始すれば、弱い敵と戦うことができます。

※つまりいつでも弱い(昔の)モンスターと戦うことはできるので、こころの所持上限などに到達してしまった方はばんばん弱いものから処分していって問題ないと思われます。

メガモンスターは離れていても戦える?

戦えません。
離れていると「近くへ移動してください」的なメッセージが出て、戦闘から離脱するか、近づいて再開するまで戦うことができなくなります。

戦闘から離脱すると、手形は無くなりますので注意してください。

目的地周辺のモンスターにメタル系のモンスターが現れた!今すぐ行けないんだけど、消えたりしないかな?

先日8時間程度放置しましたが、消えませんでした。
日付が変わったりするとどうなのかわかりませんが、短時間なら焦らなくて大丈夫みたいですよ!

4章10話のアームライオンが倒せない!

ラリホーがめっちゃ効きます!ずっと寝てましたw

ウォークモード

範囲内に敵がいるのに戦ってくれない
  • 移動していないと自動で戦ってくれません
  • 瀕死やピンチの状態だと戦ってくれません
範囲内に複数の敵や回復スポットがある場合の優先順位

優先順はないようです。つまりランダムということになります。
ちなみにウォークモード中でも目標物に対するタップは有効なので、優先的に回復スポットに触りたい等の場合はタップを活用すると良いでしょう。

マップについて

クリアした目的地周辺に、新たに「どこでも目的地」を置くことができないのだけど…クリア済の目的地が邪魔!

クリアしたクエストを、別の場所で再度クリアすればクリア済の目的地が移動するようです。
これ改善してほしいですねぇ…。

回復スポットをずらす方法

「どこでも目的地」機能で、回復スポットに被るように目的地を設定するとズレることがあるようです。
裏技の部類なので、修正される可能性があります。

よく行く目的地を記憶しておき、一発で目的地を設定する方法 (iPhone限定)
  1. 目的地を選ぶ画面で、右上の「登録リスト」アイコン→「外部マップへ」の順にタップ。
  2. マップから住所を入れたり、目的地を直接選んだりします。
  3. 画面下から出てきた画面から「共有」→「DQウォーク」を選ぶ。

これでドラクエウォーク内に位置が登録されます。10個まで登録できます。これは便利ですねぇ。

アイテム

アクセサリの入手方法
  • メガモンスター討伐時にランダムで入手(まだドロップしたことない…)
  • サブクエストクリア時の報酬
  • イベントの報酬

HP・MPの回復手段

  • 回復スポット(同じ箇所は30分程度に1回)
  • 自宅で休む (1時間に1回)
  • 各クエストの初回クリア時 (クリア済のクエストをもう一度クリアしても、回復しないようです)
  • スラミチにたのむ(HP/MP全回復。1日1回まで無料。以降は50ジェムかかります)
  • レベルアップ時
  • ドラクエウォークを一定時間操作しない(休憩)
  • 回復アイテム・呪文
ドラクエウォークを一定時間操作しない(休憩)

10分以上操作をしなかった場合だけ、回復します。
回復量は、10分なら最大HPMPの10%、30分なら30%といった具合でした。つまり100分操作しなければ全快するということですね。

それから注意点として、フィールド画面にしたままホームに戻るなどしてアプリから離れると、なぜか回復できない場合があります(休憩開始時間がちゃんと記録されてない予感)。じゅんび画面などに切り替えてからアプリを切り替えましょう!


全滅のペナルティ

特にありません。その場で全員HP1で復活します。
つまり、ウォークモードで放置してもデメリットはないということですね!

フレンドになるとどんな良いことがあるの?フレンドになる意味は?

おみやげをあげられる

東京タワーなどのランドマークを訪れるとお土産を入手できますが、それをフレンドに渡すことができます。フレンド同士連携しておみやげ図鑑を効率的に埋めることができるのですね。

フレンドごとに自宅の公開範囲を設定できる

特定のフレンドにだけ自宅の正確の位置を教え、あとの人はぼかして公開したりできます。
設定方法は以下の通り。

メニュー→その他・設定→設定→プライバシー→フレンドごとに設定

(※2019/09/16現在、ちゃんと反映されていない気がします…)

ゴールドパスを買ったら、スタンダードパスから勝手に切り替わるの?

いいえ。ゴールドパスに切り替わるのではなく、ゴールドパスとスタンダードパス同時にマイルが入るようになります

スタンダードパスを使い切ってからゴールドパスを買う…とかそういう面倒なことは考えなくて良さそう。

ドラクエウォークアプリを起動していなくても歩数カウントさせたい場合は?

ゲーム内の設定が必要です。
またiOSの場合、OSの設定も必要です。(Androidの場合不要…?)
バッテリー消費量が上がるかもしれません。ご注意を。

ゲーム内の設定

メニュー→その他・設定→設定→システム→いつでも歩数カウントを「ON」にします

iOSの場合は、OSの設定も必要!

「設定」アプリ→プライバシー→位置情報サービス→DQウォーク→常に許可

モンスターのこころ

ドラクエウォークはこころゲーと言われるほど、こころは重要な要素です。
武器防具はガチャでしか手に入らないためカネと運の要素が強いですが、こちらはコツコツと続ければ誰でもいつかは強いこころが手に入るという安心感がありますね。

色の意味

装備する色をそろえるとステータスにボーナスが付きます。
こころは3か所装備する部分があり、上はどんな色でもよいです。左と右は職業によって色が変わる。

戦士 黄色
僧侶
武闘家
魔法使い
盗賊
メガモンスターのこころ

倒すと確定でドロップします。

キャラクターの名前はどこから変えられる?

じゅんび→名前を変えたいキャラクターの顔をタップする→左上あたりにある、現在のキャラクター名表示の隣にある羽ペンアイコンをタップ

こころチャンス(こころかくてい、こころ高確率)の法則

自分の経験や集めた情報から記載していきます。

  • こころチャンスが出現している場所(スポット)は、全ユーザーで同じ
  • こころチャンスで出現するモンスターは、進行中のクエスト、またはパーティの平均レベルで決まる。どちらで決まるかは事前にはわからない(スポットによって決まっているのかな?)
  • こころチャンスの出現位置・モンスターは午前3時にリセットされる
  • 一度表示されたこころチャンスのモンスターはリセットまで変わらない!(ここ重要。目当てのモンスターが出るクエストを受注して移動した方がいいということ!
  • こころチャンス(高確率)の確率は約50%
  • こころチャンスのレア度(よくみかける、めったにみかけない等)は全スポットで共通。ツイッターなどを使って「めったにみかけない」巡りをすることも可能ですね!
  • パーティの平均レベルで出現モンスターが変わるようなので、ツイッターの情報は、投稿者のレベルも確認すること。いざ現地に行ったら違うモンスターがいるなんて可能性もあるので…。

一度表示されたモンスターはリセットまで24時間変わらないので(途中でレベルアップしたら変わるのかも?)、
午前3時になる前にクエストを受注して寝た方がいいですね!
朝起きてからクエスト受ければいいや~とか考えていると、自分の家の周辺のこころチャンスのモンスターが確定してしまう可能性があるのです…。

パーティの平均レベルで出現するモンスターが変わるこころチャンススポットのレベル帯

ちょっとこれは正確な調査をしたわけではありません。
なんとなく、各クエストの推奨レベル帯にいるレアリティのモンスターが出現すると感じているので、整理したいと思います。
あと自分の経験上のデータがあれば、それも反映しますね。
推奨レベルの隙間など、間違いがあるかもしれませんので、ご注意ください。

モンスター名 レアリティ PT平均レベル帯 エスト帯 備考
キングスライム あまり見かけない 48~55 5-9~5-10
ヒイラギどうじ あまり見かけない 43~47 5-5~5-8
ボーンナイト あまり見かけない 40~42 4-10~5-4
ベビル あまり見かけない 35~39 4-7~4-9
よろいのきし あまり見かけない 31~35 4-1~4-7
キラーマシン めったに見かけない 48~55 5-9~5-10
ホークブリザード めったに見かけない 43~47 5-5~5-8
あくま神官 めったに見かけない 38~42 4-9~5-4
ホークマン めったに見かけない 33~37 4-5~4-8
はぐれメタル めったに見かけない 31~48 4-1~5-9

■あまり見かけない(パーティ平均レベル帯)

f:id:taiyakisun:20191026035723p:plain

■めったに見かけない(パーティ平均レベル帯)

f:id:taiyakisun:20191026035806p:plain

■あまり見かけない(クエスト帯)

f:id:taiyakisun:20191026040918p:plain

■めったに見かけない(クエスト帯)

f:id:taiyakisun:20191026041118p:plain

こころのドロップ率
項目 おおよその確率
こころ自体のドロップ率 4%
Sのドロップ率 3%
Aのドロップ率 7%
Bのドロップ率 15%
Cのドロップ率 35%
Dのドロップ率 45%

レアリティ別モンスター出現率

最初に断っておきますが、おそらくクエストによって(モンスターによって?)、同じレアリティでも出現率が違います。
今回はクエスト5-8で超適当に実測したものを共有しておきます(気が向いたら更新します)。

■クエスト5-8

レアリティ 出現率(%) 出現モンスター
とてもよく見かける 297 80.054% ベホイミスライムとかパペットマンとかいろいろ
よく見かける 37 9.973% ミニデーモン, キラーパンサー
ときどき見かける 27 7.278% ドラゴスライム, つむりんママ(雨/水辺限定)
あまり見かけない 6 1.617% ヒイラギどうじ
めったに見かけない 4 1.078% はぐれメタル, ホークブリザード

ときどき見かけるの確率が思ったより高かったです。そのほかは予想通りですね~。
4-9でひとつめピエロを狙ったときはぜんっぜんでないイメージだったので意外です。
4-9はメタルライダーハートナイト(関東限定)がいるので、ときどき自体の確率はこの通りでも、
そのうちのモンスター一点狙いだと当然確率は下がってしまうので、出ないと感じていたのかもしれません。
4-9も出現率調査したいっす。

■参考情報
においぶくろ1個で37体くらいのモンスターを倒すことができました。
レベル上げパーティなので盗LV48 僧LV44 魔LV31 魔LV30です。ガチパーティならもっと速くなりそうですね。

倒したモンスター数 単位時間
37体 /5分
7.4体 /1分

ということになります。
ここからどれだけ時間をかければモンスターにどれだけ会うことができて、こころドロップまでにかかる時間(期待値)も出せそうですね。

例えば、ヒイラギどうじの場合、1分間に1体以上出会える確率はだいたい11%程度(1-(0.984^7))。
こころドロップ率が4%なので、1分間にヒイラギどうじのこころを1つ以上入手できる確率は0.44%。
で、例えば80%の確率でヒイラギどうじのこころを入手したければ1-0.9956^366=0.199978...ということで366分このペースでモンスターを倒し続ければ、10人に8人はヒイラギどうじのこころが最低1つは手に入るということですね!
うーん、あってますかね?この計算…確率苦手です。これは…確定スポット巡りますわ…!

ケース かかる時間 備考
80%の確率で最低1つ以上こころ入手 366分 1-0.9956^366
90%の確率で最低1つ以上こころ入手 523分 1-0.9956^523
95%の確率で最低1つ以上こころ入手 680分 1-0.9956^680
99%の確率で最低1つ以上こころ入手 1047分 1-0.9956^1047

各スポットの復活時間

自宅で休める間隔 1時間
回復スポット たぶん15分程度
他人の家のアイテム たぶん24時間程度

経験値(EXP)テーブル

わかったところ(実経験)から記載します。それぞれだいたいの数値ですよ~。
LV21~27はメモし忘れました…LV39も怪しいです…_(´ཀ`」 ∠)_
ウワサには聞いてましたが、LV50から経験値がハネ上がりますね…LV51が55までの折り返しと聞いたこともあります…。

このLVになるまで 必要な経験値 累計
1から11まで 6,000 6,000
12 2,600
13 3,600
14 4,900
15 6,400
16 8,400
17 10,600
18 13,700
19 16,700
20 19,700
21 23,300
22 27,229 144,276
23 31,674 175,950
24 36,570 212,520
25
26 47,824 303,153
27 54,540 356,829
28 61,861 418,690
29 69,822
30 78,459
31 88,198
32 98,738
33 110,123
34 122,000
35 135,500
36 150,861
37 166,718
38 183,000
39 202,000
40 222,153
41 243,755
42 266,857 2,558,591
43 291,535 2,850,126
44 318,675 3,168,801
45 347,641 3,516,442
46 378,530 3,894,972
47 412,543 4,307,515
48 447,454 4,754,969
49 485,797 5,240,766
50 526,592 5,767,358
51 845,922 6,613,280
52 1,265,137 7,877,316
53 1,811,064 9,688,380
54 2,519,375 12,207,755
55 3,441,626 15,649,381

リセット時間

ログインボーナス・スラミチの無料全回復・一日一回のサブクエス

夜中の午前3:00です。

とうばつ手形

こちらは午後3:00だそうです!

バグ?(不具合)

止まっているのに、「移動速度が速いためプレイを制限しています。」「あなたは運転者ではありませんか?」と聞かれる。

自分もスマホの位置を取得するアプリを使ったことがありますが、けっこうずれます。
特に位置計測直後はむちゃくちゃずれるので、このせいで表示されている可能性があります。
実害はない(し、けっこうどうしようもない側面もある)ので、対応優先度は低そうです。

戦闘終了後にフリーズする

発生条件がよくわかりませんが、けっこう固まります…。
タップしても無反応。いくらまっても動きません。アプリをKILLして対応しましょ。

要望メモ

個人的に要望が出せれば出そうと思っていることをメモしておきます。

  • モンスター図鑑の報酬で、いちいちモンスターを選ばせるのはやめてほしい。けっこうストレスです。
  • ほぼまんたん(ドラクエ11であったやつ)がほしい
  • ウォークモード時、一戦ごとにほぼまんたんする仕掛けがほしい
  • まんたんはメイン画面(マップ画面)からワンタップで使えるようにしてほしい。「まんたんにしました」のような確認メッセージも不要。
  • AIの強化もしくは、AIが使っていいスキルをユーザーが選べるようにしてほしい。
  • 転職の演出が長い。カットしてほしい。
  • というか、歩きながらやるゲームなのに、数秒操作できない演出(クエストクリアや冒険者ランクアップ)が多すぎる。表示しないオプションが欲しい。
  • クリア済の目的地周辺に「どこでも目的地」が置けない問題。仕様だとしても不便すぎます。
  • こころや図鑑などのページのスワイプの感度がおかしい。どうやらモンスターの絵の部分を触ってスワイプすると正常に動作するけど、モンスターとモンスターの間などを触るとスクロールしないみたい。なんでこんなことに???携帯2台で確認済。
  • スキルの位置を移動させてほしい。特にスキルが2ページ目になると戦闘中、いちいちページ移動→スキル選択しなければならず、ストレスです。
  • フィールド画面のままアプリを切り替えたりすると、その後ドラクエウォークに戻っても正しく休憩時間とカウントされずHPMPが回復しないときがある。(朝起きてアプリを起動したら、MPがほぼ0のままなんてこともありました)
  • クリア済みの目的地が邪魔で敵をタップできない。レアモンスターが出た時とかほんと〜〜〜〜に腹が立ちます。携帯投げつけて割りそう。なんとかしてほしいです。

ノートンアンチウィルス(Norton Antivirus)でスケジュール実行されたスキャンのキャンセル方法

マニュアル読んだけどわかりませんでしたーッ!ということで備忘録としてメモしておきます。
ノートン アンチウィルスのバージョンは22.18.0.213です。

バージョンはメインウィンドウ→[ヘルプ]→[バージョン情報]から確認できます。

キャンセル手順

  1. ノートンアンチウィルスのメインウィンドウから[セキュリティ]→[スキャン]を選びます
  2. [スキャンとタスク]の項目から[カスタムスキャン]ラジオボタンを選択し、[実行する]ボタンを押します
  3. スキャンウィンドウで実行中のスキャン名(例:システムの完全スキャン)の横にある「X」チェックマークを外します。
  4. チェックを外した行の[実行する]ボタンを押すと、スキャンが開始するのですぐにキャンセルします

現在進行中のスキャンを確認するのにスキャンを実行しなきゃいけないなんて気づかないよッ!
あれやこれやと探して無駄な時間を過ごしてしまいました。。。

Minecraft(マインクラフト)のクリエイティブモードで建築を始める前に、最低限覚えておいた方がいい知識

いまさらですがSwitch版のマイクラをちょこちょこ触ってます。
先日クリエイティブモードを遊んでみましたが、色々と前提知識がなく四苦八苦したので、
最低限まぁこれは知っといたほうがいいか、と思った知識をメモしておきます。個人的な備忘録です

エディションの整理

エディション 2019/8/13時点での最新バージョン 説明
Java 1.14.4 PC版。一番何でもできるエディションで、Modは使用可だが、クロスプラットフォームでのマルチプレイ不可
統合版(BE(Bedrock)版) 1.12.0 PC版(こちらはWindows 10版という名前がついている)、XBox One版、Switch版、スマホタブレット版はすべてこれ。一部は昔ポケットエディション(PE版)という名前だった。Mod不可だがクロスプラットフォームでプレイ可能
PS4 1.90 BE版が先にアップデートされてから、後を追ってアップデートされるサイクルになっている。クロスプラットフォームでのプレイ不可
XBox 360番・Wii U版・PS3版・PS Vita版 ? PS4版と同じアップデート方式。ただ現在はアップデート終了している?クロスプラットフォームでのプレイ不可

※PCでプレイできるマイクラには、Java版とWindows 10版の二種類があります。

まぁ普通に考えて、Java版か統合版(BE版)のどちらかを選ぶことになると思います!
マルチプラットフォームで遊ぶなら統合版(BE版)一択かと思います。

前提とか注意点

  • 当方SwitchなのでBE版を使用しています。2019/8/13現在、バージョンは1.12.0でした。
  • fillコマンドやsetblockコマンドはやり直し(Ctrl+zのような機能)がない。つまり一度fillコマンドでブロックが配置されてしまったら、上書きした既存のブロック等は元に戻せないので注意が必要。

用語

用語 意味
コマンドブロック 起動すると、任意のコマンドを実行することができるブロック。giveコマンドでアイテム名を「command_block」とすることで入手可。(コマンド実行例:/give @s command_block 2)
NBT Named Binary Tagの略。コマンドブロック等は任意のコマンドを設定できるが、これを記憶しておく領域というかフォーマットがNBTである。中身は拡張されたXML?マイクラオリジナルのフォーマットらしい。

細かい知識

  • 座標系は右手座標系であり、相対座標によるコマンドを使用する場合は向きを気にする必要があるかもしれない?
  • fillコマンド等で同時に処理できるブロック数は32,768個(2^15)である

Java版で出来て、BE版で出来ないこと

  • giveコマンドで、Java版のNBTは使用できない→コマンドブロック生成時にBlockEntityTagを指定できない→コマンドブロックの配置でまとめて複数のブロックを配置したりできない

設定

  • 「座標を表示」をONにしましょう
  • 「チートの実行」をONにしましょう
  • 「コマンドブロックが有効」をONにしましょう
  • 純粋に建築だけが目的なら「常に昼間」「モブの出現」「モブによる妨害」をOFFにしましょう
  • マルチプレイで全員にコマンドを実行できる権限を持たせるなら、「招待から参加した場合のプレイヤー権限」を「オペレーター」にしましょう

飛行(浮遊)モード

ジャンプボタン(Switch版ならAボタン)を素早く二回押すことで、飛行モードと通常モードが交互に切り替わる。空中で通常モードに切り替えると落下するので注意。

飛行モード中は、ジャンプボタンで上(+y方向)へ移動し、しゃがみボタン(Switch版ならBボタン)で下(-y方向)へ移動する。

整地方法

何はともあれまずはコレ。ここから整地したいな~と思った座標を決めます。
ここでは例として(10, 10, 20)に決め、100x100を同じブロックで整地します。(座標は(x座標, y座標, z座標)と記載しています)

/fill 10 10 20 110 10 120 concrete
/fill 10 11 20 110 13 120 air
/fill 10 14 20 110 16 120 air
/fill 10 17 20 110 19 120 air

2行目以降は、整地した範囲の上(+y座標方向、空の方向)のブロックを排除するために実行してます。
必要に応じて実行してください。fillコマンドで同時に処理できるブロック数が32,768個のため複数回実行してます。

ぼやき

  • こりゃキーボード必須ですね…。なんとSwitch版はbluetoothキーボードが使用できないという…クソクソクソ(>_<)
  • イクラ、遊んでいて大変面白いのですが、普段からプログラムを組んでいると、直感的にやりたいことができなくてかなりストレスが溜まりますね〜。純粋に強化版レゴのソフトウェア版!と割り切った方がよさそうです。

RPGツクールMVで効果音(SE)が鳴っているかどうかの判定および特定の効果音だけを停止する方法 他

RPGツクールMVいじり二日目です。昨日の記事の続きです。
結論から言うと、効果音(SE)が鳴っているかどうかの判定はできませんでしたが、
やりたいこと(効果音を多重で再生せずループさせる)はできました。

RPGツクールMVの内情はちんぷんかんぷんなので、誤りや慣習などはご教示いただければと思います。

効果音(SE)が鳴っているかどうかの判定

冒頭でも言った通り、うまく動作しなかったのですが、経緯だけご紹介します。

まずrpg_managers.jsのファイルの先頭あたりに以下の一文を追加しておきます。

const path = require('path');

rpg_managers.jsに以下のメソッドを追加します。

AudioManager.isSEPlaying = function(sename) {
  if (sename)
  {
    var seBuffers = this._seBuffers.filter( 
                        function(audio)
                        {
                            var audioname = path.basename(audio.url, path.extname(audio.url));
                            return ((audioname === sename) && audio.isPlaying())
                        });

    return (seBuffers.length != 0)
  }
  else
  {
    return false
  }
};

そのまんまなのですが、SE名が一致し、かつ再生中のエントリを
管理配列であるthis._seBuffersから検索して取得しています。
1つでも見つかれば再生中、そうでなければ停止中と判定しています。

あまりわかっていませんが実機検証の結果、効果音(SE)再生直後などは、実際には再生が開始されていてもこの結果がfalseになることがあるみたいで、再生し始めのときに不当にfalseが数回返る→数回分は効果音が被って再生されてしまう…という結果になってしまいました。これを回避する方法は、サウンドバッファのシーク位置とかを見ればいけそうな気がしますがめんどくさくて見つからなかったということにしてます。それよりも、後述する方法を使えばもっとシンプルにやりたいことが実現できそうでした。

効果音(SE)を二重以上で被らずに再生させる方法

単純に、WebAudioオブジェクトのplay系関数の変数にtrueを渡すだけでうまくいきそうな気がしました。

rpg_managers.jsに以下の内容を追加します。

AudioManager.playSeLoop = function(se) {
    if (se.name) {
        this._seBuffers = this._seBuffers.filter(function(audio) {
            return audio.isPlaying();
        });
        var buffer = this.createBuffer('se', se.name);
        this.updateSeParameters(buffer, se);
        buffer.play(true);
        this._seBuffers.push(buffer);
    }
};

なんてことはない。通常のplaySeと比べplayに渡す引数をfalse→trueと変更しているだけです。
これにより効果音の被りを気にする必要はなくなりました。

または、コアスクリプトの関数を書き換えてもいいのであれば、以下のようにplaySeメソッドの
第二引数でループするかどうかを指定できるようにし、
引数なし(つまり既存でコールされている部分)についてはデフォルト引数で
必ずループさせない(既存と同じ動作)ようにさせても良いです。
個人的にはこちらの方法を推奨します。似たような関数を2つ作成したくはないので。

// 既存のplaySeメソッドに第二引数を追加
AudioManager.playSe = function(se, bLoop=false) {
    if (se.name) {
        this._seBuffers = this._seBuffers.filter(function(audio) {
            return audio.isPlaying();
        });
        var buffer = this.createBuffer('se', se.name);
        this.updateSeParameters(buffer, se);
        buffer.play(bLoop);
        this._seBuffers.push(buffer);
    }
};

もともとやりたいことはSE再生中は、再度同じSEを鳴らさないということで、それを実現する
ためにSEの再生時間分だけフレームをカウントしていました。
つまりループ再生ができれば上述した課題は自動的に解決され、フレームをカウントする必要がなくなります。
# 勢いで書いたエントリなのでもうちょっと検証しますが。

特定の効果音(SE)だけ停止する方法

先日のエントリだと、プレイヤーが停止したらすべての効果音を停止させる動きをしていましたが、
関係ないSEも止めちゃうってそりゃないでしょということで、足跡の効果音だけを停止させることにします。

rpg_managers.jsに以下の関数を追加します。

AudioManager.stopPlayedSE = function(sename)
{
    if (sename)
    {
        for ( var i = 0; i < this._seBuffers.length; ++i )
        {
            var file = path.basename(this._seBuffers[i].url, path.extname(this._seBuffers[i].url))
            if ( file == sename )
            {
                this._seBuffers[i].stop()       // 止めるべきSEを発見した
                this._seBuffers.splice( i, 1 )  // 止めた要素は削除してしまう
                break
            }
        }
    }
}

filterを使うことなども考えましたが、とりあえず線形検索して最初に見つかった要素を
対象にして効果音の停止および管理配列からの削除をさせることにしました。
どうやらこの配列、再生中の効果音(SE)が入るようで、効果音はそこまで多重で再生しない=配列サイズも
そんなに多くはならない=線形探索しても性能への影響はない、と考えています。
# これもちょっと検証が必要な気がしますけど。

昨日の記事は上記の内容を更新しておきます。

RPGツクールMVでプレイヤーが移動しているときだけ足音を鳴らす方法

ワケあってRPGツクールMVを触ることになりました。
RPGツクールに触った機会と言えば・・・

あぁ年がバレるぅ~~~。友達とワイワイ作ったりプレイしたり、楽しかったなぁ……とノスタルジーに浸るのは置いといて。

初日ということで、とりあえずプレイヤーが移動したときに足音を鳴らす機能を実装してみました。後々必要になりそうだったので。
ネット軽く調べてみたところ、歩数やキーの押下状況で音の再生/停止をコントロールする方法を見つけましたが、
以下の観点から別の方法でコントロールすることにしました。

  • 再生時間の長いSEでも自然に聞こえるようにしたい (歩数コントロールだと、場合によって音がかぶりそう(たぶんね))
  • マウスクリック、スマホのタップでも正常にSEを鳴らしたい (←だと方向キーは押してない状態になるので、判定条件に方向キーの押下状況を使いたくない)

なお当方RPGツクールの慣習などをほとんど知りませんので、誤り等ありましたら教えてくださいね~。

前書き

  • 本機能で使用する変数は101~104番の4つを使用しています。
  • RPGツクールMVの仕様で1つのスクリプトに書ける行数が12行なので横長になってます。読みづらくてごめんなさい。
  • 突貫で作成していますので、なんかまだ怪しい挙動をすることがあります…ご承知おきください。

考え方

  • プレイヤーの移動を検知したとき、SE再生中フラグがすでにONなら何もしない。SE再生中フラグがOFFなら、SEをループで鳴らし、SE再生中フラグをONにする。
  • プレイヤーが移動をやめたらSEを停止し、SE再生中フラグをOFFにする。

実装

自作メソッドをrpg_managers.jsに追加します。
効果音ごとに再生を停止するメソッドと、効果音をループ再生させるメソッドです。
rpg_managers.jsの先頭に以下を追加。

const path = require('path');

また以下をrpg_managers.jsの任意の位置に追加。

AudioManager.stopPlayedSE = function(sename)
{
    if (sename)
    {
        for ( var i = 0; i < this._seBuffers.length; ++i )
        {
            var file = path.basename(this._seBuffers[i].url, path.extname(this._seBuffers[i].url))
            if ( file === sename )
            {
                this._seBuffers[i].stop()       // 止めるべきSEを発見した
                this._seBuffers.splice( i, 1 )  // 止めた要素は削除してしまう
                break
            }
        }
    }
}

次に、コアスクリプトの関数を書き換えてしまっていいのかわかりませんが、
AudioManager.playSeメソッドを改造します。
以下のように第二引数でループするかどうかを指定できるようにし、
引数なし(つまり既存でコールされている部分)についてはデフォルト引数で
必ずループさせない(既存と同じ動作)ようにさせます。

// 既存のplaySeメソッドに第二引数を追加
AudioManager.playSe = function(se, bLoop=false) {
    if (se.name) {
        this._seBuffers = this._seBuffers.filter(function(audio) {
            return audio.isPlaying();
        });
        var buffer = this.createBuffer('se', se.name);
        this.updateSeParameters(buffer, se);
        buffer.play(bLoop);
        this._seBuffers.push(buffer);
    }
};

次にプレイヤーが移動しているかどうかを判定するコモンイベントを1つ作成します。

const PREV_MOVING=101, CUR_MOVING=102, STOP_COUNTER=104
{
    if ( this.character(-1).isMoving() ){ 
      $gameVariables.setValue( CUR_MOVING, 1 )     // プレイヤーが移動中かどうかのフラグは「移動中」
      $gameVariables.setValue( STOP_COUNTER, 0 )   // isMoving()連続false(停止)回数は0にリセット
    } else {
      // isMoving()が一定回数連続でfalse(停止)にならない限り「停止中」とは判定せず、前回の結果をそのまま使う。
      $gameVariables.setValue( CUR_MOVING, ($gameVariables.value(STOP_COUNTER) <= 2) ? $gameVariables.value(PREV_MOVING) : 0 )
      $gameVariables.setValue( STOP_COUNTER, $gameVariables.value(STOP_COUNTER) + 1 )  // isMoving()連続false(停止)回数を+1
    }
    $gameVariables.setValue( PREV_MOVING, $gameVariables.value(CUR_MOVING) )    // 次回向け、前回の移動中フラグを保存する
}

プレイヤーが移動しているかどうかは「this.character(-1).isMoving()」で判定できるのですが、
これをそのまま使うと思った通りに動作しません。

方向キーを押しっぱなしにしていても、グリッドとグリッドの間で一瞬停止期間があるようで、
そのまま実装すると、プレイヤーはずっと移動しているのに、上述した停止期間にひっかかって足跡のSEが所々で
停止してしまうのです。そのため、ここでは連続してisMoving()がfalse(プレイヤーの移動停止)を返してきたときに、
はじめて本当にプレイヤーの動作が停止したと判定することにします。
ここでは連続して3回isMoving()がfalseを返したら停止と判断しています。

次に、足音を鳴らしたいマップにイベントを作成し、トリガーを「並列処理」にします。
イベントの実行内容の1つ目は、↑で作成したコモンイベントを呼び出します。

実行内容の2つ目で、スクリプトを実行します。
なお以下の項目については、ご自分の環境に合わせて変更してください。

  • playSeLoopメソッドおよびstopPlayedSEメソッドに渡す変数。SE名(ファイルの拡張子を除いたもの)、ボリューム、ピッチ、パン。
const CUR_MOVING=102, SE_PLAYED=103, $bPlayerMoving = $gameVariables.value(CUR_MOVING)
{
  if ( $bPlayerMoving ) {
    if ( $gameVariables.value(SE_PLAYED) != 1 ){
      AudioManager.playSe({"name":"stepsound","volume":100,"pitch":100,"pan":0}, true)
      $gameVariables.setValue( SE_PLAYED, 1 )
    }
  } else {
    AudioManager.stopPlayedSE("stepsound"); $gameVariables.setValue( SE_PLAYED, 0 )
  }
  this.wait(1)
}

効果音は停止までループして再生させています。
this.wait(1)はノーウェイトだと重そうなのと、1FPSに一度処理する、とタイミングが決まっていた方が
何かと都合が良いと思ったためです。RPGツクールの常識、よくわかんねぇ。
実装は以上です。

今後は以下を考えてます。

  • 足元のマップチップの種別やリージョンID?とやらで判定する

ところで

RPGツクールってRubyガリガリ書けるようになったと聞きましたが、また元に戻ったんですかね?
マルチデバイス対応でHTML5 + JavaScriptで動作しているというのは納得なのですが。
できれば全部スクリプトで組ませて欲しいですねぇ。
せめて1つのスクリプトの命令で今の100倍くらいは行数を書けるようにして欲しいっす。

2019/07/24追記
と思ったらこんなプラグインを作成しておられる方がいらっしゃるではありませんか!
ありがとうございます。使わせていただいてます。

翠さんのエディタ内で12行以上のスクリプトを書けるプラグイン +エラー時に該当箇所を標準出力する機能を追加しました - ツクマテ

はてなブログ(無料版)にnend(クリック報酬型アド)の広告を表示する方法

はじめに

はてなブログの場合、仕組み上Google AdSenseの審査が通らず、別の広告を探す必要があります。
そこで自分が目を付けたのが「nend」です。
はてなブログの無料版でも広告を貼り付けることができますよ。

特徴

まずはnendにアカウントを登録

以下のURLにアクセスします。
2019/07/05現在のレイアウトとなりますが「広告主様」→「会員登録」と進んで、[メディアパートナーご登録]画面から必要な情報を登録しましょう!
nend.net

ここで入力した登録メールアドレスに仮登録の通知が来ますので、メールに記載されているURLをクリックして登録を完了させます。
すると審査(本登録)が開始されるのでしばらく待ちましょう。1日くらいで審査(本登録)を通過するはずです。

広告枠を作成する

nendでは、広告を貼り付ける場所ごとに広告枠を作成する必要があります。

nendにログインして[広告枠の管理]→[新規サイト/アプリの作成]と進み、
ご自分の運用されているサイト名やURL、サイトの紹介なんかを入力してください。
作成すると、これまた審査に入りますが、これは早ければ数分で完了します。

まずはテスト用のバナー広告を貼り付けてみよう!

↑で広告枠の審査がおりるまで、こちらを進めておきましょう。
この工程を完了させておけば、後にテスト用広告コードを本番用広告コードに書き換えるだけで、本番の広告を表示することができます。

最初に、はてなブログの管理画面から「デザイン」に移動します。
f:id:taiyakisun:20190705234435j:plain

続いて、「工具」アイコンをクリックします。
今回はタイトルと記事の間に広告を載せることにしますので、「記事上」をクリックします。
f:id:taiyakisun:20190705231347j:plain

テスト用広告コードを貼り付けます。コードは以下のサイトに記載されてます。
スマートフォン広告なら日本最大級のnend(スマホweb広告/アプリ広告/インフィード広告・ネイティブ広告/インタースティシャル広告対応)

2019/07/05時点ですが、サイズ320x50バナーの広告コードは以下です。
現在はコードが変わっている可能性もありますので、うまく広告が表示されない場合は、↑のサイトにアクセスして最新のコードをコピペしてみてくださいね!

<script type="text/javascript">
var nend_params = {"media":82,"site":58536,"spot":127513,"type":1,"oriented":1};
</script>
<script type="text/javascript" src="https://js1.nend.net/js/nendAdLoader.js"></script>


nendの広告はスマホ専用なので、スマホの設定も必要です。
スマホ」アイコンをクリックして[PCと同じHTMLを表示する]にチェックをつけておきます。
f:id:taiyakisun:20190705234604j:plain

スマホからWebページにアクセスして広告が表示されるか確認する

うまく表示されない場合はブラウザを変えて試してみてください。
自分はSafariではうまく表示されず、Chromeなら表示されました。
(たぶんSafariには広告ブロックアプリを入れているからだと思いますが~)

成功していれば赤枠の部分が表示されます。(青枠はもともと(無料版だから?)表示されている広告です)
f:id:taiyakisun:20190705232454j:plain

本番用広告コードに変更する

nendの[広告枠の管理]から作成した広告ユニットのステータスが「アクティブ」になっていることを確認したあと、「広告枠」をクリックします。
アクティブになっていなかったらまだ審査がおりていないので、しばらく待ちましょうね!
f:id:taiyakisun:20190705232820j:plain

その後コードが2つ表示されると思いますが、「広告コード」の方のコードをコピーし、↑でペーストしたテスト用のバナー広告のコードと差し替えてください。

あとはスマホから本番用の広告が表示されているかを確認してみてください。

プライバシーポリシー お問い合わせ