Skip to content
This repository has been archived by the owner on Nov 9, 2021. It is now read-only.

Commit

Permalink
Scan when adding a new device. Small fixes.
Browse files Browse the repository at this point in the history
  • Loading branch information
Sergey Avdeev committed Sep 14, 2018
1 parent 6483db0 commit a74e34c
Show file tree
Hide file tree
Showing 2 changed files with 157 additions and 60 deletions.
149 changes: 97 additions & 52 deletions modules/bluetoothdevices/bluetoothdevices.class.php
Expand Up @@ -26,10 +26,8 @@ function bluetoothdevices() {
if(IsWindowsOS()) {
// Windows
$this->scanMethod = 'discovery';
if($bluetoothview_version = $this->get_product_version(SERVER_ROOT.'/apps/bluetoothview/BluetoothView.exe')) {
if(!$this->compare_programs_versions($bluetoothview_version, '1.41')) {
$this->scanMethod = 'connect';
}
if($this->check_programs_version(SERVER_ROOT.'/apps/bluetoothview/BluetoothView.exe', '1.41')) {
$this->scanMethod = 'connect';
}
} else {
// Linux
Expand Down Expand Up @@ -108,16 +106,27 @@ private function compare_programs_versions($first, $second) {
return FALSE;
}

// Check programs version
private function check_programs_version($exe, $version) {
$results = FALSE;
if($product_version = $this->get_product_version($exe)) {
if(!$this->compare_programs_versions($product_version, $version)) {
$results = TRUE;
}
}
return $results;
}

// Bluetooth: reset
private function bluetooth_reset(&$messages=array()) {
$results = FALSE;
if(IsWindowsOS()) {
// Windows
$messages[] = date('[d/m/Y H:i:s]:').' Reset bluetooth is not supported for Windows OS!';
$messages[] = array('time' => time(), 'text' => 'Reset bluetooth is not supported for Windows OS!');
} else {
// Linux
$this->get_config();
$messages[] = date('[d/m/Y H:i:s]:').' Reset bluetooth...';
$messages[] = array('time' => time(), 'text' => 'Reset bluetooth...');
exec(($this->sudo?'sudo ':'').'hciconfig hci0 down; sudo hciconfig hci0 up');
setGlobal('bluetoothdevices_resetTime', time());
$results = TRUE;
Expand All @@ -132,9 +141,8 @@ private function bluetooth_scan(&$messages=array()) {
// Windows
// FIXME: does not find BLE devices
// FIXME: finds an offline device if it is paired
$devices_file = SERVER_ROOT.'/apps/bluetoothview/devices.txt';
@unlink($devices_file);
exec(SERVER_ROOT.'/apps/bluetoothview/bluetoothview.exe /stab '.$devices_file);
$devices_file = SERVER_ROOT.'/apps/bluetoothview/devices_'.uniqid().'.txt';
exec(SERVER_ROOT.'/apps/bluetoothview/bluetoothview.exe /stab "'.$devices_file.'"');
if(file_exists($devices_file)) {
if($data = LoadFile($devices_file)) {
$data = str_replace(chr(0), '', $data);
Expand All @@ -143,17 +151,22 @@ private function bluetooth_scan(&$messages=array()) {
$total = count($lines);
for($i=0; $i<$total; $i++) {
$fields = explode("\t", $lines[$i]);
$results[] = array(
'address' => strtolower($fields[2]),
'name' => trim($fields[1]),
);
$address = trim(strtolower($fields[2]));
$name = trim($fields[1]);
if(!empty($address)) {
$results[] = array(
'address' => $address,
'name' => $name,
);
}
}
} else {
$messages[] = date('[d/m/Y H:i:s]:').' Error opening file "'.$devices_file.'"!';
$messages[] = array('time' => time(), 'text' => 'Error opening file "'.$devices_file.'"!');
$results = FALSE;
}
@unlink($devices_file);
} else {
$messages[] = date('[d/m/Y H:i:s]:').' Missing file "'.$devices_file.'"!';
$messages[] = array('time' => time(), 'text' => 'Missing file "'.$devices_file.'"!');
$results = FALSE;
}
} else {
Expand All @@ -165,13 +178,14 @@ private function bluetooth_scan(&$messages=array()) {
$total = count($data);
for($i=0; $i<$total; $i++) {
$data[$i] = trim($data[$i]);
if(!$data[$i]) {
continue;
$address = trim(strtolower(substr($data[$i], 0, 17)));
$name = trim(substr($data[$i], 17));
if(!empty($address)) {
$results[] = array(
'address' => $address,
'name' => $name,
);
}
$results[] = array(
'address' => strtolower(substr($data[$i], 0, 17)),
'name' => trim(substr($data[$i], 17)),
);
}
}
return $results;
Expand Down Expand Up @@ -200,7 +214,7 @@ private function bluetooth_ping($address, &$messages=array()) {
$results = FALSE;
if(IsWindowsOS()) {
// Windows
$messages[] = date('[d/m/Y H:i:s]:').' Method "ping" is not supported for Windows OS!';
$messages[] = array('time' => time(), 'text' => 'Method "ping" is not supported for Windows OS!');
} else {
// Linux
$this->get_config();
Expand All @@ -214,7 +228,7 @@ private function bluetooth_ping($address, &$messages=array()) {

// Bluetooth: discovery
private function bluetooth_discovery($address, &$messages=array()) {
$devices = bluetooth_scan($messages);
$devices = $this->bluetooth_scan($messages);
if(is_array($devices)) {
foreach($devices as $device) {
if($device['address'] == $address) {
Expand All @@ -230,18 +244,14 @@ private function bluetooth_connect($address, &$messages=array()) {
$results = FALSE;
if(IsWindowsOS()) {
// Windows
if($bluetoothview_version = $this->get_product_version(SERVER_ROOT.'/apps/bluetoothview/BluetoothView.exe')) {
if(!$this->compare_programs_versions($bluetoothview_version, '1.41')) {
// BluetoothView version >= 1.41
exec(SERVER_ROOT.'/apps/bluetoothview/bluetoothview.exe /try_to_connect '.$address, $data, $code);
if($code == 0) {
$results = TRUE;
}
} else {
$messages[] = date('[d/m/Y H:i:s]:').' The current version of BluetoothView is lower than required (1.41)!';
if($this->check_programs_version(SERVER_ROOT.'/apps/bluetoothview/BluetoothView.exe', '1.41')) {
// BluetoothView version >= 1.41
exec(SERVER_ROOT.'/apps/bluetoothview/bluetoothview.exe /try_to_connect '.$address, $data, $code);
if($code == 0) {
$results = TRUE;
}
} else {
$messages[] = date('[d/m/Y H:i:s]:').' it is impossible to determine the version of BluetoothView!';
$messages[] = array('time' => time(), 'text' => 'The current version of BluetoothView is lower than required (1.41)!');
}
} else {
// Linux
Expand Down Expand Up @@ -327,6 +337,11 @@ function admin(&$out) {
}
// OS type
$out['IS_WINDOWS_OS'] = (int)IsWindowsOS();
// Features
$out['IS_HYBRID_AVAILABLE'] = (int)!IsWindowsOS();
$out['IS_PING_AVAILABLE'] = (int)!IsWindowsOS();
$out['IS_SCAN_AVAILABLE'] = (int)TRUE;
$out['IS_CONNECT_AVAILABLE'] = (int)TRUE;
// Views
if($this->data_source == 'bluetoothdevices' || $this->data_source == '') {
switch($this->view_mode) {
Expand All @@ -350,10 +365,8 @@ function admin(&$out) {
$out['BV_UNSUPPORTED_VERSION'] = (int)FALSE;
if(IsWindowsOS()) {
$out['BV_UNSUPPORTED_VERSION'] = (int)TRUE;
if($bluetoothview_version = $this->get_product_version(SERVER_ROOT.'/apps/bluetoothview/BluetoothView.exe')) {
if(!$this->compare_programs_versions($bluetoothview_version, '1.41')) {
$out['BV_UNSUPPORTED_VERSION'] = (int)FALSE;
}
if($this->check_programs_version(SERVER_ROOT.'/apps/bluetoothview/BluetoothView.exe', '1.41')) {
$out['BV_UNSUPPORTED_VERSION'] = (int)FALSE;
}
}
}
Expand All @@ -379,18 +392,11 @@ function settings_bluetoothdevices(&$out) {
$out['SCAN_INTERVAL'] = $this->scanInterval;
$out['SCAN_TIMEOUT'] = $this->scanTimeout;
$out['RESET_INTERVAL'] = $this->resetInterval;
// Features
$out['IS_HYBRID_AVAILABLE'] = (int)!IsWindowsOS();
$out['IS_PING_AVAILABLE'] = (int)!IsWindowsOS();
$out['IS_SCAN_AVAILABLE'] = (int)TRUE;
$out['IS_CONNECT_AVAILABLE'] = (int)TRUE;
// BluetoothView
if(IsWindowsOS()) {
$out['IS_CONNECT_AVAILABLE'] = (int)FALSE;
if($bluetoothview_version = $this->get_product_version(SERVER_ROOT.'/apps/bluetoothview/BluetoothView.exe')) {
if(!$this->compare_programs_versions($bluetoothview_version, '1.41')) {
$out['IS_CONNECT_AVAILABLE'] = (int)TRUE;
}
if($this->check_programs_version(SERVER_ROOT.'/apps/bluetoothview/BluetoothView.exe', '1.41')) {
$out['IS_CONNECT_AVAILABLE'] = (int)TRUE;
}
}
}
Expand Down Expand Up @@ -512,7 +518,46 @@ function list_bluetoothdevices(&$out) {

// FrontEnd
function usual(&$out) {
global $session;
global $session, $ajax, $command;
if(isset($ajax)) {
// JSON default
$json = array(
'command' => $command,
'success' => FALSE,
'message' => NULL,
'data' => NULL,
);
// Command
switch($command) {
case 'scan':
$messages = array();
$data = $this->bluetooth_scan($messages);
if(is_array($data)) {
$json['success'] = TRUE;
$json['message'] = 'OK';
$json['data'] = $data;
} else {
$json['success'] = FALSE;
if(count($messages) > 0) {
foreach($messages as $message) {
$json['message'] .= $message['text'].' ';
}
$json['message'] = trim($json['message']);
} else {
$json['message'] = 'bluetooth_scan() error!';
}
}
break;
default:
$json['success'] = FALSE;
$json['message'] = 'Unknown command!';
}
// Return json
if(!$this->intCall) {
$session->save();
die(json_encode($json));
}
}
}

// Cycle
Expand All @@ -536,20 +581,20 @@ function processCycle() {
$is_found = $this->bluetooth_hybrid($address, $messages);
break;
case 'ping': // Ping
$is_found = $this->bluetooth_hybrid($address, $messages);
$is_found = $this->bluetooth_ping($address, $messages);
break;
case 'discovery': // Discovery
$is_found = $this->bluetooth_hybrid($address, $messages);
$is_found = $this->bluetooth_discovery($address, $messages);
break;
case 'connect': // Connect
$is_found = $this->bluetooth_hybrid($address, $messages);
$is_found = $this->bluetooth_connect($address, $messages);
break;
default:
$messages[] = date('[d/m/Y H:i:s]:').' Unknown method "'.$this->scanMethod.'"!';
$messages[] = array('time' => time(), 'text' => 'Unknown method "'.$this->scanMethod.'"!');
}
// Print messages
foreach($messages as $message) {
echo $message.PHP_EOL;
echo date('[d/m/Y H:i:s]:', $message['time']).' '.$message['text'].PHP_EOL;
}
// Update object
if($is_found) {
Expand Down
68 changes: 60 additions & 8 deletions templates/bluetoothdevices/bluetoothdevices.html
Expand Up @@ -20,14 +20,14 @@
[#endif#]
[#if DEVICES#]
<table align="center" class="table table-striped">
<tr>
<td><b>Объект</b></td>
<td>&nbsp;</td>
<td><b>Описание</b></td>
<td><b>Адрес устройства</b></td>
<td><b>Последняя активность</b></td>
<td><b>Пользователь</b></td>
<td>&nbsp;</td>
<tr class="table_header">
<th>Объект</th>
<th>&nbsp;</th>
<th>Описание</th>
<th>Адрес устройства</th>
<th>Последняя активность</th>
<th>Пользователь</th>
<th>&nbsp;</th>
</tr>
[#begin DEVICES#]
<tr>
Expand Down Expand Up @@ -57,6 +57,58 @@

[#if VIEW_MODE="add_bluetoothdevices"#]
[#if ERROR_TEXT#]<div class="alert alert-error">[#ERROR_TEXT#]</div>[#endif#]
[#if IS_SCAN_AVAILABLE==1#]
<script type="text/javascript">
// Scan bluetooth devices
function bluetooth_rescan() {
if($('#bluetooth_searching').is(':hidden')) {
$('.bt_scan_btn').css('color', '#ccc');
$('table.devices_list').find('tr').not('.table_header').remove();
$('#bluetooth_searching').show();
$.ajax({
url: '/apps/bluetoothdevices.html?ajax=1&command=scan',
dataType: 'json'
}).done(function(json) {
if(json.success) {
json.data.forEach(function(item) {
$('table.devices_list tr:last').after('<tr><td class="bt_address" style="vertical-align: middle; padding-left: 15px;">'+item.address+'</td><td class="bt_name" style="vertical-align: middle;">'+item.name+'</td><td style="vertical-align: middle; padding-right: 15px; text-align: right;"><a href="#" class="btn btn-default btn-sm" title="Выбрать устройство" onclick="return bluetooth_select(this);"><i class="glyphicon glyphicon-ok"></i></a></td></tr>');
});
} else {
console.warn(json.message);
}
}).fail(function(jqXHR) {
console.error('Error '+jqXHR.status+': '+jqXHR.statusText);
}).always(function() {
$('#bluetooth_searching').hide();
$('.bt_scan_btn').css('color', '');
});
}
}

// Select bluetooth device
function bluetooth_select(obj) {
var tr = $(obj).closest('tr');
var address = $(tr).find('td.bt_address').text();
var name = $(tr).find('td.bt_name').text();
$('input[name=address]').val(address);
$('input[name=description]').val(name);
}

// Page has fully loaded
$(document).ready(function() {
bluetooth_rescan();
});
</script>
<table align="center" class="table table-striped devices_list">
<tr class="table_header">
<th style="vertical-align: middle; padding-left: 15px;">Адрес устройства</th>
<th style="vertical-align: middle;">Имя устройства</th>
<th style="vertical-align: middle; padding-right: 15px; text-align: right;"><a href="#" class="btn btn-default btn-sm bt_scan_btn" title="Обновить список" onclick="return bluetooth_rescan();"><i class="glyphicon glyphicon-refresh"></i></a></th>
</tr>
</table>
<div id="bluetooth_searching" style="text-align: center; display: none;">Поиск Bluetooth устройств...</div>
<hr>
[#endif#]
<form action="?" method="post" class="form-horizontal">
<fieldset>
<div class="form-group">
Expand Down

0 comments on commit a74e34c

Please sign in to comment.