Categories
Android Source Code

Hello Moto 360 from Delphi XE7

Moto 360I really like my Moto 360 watch. It looks fabulous, and does great as an extension of my Android phone, but of course the most important question is how to make an app for it. Turns out it just works with RAD Studio X7, Delphi or C++. Thanks to the new FireUI Multi-Device designer I can actually create a custom view in the UI to make designing the perfect user interface a breeze. Here are some of the details of what I discovered along the way, followed by a download of my sample and the custom view.

The bottom line is it just works, which really isn’t a surprise. Most new Android devices use ARMv7 and the NEON instruction set. (NEON is kind of like the MMX standard on the Intel platform. At first not everyone used those instructions, but once they caught on, everyone did.) So it is no surprise that the Moto 360 does too. Unlike some of the other watches, the Moto 360 does not have a micro USB port. So you have to use ADB over BlueTooth. This requires a few extra steps to setup, and is really slow to deploy over. So slow I canceled the first two deployments because I thought I set something up wrong.

First of all, the Moto 360 display is not perfectly round. It has a flat area on the bottom. If you look closely you can see the light sensor there. Not sure if that was why it wasn’t round, or if there was another design reason. In any case, the screen resolution is 320 x 290 pixels at 213 Pixels Per Inch. This means at design time you have a usable area of 240 x 218 pixels. This is the information we need to create a custom view. Just put the following code in a package.

  TDeviceinfo.AddDevice(TDeviceinfo.TDeviceClass.Tablet, ViewName,
    // The Moto360 is 320x290 phyiscal and 240x218 logical with 213 PPI
    TSize.Create(320, 290), TSize.Create(240, 218),
    TOSVersion.TPlatform.pfAndroid, 213,
    True); // Exclusive

The Device class enumeration actually has a Watch class, but looking in the code that detects the class at runtime and it doesn’t know how to detect a watch yet. So it defaults to Tablet. It makes sense if you think about the fact that XE7 was released before the Moto 360. I imagine an update will address this.

The requirement to get the custom view to show up in the IDE is you need to update the XML file found at %AppData%\Roaming\Embarcadero\BDS\15.0\MobileDevices.xml to reference the new view. Inside the MobileDevices element, add the following:

  <MobileDevice>
    <Displayname>Moto360</Displayname>
    <Name>Moto360</Name>
    <DevicePlatform>3</DevicePlatform>
    <FormFactor>2</FormFactor>
    <Portrait Enabled="True" Width="240" Height="218" Top="102" Left="29" StatusbarHeight="0" StatusBarPos="0" Artwork="C:\Users\jim\Documents\Embarcadero\Studio\Projects\HelloMoto360\Moto360.png" />
    <UpsideDown Enabled="False" Width="240" Height="218" Top="0" Left="0" StatusbarHeight="0" StatusBarPos="0" Artwork="" />
    <LandscapeLeft Enabled="False" Width="240" Height="218" Top="0" Left="0" StatusbarHeight="0" StatusBarPos="0" Artwork="" />
    <LandscapeRight Enabled="False" Width="240" Height="218" Top="0" Left="0" StatusbarHeight="0" StatusBarPos="0" Artwork="" />
  </MobileDevice>

You’ll need to update the path to that Artwork to point to the correct location of the PNG on your system. Or you can just leave it blank. Here is what it all looks like when setup in the IDE.

Hello Moto 360 in the XE7 IDE

You’ll notice a red circle on the design surface. I added this to see where the corners are (since the display is round). At runtime you can just barely see the red if you hold the watch right. In production I’d hide this at runtime. I placed the TCircle at -1, -1 and set the size to 242 x 242. This way the circle follows the bezel and not the display area of the screen. I suppose if I bumped it out another pixel it would disappear completely at runtime.

To get the Moto 360 to show up as a target device you first need to enable Bluetooth debugging.

  1. Hold the side button in until Settings appears
  2. Swipe down to About and tap it.
  3. Tap on build number until it tells you that you are a developer.
  4. Swipe back to settings and then tap on Developer options.
  5. Tap on ADB Debugging until it says Enabled.
  6. Tap on Debug over Bluetooth until it says Enabled.
  7. On your paired phone, go into Android Wear settings (gears in the upper right)
  8. Enable Debugging over Bluetooth.
    1. It should show
      • Host: disconnected
      • Target: connected
    2. Target is the watch, Host is your computer.

Then you connect your phone that is connected to the Moto 360 via USB and run the following commands (assuming ADB is on your system path) to connect via Bluetooth. I made a batch file.

 @echo off
 REM optional cleaning up
 adb disconnect localhost:4444
 adb -d forward --remove-all
 REM this is the connection
 adb -d forward tcp:4444 localabstract:/adb-hub
 adb -d connect localhost:4444
 REM these lines are to see if it worked
 echo Here is the forwarded ports . . . .
 adb forward --list
 echo.
 echo Wait a second for it to connect . . . .
 pause
 adb devices

The ADB Devices list should show something like

List of devices attached 
123456abcd device 
localhost:4444 device

Now the Android Wear app on your phone should show

  • Host: connected
  • Target: connected

Be sure that your Moto 360 app uses the unit that defines the Moto 360 device (from your package). This way your app can select it at runtime. If you do all that, you’ll see something similar to this with it running on the Moto 360:

Hello Moto 360 from Delphi XE7

My camera had a hard time focusing on it, but rest assured it looks fabulous! I tried C++ too, and no surprises, it works as well. More experimenting to do, but it is nice to know I have a tool that will take me everywhere I want to go.

If you don’t have a Moto 360, you can setup an Android emulator (AVD) instead. I did that before mine showed up. You need to download the Android 4.4W (API20) SDK Platform and ARM System image.

Android Wear SDK Download

Then create an AVD with the new Emulator.

Android Wear AVD Settings

It actually gives you the rectangle screen with a round bezel. Also it is 320 x 320 (so completely round) and 240 PPI. This means the view I created (since it was exclusive) won’t work on the emulator. You’ll need to create a new custom view for the emulator, but I’ll leave that up to to.

you can download all of my code for the custom view, Bluetooth ADB batch file, and sample apps from Github. (Update: Added a view for Galaxy Gear Live & LG-G) BTW, XE7 adds local Git support, which is another great new feature. Download the trial and check it out.

39 replies on “Hello Moto 360 from Delphi XE7”

[…] Jim McKeeth walks thru Moto 360 support for Delphi XE7. Jim is using XE7’s new FireUI and the new Moto 360 circular FireUI view (available soon as a free XE7 download) to build and deploy a native Moto 360 app to the watch. Demos for C++ and Appmethod also soon. Developers without access to a Moto 360 can deploy/debug to the Android Wear round face emulator. Note: the Android emulator requires high performance PC and host GPU turned off. […]

This is fantastic ! And a very small code to define a new device. Wish: A new tag in xml could do a (wish too:) Canvas.ClipPath.

[…] You can also create and add new views to the View Selector in the Form Designer if the available views do not cover the specifications of your target device. Usually, that is not necessary, but if you want to fine-tune the layout for a specific device (i.e. your company has standardized on Nexus 5), creating a custom view will allow you to further customize your UI. This is also a great way to add views for new wearable form factors such as various watches that you may want to target, like the Moto 360, which Jim McKeeth recently covered. […]

[…] You can also create and add new views to the View Selector in the Form Designer if the available views do not cover the specifications of your target device. Usually, that is not necessary, but if you want to fine-tune the layout for a specific device (i.e. your company has standardized on Nexus 5), creating a custom view will allow you to further customize your UI. This is also a great way to add views for new wearable form factors such as various watches that you may want to target, like the Moto 360, which Jim McKeeth recently covered. […]

I tried it and it worked really nice, but….I tried to get info with idHTTP from a server and present it on the moto360…but no results 🙁

In the simulator it works, but in realtime I get an error.

Does anybody have a solution?

I believe the Moto 360 doesn’t actually have network. It doesn’t have WiFi. Just a bluetooth connection to your phone. You would need to marshal the communication through the phone.

I though it would be managed in the andriod wear OS and the network is bluetooth. For the pebble I know that there is different construction, done by the program on the phone and the pebble.
Pitty, if you can not communicate to the outside world … you don’t have any advantage to use delphi.

Not sure in what context you are wanting to display chinese characters. I’m sure there are at least some situations where it can display chinese characters, but not sure if it does in all situations.

Hi Jim,
Thanks for the code.
How do you define the logical size? What is the calculation. You say “This means at design time you have a usable area of 240 x 218 pixels”. Where do those numbers come from? Any math to do? Any way to define this?
I have my own custom view but it has nothing to do with the real device, it’s way too big compared to the device, even though the numbers for the physical device are fine, but the logical ones? Also, Android devices have several densities, I guess this also impacts everything.

What happens when you run it on your Samsung watch? Do you get an error? Are you able to connect? What troubleshooting steps have you taken?

Hi Jim. I’ve followed your instructions for XE7 and XE8, including edited the MobileDevices.xml (XE7) and DevicePresets.xml (XE8), closed and re-run the IDE and yet the Moto360 isn’t appearing under the View list in the FireUI designer. When I load your demo project for Moto360, the IDE crashes because it can’t find that preset. I’ve installed the package with the AddDevice code in… I wonder if I’m missing something?

I don’t have a MobileDevices anymore in XE8, but I added the lines in DevicePresets and it works.
Did you create and install the PKG file as well?

I just played with XE8 and my LG Watch R (which is supposedly not NEON compatible… )
Works like a charm. Have to adjust the screen but it proves it’s working.
Screenshot https://db.tt/ZhAUIfH4

Hi Jim,

How do you figure out the logical resolution? I want to develop an application for my G Watch R, and I’m unsure how and can’t find anything.

Thanks,
Xander

Hi Jim,

I just got a Sony Smartwatch 3 and tried a simple hello world app using Delphi 10 Seattle. I configured the watch and managed to run my app from the debugger. Trouble is when I close the app it doesn’t appear in the App Menu. The only way I can get the app to run is via Delphi.

What am I doing wrong?

Thanks

Simon

For anyone having a similar problem it turned out the watch wasn’t updating properly when linked to iOS. Once connected to an Android phone it did all the updates and is now working as expected.

The latest Android Wear includes Wifi which means it doesn’t have to be permanently connected to your phone.

Has anyone managed to get setAmbientEnabled() working with Delphi? I can’t find any way to use this feature.

Thanks

Simon

[…] You can also create and add new views to the View Selector in the Form Designer if the available views do not cover the specifications of your target device. Usually, that is not necessary, but if you want to fine-tune the layout for a specific device (i.e. your company has standardized on Nexus 5), creating a custom view will allow you to further customize your UI. This is also a great way to add views for new wearable form factors such as various watches that you may want to target, like the Moto 360, which Jim McKeeth recently covered. […]

Comments are closed.