Typescript and polymer and a few issues I seen

703 views
Skip to first unread message

silverdr...@gmail.com

unread,
Feb 2, 2015, 2:31:37 PM2/2/15
to polym...@googlegroups.com
HI all

Love the polymer code. I have been using Polymer and typescript in my latest project and it has been working very well, nice looking app is forming up and work in all the main browsers ie 10,11, firefox, Chrome, etc. Still have tweaking work to get it to work better on window phone 8.1, android, and iphone, but it looks better than I thought it would with almost no effort

So first a few quirks I have seen. First one is that the core-animation only works in chrome, firefox and ie have issues about a play member not defined and some warning about a playbackrate is going away. I assume this is just out of sync with the latest webanimation updates

one is with re-sizeing in a component. Honestly I wish the web community would just add the silly resize event to a element and move on, vs all this hackery. Anyway I use the Polymer.CoreResizable mixing. It seems to work except for when the element is hidden and shown. Maybe I am doing something wrong, but I hide and show via style.display style. I am not getting the core-resize event in this case. other than that it works fine and is a great help.

Along with that i was trying to find a way to get this work and i was trying out different idea's. I found that i could add a function:

clientWidthChanged(oldval) {}

and this worked great in IE and firefox. The event when off perfectly at the correct points in time, and happened only once. It worked with hiding and showing or having some parent element getting a new size. However this did nothing in chrome. Just an observation, as this would be a great and simple way to solve the problem in my view that is a little simpler that the mixin way.

Last of all I wanted to post my ugly, incomplete but mostly there solutions to getting typescript to work in case others wanted to use it and maybe have someone make it better, extra...

to do this I have two files one to deal with basic Polymer definitions and one to deal with creating a typescript class. I should point out that Polymer does not work on a class based design, but one of behaviors. This is not a big deal, but leads to what looks like a little extra work from a purely classed based point of view. Also I should add that typescript is still working on dealing with the idea of mixins better, so you will see some hacks i have to deal with the re-sizing mixins I used as there has to be some definition for them. (This could be solved some other ways.. again i was hacking a little to get it working) 

First the main polymer.d.ts file as it is at the moment ( again could be done better, probably has bugs, but the API was sort of a self-discovery at time as documentation is changing, and i am not a polymer developer )
///////////
declare module Polymer {

    export interface PolymerOptions {

        // definition
        publish?: Object;
        computed?: Object;
        // object mapping variable names to functions name
        observe?: Object;

        // life time API
        created?: () => void;
        ready?: () => void;
        attached?: () => void;
        domReady?: () => void;
        detached?: () => void;
        attributeChanged?: (attrName: string, oldVal: any, newVal: any) => void;

    }

}

//declare class Polymer {
interface Polymer {

    importElements(node: Node, callback: Function);
    import(url: string, callback?: () => void): void;

    mixin(target: any, ...obj1): any;
    waitingFor(): Array<string>;
    // should be an "integer" for milliseconds
    forceReady(timeout: number): void;

    (tag_name: string, prototype: Polymer.PolymerOptions): void;
    (tag_name: string, prototype: any): void;
    (prototype: Polymer.PolymerOptions): void;
    (): void;
// hacks for mixins
    CoreResizer: any;
    CoreResizable: any;
}

declare var Polymer: Polymer;


// these are for web-animation API... should be moved to own file


declare class Animation {
    constructor(targetElement: HTMLElement, effect: any, options: any);
}

declare module document {
    export interface timeline {
         play(animation);
    }
}
/////////////////

Then the PolymerTS.ts file which i what I used to get a typescript class to work. The Adapter function allows mixing and class to be defined correctly. Might be better ways to do this, but I not java script language expert

///////////////////
/// <reference path="Polymer.d.ts" />

    export function contains(obj: any, arr: Array<any>) {
        for (var i = 0; i < arr.length; i++)
        {
            if (arr[i] === obj) {
                return true;
            }
        }
        return false
    }

module PolymerTS {

    export class PolymerBase implements Polymer.PolymerOptions {

        $: any; //polymer object for elements that have an ID
        $el: HTMLElement; // my addition to have easy "typed" point to this as HTMLElements

        Constructor() {}

        ready() {
            //console.log("Base ready");
            this.$el = <any>this;
            this.Constructor();
        }

        ////////////////////////
        // for built in stuff to Polymer

        // inargs is the [args] for the callback.. need to update function def
        async(inMethod: () => void, inArgs?: Array<any>, inTimeout?: number) { }
        job(jobName: string, inMethod: () => void, inTimeout?: number) { }
        fire(eventName: string, details?:any, targetNode?:any, bubbles?:boolean, cancelable?:boolean) { }
        asyncFire(eventName: string, details?: any, targetNode?: any, bubbles?: boolean, cancelable?: boolean) { }

        cancelUnbindAll() { }

        // these are mix in API's.. hacky way to deal with them at the moment.
        resizableAttachedHandler;
        resizableDetachedHandler;

    }

    function applyMixins(obj: any, mixins: any[]) {
        mixins.forEach(mixin => {
            for (var i in mixin) {
                if (mixin.hasOwnProperty(i)) {
                    obj.prototype[i] = mixin[i];
                }
            }
        });
        
    }
        
    //  this allows polymer to work correctly
    export function Adapter(t: any, ...mixins) {
        var ret = {};
        var poly_func = ["async", "job", "fire", "asyncFire",
            "cancelUnbindAll"];    
        if (mixins) {
            applyMixins(t, mixins);
        }
        var o = new t();
        for (var i in o) {
            if (!contains(i, poly_func))
                ret[i] = o[i];
        }
        
        return ret;
    }
}
//////////////////
 oh and the component file polymer.html

/////
<link rel="import" href="../../components/polymer/polymer.html">
<script src="PolymerTS.js"></script>
////


Again it is a start an has been enough for me to do some work i needed to do rather quickly.

A quick example of how this would look like.. a simple component...

// component html file

<link rel="import" href="../polymerTS/polymerTS.html" />

<polymer-element name="my-test">
    <template>
        <style>
        </style>
        <p>{{someValue}}</p>
        <content select="p"></content>
        <content></content>
    </template>

    <script src="my-test.js"></script>
</polymer-element>
/////

The typescript file...

/////////////

class MyTest extends PolymerTS.PolymerBase {

    someValue: string;

    get publish() {
        return {
           someValue:"default value"
        }
    }

    // replaces the normal constructor() call
    Constructor() {
        
    }

    joe() {
        return "joe";
    }
}

Polymer("my-test", PolymerTS.Adapter(MyTest));

////////////

Very simple example ( more of a starter template). 

A few notes on this. I added a $el to access "this" as an HtmlElement type. This way you don't have to try to cast "this" manually. This also prevent the need to try to deal with the issue with not being able to inherit from HtmlElement in the current typescript drops. Maybe this will be fixed in a future drop and the object can extend from this type correctly in the typescript sense.

I hope this is helpful. Love Polymer, look forward to improvements. It is really a system i see that can be used by teams of people making complex webs apps.



louis....@gmail.com

unread,
Feb 25, 2015, 9:20:35 AM2/25/15
to polym...@googlegroups.com, silverdr...@gmail.com
Hi,

  Nice work.

  why don't you post it on the official github for TS definition files ? 


  Regards.
Reply all
Reply to author
Forward
0 new messages