Sunday, June 11, 2017

OpenLayers 4 + ES2015 Modules + TypeScript

I've just recently upgraded to Angular 4 from version 2. It was pretty straight forward and easy. Nothing really to talk about there, except maybe that I had to now include the animation modules separately.

What's really challenging was upgrading to OpenLayers 4 and using the ES2015 module version of it (https://www.npmjs.com/package/ol)... in TypeScript!

Here's a quick summary:

Biggest lesson was a reminder that TypeScript is a strict superset of ES2015.

I was able to simply use the OL4 Modules as is, but, I have to admit, I stumbled a lot.  First I installed the ol package from npm:
npm install ol@4.1.1 --save
Easy enough. Then I tried using it like I do with all the other Angular stuff:
import { Map } from 'ol/map';
What!? Why does this not work?! Remember, I'm still new at ES2015...

So yes, the first problem was that OL was not exporting named members, only one default member. So removing those curly braces fixed that issue, but took me way too long to get there in the first place :(

Hopefully, this alone will help save someone else's precious time.  More than likely, I'm probably the only dumbass in the world that didn't realize this.

This will work with Webpack and Angular CLI out of the box.

If you want typing to work (which, of course, you do... who wouldn't when you're working in TypeScript?), you're gonna need to do a bit more.  DefinitelyTyped only has the definition for OpenLayers 3 as of this writing.  They may have version 4 now by the time you read this, so check with them first.

In the meantime, I used @jumpinjackie auto-generated OpenLayers 4 typings he used for one of his projects.  This part also took me forever since I didn't really understand how to use custom typings.  I ended up installing "typings" and installed a local custom typing:
typings install file:custom_typings/ol.d.ts --save --global
Note the special "file:" protocol.  I've also put my custom typing for this in my "custom_typings" directory.  Seems, though, that I had to exclude this directory in my tsconfig.json file, otherwise I was getting duplicate definition errors.

Another snag I hit was that I was using things like ol.interaction.Select.Event, which is a public class, by the way.  These were not its own module and there were no typings definition for it.  I had to create my own "extended" typing file for these.  I was able to open up ol module again and extend like such:

Sunday, February 12, 2017

Empty Promises: From Promise to Deferred

The JavaScript Deferred pattern is well documented and used a lot. You've probably even used a jQuery's implementation before.

I needed this "empty promise" pattern for this project and didn't want to be coupled to jQuery anymore than I am by using Bootstrap.

Here's the implementation in TypeScript as an extra layer on Promise:
I have deployed this in various places throughout this project, but one particular example is when a component needs the Selector object (to get selection count, for example). The component initialization is obviously asynchronous. Initializing the Selector object is also done asynchronously and the promise would be better resolved elsewhere. So in the meantime, I would return an "empty promise" to the component requesting the Selector object.