| OLD | NEW |
| 1 // Copyright 2015 The Chromium Authors. All rights reserved. | 1 // Copyright 2015 The Chromium Authors. All rights reserved. |
| 2 // Use of this source code is governed by a BSD-style license that can be | 2 // Use of this source code is governed by a BSD-style license that can be |
| 3 // found in the LICENSE file. | 3 // found in the LICENSE file. |
| 4 | 4 |
| 5 /** | 5 /** |
| 6 * @fileoverview | 6 * @fileoverview |
| 7 * 'settings-bluetooth-page' is the settings page for managing bluetooth | 7 * 'settings-bluetooth-page' is the settings page for managing bluetooth |
| 8 * properties and devices. | 8 * properties and devices. |
| 9 * | 9 * |
| 10 * Example: | 10 * Example: |
| (...skipping 14 matching lines...) Expand all Loading... |
| 25 /** | 25 /** |
| 26 * Set this to provide a fake implementation for testing. | 26 * Set this to provide a fake implementation for testing. |
| 27 * @type {BluetoothPrivate} | 27 * @type {BluetoothPrivate} |
| 28 */ | 28 */ |
| 29 bluetoothPrivateApiForTest: null, | 29 bluetoothPrivateApiForTest: null, |
| 30 }; | 30 }; |
| 31 | 31 |
| 32 Polymer({ | 32 Polymer({ |
| 33 is: 'settings-bluetooth-page', | 33 is: 'settings-bluetooth-page', |
| 34 | 34 |
| 35 behaviors: [ | 35 behaviors: [I18nBehavior, CrScrollableBehavior], |
| 36 I18nBehavior, | |
| 37 ], | |
| 38 | 36 |
| 39 properties: { | 37 properties: { |
| 40 /** Whether bluetooth is enabled. */ | 38 /** Whether bluetooth is enabled. */ |
| 41 bluetoothEnabled: { | 39 bluetoothEnabled: { |
| 42 type: Boolean, | 40 type: Boolean, |
| 43 value: false, | 41 value: false, |
| 44 observer: 'bluetoothEnabledChanged_', | 42 observer: 'bluetoothEnabledChanged_', |
| 45 }, | 43 }, |
| 46 | 44 |
| 47 /** Whether the device list is expanded. */ | 45 /** Whether the device list is expanded. */ |
| 48 deviceListExpanded: { | 46 deviceListExpanded: { |
| 49 type: Boolean, | 47 type: Boolean, |
| 50 value: false, | 48 value: false, |
| 51 }, | 49 }, |
| 52 | 50 |
| 53 /** | 51 /** |
| 54 * The cached bluetooth adapter state. | 52 * The cached bluetooth adapter state. |
| 55 * @type {!chrome.bluetooth.AdapterState|undefined} | 53 * @type {!chrome.bluetooth.AdapterState|undefined} |
| 56 */ | 54 */ |
| 57 adapterState: Object, | 55 adapterState: Object, |
| 58 | 56 |
| 59 /** | 57 /** |
| 60 * The ordered list of bluetooth devices. | 58 * The ordered list of bluetooth devices. |
| 61 * @type {!Array<!chrome.bluetooth.Device>} | 59 * @type {!Array<!chrome.bluetooth.Device>} |
| 62 */ | 60 */ |
| 63 deviceList: { | 61 deviceList: { |
| 64 type: Array, | 62 type: Array, |
| 65 value: function() { return []; }, | 63 value: function() { |
| 64 return []; |
| 65 }, |
| 66 }, | 66 }, |
| 67 | 67 |
| 68 /** | 68 /** |
| 69 * Reflects the iron-list selecteditem property. |
| 70 * @type {!chrome.bluetooth.Device} |
| 71 */ |
| 72 selectedItem: { |
| 73 type: Object, |
| 74 observer: 'selectedItemChanged_', |
| 75 }, |
| 76 |
| 77 /** |
| 69 * Set to the name of the dialog to show. This page uses a single | 78 * Set to the name of the dialog to show. This page uses a single |
| 70 * paper-dialog to host one of three dialog elements, 'addDevice', | 79 * paper-dialog to host one of three dialog elements, 'addDevice', |
| 71 * 'pairDevice', or 'connectError'. This allows a seamless transition | 80 * 'pairDevice', or 'connectError'. This allows a seamless transition |
| 72 * between dialogs. Note: This property should be set before opening the | 81 * between dialogs. Note: This property should be set before opening the |
| 73 * dialog and setting the property will not itself cause the dialog to open. | 82 * dialog and setting the property will not itself cause the dialog to open. |
| 74 */ | 83 */ |
| 75 dialogId: String, | 84 dialogId: String, |
| 76 | 85 |
| 77 /** | 86 /** |
| 78 * Current Pairing device. | 87 * Current Pairing device. |
| (...skipping 105 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 184 this.bluetoothDeviceUpdatedListener_); | 193 this.bluetoothDeviceUpdatedListener_); |
| 185 this.bluetooth.onDeviceChanged.removeListener( | 194 this.bluetooth.onDeviceChanged.removeListener( |
| 186 this.bluetoothDeviceUpdatedListener_); | 195 this.bluetoothDeviceUpdatedListener_); |
| 187 } | 196 } |
| 188 if (this.bluetoothDeviceRemovedListener_) { | 197 if (this.bluetoothDeviceRemovedListener_) { |
| 189 this.bluetooth.onDeviceRemoved.removeListener( | 198 this.bluetooth.onDeviceRemoved.removeListener( |
| 190 this.bluetoothDeviceRemovedListener_); | 199 this.bluetoothDeviceRemovedListener_); |
| 191 } | 200 } |
| 192 }, | 201 }, |
| 193 | 202 |
| 203 /** @private */ |
| 194 bluetoothEnabledChanged_: function() { | 204 bluetoothEnabledChanged_: function() { |
| 195 // When bluetooth is enabled, auto-expand the device list. | 205 // When bluetooth is enabled, auto-expand the device list. |
| 196 if (this.bluetoothEnabled) | 206 if (this.bluetoothEnabled) |
| 197 this.deviceListExpanded = true; | 207 this.deviceListExpanded = true; |
| 198 }, | 208 }, |
| 199 | 209 |
| 210 /** @private */ |
| 211 selectedItemChanged_: function() { |
| 212 if (this.selectedItem) |
| 213 this.connectDevice_(this.selectedItem); |
| 214 }, |
| 215 |
| 200 /** | 216 /** |
| 201 * @param {boolean} bluetoothEnabled | 217 * @param {boolean} bluetoothEnabled |
| 202 * @param {boolean} deviceListExpanded | 218 * @param {boolean} deviceListExpanded |
| 203 * @return {boolean} Whether the <iron-collapse> can be shown. | 219 * @return {boolean} Whether the <iron-collapse> can be shown. |
| 204 * @private | 220 * @private |
| 205 */ | 221 */ |
| 206 canShowDeviceList_: function(bluetoothEnabled, deviceListExpanded) { | 222 canShowDeviceList_: function(bluetoothEnabled, deviceListExpanded) { |
| 207 return bluetoothEnabled && deviceListExpanded; | 223 return bluetoothEnabled && deviceListExpanded; |
| 208 }, | 224 }, |
| 209 | 225 |
| 210 /** | 226 /** |
| 211 * If bluetooth is enabled, request the complete list of devices and update | 227 * If bluetooth is enabled, request the complete list of devices and update |
| 212 * |deviceList|. | 228 * |deviceList|. |
| 213 * @private | 229 * @private |
| 214 */ | 230 */ |
| 215 updateDeviceList_: function() { | 231 updateDeviceList_: function() { |
| 216 if (!this.bluetoothEnabled) { | 232 if (!this.bluetoothEnabled) { |
| 217 this.deviceList = []; | 233 this.deviceList = []; |
| 218 return; | 234 return; |
| 219 } | 235 } |
| 220 this.bluetooth.getDevices(function(devices) { | 236 this.bluetooth.getDevices(function(devices) { |
| 221 this.deviceList = devices; | 237 this.deviceList = devices; |
| 238 this.updateScrollableContents(); |
| 222 }.bind(this)); | 239 }.bind(this)); |
| 223 }, | 240 }, |
| 224 | 241 |
| 225 /** | 242 /** |
| 226 * Event called when a user action changes the bluetoothEnabled state. | 243 * Event called when a user action changes the bluetoothEnabled state. |
| 227 * @private | 244 * @private |
| 228 */ | 245 */ |
| 229 onBluetoothEnabledChange_: function() { | 246 onBluetoothEnabledChange_: function() { |
| 230 this.bluetoothPrivate.setAdapterState( | 247 this.bluetoothPrivate.setAdapterState( |
| 231 {powered: this.bluetoothEnabled}, function() { | 248 {powered: this.bluetoothEnabled}, function() { |
| (...skipping 22 matching lines...) Expand all Loading... |
| 254 * @private | 271 * @private |
| 255 */ | 272 */ |
| 256 onBluetoothDeviceUpdated_: function(device) { | 273 onBluetoothDeviceUpdated_: function(device) { |
| 257 var address = device.address; | 274 var address = device.address; |
| 258 if (this.dialogId && this.pairingDevice && | 275 if (this.dialogId && this.pairingDevice && |
| 259 this.pairingDevice.address == address) { | 276 this.pairingDevice.address == address) { |
| 260 this.pairingDevice = device; | 277 this.pairingDevice = device; |
| 261 } | 278 } |
| 262 var index = this.getDeviceIndex_(address); | 279 var index = this.getDeviceIndex_(address); |
| 263 if (index >= 0) { | 280 if (index >= 0) { |
| 264 // Use splice to update the item in order to update the dom-repeat lists. | 281 this.set('deviceList.' + index, device); |
| 265 // See https://github.com/Polymer/polymer/issues/3254. | |
| 266 this.splice('deviceList', index, 1, device); | |
| 267 return; | 282 return; |
| 268 } | 283 } |
| 269 this.push('deviceList', device); | 284 this.push('deviceList', device); |
| 270 }, | 285 }, |
| 271 | 286 |
| 272 /** | 287 /** |
| 273 * Process bluetooth.onDeviceRemoved events. | 288 * Process bluetooth.onDeviceRemoved events. |
| 274 * @param {!chrome.bluetooth.Device} device | 289 * @param {!chrome.bluetooth.Device} device |
| 275 * @private | 290 * @private |
| 276 */ | 291 */ |
| (...skipping 62 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 339 if (e.pairing == chrome.bluetoothPrivate.PairingEventType.KEYS_ENTERED && | 354 if (e.pairing == chrome.bluetoothPrivate.PairingEventType.KEYS_ENTERED && |
| 340 e.passkey === undefined && this.pairingEvent) { | 355 e.passkey === undefined && this.pairingEvent) { |
| 341 // 'keysEntered' event might not include the updated passkey so preserve | 356 // 'keysEntered' event might not include the updated passkey so preserve |
| 342 // the current one. | 357 // the current one. |
| 343 e.passkey = this.pairingEvent.passkey; | 358 e.passkey = this.pairingEvent.passkey; |
| 344 } | 359 } |
| 345 this.pairingEvent = e; | 360 this.pairingEvent = e; |
| 346 }, | 361 }, |
| 347 | 362 |
| 348 /** @private */ | 363 /** @private */ |
| 349 onAddDeviceTap_: function() { this.openDialog_('addDevice'); }, | 364 onAddDeviceTap_: function() { |
| 365 this.openDialog_('addDevice'); |
| 366 }, |
| 350 | 367 |
| 351 /** | 368 /** |
| 352 * @param {!{detail: {action: string, device: !chrome.bluetooth.Device}}} e | 369 * @param {!{detail: {action: string, device: !chrome.bluetooth.Device}}} e |
| 353 * @private | 370 * @private |
| 354 */ | 371 */ |
| 355 onDeviceEvent_: function(e) { | 372 onDeviceEvent_: function(e) { |
| 356 var action = e.detail.action; | 373 var action = e.detail.action; |
| 357 var device = e.detail.device; | 374 var device = e.detail.device; |
| 358 if (action == 'connect') | 375 if (action == 'connect') |
| 359 this.connectDevice_(device); | 376 this.connectDevice_(device); |
| (...skipping 39 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 399 return i; | 416 return i; |
| 400 } | 417 } |
| 401 return -1; | 418 return -1; |
| 402 }, | 419 }, |
| 403 | 420 |
| 404 /** | 421 /** |
| 405 * @param {!chrome.bluetooth.Device} device | 422 * @param {!chrome.bluetooth.Device} device |
| 406 * @return {string} The text to display for |device| in the device list. | 423 * @return {string} The text to display for |device| in the device list. |
| 407 * @private | 424 * @private |
| 408 */ | 425 */ |
| 409 getDeviceName_: function(device) { return device.name || device.address; }, | 426 getDeviceName_: function(device) { |
| 410 | 427 return device.name || device.address; |
| 411 /** | |
| 412 * @param {!chrome.bluetooth.Device} device | |
| 413 * @return {boolean} | |
| 414 * @private | |
| 415 */ | |
| 416 deviceIsPairedOrConnecting_: function(device) { | |
| 417 return !!device.paired || !!device.connecting; | |
| 418 }, | 428 }, |
| 419 | 429 |
| 420 /** | 430 /** |
| 431 * @return {!Array<!chrome.bluetooth.Device>} |
| 432 * @private |
| 433 */ |
| 434 getPairedOrConnecting_: function() { |
| 435 return this.deviceList.filter(function(device) { |
| 436 return !!device.paired || !!device.connecting; |
| 437 }); |
| 438 }, |
| 439 |
| 440 /** |
| 421 * @param {Object} deviceListChanges Changes to the deviceList Array. | 441 * @param {Object} deviceListChanges Changes to the deviceList Array. |
| 422 * @return {boolean} True if deviceList contains any paired devices. | 442 * @return {boolean} True if deviceList contains any paired devices. |
| 423 * @private | 443 * @private |
| 424 */ | 444 */ |
| 425 haveDevices_: function(deviceListChanges) { | 445 haveDevices_: function(deviceListChanges) { |
| 426 return this.deviceList.findIndex(function(d) { return !!d.paired; }) != -1; | 446 return this.deviceList.findIndex(function(d) { |
| 447 return !!d.paired; |
| 448 }) != -1; |
| 427 }, | 449 }, |
| 428 | 450 |
| 429 /** | 451 /** |
| 430 * @param {!chrome.bluetooth.Device} device | 452 * @param {!chrome.bluetooth.Device} device |
| 431 * @private | 453 * @private |
| 432 */ | 454 */ |
| 433 connectDevice_: function(device) { | 455 connectDevice_: function(device) { |
| 434 // If the device is not paired, show the pairing dialog. | 456 // If the device is not paired, show the pairing dialog. |
| 435 if (!device.paired) { | 457 if (!device.paired) { |
| 436 // Set the pairing device and clear any pairing event. | 458 // Set the pairing device and clear any pairing event. |
| (...skipping 64 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 501 this.updateDeviceList_(); | 523 this.updateDeviceList_(); |
| 502 }.bind(this)); | 524 }.bind(this)); |
| 503 }, | 525 }, |
| 504 | 526 |
| 505 /** | 527 /** |
| 506 * @param {string} dialogId | 528 * @param {string} dialogId |
| 507 * @param {string} dialogToShow The name of the dialog. | 529 * @param {string} dialogToShow The name of the dialog. |
| 508 * @return {boolean} | 530 * @return {boolean} |
| 509 * @private | 531 * @private |
| 510 */ | 532 */ |
| 511 dialogIsVisible_(dialogId, dialogToShow) { return dialogToShow == dialogId; }, | 533 dialogIsVisible_(dialogId, dialogToShow) { |
| 534 return dialogToShow == dialogId; |
| 535 }, |
| 512 | 536 |
| 513 /** | 537 /** |
| 514 * @param {string} dialogId | 538 * @param {string} dialogId |
| 515 * @private | 539 * @private |
| 516 */ | 540 */ |
| 517 openDialog_: function(dialogId) { | 541 openDialog_: function(dialogId) { |
| 518 if (this.dialogId) { | 542 if (this.dialogId) { |
| 519 // Dialog already opened, just update the contents. | 543 // Dialog already opened, just update the contents. |
| 520 this.dialogId = dialogId; | 544 this.dialogId = dialogId; |
| 521 return; | 545 return; |
| 522 } | 546 } |
| 523 this.dialogId = dialogId; | 547 this.dialogId = dialogId; |
| 524 // Call flush so that the dialog gets sized correctly before it is opened. | 548 // Call flush so that the dialog gets sized correctly before it is opened. |
| 525 Polymer.dom.flush(); | 549 Polymer.dom.flush(); |
| 526 var dialog = this.$$('#deviceDialog'); | 550 var dialog = this.$$('#deviceDialog'); |
| 527 dialog.open(); | 551 dialog.open(); |
| 528 this.startDiscovery_(); | 552 this.startDiscovery_(); |
| 529 }, | 553 }, |
| 530 | 554 |
| 531 /** @private */ | 555 /** @private */ |
| 532 onDialogClosed_: function() { | 556 onDialogClosed_: function() { |
| 533 this.stopDiscovery_(); | 557 this.stopDiscovery_(); |
| 534 this.dialogId = ''; | 558 this.dialogId = ''; |
| 535 this.pairingDevice = null; | 559 this.pairingDevice = null; |
| 536 this.pairingEvent = null; | 560 this.pairingEvent = null; |
| 537 }, | 561 }, |
| 538 }); | 562 }); |
| OLD | NEW |