diff options
Diffstat (limited to 'app/bluetooth')
-rw-r--r-- | app/bluetooth/Bluetooth.qml | 341 | ||||
-rw-r--r-- | app/bluetooth/bluetooth.qrc | 8 | ||||
-rw-r--r-- | app/bluetooth/images/HMI_Pair_Button.svg | 98 | ||||
-rw-r--r-- | app/bluetooth/images/HMI_Paired_Button.svg | 98 | ||||
-rw-r--r-- | app/bluetooth/images/HMI_Settings_BluetoothIcon.svg | 55 |
5 files changed, 600 insertions, 0 deletions
diff --git a/app/bluetooth/Bluetooth.qml b/app/bluetooth/Bluetooth.qml new file mode 100644 index 0000000..ded2c36 --- /dev/null +++ b/app/bluetooth/Bluetooth.qml @@ -0,0 +1,341 @@ +/* + * Copyright (C) 2016 The Qt Company Ltd. + * + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ + +import QtQuick 2.6 +import QtQuick.Layouts 1.1 +import QtQuick.Controls 2.0 +import '..' + +SettingPage { + id: root + icon: '/bluetooth/images/HMI_Settings_BluetoothIcon.svg' + title: 'Bluetooth' + checkable: true + + property string protocol: 'http://' + property string ipAddress: '127.0.0.1' + property string portNumber: Qt.application.arguments[1] + property string tokenString: Qt.application.arguments[2] + property string btAPI: '/api/Bluetooth-manager/' + property string btAPIpath: protocol + ipAddress + ':' + portNumber + btAPI + property var jsonObjectBT + property string currentState: 'idle' + + Text { + id: log + anchors.fill: parent + anchors.margins: 10 + horizontalAlignment: Text.AlignHCenter + verticalAlignment: Text.AlignVCenter + //text: "log" + } + + onCheckedChanged: { + console.log("Bluetooth set to", checked) + if (checked == true) { + request(btAPIpath + 'power?value=1', function (o) { + // log the json response + console.log(o.responseText) + }) + request(btAPIpath + 'start_discovery', function (o) { + console.log(o.responseText) + }) + currentState = 'discovering' + //search_device() + periodicRefresh.start() + + } else { + //console.log(networkPath) + btDeviceList.clear() + periodicRefresh.stop() + request(btAPIpath + 'stop_discovery', function (o) { + // log the json response + console.log(o.responseText) + }) + request(btAPIpath + 'power?value=0', function (o) { + // log the json response + //showRequestInfo(o.responseText) + console.log(o.responseText) + }) + currentState = 'idle' + } + } + + ListModel { + id: btDeviceList + } + + Rectangle { + anchors.horizontalCenter: parent.horizontalCenter + anchors.bottom: parent.bottom + anchors.margins: 80 + width: buttonScan.width + 10 + height: buttonScan.height + 10 + color: "#222" + border.color: "white" + + Button { + id: buttonScan + anchors.centerIn: parent + width: 100 + text: "SEARCH" + + MouseArea { + //id: mouseArea + anchors.fill: parent + + onClicked: { + if (buttonScan.text == "SEARCH"){ + request(btAPIpath + 'start_discovery', function (o) { + + // log the json response + //showRequestInfo(o.responseText) + console.log(o.responseText) + }) + buttonScan.text = "CANCEL" + currentState = 'discovering' + periodicRefresh.start() + }else{ + request(btAPIpath + 'stop_discovery', function (o) { + + // log the json response + //showRequestInfo(o.responseText) + console.log(o.responseText) + }) + buttonScan.text = "SEARCH" + currentState = 'idle' + //periodicRefresh.stop() //in order to update the content from bluez + } + } + } + } + } + + function request(url, callback) { + var xhr = new XMLHttpRequest() + xhr.onreadystatechange = (function (myxhr) { + return function () { + if (xhr.readyState == 4 && xhr.status == 200){ + callback(myxhr) + } + } + })(xhr) + xhr.open('GET', url, false) + xhr.send('') + } + + Component { + id:blueToothDevice + Rectangle { + height: 150 + width: parent.width + color: "#222" + + Column { + Text { + id: btName + text: deviceName + font.pointSize: 36 + color: "#ffffff" + } + Text { + id: btAddr + text: deviceAddress + visible: false + } + Text { + text: { + if ((devicePairable === "True") + && (deviceConnect === "False")) + text = "paired" + else if ((devicePairable === "True") + && (deviceConnect === "True") + && (connectAVP) === "True") + text = "AV Connection" + else if ((devicePairable === "True") + && (deviceConnect === "True") + && (connectHFP) === "True") + text = "Handsfree Connection" + else + text = "" + } + font.pointSize: 18 + color: "#ffffff" + font.italic: true + } + Text { + id: btPairable + text: devicePairable + visible: false + } + Text { + id: btConnectstatus + text: deviceConnect + visible: false + } + + } + Button { + id: connectButton + anchors.top:parent.top + anchors.topMargin: 15 + anchors.right: parent.right + anchors.rightMargin: 10 + + text:(btConnectstatus.text == "True")? "Disconnect":((btPairable.text == "True")? "Connect":"Pair") + MouseArea { + anchors.fill: parent + onClicked: { + if (currentState == 'discovering'){ + request(btAPIpath + 'stop_discovery', function (o) { + currentState = "idle" + console.log(o.responseText) + }) + } + if (connectButton.text == "Pair"){ + connectButton.text = "Connect" + request(btAPIpath + 'pair?value=' + btAddr.text, function (o) { + btPairable.text = "True" + console.log(o.responseText) + }) + request(btAPIpath + 'set_property?Address=' + btAddr.text + '\&Property=Trusted\&value=true', function (o) { + console.log(o.responseText) + }) + } + else if (connectButton.text == "Connect"){ + connectButton.text = "Disconnect" + request(btAPIpath + 'connect?value=' + btAddr.text, function (o) { + console.log(o.responseText) + }) + } + else if (connectButton.text == "Disconnect"){ + request(btAPIpath + 'disconnect?value=' + btAddr.text, function (o) { + console.log(o.responseText) + }) + connectButton.text = "Connect" + btDeviceList.remove(findDevice(btAddr.text)) + } + } + } + } + /*Image{ + id: removeDevice + anchors.top:parent.top + anchors.topMargin: 15 + anchors.right: parent.right + anchors.rightMargin: 5 + width: 25 + height: 25 + source: "component/images/trash.png" + + MouseArea { + anchors.fill: parent + onClicked: { + request(btAPIpath + 'remove_device?value=' + btAddr.text, function (o) { + console.log(o.responseText) + }) + btDeviceList.remove(findDevice(btAddr.text)) + } + } + }*/ + } + } + + ListView { + width: parent.width + anchors.top: parent.top + anchors.topMargin: 200 + anchors.bottom: parent.bottom + anchors.bottomMargin: 150 + model: btDeviceList + delegate: blueToothDevice + clip: true + } + + function findDevice(address){ + for (var i = 0; i < jsonObjectBT.length; i++) { + if (address === jsonObjectBT[i].Address){ + return i + } + } + } + function search_device(){ + btDeviceList.clear() + request(btAPIpath + 'discovery_result', function (o) { + + // log the json response + console.log(o.responseText) + + // translate response into object + var jsonObject = eval('(' + o.responseText + ')') + + jsonObjectBT = eval('(' + JSON.stbtPairableringify( + jsonObject.response) + ')') + + console.log("BT list refreshed") + + //console.log(jsonObject.response) + for (var i = 0; i < jsonObjectBT.length; i++) { + btDeviceList.append({ + deviceAddress: jsonObjectBT[i].Address, + deviceName: jsonObjectBT[i].Name, + devicePairable:jsonObjectBT[i].Paired, + deviceConnect: jsonObjectBT[i].Connected, + connectAVP: jsonObjectBT[i].AVPConnected, + connectHFP: jsonObjectBT[i].HFPConnected + }) + } + }) + } + + //Timer for periodic refresh; this is BAD solution, need to figure out how to subscribe for events + Timer { + id: periodicRefresh + interval: (currentState == "idle")? 10000:5000 // 5seconds + onTriggered: { + + btDeviceList.clear() + + request(btAPIpath + 'discovery_result', function (o) { + + // log the json response + console.log(o.responseText) + + // translate response into object + var jsonObject = eval('(' + o.responseText + ')') + + jsonObjectBT = eval('(' + JSON.stringify( + jsonObject.response) + ')') + + console.log("BT list refreshed") + + //console.log(jsonObject.response) + for (var i = 0; i < jsonObjectBT.length; i++) { + btDeviceList.append({ + deviceAddress: jsonObjectBT[i].Address, + deviceName: jsonObjectBT[i].Name, + devicePairable:jsonObjectBT[i].Paired, + deviceConnect: jsonObjectBT[i].Connected, + connectAVP: jsonObjectBT[i].AVPConnected, + connectHFP: jsonObjectBT[i].HFPConnected + }) + } + }) + start() + } + } + } + diff --git a/app/bluetooth/bluetooth.qrc b/app/bluetooth/bluetooth.qrc new file mode 100644 index 0000000..bc8b70a --- /dev/null +++ b/app/bluetooth/bluetooth.qrc @@ -0,0 +1,8 @@ +<RCC> + <qresource prefix="/bluetooth"> + <file>Bluetooth.qml</file> + <file>images/HMI_Pair_Button.svg</file> + <file>images/HMI_Paired_Button.svg</file> + <file>images/HMI_Settings_BluetoothIcon.svg</file> + </qresource> +</RCC> diff --git a/app/bluetooth/images/HMI_Pair_Button.svg b/app/bluetooth/images/HMI_Pair_Button.svg new file mode 100644 index 0000000..930a75b --- /dev/null +++ b/app/bluetooth/images/HMI_Pair_Button.svg @@ -0,0 +1,98 @@ +<?xml version="1.0" encoding="UTF-8" standalone="no"?> +<!-- Generator: Adobe Illustrator 21.0.0, SVG Export Plug-In . SVG Version: 6.00 Build 0) --> + +<svg + xmlns:i="&ns_ai;" + xmlns:dc="http://purl.org/dc/elements/1.1/" + xmlns:cc="http://creativecommons.org/ns#" + xmlns:rdf="http://www.w3.org/1999/02/22-rdf-syntax-ns#" + xmlns:svg="http://www.w3.org/2000/svg" + xmlns="http://www.w3.org/2000/svg" + xmlns:sodipodi="http://sodipodi.sourceforge.net/DTD/sodipodi-0.dtd" + xmlns:inkscape="http://www.inkscape.org/namespaces/inkscape" + version="1.1" + id="Layer_1" + x="0px" + y="0px" + viewBox="0 0 151 51" + style="enable-background:new 0 0 151 51;" + xml:space="preserve" + inkscape:version="0.91 r13725" + sodipodi:docname="HMI_Pair_Button.svg"><metadata + id="metadata33"><rdf:RDF><cc:Work + rdf:about=""><dc:format>image/svg+xml</dc:format><dc:type + rdf:resource="http://purl.org/dc/dcmitype/StillImage" /></cc:Work></rdf:RDF></metadata><defs + id="defs31" /><sodipodi:namedview + pagecolor="#ffffff" + bordercolor="#666666" + borderopacity="1" + objecttolerance="10" + gridtolerance="10" + guidetolerance="10" + inkscape:pageopacity="0" + inkscape:pageshadow="2" + inkscape:window-width="2560" + inkscape:window-height="1464" + id="namedview29" + showgrid="false" + inkscape:zoom="4.4503311" + inkscape:cx="-17.97619" + inkscape:cy="25.5" + inkscape:window-x="0" + inkscape:window-y="0" + inkscape:window-maximized="1" + inkscape:current-layer="Layer_1" /><style + type="text/css" + id="style3"> + .st0{fill:none;stroke:url(#SVGID_1_);stroke-miterlimit:10;} + .st1{opacity:0.3;fill:url(#SVGID_2_);} + .st2{fill:#FFFFFF;} + .st3{font-family:'Roboto-Regular';} + .st4{font-size:19.7348px;} + .st5{letter-spacing:3;} +</style><switch + id="switch5"><g + i:extraneous="self" + id="g7"><g + id="g9"><linearGradient + id="SVGID_1_" + gradientUnits="userSpaceOnUse" + x1="24.7258" + y1="75.9063" + x2="126.2742" + y2="-24.9063"><stop + offset="0" + style="stop-color:#59FF7F" + id="stop12" /><stop + offset="1" + style="stop-color:#6BFBFF" + id="stop14" /></linearGradient><rect + x="0.5" + y="0.5" + class="st0" + width="150" + height="50" + id="rect16" /><linearGradient + id="SVGID_2_" + gradientUnits="userSpaceOnUse" + x1="-25.8746" + y1="126.14" + x2="190.2191" + y2="-88.3878"><stop + offset="0" + style="stop-color:#59FF7F" + id="stop19" /><stop + offset="1" + style="stop-color:#6BFBFF" + id="stop21" /></linearGradient><rect + x="0.5" + y="0.5" + class="st1" + width="150" + height="50" + id="rect23" /><g + id="g25"><text + transform="matrix(1 0 0 1 46.5699 33.9046)" + class="st2 st3 st4 st5" + id="text27">Pair</text> +</g></g></g></switch></svg>
\ No newline at end of file diff --git a/app/bluetooth/images/HMI_Paired_Button.svg b/app/bluetooth/images/HMI_Paired_Button.svg new file mode 100644 index 0000000..17419d4 --- /dev/null +++ b/app/bluetooth/images/HMI_Paired_Button.svg @@ -0,0 +1,98 @@ +<?xml version="1.0" encoding="UTF-8" standalone="no"?> +<!-- Generator: Adobe Illustrator 21.0.0, SVG Export Plug-In . SVG Version: 6.00 Build 0) --> + +<svg + xmlns:i="&ns_ai;" + xmlns:dc="http://purl.org/dc/elements/1.1/" + xmlns:cc="http://creativecommons.org/ns#" + xmlns:rdf="http://www.w3.org/1999/02/22-rdf-syntax-ns#" + xmlns:svg="http://www.w3.org/2000/svg" + xmlns="http://www.w3.org/2000/svg" + xmlns:sodipodi="http://sodipodi.sourceforge.net/DTD/sodipodi-0.dtd" + xmlns:inkscape="http://www.inkscape.org/namespaces/inkscape" + version="1.1" + id="Layer_1" + x="0px" + y="0px" + viewBox="0 0 151 51" + style="enable-background:new 0 0 151 51;" + xml:space="preserve" + inkscape:version="0.91 r13725" + sodipodi:docname="HMI_Paired_Button.svg"><metadata + id="metadata33"><rdf:RDF><cc:Work + rdf:about=""><dc:format>image/svg+xml</dc:format><dc:type + rdf:resource="http://purl.org/dc/dcmitype/StillImage" /></cc:Work></rdf:RDF></metadata><defs + id="defs31" /><sodipodi:namedview + pagecolor="#ffffff" + bordercolor="#666666" + borderopacity="1" + objecttolerance="10" + gridtolerance="10" + guidetolerance="10" + inkscape:pageopacity="0" + inkscape:pageshadow="2" + inkscape:window-width="2560" + inkscape:window-height="1464" + id="namedview29" + showgrid="false" + inkscape:zoom="4.4503311" + inkscape:cx="-11.909226" + inkscape:cy="25.5" + inkscape:window-x="0" + inkscape:window-y="0" + inkscape:window-maximized="1" + inkscape:current-layer="Layer_1" /><style + type="text/css" + id="style3"> + .st0{fill:none;stroke:url(#SVGID_1_);stroke-miterlimit:10;} + .st1{opacity:0.84;fill:url(#SVGID_2_);} + .st2{fill:#27232B;} + .st3{font-family:'Roboto-Regular';} + .st4{font-size:19.7348px;} + .st5{letter-spacing:2.9;} +</style><switch + id="switch5"><g + i:extraneous="self" + id="g7"><g + id="g9"><linearGradient + id="SVGID_1_" + gradientUnits="userSpaceOnUse" + x1="24.7258" + y1="75.9063" + x2="126.2742" + y2="-24.9063"><stop + offset="0" + style="stop-color:#59FF7F" + id="stop12" /><stop + offset="1" + style="stop-color:#6BFBFF" + id="stop14" /></linearGradient><rect + x="0.5" + y="0.5" + class="st0" + width="150" + height="50" + id="rect16" /><linearGradient + id="SVGID_2_" + gradientUnits="userSpaceOnUse" + x1="-25.8746" + y1="126.14" + x2="190.2191" + y2="-88.3878"><stop + offset="0" + style="stop-color:#59FF7F" + id="stop19" /><stop + offset="1" + style="stop-color:#6BFBFF" + id="stop21" /></linearGradient><rect + x="0.5" + y="0.5" + class="st1" + width="150" + height="50" + id="rect23" /><g + id="g25"><text + transform="matrix(1.0253 0 0 1 33.1099 33.9038)" + class="st2 st3 st4 st5" + id="text27">PairED</text> +</g></g></g></switch></svg>
\ No newline at end of file diff --git a/app/bluetooth/images/HMI_Settings_BluetoothIcon.svg b/app/bluetooth/images/HMI_Settings_BluetoothIcon.svg new file mode 100644 index 0000000..d41de2a --- /dev/null +++ b/app/bluetooth/images/HMI_Settings_BluetoothIcon.svg @@ -0,0 +1,55 @@ +<?xml version="1.0" encoding="UTF-8" standalone="no"?> +<!-- Generator: Adobe Illustrator 21.0.0, SVG Export Plug-In . SVG Version: 6.00 Build 0) --> + +<svg + xmlns:i="&ns_ai;" + xmlns:dc="http://purl.org/dc/elements/1.1/" + xmlns:cc="http://creativecommons.org/ns#" + xmlns:rdf="http://www.w3.org/1999/02/22-rdf-syntax-ns#" + xmlns:svg="http://www.w3.org/2000/svg" + xmlns="http://www.w3.org/2000/svg" + xmlns:sodipodi="http://sodipodi.sourceforge.net/DTD/sodipodi-0.dtd" + xmlns:inkscape="http://www.inkscape.org/namespaces/inkscape" + version="1.1" + id="Layer_1" + x="0px" + y="0px" + viewBox="0 0 100 100" + style="enable-background:new 0 0 100 100;" + xml:space="preserve" + inkscape:version="0.91 r13725" + sodipodi:docname="HMI_Settings_BluetoothIcon.svg"><metadata + id="metadata16"><rdf:RDF><cc:Work + rdf:about=""><dc:format>image/svg+xml</dc:format><dc:type + rdf:resource="http://purl.org/dc/dcmitype/StillImage" /></cc:Work></rdf:RDF></metadata><defs + id="defs14" /><sodipodi:namedview + pagecolor="#ffffff" + bordercolor="#666666" + borderopacity="1" + objecttolerance="10" + gridtolerance="10" + guidetolerance="10" + inkscape:pageopacity="0" + inkscape:pageshadow="2" + inkscape:window-width="2560" + inkscape:window-height="1464" + id="namedview12" + showgrid="false" + inkscape:zoom="2.36" + inkscape:cx="-130.29661" + inkscape:cy="50" + inkscape:window-x="0" + inkscape:window-y="0" + inkscape:window-maximized="1" + inkscape:current-layer="Layer_1" /><style + type="text/css" + id="style3"> + .st0{fill:#FFFFFF;} +</style><switch + id="switch5"><g + i:extraneous="self" + id="g7"><g + id="Bluetooth_Icon"><path + class="st0" + d="M48.3,86.9V53.4L30.9,69.7l-1.4-1.5l18.8-17.6v-0.2L27.9,36.4l1.1-1.6L48.3,48v-35l23.6,18.2l-20.3,19 l20.5,14.1L48.3,86.9z M50.3,51.8v30.5l18.6-17.6L50.3,51.8z M50.3,17.1v31.6l18.5-17.3L50.3,17.1z" + id="path10" /></g></g></switch></svg>
\ No newline at end of file |