📢 Webサイト閉鎖と移転のお知らせ
このWebサイトは2026年9月に閉鎖いたします。
新しい記事は移転先で追加しております。(旧サイトでは記事を追加しておりません)
ページの作成:「== 概要 == 設計者は、既存のQMLタイプを使用して、独自の機能を追加したカスタムQMLタイプを作成することができる。<br> <br><br> == カスタムQMLタイプの作成 == # Qt Creatorを起動して、[ファイル]メニューバー - [New File...]を選択する。 # 次に、[New File]ダイアログの左ペインにある[Qt] - 右ペインにある[QMLファイル(Qt Quick 2)]を選択する。 # 作成するQMLファ…」 |
|||
| (同じ利用者による、間の9版が非表示) | |||
| 1行目: | 1行目: | ||
== 概要 == | == 概要 == | ||
設計者は、既存のQMLタイプを使用して、独自の機能を追加したカスタムQMLタイプを作成することができる。<br> | 設計者は、既存のQMLタイプを使用して、独自の機能を追加したカスタムQMLタイプを作成することができる。<br> | ||
<br> | |||
カスタムQMLタイプは、コンポーネントと呼ぶこともある。<br> | |||
コンポーネントとは、複数のQMLタイプをまとめて1つのQMLタイプとして扱う仕組みである。<br> | |||
<br> | |||
カスタムQMLタイプ以外にも、Componentタイプを使用してコンポーネントを作成することができる。<br> | |||
<br><br> | <br><br> | ||
| 20行目: | 25行目: | ||
<br><br> | <br><br> | ||
== | == カスタムQMLタイプの例 == | ||
以下の例では、押下するたびに乱数を発生させて、テキストに乱数値を表示するカスタムQMLタイプを作成および使用している。<br> | 以下の例では、押下するたびに乱数を発生させて、テキストに乱数値を表示するカスタムQMLタイプを作成および使用している。<br> | ||
なお、カスタムQMLファイル名は"CustomItem.qml"として、Qtプロジェクトのトップディレクトリに配置している。<br> | なお、カスタムQMLファイル名は"CustomItem.qml"として、Qtプロジェクトのトップディレクトリに配置している。<br> | ||
| 68行目: | 73行目: | ||
height: 50 | height: 50 | ||
} | } | ||
} | |||
} | |||
</syntaxhighlight> | |||
<br><br> | |||
== コンポーネントの作成 == | |||
まず、カスタムQMLタイプを作成する。<br> | |||
# Qt Creatorを起動して、[ファイル]メニューバー - [New File...]を選択する。 | |||
# 次に、[New File]ダイアログの左ペインにある[Qt] - 右ペインにある[QMLファイル(Qt Quick 2)]を選択する。 | |||
# 作成するQMLファイル名を入力して、[次へ]ボタンを押下する。 | |||
# [プロジェクト管理]画面にある[完了]ボタンを押下する。 | |||
<br> | |||
カスタムQMLファイル名には、英数字や<code>_</code>(アンダーバー)が使用できる。<br> | |||
<u>ただし、ファイル名の1文字目は大文字のアルファベットで始まる必要がある。</u><br> | |||
<br> | |||
コンポーネントは、以下に示すいずれかの手順により、オブジェクトを動的に生成することができる。<br> | |||
* <code>Loader</code>タイプを使用する。 | |||
* <code>Component</code>タイプの<code>createObject</code>関数を使用する。 | |||
<br> | |||
オブジェクトを必要に応じて生成する場合、または、パフォーマンス性からオブジェクトを不必要に削除したくない場合等に使用する。<br> | |||
<br><br> | |||
== コンポーネントの例 == | |||
==== Loaderタイプを使用する場合 ==== | |||
<code>Loader</code>タイプは、カスタムQMLファイルを読み込み、オブジェクトを動的に生成することができる。<br> | |||
カスタムQMLファイルのオブジェクトを生成するには、<code>source</code>プロパティにカスタムQMLファイルのパスを指定する。<br> | |||
<br> | |||
生成したオブジェクトを削除する場合は、<code>source</code>プロパティを空に指定する。<br> | |||
<br> | |||
<code>Loader</code>タイプは<code>Item</code>タイプを継承しているため、<code>x</code>プロパティ、<code>y</code>プロパティ、<code>anchors</code>プロパティを使用して、<br> | |||
動的に生成したカスタムQMLファイルのオブジェクトのレイアウトを設定することができる。<br> | |||
デフォルトの<code>x</code>プロパティおよび<code>y</code>プロパティの値は、<code>0</code>であるため、そのオブジェクトは左上に表示される。<br> | |||
<syntaxhighlight lang="qml"> | |||
// main.qmlファイル | |||
import QtQuick 2.15 | |||
import QtQuick.Window 2.15 | |||
Window { | |||
visible: true | |||
width: 640 | |||
height: 480 | |||
MouseArea { | |||
anchors.fill: parent | |||
function onClicked() { | |||
pageLoader.source = "CustomItem.qml" | |||
} | |||
} | |||
Loader { | |||
id: pageLoader | |||
} | |||
} | |||
</syntaxhighlight> | |||
<br> | |||
また、読み込んだカスタムQMLタイプがシグナルを送信してそれを呼び出し側が受信する場合、<code>Connections</code>タイプを<code>Loader</code>タイプの<code>item</code>プロパティと一緒に使用する必要がある。<br> | |||
また、読み込んだカスタムQMLタイプが破棄された場合、カスタムQMLタイプが再び生成されるまで、全てのシグナルハンドラは無視される。<br> | |||
<syntaxhighlight lang="qml"> | |||
// main.qmlファイル | |||
Loader { | |||
id: pageLoader | |||
source: "CustomQML.qml" | |||
} | |||
Connections { | |||
target: pageLoader.item | |||
// Qt 5.14以前の場合 | |||
onMessage: { | |||
pageLoader.source = "" | |||
} | |||
// Qt 5.15以降は、以下に示すシンタックスでも可能 | |||
function onMessage() | |||
{ | |||
pageLoader.source = "" | |||
} | |||
} | |||
</syntaxhighlight> | |||
<br> | |||
<syntaxhighlight lang="qml"> | |||
// CustomQML.qmlファイル | |||
import QtQuick 2.15 | |||
Rectangle { | |||
id: root | |||
width: 100 | |||
height: 100 | |||
signal message(string msg) | |||
MouseArea { | |||
anchors.fill: parent | |||
onClicked: { | |||
root.message("clicked!") | |||
} | |||
} | |||
} | |||
</syntaxhighlight> | |||
<br> | |||
==== Componentタイプを使用する場合 ==== | |||
Componentタイプは、複数のQMLオブジェクトをまとめてコンポーネント化して、再利用可能なオブジェクトとして部品化する。<br> | |||
<syntaxhighlight lang="qml"> | |||
Component { | |||
// ...略 | |||
<任意のカスタムQMLタイプ名 例. CustomItem> { | |||
// ...略 | |||
} | |||
} | |||
</syntaxhighlight> | |||
<br> | |||
<code>Component</code>タイプは、Itemタイプを継承していないため、<code>x</code>プロパティ、<code>y</code>プロパティ、<code>anchors</code>プロパティ、レイアウトの設定は使用できない。<br> | |||
レイアウトの設定が必要な場合、カスタムQMLタイプのプロパティを変更して、レイアウトを設定する必要がある。<br> | |||
<br> | |||
<code>Component</code>タイプ内に定義したカスタムQMLタイプをウインドウに表示する場合は、<code>Component</code>タイプを<code>Loader</code>タイプの<code>sourceComponent</code>プロパティに設定する。<br> | |||
また、<code>Loader</code>タイプの<code>sourceComponent</code>プロパティに<code>undefined</code>を指定することにより、読み込み済みのオブジェクトを削除することができる。<br> | |||
<br> | |||
以下の例では、カスタムQMLタイプ(CustomItem)をコンポーネント化したComponentタイプを読み込んで表示している。<br> | |||
<syntaxhighlight lang="qml"> | |||
import QtQuick 2.15 | |||
import QtQuick.Window 2.15 | |||
window { | |||
visible: true | |||
width: 640 | |||
height: 480 | |||
MouseArea { | |||
anchors.fill: parent | |||
onClicked: { | |||
componentLoader.sourceComponent = customComponent | |||
} | |||
} | |||
Loader { | |||
id: componentLoader | |||
} | |||
Component { | |||
id: customComponent | |||
CustomItem { | |||
id: customItem | |||
} | |||
} | |||
} | |||
</syntaxhighlight> | |||
<br> | |||
<code>Component</code>タイプの重要な機能として、<code>completed</code>と<code>destruction</code>という2つのアタッチドシグナルが存在する。<br> | |||
* completed | |||
*: インスタンスが生成された直後に送信される。 | |||
*: シグナルハンドラである<code>onCompleted</code>は、インスタンスの生存確認およびインスタンスの生成直後に何らかの処理が必要な場合に使用するため、使用頻度が高い。 | |||
* destruction | |||
*: インスタンスが削除された時に送信される。 | |||
<br> | |||
==== ComponentタイプのcreateObject関数を使用する場合 ==== | |||
グローバル関数である<code>Qt.createComponent</code>関数を使用することにより、<code>Component</code>タイプのインスタンスを生成することができる。<br> | |||
このインスタンスから、<code>Component</code>タイプにある<code>createObject</code>関数を使用して、表示可能なインスタンスを動的に生成することができる。<br> | |||
<br> | |||
また、<code>createObject</code>関数の第2引数にカスタムQMLタイプに渡すプロパティを指定することにより、インスタンスの生成と同時にプロパティを設定することができる。<br> | |||
<br> | |||
以下の例では、<code>Qt.createComponent</code>関数と<code>createObject</code>関数を使用して、カスタムQMLタイプ(CustomItem)を動的に生成している。<br> | |||
<syntaxhighlight lang="qml"> | |||
import QtQuick 2.15 | |||
import QtQuick.Window 2.15 | |||
window { | |||
id: mainWindow | |||
visible: true | |||
width: 640 | |||
height: 480 | |||
Component.onCompleted { | |||
var component = Qt.createComponent("CustomItem.qml") | |||
component.createObject(mainWindow, {"anchors.fill": mainWindow}) | |||
} | |||
} | |||
</syntaxhighlight> | |||
<br> | |||
<code>Component</code>タイプは、<code>Loader</code>タイプと比較して手順が複雑であるが複数のインスタンスを生成できる等、<code>Loader</code>タイプには無いメリットが存在する。<br> | |||
<br><br> | |||
== ダイアログの例 == | |||
ダイアログは、カスタムQMLタイプとして定義することができない。<br> | |||
ただし、<code>Window</code>タイプまたは<code>ApplicationWindow</code>タイプを定義したカスタムQMLタイプを、<code>createComponent</code>関数を使用して読み込むことにより実現できる。<br> | |||
<br> | |||
また、ダイアログから戻り値を取得する場合は、カスタムQMLタイプに<code>property</code>を定義して、<code>Connections</code>タイプから取得する。<br> | |||
<syntaxhighlight lang="qml"> | |||
// main.qmlファイル | |||
import QtQuick 2.15 | |||
import QtQuick.Controls 2.15 | |||
import QtQuick.Layouts 1.15 | |||
import QtQuick.Window 2.15 | |||
// ...略 | |||
Button { | |||
text: "Popup MessageDialog" | |||
onClicked: { | |||
var component = Qt.createComponent("MessageDialog.qml"); | |||
if (component.status === Component.Ready) { | |||
var messageDialog = component.createObject(parent, {someValue1: 1, someValue2: 2}); | |||
messageDialogConnection.target = dlg | |||
messageDialog.show(); | |||
} | |||
} | |||
Connections { | |||
id: messageDialogConnection | |||
onVisibleChanged: { | |||
if(!target.visible) { | |||
console.log(target.returnValue); | |||
} | |||
} | |||
} | |||
// ...略 | |||
</syntaxhighlight> | |||
<br> | |||
<syntaxhighlight lang="qml"> | |||
// MessageDialog.qmlファイル | |||
import QtQuick 2.15 | |||
import QtQuick.Window 2.15 | |||
import QtQuick.Layouts 1.15 | |||
import QtQuick.Controls 2.15 | |||
ApplicationWindow { | |||
property int someValue1: 0 | |||
property int someValue2: 0 | |||
property int returnValue: 0 | |||
id: messageDialog | |||
title: "Some Title" | |||
width: 600 | |||
height: 450 | |||
flags: Qt.Dialog | |||
modality: Qt.WindowModal | |||
onVisibleChanged: { | |||
messageDialogBtnCancel.focus = true | |||
} | |||
ColumnLayout { | |||
id: messageColumn | |||
width: parent.width | |||
spacing: 20 | |||
Label { | |||
text: "Some Message" | |||
width: parent.width | |||
font.pointSize: 12 | |||
wrapMode: Label.WordWrap | |||
horizontalAlignment: Label.AlignHCenter | |||
verticalAlignment: Label.AlignVCenter | |||
Layout.fillWidth: true | |||
Layout.fillHeight: true | |||
Layout.topMargin: 20 | |||
Layout.bottomMargin: 20 | |||
} | |||
RowLayout { | |||
x: parent.x | |||
width: parent.width | |||
Layout.alignment: Qt.AlignHCenter | |||
Layout.bottomMargin: 20 | |||
spacing: 20 | |||
Button { | |||
id: messageDialogBtnOK | |||
text: "OK" | |||
Connections { | |||
target: messageDialogBtnOK | |||
function onClicked() { | |||
returnValue = 0 | |||
messageDialog.close() | |||
} | |||
} | |||
} | |||
Button { | |||
id: messageDialogBtnCancel | |||
text: "Cancel" | |||
focus: true | |||
Connections { | |||
target: messageDialogBtnCancel | |||
function onClicked() { | |||
returnValue = 1 | |||
messageDialog.close(); | |||
} | |||
} | |||
} | |||
} | |||
} | } | ||
} | } | ||