Skip to content

Commit

Permalink
Merge dab36cb into 6b9a0ac
Browse files Browse the repository at this point in the history
  • Loading branch information
m1n3rva committed Mar 26, 2018
2 parents 6b9a0ac + dab36cb commit eb25b09
Show file tree
Hide file tree
Showing 4 changed files with 55 additions and 1 deletion.
4 changes: 3 additions & 1 deletion .gitignore
Original file line number Diff line number Diff line change
Expand Up @@ -9,4 +9,6 @@ __pycache__
.vscode
vehicle_fingerprint
docs/build/
.cache/
.cache/
image.png
venv/
1 change: 1 addition & 0 deletions bimmer_connected/const.py
Original file line number Diff line number Diff line change
Expand Up @@ -17,3 +17,4 @@
VEHICLE_STATUS_URL = VEHICLE_VIN_URL + '/status'
REMOTE_SERVICE_STATUS_URL = VEHICLE_VIN_URL + '/serviceExecutionStatus?serviceType={service_type}'
REMOTE_SERVICE_URL = VEHICLE_VIN_URL + "/executeService"
VEHICLE_IMAGE_URL = VEHICLE_VIN_URL + "/image?width={width}&height={height}&view={view}"
34 changes: 34 additions & 0 deletions bimmer_connected/vehicle.py
Original file line number Diff line number Diff line change
Expand Up @@ -5,6 +5,7 @@

from bimmer_connected.state import VehicleState
from bimmer_connected.remote_services import RemoteServices
from bimmer_connected.const import VEHICLE_IMAGE_URL

_LOGGER = logging.getLogger(__name__)

Expand All @@ -24,6 +25,21 @@ class DriveTrainType(Enum):
HV_BATTERY_DRIVE_TRAINS = {DriveTrainType.PHEV, DriveTrainType.BEV, DriveTrainType.BEV_REX}


class VehicleViewDirection(Enum):
"""Viewing angles for the vehicle.
This is used to get a rendered image of the vehicle.
"""
FRONTSIDE = 'FRONTSIDE'
FRONT = 'FRONT'
REARSIDE = 'REARSIDE'
REAR = 'REAR'
SIDE = 'SIDE'
DASHBOARD = 'DASHBOARD'
DRIVERDOOR = 'DRIVERDOOR'
REARBIRDSEYE = 'REARBIRDSEYE'


class ConnectedDriveVehicle(object):
"""Models state and remote services of one vehicle.
Expand Down Expand Up @@ -84,6 +100,24 @@ def drive_train_attributes(self) -> List[str]:
result += ['remaining_range_electric', 'remaining_range_fuel']
return result

def get_vehicle_image(self, width: int, height: int, direction: VehicleViewDirection) -> bytes:
"""Get a rendered image of the vehicle.
:returns bytes containing the image in PNG format.
"""
url = VEHICLE_IMAGE_URL.format(
vin=self.vin,
server=self._account.server_url,
width=width,
height=height,
view=direction.value,
)
header = self._account.request_header
# the accept field of the header needs to be updated as we want a png not the usual JSON
header['accept'] = 'image/png'
response = self._account.send_request(url, headers=header)
return response.content

def __getattr__(self, item):
"""In the first version: just get the attributes from the dict.
Expand Down
17 changes: 17 additions & 0 deletions bimmerconnected
Original file line number Diff line number Diff line change
Expand Up @@ -8,6 +8,7 @@ import os
import time
from bimmer_connected.account import ConnectedDriveAccount
from bimmer_connected.country_selector import get_region_from_name, valid_regions
from bimmer_connected.vehicle import VehicleViewDirection

FINGERPRINT_DIR = os.path.join(os.path.dirname(os.path.abspath(__file__)),
'vehicle_fingerprint')
Expand All @@ -34,6 +35,11 @@ def main() -> None:
flash_parser.add_argument('vin', help='vehicle identification number')
flash_parser.set_defaults(func=light_flash)

image_parser = subparsers.add_parser('image', description='flash the vehicle lights')
_add_default_arguments(image_parser)
image_parser.add_argument('vin', help='vehicle identification number')
image_parser.set_defaults(func=image)

args = parser.parse_args()
args.func(args)

Expand Down Expand Up @@ -78,6 +84,17 @@ def light_flash(args) -> None:
print(status.state)


def image(args) -> None:
"""Trigger the vehicle to flash its lights."""
account = ConnectedDriveAccount(args.username, args.password, get_region_from_name(args.region))
vehicle = account.get_vehicle(args.vin)

with open('image.png', 'wb') as output_file:
image_data = vehicle.get_vehicle_image(400, 400, VehicleViewDirection.FRONT)
output_file.write(image_data)
print('vehicle image saved to image.png')


def _add_default_arguments(status_parser: argparse.ArgumentParser):
"""Add the default arguments username, password, region to the parser."""
status_parser.add_argument('username', help='Connected Drive user name')
Expand Down

0 comments on commit eb25b09

Please sign in to comment.