2021年1月22日金曜日

VirtualBox で Android x86 を動かすと黒画で止まってしまう!


こんにちは。よっしーです。

VirtualBoxでAndroidを動かす時にハマってしまったので、

トラブル解決した手順を記載したいと思います。


VirtualBoxにAndroidをインストールする手順については

検索するといっぱい出てきますので割愛します。


実際にAndroidをインストールして起動すると、私の環境だと

黒画になり、ここから何も進まなくなります。


で、この症状は使ってるパソコンのグラフィック系の環境に依存するようです。

黒画にならず、普通に動作するのがほとんどのようですが、私のPC環境がハズレだったようです。。。


で、対処方法ですが、起動パラメータを変更する必要があります。

起動時にbootメニューが出ますが、この時に 'e' を押してください。


で、起動パラメータが表示された画面にくるので、ここでもさらに 'e' を押します。


起動パラメータの編集が可能になります。


一番右までカーソルを移動し「nomodeset i915.modeset=0」を追加します。


パラメータの詳細は以下サイトなど、具体的な解説があります。

https://wiki.archlinux.jp/index.php/Kernel_Mode_Setting


私が使用しているPCのグラフィックチップはIntel内蔵だったので、

i915.modeset=0 を追加しています。


i915.modeset=0 のパラメータはなくても起動はするものの、

ありとなしだと動作のスムーズさが違うように思いました。


起動パラメータを追加した後、'Enter' を押すと元画面に戻り、

続けて 'b' を押すと無事に起動することが出来ました。


Google の Playストア も使えますし、そこからアプリをインストールすることもできます。


Playストア からインストールしたアプリも使えます。(動かないものはいくつかありますが。。。)

youtube だって見れますよ。


Androidアプリを開発している人で、エミュレーター等の動きが重たく

困っている。という人もいるかと思います。

仮想環境だとそれなりにスムーズに動作するので、こういった環境を利用してみるのも

いいかもしれませんよ。


ではまた~。

2021年1月17日日曜日

cron 設定ファイルでの起動に失敗

こんにちは。ひっくです。

Linuxで定期的に処理をする機能をcronで実行しようとした際
cronの設定ミスでエラーが発生して少し時間がかかってしまいました。
結果としてそんなこと?というレベルの内容でしたが、備忘録として残しておきます。

前提条件


 ・/etc/cron.d/ ディレクトリ内に設定ファイルを配置して定期起動を行う

cron設定ファイルの記載内容



cron.dディレクトリ下に配置する設定ファイルについて、 書式は「/etc/crontab」ファイルと同じ設定方法となります。
// 分 時 日 月 曜日 ユーザー コマンド
10 0 * * * root sh XXXX.sh // (毎日0:10にXXXX.shを起動)
この設定ファイルをcron.dディレクトリ下に配置の上、シェルファイルの
実行を待っていたのですが、実行されず・・・。

「var/log/cron」のログも確認してみたものの、何も出力されていないので
そもそもcronでの起動自体ができていないようでした。

対処法



問題は設定ファイルの書き方にありました。
以下に変更するとうまくいきました。

変更前
// 分 時 日 月 曜日 ユーザー コマンド
10 0 * * * root sh XXXX.sh // (毎日0:10にXXXX.shを起動)

変更後
// 分 時 日 月 曜日 ユーザー コマンド
10 0 * * * root sh XXXX.sh // (毎日0:10にXXXX.shを起動)

// ↑ここに改行を挿入
改行を挿入しないと実行されないんですね。。
「/etc/crontab」ファイルも後からよくよく見てみると、改行の記載がありました。

新しくcron起動用の設定ファイルを作成する場合に
実行されないことがあれば、この辺りも再確認してみた方が良いですね。

今回は問題ありませんでしたが、ファイルパーミッション関連も起動しない原因に
なることがあるようです。

今回はこのへんで。ではまた!

2021年1月11日月曜日

Blazor向けUIコンポーネントMatBlazorでマテリアルデザイン

どうも、もりもりです。

前回は .NETでSPA(SinglePageApplication)を実現できるWebフレームワークの BlazorWebAssemblyでTodo画面を作成しました。 今回はMatBlazorを使って、そのTodo画面をマテリアルデザインにしてみました。

MatBlazor使ったらどうなるの?

こんな感じの画面が

こんな感じの画面になっちゃいます。

ソースコードは下記に置いてます。

前準備

まずは前準備としてMatBlazorのパッケージを追加し、使用できるように設定していきます。

◆ パッケージの追加

下記のコマンドでパッケージを追加します。念のためcsprojに追加されていることを確認しておきましょう。

$ dotnet add package MatBlazor
◆ _imports.razorを編集

下記を追加します。

_imports.razor

@using MatBlazor
◆ wwwroot/index.htmlを編集

下記を追加します。

index.html

<body>
    <div id="app">Loading...</div>

    <div id="blazor-error-ui">
        An unhandled error has occurred.
        <a href="" class="reload">Reload</a>
        <a class="dismiss">🗙</a>
    </div>
    <script src="_framework/blazor.webassembly.js"></script>
    <!-- 下記を追加 -->
    <script src="_content/MatBlazor/dist/matBlazor.js"></script>
</body>

これで準備は整いました。

Todoアイテム入力欄

ここではチェックボックス、入力欄、ボタンにMatBlazorを使用しています。

TodoMat.razor

@page "/todomat"

<style>
    .new-item-text-field > label.mat-text-field > span {
        margin-left: 30px;
    }
</style>

<h1>Todo</h1>

<div class="new-item-text-field" style="display: flex; position: relative; align-items: center;">
    <MatCheckbox Style="z-index: 1; position: absolute; left: 0;" 
                 @bind-Value="allChecked" Disabled="@(!TodoItemExists())"></MatCheckbox>
    <MatTextField @bind-Value="newItem" Label="What needs to be done?"
                  OnKeyDown="@Enter" OnInput="@OnInput"
                  Style="z-index: 0; width: 500px; padding-left: 50px;"></MatTextField>
    <MatButton OnClick="@AddItem" Outlined="true">add</MatButton>
</div>

MatBlazorのドキュメントに使用例がたくさん載ってるのでさらっと説明を。

◆ MatCheckbox

チェックボックスのコンポーネント。前回作成したTodo画面では入力欄のとこにチェックボックスを付けてなかったのですが追加しました。

Name Description
@bind-Value バインドする値。true / false
Disabled 無効にするかどうか。true / false

@bind-Valueには、プロパティallCheckedをバインド。 コメントの通りです。

Disabledには、メソッドTodoItemExists()の戻り値をバインド。

TodoMat.cs

// newItemのチェック状態
private bool allChecked
{
    get
    {
        // 未完了アイテムがない場合にチェックON、一つでもあればチェックOFF
        return !allTodos.Any(x => !x.IsDone);
    }
    set
    {
        // チェック状態に合わせてTodoアイテムすべてのチェック状態を変更
        allTodos.ForEach(x => x.IsDone = value);
    }
}
        
/// <summary>
/// Todoアイテムが存在するかどうか
/// </summary>
/// <returns></returns>
private bool TodoItemExists()
{
    return allTodos.Any();
}
◆ MatTextField

テキストフィールドのコンポーネント。

Name Description
@bind-Value バインドする値。入力した値を保持。
Label 入力項目名。今回はPlaceholder的な使い方してます。
HelperTextというのが別に用意されているので本来はこちらの方がいいのかな?
OnKeyDown キーダウンイベント。
OnInput 入力イベント。

ただ1個だけ面倒だったのがあります。

MatTextFieldのLabel「What needs to be done?」の文字の位置。 CheckBoxとTextFieldを重ねてるので入力内容はStyle属性で paddingを指定してやればズラせたのですが Labelの文字位置は用意されてる属性では触れそうになかったので Styleを強引にイジってます。(上記ソースの4-6行目) これが正解なのかどうかわかりませんがまたどっかで時間作って確認してみます。

◆ MatButton

ボタンのコンポーネント。

Name Description
OnClick クリックイベント。
Outlined ボタンの枠を表示するかどうか。

Todoアイテムリスト

リスト用コンポーネント。MatListとMatListItemを使用してます。今回はStyleのみ指定。

TodoMat.razor

<style>
    .completed-todo-item {
        text-decoration: line-through;
        color: lightgray !important;
    }
</style>
・・・
・・・
<MatList Style="width: 500px">
    @foreach (var item in todosForDisplay)
    {
        <MatListItem Style="padding: 0;">
            <MatCheckbox Style="z-index: 1;" @bind-Value="item.IsDone"></MatCheckbox>
            <MatStringField Style="z-index: 0; width: 100%; position: absolute; padding-left: 50px;" 
                            InputClass="@GetCompletedTodoItemCssClass(item.IsDone)" 
                            @bind-Value="item.Content"></MatStringField>
        </MatListItem>
    }
</MatList>

MatListItem内ではMatCheckboxとMatStringFieldを使用しています。 MatStringFieldはMatTextFieldと違ってString型専用のコンポーネントっぽいです。 MatTextFieldはintやDateTimeなどの型がバインドできます。

◆ MatStringField

String専用の入力用コンポーネント。

Name Description
InputClass input要素のCSSクラス。

Styleに「completed-todo-item」を用意し、InputClassに チェック状態によって異なるStyle名を返すメソッド「GetCompletedTodoItemCssClass()」をバインドしています。

TodoMat.cs

/// <summary>
/// Todo完了アイテムCSSクラス名を取得
/// </summary>
/// <param name="isDone">完了フラグ</param>
/// <returns>クラス名</returns>
private string GetCompletedTodoItemCssClass(bool isDone)
{
    return isDone ? "completed-todo-item" : "";
}

リスト下のボタン群

ボタン用のコンポーネント。

TodoMat.razor

@allTodos.Count(x => !x.IsDone) items left
<MatButton OnClick="@ShowAll" Outlined="true" Style="margin-left: 20px">All</MatButton>
<MatButton OnClick="@ShowActive" Outlined="true">Active</MatButton>
<MatButton OnClick="@ShowCompleted" Outlined="true" Style="margin-right: 20px">Completed</MatButton>
<MatButton OnClick="@ClearCompleted" Outlined="true" 
           Disabled="@(!CompletedTodoItemExists())">Clear completed</MatButton>

TodoMat.cs

/// <summary>
/// 完了済みのTodoアイテムが存在するかどうか
/// </summary>
/// <returns></returns>
private bool CompletedTodoItemExists()
{
    return allTodos.Any(x => x.IsDone);
}

さいごに

使ってみた感じ、CSSの知識がない人にとっては嬉しいとは思いますが Webの知識がある人からすると物足りなさそうな感じがします。 ちょっと細かいことに拘るとCSSの知識も必要になってきます。 ドキュメントはわかりやすかったのですんなり使えました。 他にもBlazor向けのコンポーネントで良さそうなのがあったらまた紹介したいと思います。

以上、もりもりでした。