© 2011 Appcelerator, Inc.!
TiAppCamp Alloy Overview
JAMIL HASSAN SPAIN, SOLUTIONS ARCHITECT
@JAMILSPAIN SKYPE: JAMIL.HASSAN.SPAIN
© 2011 Appcelerator, Inc.!© 2011 Appcelerator, Inc.!
Little Bit About Me
UIF-2
• Career software Engineer • From North Carolina, home of RedHat ( Big Fedora Fan ) • Started with PHP in early days 3.x or PHP F/I • Few years in Education, Cisco, open consulting market, entrepreneur to AppC in 2011
• Started career as Training Instructor for Titanium Certifications • Currently Solutions Architect for Enterprise Sales
© 2011 Appcelerator, Inc.!
Alloy Overview
UIF-3
© 2011 Appcelerator, Inc.!© 2011 Appcelerator, Inc.!
Overview & Goals
• Titanium Classic was the de facto standard • Resulted in many different implementations ( code generation ) • Projects passed had learning curves, “learn my style” ( business ) • Many community solutions popped up.. Extanium
• MVC separates form and function • Speed and simplify development • Improve maintainability
• Alloy is Appcelerator’s MVC-like framework for Titanium
UIF-4
© 2011 Appcelerator, Inc.!© 2011 Appcelerator, Inc.!
Alloy MVC Components
• Everything from Titanium Classic +
• Views • Styles • Controllers • Models • Widgets
Alloy acts as a Pre-Compiler to convert MVC output to Titanium Classic Code in Resources Folder.
UIF-5
© 2011 Appcelerator, Inc.!© 2011 Appcelerator, Inc.!
View – Index.xml
Alloy View != Ti.UI.View ( that <div> like thing). We’re talking MVC View here.
UIF-6
<Alloy> <Window class="container"> <Label id="label" onClick="doClick">Hello, World</Label> </Window> </Alloy>
© 2011 Appcelerator, Inc.!© 2011 Appcelerator, Inc.!
Styles – Fugitives.tss ".container": { backgroundColor: "white" }, "Tab" : { icon: '/images/fugitives.png', }, "Window": { backgroundColor:'transparent', backgroundImage: 'images/grain.png', title: 'Fugitives', barColor: '#6d0a0c', }, '#table' : { backgroundColor: 'transparent' }
© 2011 Appcelerator, Inc.!© 2011 Appcelerator, Inc.!
Controllers
function doClick(e) { alert($.label.text); } $.index.open();
© 2011 Appcelerator, Inc.!© 2011 Appcelerator, Inc.!
Models exports.definition = { config : { "columns" : { "name" : "string", "captured" : "integer", "url" : "string", "capturedLat" : "real", "capturedLong" : "real" }, "adapter" : { "type" : "sql", "collection_name" : "fugitives" } }, }
© 2011 Appcelerator, Inc.!© 2011 Appcelerator, Inc.!
Convention Over Configuration
File/Directory Contents & Purpose
/app/config.json Specify global values, conditional environment and operating system values, and widget dependencies.
/app/views XML View files
/app/styles TSS Style Files
/app/controllers JavaScript Controller Files
/app/models JavaScript Model Files
/app/migrations JSON files that describe incremental changes in your database, in the format DATETIME_modelname.json
/app/assets Graphic, data file, and other app assets; not created by default
/app/lib App-specific library files; not created by default.
/app/themes Theme files and assets to customize your UI; not created by default
/app/widgets Files and assets associated with widgets ( self-contained app components )
© 2011 Appcelerator, Inc.!
Controllers in Depth
UIF-11
© 2011 Appcelerator, Inc.!© 2011 Appcelerator, Inc.!
Controllers
• Contain the application logic
• Communicate between Views and Models
• Handle user interaction and dynamic UI updates
• Access components via their id attribute: $.idstring
© 2011 Appcelerator, Inc.!© 2011 Appcelerator, Inc.!
Views Without IDs
// index.xml <Alloy> <Window class="container" id="mainwin"> <Label id="label" onClick="doClick">Hello, World</Label> </Window> </Alloy> // in index.js // Window tag has an id, so $.index.open() would fail! $.mainwin.open();
// index.xml <Alloy> <Window class="container"> <Label id="label" onClick="doClick">Hello, World</Label> </Window> </Alloy>
* Controller name determines controller open() unless you assign an ID for root element ( window )
© 2011 Appcelerator, Inc.!© 2011 Appcelerator, Inc.!
Event Handling
/* listening for an event on a Ti object with id of 'button' */ $.button.addEventListener('click', function(e){ // do something }); // firing an event $.button.fireEvent('click', {foo: 'bar'}); // adding and removing an event var listener = function() { Ti.API.info("Event listener called."); } $.win.addEventListener('click', listener); $.win.removeEventListener('click', listener);
© 2011 Appcelerator, Inc.!© 2011 Appcelerator, Inc.!
Dynamically Creating Views Alloy.createController – factory method for instantiating controller Controller.getView – return the view associated with the controller Controller.#element – allows access directly to view elements
// controller file something like index.js // we're dynamically loading and showing some other view var foo = Alloy.createController('foo').getView(); foo.open(); var foo = Alloy.createController(‘foo’); foo.mainwin.open();
© 2011 Appcelerator, Inc.!© 2011 Appcelerator, Inc.!
Controllers as Factories
Using custom rows in a tableview
var rows = []; // arr is some array of data to show in a table for (var i = 0; i < arr.length; i++) { var row = Alloy.createController('CustomRow', arr[i].toJSON()).getView(); rows.push(row); } // set the table $.table.setData(rows);
© 2011 Appcelerator, Inc.!© 2011 Appcelerator, Inc.!
Passing Arguments
Pass arguments when initializing a controller
// Controller index.js var data[]; for (var i=0; i < source.length; i++) { var arg = { title: source[i].postTitle, url: source[i].postLink }; var row = Alloy.createController('row', arg).getView(); data.push(row); } $.tableView.setData(data);
// controller row.js var args = arguments[0] || {}; $.rowView.title = args.title || ''; $.rowView.url = args.url || '';
© 2011 Appcelerator, Inc.!© 2011 Appcelerator, Inc.!
Controller Communication “into”
Publish public methods for controllers
// Controller index.js var web = Alloy.createController(“index2”); web.updateWebView(‘google.com’); // Controller index2.js exports.updateWebView = function(webpage){
$.web.setUrl(webpage); }
© 2011 Appcelerator, Inc.!© 2011 Appcelerator, Inc.!
Controller Communication “outside”
Trigger Events outside controllers
// Controller index.js( index.xml ) <Require id=“bottom” onClick=“bottomBarClick” src=“index2” /> // Controller index2.js $.button.addEventListener(‘click’, function() { $.trigger(‘click’, { action: “show”,
menu: “events” });
});
© 2011 Appcelerator, Inc.!© 2011 Appcelerator, Inc.!
Controller Communication “outside”
Trigger Events outside controllers
// Controller index.js( index.xml ) <Require id=“bottom” onClick=“bottomBarClick” src=“index2” /> // Controller index2.js $.button.addEventListener(‘click’, function() { $.trigger(‘click’, { action: “show”,
menu: “events” });
});
© 2011 Appcelerator, Inc.!
Alloy Views & Styles in Detail
UIF-21
© 2011 Appcelerator, Inc.!© 2011 Appcelerator, Inc.!
View Tag Require
// view file - fugitives.xml <Alloy> <ImageView id='foo' image='foo.png'/> </Alloy> // style file – fugitives.tss "#foo": { height:Ti.UI.SIZE, width: Ti.UI.SIZE }
// From other file like TabGroup/Window <Require type="view" src="fugitives" id="fugitivetab"/>
© 2011 Appcelerator, Inc.!© 2011 Appcelerator, Inc.!
NameSpaces “View Language”
• Imagine a create with <View, <NavigationGroup • Defaults to the “Ti.UI” namespace * Create Elements not in the Ti.UI namespace:
// for objects not in Ti.UI namespace, such as Ti.Map.View: <View ns="Ti.Map" id="map"/> // for objects in sub-namespaces, such as Ti.UI.iOS.NavigationGroup: <NavigationGroup platform="ios,mobileweb"/>
© 2011 Appcelerator, Inc.!© 2011 Appcelerator, Inc.!
Style Files
• Component, class, and ID
• Global app.tss
• Constants
• i18n functions
• Alloy Globals
© 2011 Appcelerator, Inc.!© 2011 Appcelerator, Inc.!
Style Files
• Component, class, and ID
• Global app.tss
• Constants
• i18n functions
• Alloy Globals
".activeButton": { backgroundColor:"blue" }, "Button": { width: Ti.UI.SIZE, height: Ti.UI.SIZE, color: "#000" }, "#iosBtn": { color: "#999", systemButton: Titanium.UI.iPhone.SystemButton.DISCLOSURE, title: L('iosbutton'), left: Alloy.Globals.computedWidth }
© 2011 Appcelerator, Inc.!
Platform Handling
UIF-26
© 2011 Appcelerator, Inc.!© 2011 Appcelerator, Inc.!
Platform & Form Factor
• Conditional Code
• App assets
• Platform Build-time Folders
• Markup-based Techniques
• TSS-based Qualifiers
© 2011 Appcelerator, Inc.!© 2011 Appcelerator, Inc.!
Conditional Code
• OS_IOS, OS_Android, OS_MOBILEWEB • ENV_DEV, ENV_TEST, ENV_PRODUCTION
if (ENV_DEV && OS_IOS) { alert("You are running iOS in the simulator"); }
© 2011 Appcelerator, Inc.!© 2011 Appcelerator, Inc.!
Asset Folders
© 2011 Appcelerator, Inc.!© 2011 Appcelerator, Inc.!
Platform Overrides
Work for Views, styles, and controllers.. Let me explain
© 2011 Appcelerator, Inc.!© 2011 Appcelerator, Inc.!
Platform and Device Markup
<Alloy> <Window class="container"> <View formFactor="handheld"> <Label>I'm a handheld!</Label> </View> <View formFactor="tablet"> <Label>I'm a tablet!</Label> </View> <View height="50" width="200" bottom="10" backgroundColor="#cdcdcd"> <Label class="platformLbl" platform="android" formFactor="tablet">android tablet</Label> <Label class="platformLbl" platform="android" formFactor="handheld">android handset</Label> <Label class="platformLbl" platform="ios" formFactor="tablet">ios tablet</Label> <Label class="platformLbl" platform="ios" formFactor="handheld">ios handset</Label> </View> </Window> </Alloy>
© 2011 Appcelerator, Inc.!© 2011 Appcelerator, Inc.!
TSS-Based Qualifiers
"#mybutton[platform=android]" : { height:'40dp',
}, "#mybutton[platform=ios]" : {
height:50, }, "#osLabel[platform=ios formFactor=tablet]": { text: "iPad" }, "#osLabel[platform=ios formFactor=handheld]": { text: "iPhone" },
© 2011 Appcelerator, Inc.!© 2011 Appcelerator, Inc.!
Configurations
// config.json file { "global": { "foo": 1}, "env:development": {}, "env:test": {}, "env:production": {}, "os:ios": { "foo": 2 }, "os:android": {}, "dependencies": {} } // in your code alert(Alloy.CFG.foo); // value is 1 or 2 depending on OS
© 2011 Appcelerator, Inc.!© 2011 Appcelerator, Inc.!
Themes
• Named collection of styles and assets
• Applied via setting in the config.json file ( can be platform-specific )
• Theme settings override base styles and assets
• Overrides are made on an attribute by attribute basis, not whole files
© 2011 Appcelerator, Inc.!© 2011 Appcelerator, Inc.!
Themes Example
// file system structure app/ assets/ appicon.png background.png styles/ app.tss index.tss themes/ mytheme/ assets/ background.png styles/ app.tss green/ ...
// config.json { "global": { "theme":"mytheme" }, "env:development": {}, "env:test": {}, "env:production": {}, "os:ios": { "theme":"green" }, "os:android": { "theme":"blue" }, "dependencies": {} }
© 2011 Appcelerator, Inc.!© 2011 Appcelerator, Inc.!
Alloy vs. “Traditional”
• It’s not all or nothing – Ti.UI.createView() and its brethren still are valid
• API techniques used withing controllers, in helper libraries ( network, database, etc )
• Alloy is essentially a pre-compiler
• In the end, Alloy creates traditional “classic” code for you – Check out the Resources Folder!!!
© 2011 Appcelerator, Inc.!
Cool Utilities
UIF-37
© 2011 Appcelerator, Inc.!© 2011 Appcelerator, Inc.!
TiShadow
• Historically, we had to build an app and wait about 20 or so seconds for it to build.. Iterative dev process
• Community Member David Bankier created TiShadow • https://github.com/dbankier/TiShadow
• Works as a way to cache the app build process and through command line, allow you to speed your workflow.
• Involves installing NPM package, downloading Github
Package, starting the server, and running command line to build each project individually.
© 2011 Appcelerator, Inc.!© 2011 Appcelerator, Inc.!
TiShadow Install Steps
• Npm install –g tishadow
• Download git repo, import the project into Studio, build project to install on simulator. https://github.com/dbankier/TiShadow
• Start the tishadow server component. Should be
available to http://localhost:3000
• Command line to project your are working on and run:
To Start: Tishadow run ( in root of project ) After updates, run this command: alloy compile --config platform=ios && tishadow run
© 2011 Appcelerator, Inc.!© 2011 Appcelerator, Inc.!
Introducing LiveView
• Feature of our Appcelerator Studio which comes with Appcelerator Platform
• Based on TiShadow theory, allows you to rapidly prototype your application UI.
• Quick Demo of the power .. Included with Appcelerator Platform subscription
• Other Enterprise Features are here:
• http://docs.appcelerator.com/platform/latest/#!/guide/Enterprise_Features
© 2011 Appcelerator, Inc.!© 2011 Appcelerator, Inc.!
Other Enterprise Features
• App Analytics for all your applications
• Appcelerator Studio which includes LiveView, Code Analysis, and Code Profiler.
http://docs.appcelerator.com/platform/latest/#!/guide/Enterprise_Features
• More information about the Platofrm • http://www.appcelerator.com/products/
© 2011 Appcelerator, Inc.!© 2011 Appcelerator, Inc.!
Appcelerator Test
• Integrated Functional Test Automation to improve the workflow of your QA process
© 2011 Appcelerator, Inc.!© 2011 Appcelerator, Inc.!
Appcelerator Performance Management
• Captures data in real-time to provide actionable information about user, device and application problems
© 2011 Appcelerator, Inc.!
Thank you JAMIL HASSAN SPAIN @JAMILSPAIN SKYPE: JAMIL.HASSAN.SPAIN [email protected]