Notes on Ext JS - The Risberg Family

nutritionistcornInternet and Web Development

Dec 14, 2013 (3 years and 8 months ago)

103 views

Page
1

of
22

Notes on
Ext JS

Created

03/1
5/10

Updated 06/11
/10
,
Updated 09/12/10
,
Updated 10/11/10
, Updated 02/01/11
,
Updated 02/15/11
, Updated 03/12/11

Updated 05/26/11
,
Updated 02/01/12,
Updated 03/31/12
, Updated 04/13
/12
, Updated 04/19
/12
, Updated 04/27
/12

Updated
0
5/04/12
, Updated 06/24/12
, Updated 09/22/12
, Updated 10/02/13

Introduction

Ext JS is a cross
-
browser JavaScript library
from Sencha
(based in Palo Alto)
for building rich internet
applications.

Build rich, sustainable web applications faster than ever.

I
t includes:



High performance, customizable UI widgets



Well designed and extensible Component model



An intuitive, easy to use
API



Commercial

and
Open Source

licenses available


The current public version

is 4.2.2

released
in
early

2
013
. The download size i
s about 4
0MB, as it contains
several copies of the framework, plus
documentation and examples.

The 4.0.x version has a new MVC model, and
a number of added and renamed object classes.

It also has a theming system.


Ext JS supports all major web browsers
including:



Internet Explorer 6+



FireFox 1.5+ (PC, Mac)



Safari 3+



Chrome 3+



Opera 9+ (PC, Mac)


The license terms are on based on th
e principle of
Quid Pro Quo

-

"something for something".

In return for the
advantages you realize from using a Sencha produc
t to create your application, we require that you do
one of the
following
:



Contribute to the continued development of the product by purchasing commercial licenses from Sencha.
This option secures you the right to distribute your application under the lice
nse terms of your choice.



Contribute to the Open Source community by placing your application under an Open Source license (e.g.
GPL v3).

This option secures all users the rights to obtain the application's full source code, modify it,
and redistribute i
t.


The commercial license
comes out to $595 per developer, or $1000 per develop
er with support and the Ext
Builder.

Related Products

Sencha Touch: the f
irst HTML5 Mobile App Framework
.
Sencha Touch allows you to develop web apps that
look and feel nati
ve on Apple iOS and Google Android touchscreen devices.

Resources

Primary source is the online documentation, much of which is also provided in the download. See
http://sencha.com/learn


There was a presentation by

Ted Patrick of Sencha at a
Meetup in Santa Clara on April 5, 2012
. Contact
ted@sencha.com

But I haven’t found his slides yet.


“Ext JS in Action, Second Edition” by Jesus Garcia. Manning Press, expected August 201
2.

Updated to Ext JS
version 4.


Page
2

of
22

“Sench
a

Touch in Action”

by
Jesus Garcia, Anthony De Moss, and Mitchell Simoens.

Manning Press, expected
June
to August
2012.

MEAP started already.


“Ext JS 4 First Look” by Loiane Groner. Packt Press, January 2012, 340

pages. List price $44.99, Amazon price
$43.59, used from $42.19. Rated 4 stars on Amazon.com.

Reviews were mixed as comments indicated that it was
poorly edited.


“Ext JS in Action” by Jesus Garcia. Manning Press, November 2010, 496 pages. List price

$49.99, Amazon price
$3
1.49, used from $27.26. Rated 4

star
s on Amazon.com
. We bought this in early February 2011.

While well
-
written, and the only book about the framework, i
t is about Ext JS version 3, not the current version 4.


“Practical Ext JS Pr
ojects with Gears”,
APress,
July 2009.


“Learning Ext JS”, November 2008.

Concepts

Like the combination of jQuery and jQueryUI, Ext JS is a JavaScript library with a foundation that handles
component classing and event management, and then contains the ind
ustry’s largest widget set, where the widgets
are quite similar to the traditional desktop application components. Ext JS goes several steps beyond
jQuery/jQueryUI, however, in that the visual layout and appearance of the component is handled by the libra
ry,
meaning that most of your application file is JavaScript that creates the Ext JS components which in turn create the
HTML, while jQueryUI is mostly providing behavior that gets added onto HTML that you write.


Within the library are
components for data

display and data forms, with the most advanced being a data grid. In
many cases, the approach used to populating data into the grid is to have the client make Ajax calls to fetch
content. This means that the organization of the application tends to be a

set of small handlers, rather than a large
method that generates all data and then forwards to the view. Such an organization is also helpful toward
supporting web services API access to the content, since most access
-
oriented web services are similar to

fetching
information for a grid.


There is a strong MVC model within Ext JS. In fact, you create classes called Controllers, while classes called
Stores and Models act as the model.

This is an improvement over Ext JS 3.

Class System

All of Ext JS

(and S
encha Touch)

is built around a class management system, supporting:


Packages, Inheritance,
Scope


The methods are Ext.define(‘class_name’, {}) and Ext.create(‘class_name’, {})

The latter is like new().


Uses Framework files and JavaScript files.


Ext.de
fine(‘Animal’, {


config: { name: null },


constructor: function( config ) {


this.initConfig( config );


}

});


Ext.define(“Human”, {


extend: ‘Animal’,


speak: function () {


console.log( this.getName() ) ;


}

})
;

Page
3

of
22

MVC

Built around a standard code organization (app.js, controller, model, view). app.js organizes all of the classes and
bootstraps everything.

For instance, it causes the views and controllers to be loaded (which in turn load the
models).


Using app.j
s provides a c
onsiste
nt way to build the application, including all of the init phases.

Standard Library

Ext JS and Sencha contain a set of standard classes, almost like the

NS


classes that are at the base of the iOS and
Objective
-
C framework. These cla
sses include:


Native classes (
array
, Boolean,
number, date, function, string, etc.
)

Utility

classes

Event management classes

(Ext.TaskManager, Ext.EventObject, etc.)

xtype

Declarative model for building out components.


For instance, the items array of co
ntainers is set up to build out anything that has xtype defined. xtype is
associated with a particular class and invokes the corresponding constructor.


Loadable format: JSON of sorts, allow for sending application components over the wire.

xtemplate

Ren
der HTML from a template.

Use HTML for fine
-
grain design, within components that allow you to frame it in.

View Elements

These are the traditional elements of any visual fra
mework. Ext JS has quite a few, including
Labels, Buttons


Container
-
based element
s such as Panels, along with Drop
-
downs and Menus. Also Forms and all of the typical
Form elements.


A set of
Data Grid

classes for data display, including sorting and pagination.

Model Elements

You define “models” which are like class definitions.

Model
s can inherit from other models.

Stores

You define “stores” which are holders of content.

These can be static holders, or ones which dynamically fetch
content.

Controllers

In Ext JS 4, there is an MVC model, which means that view initialization only carry

out view set up (including the
components of the view), and scripting and event handling should only be located in Controllers.


Controllers are specified in the main application class, and will be created after the views have been made.

What can you do i
n a Controller?



A
ssociate an event with a handler name



I
mplement that handler as a method in the controller class

Page
4

of
22



I
nherit from other controller classes



D
efine references, which are selectors that are auto
-
resolved by the controller infrastructure



I
mplement

utility code

Events

Ext JS contains its own event system, which is similar to the JavaScript event system or the jQuery event system.
The event system is platform
-
neutral.


Supports Touch Events as well.

Theming

There is a full theming system in Ext JS 4
.

Tooling

They are working on Sencha Designer. Will be out soon. Is this the same as Ext JS Designer?
It l
ooks much the
same.
It is a
lso similar to Interface Builder.

Theming

Deployment

Sencha Touch a
lso supports native API’s on the iOS platform, such
as accessing the camera or the accelerometer.


There is a packaging system that helps you in finding the minimum set of component classes that need to be
deployed for an application.

Structure of an Application

Ext JS defines all of the elements of an appl
ication, and has a preferred organization of the files
.

Page
5

of
22



In Ext JS 3, the Ext.onReady method was the entry point into your application, and the developer had to come up
with an application architecture.

In
Ext JS 4, there is
an MVC
-
like pattern.

This p
attern helps you to follow best
practices when creating your applications.


The entry point into an application written with the new MVC package requires that you use the
Ext.application

method.


This method will create an
Ext.app.Application

instance for

you and will fire
the
launch

method as soon as the page is ready.


This essentially replaces the need to use
Ext.onReady

while
adding new functionality such as automatically creating a viewport

and setting up your namespace.

Example App

First, write the m
inimal HTML file with a blank body.


senche
-
touch.css

sencha
-
touch.js

myapp.js


Things get interesting in the myapp.js file:


Ext.application(


launch: function() {


Ext.create( ‘Ext.panel’, etc.)


});

}

U
I Components

There are two primary classes:

Component and Container. From these the toolkit provides b
uttons, forms, lists,
etc.


You can skin these classes

to change their visual appearance.

Page
6

of
22


E
xt JS and Touch ship with a wide range
of Containers

and the Layout classes for the containers. You ca
n have
P
anels or
a C
ontainer object loading other UI elements.


To generate a phone
-
like look and feel,
s
crollers have been well opti
mized, almost like native apps.

Controllers

Controllers are the glue that binds an application together. All they really d
o is listen for events (usually from
views) and take some action. Here's how we might create a Controller to manage Users:

Ext
.
define
(
'MyApp.controller.Users'
,

{


extend
:

'
Ext.app.Controller
'
,



init
:

function
()

{


console
.
log
(
'Initialized Users! This happens before the Application launch function is
called'
);


}

});

The init fu
nction is a special method that is called when your application boots. It is called before the
Application
's
launch function is executed so gives a hook point to run any co
de before your Viewport is created.


The init function of a
superclass

will be called before th
e init function of a given class. This allows you to extend
the behavior of a given superclass controller.


The init function is a great place to set up how you
r controller interacts with the view, and is usually used in
conjunction with another Controller function
-

control
. The control function makes it easy to li
sten to events on
your view classes and take some action with a handler function. Let's update our Users controller to tell us when
the panel is rendered:

Ext
.
define
(
'MyApp.
controller.Users'
,

{


extend
:

'
Ext.app.Controller
'
,



init
:

function
()

{


this
.
control
({


'viewport > panel'
:

{


render
:

this
.
onPanelR
endered


}


});


},



onPanelRendered
:

function
()

{


console
.
log
(
'The panel was rendered'
);


}

});

We've updated the init function to use this.control to set up listeners on views in our application.

The control
function
uses the new ComponentQuery engine to quickly and easily get references to components on the page. If
you are not familiar with ComponentQuery yet, be sure to check out the
d
ocumentation
.


In brief though, it allows
us to pass a CSS
-
like selector that will find every matching component on the page.


In our init function above we supplied 'viewport > panel', which translates to "find me every Panel that is a direct
child of a
Viewport".

We then supplied an object that maps event names (just 'render' in this case) to handler
functions. The overall effect is that whenever any component that matches our selector fires a 'render' event, our
onPanelRendered function is called.

Usi
ng Refs

One of the most useful parts of Controllers is the new ref system. These use the new
Ext.ComponentQuery

to
make it really easy to get references to Views on your pa
ge. Let's look at an example of this now:

Ext
.
define
(
'MyApp.controller.Users'
,

{


extend
:

'
Ext.app.Controller
'
,


Page
7

of
22


refs
:

[


{


ref
:

'list'
,

selector
:

'grid'


}


],



init
:

function
()

{


this
.
control
({


'button'
:

{


click
:

this
.
refreshGrid


}


});


},



refreshGrid
:

function
()

{


this
.
getList
().
store
.
load
();


}

});

This example assumes the existence of a
Grid

on the page, which contains a single button to refresh the
Grid when
clicked. In our refs array, we set up a reference to the grid. There are two parts to this
-

the 'selector', which is a
ComponentQuery

selector which finds any gr
id on the page and assigns it to the reference 'list'.


Those are not css selectors but they are like css selectors. Let's take a look at such
simple example. One of your views has such a structure:

Ext
.
define
(
'MyApp.NewView'
,

{



extends
:

'Ext.SomeCmp'
,




xtype
:

'widget.newview'
,




id
:

'idForNewView'
,




someProperty
:

'propValue'
,




// other stuff

});

Now you can assign handlers via
control

for this view using three ways:

way No1

The worst one
-

using id:

this
.
control
({





// notice the hashtag





'#i
dForNewView'
:

{









itemdblclick
:

this
.
eventRowClicked





},





// ...

});

way No2

Using xtype:

Page
8

of
22

this
.
control
({





'newview'
:

{









itemdblclick
:

this
.
eventRowClicked





},





// ...

});

way No3

Using config property:

this
.
control
({





'[someP
roperty=propValue]'
:

{









itemdblclick
:

this
.
eventRowClicked





},





// ...

});

And of course you can combine them like f.i. combine xtype and config property:

'newview[someProperty=propValue]'
:

{

Separating selectors with whitespace and
>

has the
same meaning as in css.


By giving the reference a name, we get a number of things for free. The first is the getList function that we use in
the refreshGrid method above. This is generated automatically by the Controller based on the name of our ref,
wh
ich was capitalized and prepended with get to go from 'list' to 'getList'.


The way this works is that the first time getList is called by your code, the ComponentQuery selector is run and
the first component that matches the selector ('grid' in this case)

will be returned. All future calls to getList will
use a cached reference to that grid. Usually it is advised to use a specific ComponentQuery selector that will only
match a single View in your application (in the case above our selector will match any

grid on the page).


Bringing it all together, our init function is called when the application boots, at which time we call this.control to
listen to any click on a
button

a
nd call our refreshGrid function (again, this will match any button on the page so
we advise a more specific selector than just 'button', but have left it this way for simplicity). When the button is
clicked we use our getList function to refresh the grid
.


You can create any number of refs and control any number of components this way, simply adding more functions

to your Controller as you go
.

Generated Getter M
ethods

Refs aren't the only thing that generate
s

convenient getter methods.

Controllers often
have to deal with Models
and Stores so the framework offers a couple of easy ways to get access to those too.

Let's look at another
example:

Ext
.
define
(
'MyApp.controller.Use
rs'
,

{


extend
:

'
Ext.app.Controller
'
,



models
:

[
'User'
],


stores
:

[
'AllUsers'
,

'AdminUsers'
],



init
:

function
()

{


var

User

=

this
.
getUserModel
(),



allUsers
=

this
.
getAllUsersStore
();

Page
9

of
22



var

ed
=

new

User
({
name
:

'Ed'
});


allUsers
.
add
(
ed
);


}

});

By specifying Models and Stores that the Controller cares about, it again dynamically loads them from the
appropriate locations (app/mo
del/User.js, app/store/AllUsers.js and app/store/AdminUsers.js in this case) and
creates getter functions for them all.

The example above will create a new User model instance and add it to the
AllUsers Store.

Of course, you could do anything in this fun
ction but in this case we just did something simple to
demonstrate the functionality.

Model
s

and Stores

A Model is a data transfer class definition. This is an improvement over ad
-
hoc definitions in which you set up
various maps and fields


instead of do
ing this

manually, you want structured data exchanges.


Ext.define( ‘User’, {


extend: ‘Ext.data.Model’,


fields: [


{ name: ‘id’, type: ‘int’ },


{ name: ‘name’, type: ‘string’}


]

});


The Model infrastructure s
upports type conversions

and data transfers.


A ‘Store’ is a collection of data model instances. For each store, specify a proxy object, to indic
ate where to get
the data from.

Tools and Testing

Is there a plugin for IDE’s such as Eclipse? No


WebStorm does a really good job.
Gives you a good set of hints.

They are working on something internally, but not ready to release.


PhantomJS is the web browser runtime that
Sencha

use
s internally

for testing. Instead of HTMLUnit.

Containers,

Panels
, and Layouts

A Container is a supercl
ass of P
anel.


When either specifying child
items

of a Container, or dynamically
adding

Components to a Container, remember
to consider how you wish the Container to arrange those child elements, and whether those child elements need to
be sized using one of Ext's built
-
in
layout

schemes.

By default, Containers use the
ContainerLayout

scheme
which only renders child components, appending them one after the
other inside the Container, and
does not
apply any sizing

at all.


A common mistake is when a developer neglects to specify a
layout

(e.g. widgets like GridPanels or T
reePanels
are added to Containers for which no
layout

has been specified).


If a Container is left to use the default
ContainerLayout

scheme, none of its child components will be resized, or changed in any way when the Container
is resized.


Layouts
are similar to those in S
wing

or Motif
, such as vbox, hbox, deck, etc.

We use the
vbox and hbox layouts the most. This has a number of additional features:

Page
10

of
22



One attribute that can be defined on a child is called ‘flex’ which gives the child item a 'weight'
(preference) for sizing when the parent container needs to calculate sizes.

The
flex children will be
adjusted such that the parent is filled when resized.



Another attribute that can be defined on a child is minHeight or minWidth



Also, the autoScroll attribute can be used to control if
scroll bars are to be generated (the default is f
alse).

Nesting Containers

Simply nest the “items:” attribute values. The default xtype for an item with children is Container, hence it cannot
have a title (in this case, use a ‘label’ element}.


If the layout cannot be made (perhaps because a constraint
such as min
-
width cannot be met, you will get a
“Layout run failed” message on the console

Layouts

The book describes them in this order:




Simple Container Layout



AnchorLayout



FormLayout



AbsoluteLayout



AccordionLayout



CardLayout



ColumnLayout



HBox and VBox:

One attribute that can be defined on a child is called ‘flex’ which gives the child item a
'weight' (preference) for sizing when the parent container needs to calculate sizes. The flex children will
be adjusted such that the parent is filled when resized
.



TableLayo
u
t



BorderLayout


like the one in AWT or Swing.

FormLayouts and their Elements

This is chapter 6 in the book.


Here is a typical Form:


Elements available include:



TextField



ComboBox



CheckBox



RadioButton



Etc.


The layouts are:


FieldSet


a

con
tainer for grouping sets of fields, rendered as a HTML
fieldset

element
.


The default
layout

for the FieldSet's items is
'anchor'
, but it can be configured to use
any other layout type.

Page
11

of
22


FieldContainer


a subclass of
Container

that implements the
L
abelable

mixin.

This allows it to be configured so
that it is rendered with a
field label

and optional
error message

around its sub
-
items.

This is useful for arranging a
group of fields or other components within a single item in a form, so that it lines up nicely with other fields.

A
common use is for

grouping a set of related fields under a single label in a form.


Data

Driven View Objects

These include lists, comboboxes, grids, etc.


Each one is defined like other views, and can be integrated into the layout like other elements.


But they fetch data
through a store.

Grid

Has a set of column definitions. Each is an object. The default xtype is gridcolumn, but there are others su
ch as
date
colum
n
.


The Grid column does not have a
minWidth

property.

The
width

property does behave as a
minWith

when
the
f
ixed

property is set to false. So, you will have to have your configured as such:


{





header: 'Name (English)',





dataIndex: 'name_en',





sortable: true,





width: 150

}


The
width

being set to 150 ensures that you have a width of 150 pixels. And s
ince I do not have the
fixed

set
to true, I will be able to expand the column width. If you remove the width property, the column will display with
a width of largest data element for that column.

HTML inside Containers

Here we discuss the problem of addin
g HTML code

inside of a ExtJS container. There are several

different ways


let’s take a look at them:

Ext.
onReady
(
function
(){


new

Ext.
Panel
({



renderTo
:

Ext.
getBody
()
,


title
:

'3 Ways to render HTML inside of a ExtJS container'
,


items
:

[{


html
:

"<a href='#'>1. HTML property of a panel</a>"
,


xtype
:

"panel"


}
,

{


xtype
:

"panel"
,


html
:

new

Ext.
XTemplate
(
"<a href='#'>{value}"
)
.
apply
({


value
:

'2. HTML property of a panel

generated by an XTemplate'


})


}
,

{


xtype
:

'box'
,


autoEl
:

{


tag
:

'a'
,


html
:

'3. Dom element created by a DomHelper and wrapped as
Component'
,


href
:

'#'


}


}]


})
;

Page
12

of
22

})
;

It’s easy to think about the first one and you can find it quite often by googling around.

Just setting the
html

property of a panel.

The problem I am having with it is that the overhead of a panel is generated and the HTML is
ju
st static


I can’t generate similar values at runtime (e.g. a different link label in the example).


So apart from the second example that uses a template, I thought of the third solution that generates a DOM
element at runtime using the
DomHelper

(the
au
toEl

property calls this implicitly) and wraps it in a
component.

What do you think?

4. Use Ext.Panel @cfg”contentEl” {String}, providing an element id which will be used as the Panel’s body.

5. Simply use @cfg “html” {String} property of the containing p
anel itself (no need for child items).

6. Use Ext.Panel @cfg property “autoLoad” {String}, providing an url which the panel will use to generate an
Ajax request. The response will be used as the Panel body’s innerHTML.

Theming

Ext JS 4 has a brand new them
ing system to customize the look of your application while still supporting all
browsers.

A Brief Introduction to SASS & Compass

SASS is a pre
-
processor which adds new syntax to CSS allowing for things like variables, mixins, nesting, and
math/color functi
ons. For example, in SASS we can write:

$blue
:

#3bbfce
;

$margin
:

16px
;



.
content
-
navigation
{


border
-
color
:

$blue
;


color
:

darken
(
$blue
,

9
%
)
;

}



.
border

{


padding
:

$margin
/

2
;


margin
:

$margin
/

2
;


border
-
color
:

$blue
;

}

And it will co
mpile to:

.
content
-
navigation
{


border
-
color
:

#3bbfce
;


color
:

#2b9eab
;

}



.
border

{


padding
:

8px
;


margin
:

8px
;


border
-
color
:

#3bbfce
;

}

To see the wide variety of other features available in SASS, please see
http://sass
-
lang.com/
. Compass extends
SASS by adding a variety of CSS3 mixins and providing the extension system that Ext JS leverages. With
Compass, one can include rules like:

$boxheight
:

10em
;



.
mybox

{


@
include border
-
radius
(
$boxheight
/
4
)
;

}

Page
13

of
22

Which compiles into:

.
mybox

{


-
webkit
-
border
-
radius
:

2.5em
;


-
moz
-
border
-
radius
:

2.5em
;


-
o
-
border
-
radius
:

2.5em
;


-
ms
-
border
-
radius
:

2.5em
;


-
khtml
-
border
-
radius
:

2.5em
;


border
-
radius
:

2.5em
;

}

You can learn more about the pre
-
i
ncluded mixins with Compass and the other tools it provides here:
http://compass
-
style.org/docs/
.

Requirements

Ruby

Mac OSX

XCode installs Ruby and all necessary dependencies to your Mac when installed.

Xcode
can be found on the Apple Developer Website:
http://developer.apple.com/xcode/

Windows

Visit
http://rubyinstaller.org/

and download the latest packaged version of R
uby (1.9.2
at the time of writing)

Compass/SASS gem

Mac OSX

In
/Applications/Utilities/Terminal.app
, run the following code (you will be
asked for your password):

sudo gem install compass

You can verify you have Compass and Sass installed by running the fo
llowing in
Terminal.app
:

compass
-
v



sass
-
v

At the time of writing, the latest version of Compass is
0.11.1 (Antares)
. The latest
version of Sass is
3.1.1 (Brainy Betty)

Page
14

of
22

Windows

Select
Start Command Prompt with Ruby

from the new Start Menu option.

Type t
he following:

gem install compass

You can verify you have Compass and Sass installed by running the following in
Terminal.app
:

compass
-
v

sass
-
v

At the time of writing, the latest version of Compass is
0.11.1 (Antares)
. The latest
version of Sass is
3.1.1

(Brainy Betty)

Directory Structure

The Ext JS SDK comes with a template which can be used as a base for your new theme. If you followed the
Getting Started

guide
, you should have a directory for your application with a subfolder
extjs

containing the
Ext JS SDK. It should look something like this:

appname
/

appname
/
extjs
/

appname
/
app.
js

appname
/
index.
html

Copy the template resources folder from
appname/extjs/resourc
es/themes/templates/resource

to your root application folder:

appname
/

appname
/
resources
/

appname
/
resources
/
css
/

appname
/
resources
/
sass
/

appname
/
resources
/
sass
/
config.
rb

appname
/
resources
/
sass
/
my
-
ext
-
theme.
sass

You will also need to copy the images from
ap
pname/extjs/resources/themes/images/default

to
appname/resources/images
.

Ensure the path to your Ext JS folder is correct in
appname/resources/sass/config.rb
:

# $ext_path
:

This

should be the path of the Ext JS SDK relative to
this

file

$ext_path
=

"../../e
xtjs"

Due to a bug in Ext JS 4.0.2a you will also need to edit line 62 of
appname/extjs/resources/themes/lib/utils.rb

from this:

images_path
=

File.
join
(
$ext_path
,

'resources'
,

'themes'
,

'images'
,

theme
)

to this:

images_path
=

relative_path

Page
15

of
22

This ensures im
ages will be served from
appname/resources/images

rather than
appname/extjs/resources/images

Compiling your CSS

Compiling your CSS is a simple process using Compass.

First, change to your sass directory in
appname/resources/sass
, then run the following com
mand in
Terminal.app on Mac OSX

or
Command Prompt on Windows
:

>

compass compile

This should output the following:

>

create ..
/
css
/
my
-
ext
-
theme.
css

Your minified css file should now be in
appname/resources/css/my
-
ext
-
theme.css
.

Changing global SASS variable
s

The Ext JS theming system comes with global SASS variables which you can use to change the look of your
application with a few lines of code.


These SASS variables can be added to your
appname/resources/sass/my
-
ext
-
theme.scss

file,
but they
must

be inser
ted before the call to
@import 'ext4/default/all'
. You can see an example
commented out at the top of your
my
-
ext
-
theme.scss

file:

// Insert your custom variables here.

// $base
-
color: #aa0000;

Try uncommenting this line and changing the base
-
color to some
thing else, perhaps the green #a1c148.

Now regenerate your theme by navigating to
appname/resources/sass

and running
compass
compile

Available Variables

Navigate to
appname/extjs/resources/themes/stylesheets/ext4/default/variables

directory. This directory

contains all defined variables for each component in Ext JS 4.


The naming convention for variables follows CSS property names, prepends by the component name. For
example:



Panel border radius

o

CSS Property:
border
-
radius

o

Variable:
$panel
-
border
-
radius



Pan
el body background color

o

CSS Property:
background
-
color

o

Variable:
$panel
-
body
-
background
-
color



Toolbar background color

o

CSS Property:
background
-
color

Page
16

of
22

o

Variable:
$toolbar
-
background
-
color

You can copy any of these variables and add them to your
appname/reso
urces/sass/my
-
ext
-
theme.scss

file
before

the
@import
'ext4/default/all'

line.

View the Results

To view your new theme, lets overwrite
app.js

with the Theme example from the main SDK. This example
shows most Ext JS components on a single page. Copy
appname/
extjs/examples/themes/themes.js

to
appname/app.js
.

Update
appname/index.html

to the following:

<
html
>

<
head
>


<
title
>
Ext Theme
</
title
>




<
link rel
=
"stylesheet"

type
=
"text/css"

href
=
"resources/css/my
-
ext
-
theme.css"
>


<
script type
=
"text/javascript"

src
=
"extjs/ext
-
debug.js"
></
script
>


<
script type
=
"text/javascript"

src
=
"app.js"
></
script
>

</
head
>

<
body
></
body
>

</
html
>

Now open
index.html

in your browser and you should see your new theme in action.
Try updating the base color in
my
-
ext
-
theme.sass

to

something else, recompile your
sass, and refresh your browser to see the change. Also try experimenting with other
sass variables.

Component UIs

Every component in the Ext JS framework has a
ui

configuration (which defaults to
default
). This property
can
be changed to allow components in your application to have different styles.

The
ui

of any component can be changed at any time, even after render, by using the
setUI

method. An
example of this can be found in
examples/panel/bubble
-
panel.html
.

Creating new

Ext JS UIs

Some Ext JS components have SASS
@mixin
's which allow you to quickly generate new UIs. These include:
Ext.panel.Panel
,
Ext.button.Button
,
Ext.Toolbar

and
Ext.window.Window
.

Creating these new UIs is simple. Simply call the associated
@mixin

(found in the documentation) for the
component you want to create a new UI for.


Let

s look at the Panel
@mixin

as an example (which can be

found in
examples/panel/bubble
-
panel/sass/bubble
-
panel.scss
):

@
include extjs
-
panel
-
ui
(


'bubble'
,




$ui
-
header
-
font
-
size
:

12px
,

Page
17

of
22


$ui
-
header
-
font
-
weight
:

bold
,


$ui
-
header
-
color
:

#0D2A59
,


$ui
-
header
-
background
-
color
:

#fff
,


$ui
-
header
-
b
ackground
-
gradient
:

null
,




$ui
-
border
-
color
:

#fff
,


$ui
-
border
-
radius
:

4px
,


$ui
-
body
-
background
-
color
:

#fff
,


$ui
-
body
-
font
-
size
:

14px

)
;

The above code will create a new
ui

for any
Ext.panel.Panel

component, which you can then use in your
application by specifying the
ui

configuration:

Ext.
create
(
'widget.panel'
,

{


ui
:

'bubble'
,


width
:

300
,


height
:

300
,


title
:

'Panel with a bubble UI!'

})
;

Supporting Legacy Browsers

In most cases when creating new UI's, you will want to include background gradients or rounded corners.
Unfortunately legacy browsers do not support the corresponding CSS3 properties, so we must use images instead.


With Ext
JS 4, we have included a Slicing tool which does the hard work for you. Simply pass it a manifest file of
your new UI's (if you have created any) and run the tool from the command line.


The slicing tool creates a new browser instance, which loads Ext JS a
nd a specified CSS file. Once loaded, it
parses a JavaScript file which includes every Ext JS component that needs styling (panel, window, toolbar, etc.). It
then analyzes each of those components and determines the size and location of each image that nee
ds to be sliced.
It then slices each of the images, sprites them together and saves them in the location defined in the manifest.


The slicer too itself can be run from the command line and is installed as part of the SDK Tools package. It can be
run by ca
lling
sencha slice theme
. Example usage (assuming you are in your application root directory):

sencha slice theme
-
d extjs
-
c resources
/
css
/
my
-
ext
-
theme.
css

-
o
resources
/
images
-
v

It accepts several arguments:



--
css[=]value,
-
c[=]value

The path to your the
me's complete CSS file, e.g., ext
-
all
-
access.css. Uses the default Ext JS 4
theme CSS if not provided.



--
ext
-
dir[=]value,
-
d[=]value (required)

The path to the root of your Ext JS 4 SDK directory.



--
manifest[=]value,
-
m[=]value

Page
18

of
22

The path to your Theme Gener
ator JSON manifest file, e.g., manifest.json. Uses the default
packaged manifest if not provided.



--
output
-
dir[=]value,
-
o[=]value

The destination path to save all generated theme images. This should be inside the
resources/themes/images/<themename>/

direc
tory. Defaults to the current working
directory.



--
verbose,
-
v

Display a message for every image that is generated.

Usage

Compile your CSS

You must ensure your SASS theme file has been compiled as this is used for the slicer. Passing no CSS file would
resu
lt in the slicer to revert to the default ext
-
all.css file, which would be pointless in most cases.

Creating your manifest file (optional)

The manifest file is a simple JavaScript file which tells the Slicing tool which custom UI's you would like to slice.

This step is only necessary when you have created new UI's.

Let's look at the bubble panel example again:

Ext.
onReady
(
function
()

{


Ext.
manifest

=

{


widgets
:

[


{


xtype
:

'widget.header'
,


ui
:

'bubble
'


}
,


{


xtype
:

'widget.panel'
,


ui
:

'bubble'


}


]


}
;

})
;

As you can see, you define an Object called
Ext.manifest

and give it an Array property
called
widgets
. In this Array yo
u should insert an object containing the
xtype

and
ui

of the
component you want to generate the images for.

It is important that the
Ext.manifest

Object is defined inside the
Ext.onReady

method.

Generating your images

Now all that is left is to run the command, including the arguments to the Ext JS SDK folder, your theme CSS file
and the output directory of the sliced images.

sencha slice theme
-
d extjs
-
c resourc
es
/
css
/
my
-
ext
-
theme.
css

-
o
resources
/
images
-
v

Page
19

of
22

Chart Classes

Ext JS 3 (and even more so, Ext JS 4) s
upports a full set of charts. These are built into the primary Ext JS library
file. Here is an example:


Ext
.onReady(function () {


var chart;



Ext
.get('reloadData').on('click', function() {


store1.loadData(generateData());


});


chart = new Ext.chart.Chart({


renderTo: Ext.getBody(),


width: 800,


height: 600,


animate: true,


store: store1, // this f
etches the data



shadow: true,


theme: 'Category1',


legend: {


position: 'right'


},


axes: [{


type: 'Numeric',

// is there a type that is DateTime?


minimum: 0,


pos
ition: 'left',


fields: ['data1', 'data2', 'data3'],


title: 'Number of Hits',


grid: {


odd: {


opacity: 1,
fill: '#ddd', stroke: '#bbb',

'stroke
-
width': 0.5


}


}


}, {


type: 'Category',


position: 'bottom',


fields: ['name'],


title: 'Month of the Year'


}],


series: [{

/// this is similar to HighCharts


type: 'line',


highl
ight: {

s
ize: 7, radius: 7 },


axis: 'left',


xField: 'name',


yField: 'data1',


markerCfg: {


type: 'cross',


size: 4,


radius: 4,


'stroke
-
width': 0



}


}, {


type: 'line',


highlight: { size: 7, radius: 7 },


axis: 'left',


fill: true,


xField: 'name',


yField: 'data3',


markerCfg: {


type: 'ci
rcle',


size: 4,


radius: 4,


'stroke
-
width': 0


}


}]


});

});


There is a “time” axis type:

Page
20

of
22


type: 'Time',


position: 'bottom',


fields: 'date',


title:
'Days',


dateFormat: 'M d',


groupBy: 'year,month,day',


aggregateOp: 'sum'


}],

Troubleshooting

http://www.sencha.com/forum/showthread.php?156370
-
How
-
to
-
get
-
a
-
clue
-
about
-
quot
-
c
-
is
-
not
-
a
-
constructor
-
quot

Performance Analysis and Suggestions

http://www.sencha.com/blog/ext
-
js
-
4
-
1
-
performance?mkt_tok=3RkMMJWWfF9wsRoku6XLZKXonjHpfsX%2F7eolW6Cg38431UFwdcjKPmjr1YYBTt
QhcOuuEwcWGog80wlWGeiU

Open Questions/Issues

What is the difference between item
s
:
, initComponent Ext.a
pply, initComponent Ext.applyIf
?

The first one simply
runs initialization code

(with no procedural logic possible)
, the second is a call to a copy utility

(with procedural
logic)
,
and the Ext.applyIf runs a copy utility that

appli
es

changes only if not already a
pplied.


How do we build components dynamically?


How do we indicate when a store is to refresh its content?


How might a store’s content be incrementally changed, rather than completing reloading?

Appendix A: Examples

Exam
ple 1

<html>


<head>


<meta http
-
equiv="Content
-
Type" content="text/html; charset=utf
-
8" />



<title id='title'>HTML Page S
etup Tutorial</title>



<link rel="stylesheet" type="text/css" href="../../resources/css/ext
-
all.css" />




<!
--

ExtJS library: all widgets
--
>


<script t
ype="text/javascript" src="../extjs
/
bootstrap
.js"></script>



</head>


<body>


<script type="text/javascript">


// Path to the blank image should point to a valid location on you
r server


Ext.BLANK_IMAGE_URL = '../../resources/images/default/s.gif';




Ext.onReady(function(){




console.info('woohoo!!!');




}); //end onReady


</script>


</body>

</html>


This shows how to include the JavaSc
ript files, and how to refer to them. Next, you add the JavaScript for
specifying the content in the place of the dummy console.info call in the above text.

Page
21

of
22

Example 2: Panels

A Panel is a Container with a title. Containers can have a layout mode, wher
e the layout modes are very similar to
those in Swing or ActionScript. A panel can have a collapsible flag, and can appear collapse or not.


Ext.onReady(
function
() {





var

sampleToolbar =
new

Ext.Toolbar({





width : 400,





height : 40,





renderTo
: Ext.getBody(),





style : {






marginBottom :
'20px'





}






});








var

panelA =
new

Ext.Panel({





title:
"Panel A"
,





collapsible:
true
,





html:
'<div style="padding: 10px">Welcome to the Machine</div>'




});






var

panelB =
new

Ext.P
anel({


title:
"Panel B"
,


collapsible:
true
,


collapsed:
true
,


html:
'<div style="padding: 10px">Welcome to the Real World</div>'


});







var

panelC =
new

Ext.Panel({


title:
"Panel C"
,


collapsible:
true
,


collapsed:
true
,


html:
'<div style="padding: 10px">Welcome to the Matrix</div>'


});















var

samplePanel =
new

Ext.Panel({





width : 400,





height : 300,





title :
"Panel with Top & Bottom Toolbars"
,





tbar : {






height : 30





},





bbar : {






height : 30





},





layout: {





type:
'vbox'
,
// Arrange child items vertically





align:
'stretch'

// Each takes up full width









},





items: [panelA, panelB, panelC],





renderTo : Ext.getBody()




});




Example 3: Menus

Here is a simple example of a menu:


Ext.onReady(
function
() {







new

Ext.Panel({





width : 290,





height : 300,





title :
"Toolbar with Button Menus"
,





tbar : {






items : [ {







xtype
:
'button'
,







text :
'Simple Menu'
,







menu : {
// 4

Page
22

of
22








showSeparator :
false
,
// 5








items : [ {









text :
'menu item one'








}, {









text :
'menu item two'








} ]







}






}, {







xtype :
'button'
,







iconCls :

'email
-
add
-
icon'
,







text :
'Message Type'
,







menu : [ {
// 6








text :
'email message'
,








iconCls :
'email
-
icon'







}, {








text :
'sms message'
,








iconCls :
'email
-
icon'







}, {








text :
'push message'
,








iconCls

:
'email
-
icon'







} ]






}, {







xtype :
'splitbutton'
,
// 7







text :
'Split Button'
,







iconCls :
'user
-
add
-
icon'
,







menu : [ {








text :
"<b>Bold</b>"







}, {








text :
"<i>Italic</i>"







}, {








text :
"<u>Underline
</u>"







} ]






} ]





},





renderTo : Ext.getBody(),





style : {






marginTop :
'20px'





}




});







});