sproutcore 0.9.3 → 0.9.4
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- data/History.txt +19 -0
- data/Manifest.txt +15 -1
- data/clients/view_builder/builders/builder.js +339 -0
- data/clients/view_builder/builders/button.js +81 -0
- data/clients/view_builder/controllers/document.js +21 -0
- data/clients/view_builder/core.js +19 -0
- data/clients/view_builder/english.lproj/body.css +77 -0
- data/clients/view_builder/english.lproj/body.rhtml +39 -0
- data/clients/view_builder/english.lproj/controls.css +0 -0
- data/clients/view_builder/english.lproj/strings.js +14 -0
- data/clients/view_builder/main.js +38 -0
- data/clients/view_builder/mixins/design_mode.js +92 -0
- data/clients/view_builder/tests/controllers/document.rhtml +20 -0
- data/clients/view_builder/tests/views/builder.rhtml +20 -0
- data/clients/view_builder/tests/views/palette.rhtml +21 -0
- data/clients/view_builder/views/builder.js +26 -0
- data/clients/view_builder/views/palette.js +30 -0
- data/frameworks/sproutcore/Core.js +6 -4
- data/frameworks/sproutcore/README +1 -3
- data/frameworks/sproutcore/controllers/array.js +5 -5
- data/frameworks/sproutcore/drag/drag.js +2 -0
- data/frameworks/sproutcore/english.lproj/panes.css +16 -35
- data/frameworks/sproutcore/foundation/application.js +29 -8
- data/frameworks/sproutcore/foundation/object.js +5 -1
- data/frameworks/sproutcore/foundation/run_loop.js +65 -2
- data/frameworks/sproutcore/foundation/timer.js +1 -0
- data/frameworks/sproutcore/globals/window.js +23 -18
- data/frameworks/sproutcore/mixins/array.js +2 -2
- data/frameworks/sproutcore/mixins/observable.js +127 -52
- data/frameworks/sproutcore/panes/dialog.js +1 -1
- data/frameworks/sproutcore/panes/overlay.js +6 -2
- data/frameworks/sproutcore/panes/pane.js +27 -0
- data/frameworks/sproutcore/views/collection/collection.js +1 -1
- data/frameworks/sproutcore/views/collection/grid.js +3 -15
- data/frameworks/sproutcore/views/collection/source_list.js +10 -5
- data/frameworks/sproutcore/views/field/select_field.js +11 -2
- data/frameworks/sproutcore/views/field/text_field.js +1 -1
- data/frameworks/sproutcore/views/label.js +2 -7
- data/frameworks/sproutcore/views/view.js +254 -213
- data/generators/client/README +2 -2
- data/generators/client/USAGE +2 -2
- data/lib/sproutcore/build_tools/html_builder.rb +2 -2
- data/lib/sproutcore/bundle_manifest.rb +28 -22
- data/lib/sproutcore/merb/bundle_controller.rb +4 -3
- data/lib/sproutcore/version.rb +1 -1
- metadata +17 -3
- data/frameworks/sproutcore/animation/animation.js +0 -411
@@ -0,0 +1,21 @@
|
|
1
|
+
// ==========================================================================
|
2
|
+
// ViewBuilder.DocumentController
|
3
|
+
// ==========================================================================
|
4
|
+
|
5
|
+
require('core');
|
6
|
+
|
7
|
+
/** @class
|
8
|
+
|
9
|
+
(Document Your View Here)
|
10
|
+
|
11
|
+
@extends SC.Object
|
12
|
+
@author AuthorName
|
13
|
+
@version 0.1
|
14
|
+
@static
|
15
|
+
*/
|
16
|
+
ViewBuilder.documentController = SC.Object.create(
|
17
|
+
/** @scope ViewBuilder.documentController */ {
|
18
|
+
|
19
|
+
rootView: null
|
20
|
+
|
21
|
+
}) ;
|
@@ -0,0 +1,19 @@
|
|
1
|
+
// ==========================================================================
|
2
|
+
// ViewBuilder
|
3
|
+
// ==========================================================================
|
4
|
+
|
5
|
+
ViewBuilder = SC.Object.create({
|
6
|
+
|
7
|
+
// This will create the server for your application. Add any namespaces
|
8
|
+
// your model objects are defined in to the prefix array.
|
9
|
+
server: SC.Server.create({ prefix: ['ViewBuilder'] }),
|
10
|
+
|
11
|
+
// When you are in development mode, this array will be populated with
|
12
|
+
// any fixtures you create for testing and loaded automatically in your
|
13
|
+
// main method. When in production, this will be an empty array.
|
14
|
+
FIXTURES: [],
|
15
|
+
|
16
|
+
// Any keys in this array will be instantiated automatically from main.
|
17
|
+
controllers: []
|
18
|
+
|
19
|
+
}) ;
|
@@ -0,0 +1,77 @@
|
|
1
|
+
/* @override
|
2
|
+
http://localhost:4020/static/photos/en/_cache/body-1208305764.css
|
3
|
+
http://localhost:4020/static/photos/en/_cache/body-1208344721.css
|
4
|
+
http://localhost:4020/static/view_builder/en/_cache/body-1208631407.css
|
5
|
+
http://localhost:4020/static/view_builder/en/_cache/body-1208631886.css
|
6
|
+
http://localhost:4020/static/view_builder/en/_cache/body-1208632215.css
|
7
|
+
http://localhost:4020/static/view_builder/en/_cache/body-1208632366.css
|
8
|
+
*/
|
9
|
+
|
10
|
+
/* @group Core */
|
11
|
+
|
12
|
+
body {
|
13
|
+
position: absolute ;
|
14
|
+
left: 0;
|
15
|
+
right: 0;
|
16
|
+
top: 0;
|
17
|
+
bottom: 0;
|
18
|
+
padding: 0;
|
19
|
+
margin: 0;
|
20
|
+
overflow: hidden ;
|
21
|
+
}
|
22
|
+
|
23
|
+
.workspace .sidebar {
|
24
|
+
position: absolute;
|
25
|
+
left: 0;
|
26
|
+
top: 0;
|
27
|
+
width: 200px;
|
28
|
+
bottom: 0;
|
29
|
+
}
|
30
|
+
|
31
|
+
.sc-theme .workspace.horizontal .sc-split-divider-view {
|
32
|
+
position: absolute;
|
33
|
+
left: 200px;
|
34
|
+
top: 0;
|
35
|
+
bottom: 0;
|
36
|
+
}
|
37
|
+
|
38
|
+
.workspace .document_view {
|
39
|
+
position: absolute;
|
40
|
+
left: 205px;
|
41
|
+
right: 0;
|
42
|
+
top: 0;
|
43
|
+
bottom: 0;
|
44
|
+
border: none ;
|
45
|
+
background-color: #aaa ;
|
46
|
+
}
|
47
|
+
|
48
|
+
.left.app-label {
|
49
|
+
font-weight: bold ;
|
50
|
+
padding-bottom: 9px;
|
51
|
+
text-shadow: white 0px 1px 0px;
|
52
|
+
}
|
53
|
+
|
54
|
+
.app-label img {
|
55
|
+
width: 27px;
|
56
|
+
height: 27px;
|
57
|
+
vertical-align: middle;
|
58
|
+
position: relative ;
|
59
|
+
top: -3px;
|
60
|
+
margin-right: 2px;
|
61
|
+
}
|
62
|
+
|
63
|
+
/* @end */
|
64
|
+
|
65
|
+
/* @group Sidebar */
|
66
|
+
|
67
|
+
.sidebar .source_list {
|
68
|
+
position: absolute ;
|
69
|
+
top: 0;
|
70
|
+
left: 0;
|
71
|
+
right: 0;
|
72
|
+
bottom: 0;
|
73
|
+
border: none ;
|
74
|
+
}
|
75
|
+
|
76
|
+
/* @end */
|
77
|
+
|
@@ -0,0 +1,39 @@
|
|
1
|
+
<% content_for('body') do %>
|
2
|
+
|
3
|
+
<% split_view :workspace, :class => 'sc-app-workspace footer', :direction => :horizontal do %>
|
4
|
+
<% view :sidebar, :outlet => true do %>
|
5
|
+
<% scroll_view :source_list, :outlet => true do %>
|
6
|
+
<%= source_list_view :outlet => true,
|
7
|
+
:content_value_key => :name,
|
8
|
+
:group_visible_key => true,
|
9
|
+
:content_icon_key => :icon %>
|
10
|
+
<% end %>
|
11
|
+
<% end %>
|
12
|
+
|
13
|
+
<%= split_divider_view :outlet => true, :width => 5 %>
|
14
|
+
|
15
|
+
<% split_view :document_view, :outlet => true, :direction => :vertical do %>
|
16
|
+
<% view :editor, :outlet => true do %>
|
17
|
+
<%= button_view :outlet => true, :view => 'SC.BuilderView' %>
|
18
|
+
<% end %>
|
19
|
+
<%= split_divider_view :outlet => true, :width => 5 %>
|
20
|
+
<% scroll_view :outlet => true do %>
|
21
|
+
CONTENTS
|
22
|
+
<% end %>
|
23
|
+
<% end %>
|
24
|
+
|
25
|
+
<% end %>
|
26
|
+
|
27
|
+
<% view :header, :class => 'sc-footer sc-square-theme' do %>
|
28
|
+
<div class="left app-label">
|
29
|
+
<img src="<%= static_url('images/sproutcore-logo.png') %>" />ViewBuilder
|
30
|
+
</div>
|
31
|
+
<div class="center">
|
32
|
+
</div>
|
33
|
+
<div class="right">
|
34
|
+
<%= button_view :outlet => true, :title => "Library" %>
|
35
|
+
<%= button_view :outlet => true, :title => "Options" %>
|
36
|
+
</div>
|
37
|
+
<% end %>
|
38
|
+
|
39
|
+
<% end %>
|
File without changes
|
@@ -0,0 +1,14 @@
|
|
1
|
+
// ==========================================================================
|
2
|
+
// ViewBuilder English Strings
|
3
|
+
// ==========================================================================
|
4
|
+
|
5
|
+
// Place strings you want to localize here. In your app, use the key and
|
6
|
+
// localize it using "key string".loc(). HINT: For your key names, use the
|
7
|
+
// english string with an underscore in front. This way you can still see
|
8
|
+
// how your UI will look and you'll notice right away when something needs a
|
9
|
+
// localized string added to this file!
|
10
|
+
//
|
11
|
+
Object.extend(String.English,{
|
12
|
+
// "_String Key": "Localized String"
|
13
|
+
}) ;
|
14
|
+
|
@@ -0,0 +1,38 @@
|
|
1
|
+
// ==========================================================================
|
2
|
+
// ViewBuilder
|
3
|
+
// ==========================================================================
|
4
|
+
|
5
|
+
// This is the function that will start your app running. The default
|
6
|
+
// implementation will load any fixtures you have created then instantiate
|
7
|
+
// your controllers and awake the elements on your page.
|
8
|
+
//
|
9
|
+
// As you develop your application you will probably want to override this.
|
10
|
+
// See comments for some pointers on what to do next.
|
11
|
+
//
|
12
|
+
function main() {
|
13
|
+
|
14
|
+
// Step 1: Load Your Model Data
|
15
|
+
// The default code here will load the fixtures you have defined.
|
16
|
+
// Comment out the preload line and add something to refresh from the server
|
17
|
+
// when you are ready to pull data from your server.
|
18
|
+
ViewBuilder.server.preload(ViewBuilder.FIXTURES) ;
|
19
|
+
|
20
|
+
// TODO: refresh() any collections you have created to get their records.
|
21
|
+
// ex: ViewBuilder.contacts.refresh() ;
|
22
|
+
|
23
|
+
// Step 2: Instantiate Your Views
|
24
|
+
// The default code just activates all the views you have on the page. If
|
25
|
+
// your app gets any level of complexity, you should just get the views you
|
26
|
+
// need to show the app in the first place, to speed things up.
|
27
|
+
SC.page.awake() ;
|
28
|
+
|
29
|
+
// Step 3. Set the content property on your primary controller.
|
30
|
+
// This will make your app come alive!
|
31
|
+
|
32
|
+
// TODO: Set the content property on your primary controller
|
33
|
+
// ex: ViewBuilder.contactsController.set('content',ViewBuilder.contacts);
|
34
|
+
var v = SC.ButtonView.Builder.newBuilder() ;
|
35
|
+
ViewBuilder.documentController.set('rootView', v) ;
|
36
|
+
} ;
|
37
|
+
|
38
|
+
|
@@ -0,0 +1,92 @@
|
|
1
|
+
// ==========================================================================
|
2
|
+
// SC.Buildable
|
3
|
+
// ==========================================================================
|
4
|
+
|
5
|
+
/**
|
6
|
+
Applying this mixin allows you to put a view into design mode. When a view
|
7
|
+
is in design mode, mouse selection and some keyboard handling will be
|
8
|
+
overridden to allow you to place and edit the contents of the view.
|
9
|
+
|
10
|
+
Mode designMode properties begin with the words "designMode" to separate
|
11
|
+
them from other properties that might exist on the view.
|
12
|
+
*/
|
13
|
+
SC.DesignMode = {
|
14
|
+
|
15
|
+
/**
|
16
|
+
If YES, then view will display selection handles and other state to
|
17
|
+
indicate that the item can be edited.
|
18
|
+
*/
|
19
|
+
designModeIsSelected: NO,
|
20
|
+
|
21
|
+
/**
|
22
|
+
If YES, design mode is enabled. Otherwise, the view will behave like
|
23
|
+
normal.
|
24
|
+
*/
|
25
|
+
designModeIsEnabled: NO,
|
26
|
+
|
27
|
+
// return the state for design mode methods
|
28
|
+
designModeState: function() {
|
29
|
+
if (!this._designModeState) this._designModeState = {} ;
|
30
|
+
return this._designModeState ;
|
31
|
+
},
|
32
|
+
|
33
|
+
/**
|
34
|
+
Whenever a view goes into design mode, this will trigger to swap out the
|
35
|
+
event handler methods on the view with design mode methods.
|
36
|
+
*/
|
37
|
+
_designModeIsEnabledObserver: function() {
|
38
|
+
var isEnabled = this.get('designModeIsEnabled') ;
|
39
|
+
if (isEnabled === this.get('_designModeIsEnabled')) return ;
|
40
|
+
|
41
|
+
// swap methods in and out
|
42
|
+
var state = this.designModeState() ;
|
43
|
+
var orig = state.savedMethods = state.savedMethods || {} ;
|
44
|
+
var methods = SC.DesignModeMethods;
|
45
|
+
|
46
|
+
// save original methods and replace with new ones or restore
|
47
|
+
for(var key in methods) {
|
48
|
+
if (!methods.hasOwnProperty(key)) continue ;
|
49
|
+
if (isEnabled) {
|
50
|
+
orig[key] = this[key] ;
|
51
|
+
this[key] = methods[key] ;
|
52
|
+
} else {
|
53
|
+
this[key] = orig[key] ;
|
54
|
+
}
|
55
|
+
}
|
56
|
+
}.observes('designModeIsEnabled')
|
57
|
+
|
58
|
+
};
|
59
|
+
|
60
|
+
/**
|
61
|
+
These methods are swapped out on a view when you put it into design mode.
|
62
|
+
*/
|
63
|
+
SC.DesignModeMethods = {
|
64
|
+
// allow dragging around...
|
65
|
+
mouseDown: function(evt) {
|
66
|
+
var state = this.designModeState() ;
|
67
|
+
|
68
|
+
// select if needed
|
69
|
+
if (!this.get('designModeIsSelected')) {
|
70
|
+
this.set('designModeIsSelected', YES) ;
|
71
|
+
}
|
72
|
+
|
73
|
+
// save info for dragging.
|
74
|
+
state._mouseDownLoc = Event.pointerLocation(evt) ;
|
75
|
+
state._mouseDownFrame = this.get('frame') ;
|
76
|
+
return YES ; // allow dragging
|
77
|
+
},
|
78
|
+
|
79
|
+
mouseDragged: function(evt) {
|
80
|
+
var state = this.designModeState() ;
|
81
|
+
|
82
|
+
var loc = Event.pointerLocation(evt) ;
|
83
|
+
var f = {
|
84
|
+
x: state._mouseDownFrame.x + loc.x - state._mouseDownLoc.x,
|
85
|
+
y: state._mouseDownFrame.y + loc.y - state._mouseDownLoc.y
|
86
|
+
};
|
87
|
+
|
88
|
+
this.set('frame', f) ;
|
89
|
+
},
|
90
|
+
|
91
|
+
mouseUp: function(evt) { return YES ; }
|
92
|
+
} ;
|
@@ -0,0 +1,20 @@
|
|
1
|
+
<% # ========================================================================
|
2
|
+
# ViewBuilder.DocumentController Unit Test
|
3
|
+
# ========================================================================
|
4
|
+
%>
|
5
|
+
<% content_for('final') do %>
|
6
|
+
|
7
|
+
<script>
|
8
|
+
|
9
|
+
Test.context("ViewBuilder.DocumentController",{
|
10
|
+
|
11
|
+
"TODO: Add your own tests here": function() {
|
12
|
+
true.shouldEqual(true) ;
|
13
|
+
}
|
14
|
+
|
15
|
+
}) ;
|
16
|
+
|
17
|
+
if (window.main && (appMain = main)) main = null ;
|
18
|
+
</script>
|
19
|
+
|
20
|
+
<% end %>
|
@@ -0,0 +1,20 @@
|
|
1
|
+
<% # ========================================================================
|
2
|
+
# ViewBuilder.BuilderView Unit Test
|
3
|
+
# ========================================================================
|
4
|
+
%>
|
5
|
+
<% content_for('final') do %>
|
6
|
+
|
7
|
+
<script>
|
8
|
+
|
9
|
+
Test.context("ViewBuilder.BuilderView",{
|
10
|
+
|
11
|
+
"TODO: Add your own tests here": function() {
|
12
|
+
true.shouldEqual(true) ;
|
13
|
+
}
|
14
|
+
|
15
|
+
}) ;
|
16
|
+
|
17
|
+
if (window.main && (appMain = main)) main = null ;
|
18
|
+
</script>
|
19
|
+
|
20
|
+
<% end %>
|
@@ -0,0 +1,21 @@
|
|
1
|
+
<% # ========================================================================
|
2
|
+
# ViewBuilder.PaletteView Unit Test
|
3
|
+
# ========================================================================
|
4
|
+
%>
|
5
|
+
<% content_for('final') do %>
|
6
|
+
|
7
|
+
<script>
|
8
|
+
|
9
|
+
Test.context("ViewBuilder.PaletteView",{
|
10
|
+
|
11
|
+
"TODO: Add your own tests here": function() {
|
12
|
+
true.shouldEqual(true) ;
|
13
|
+
}
|
14
|
+
|
15
|
+
}) ;
|
16
|
+
|
17
|
+
if (window.main && (appMain = main)) main = null ;
|
18
|
+
|
19
|
+
</script>
|
20
|
+
|
21
|
+
<% end %>
|
@@ -0,0 +1,26 @@
|
|
1
|
+
// ==========================================================================
|
2
|
+
// ViewBuilder.BuilderView
|
3
|
+
// ==========================================================================
|
4
|
+
|
5
|
+
require('core');
|
6
|
+
require('mixins/design_mode') ;
|
7
|
+
|
8
|
+
/** @class
|
9
|
+
|
10
|
+
A BuilderView displays the visible and editable portion of a view. You
|
11
|
+
can plug any generic builder record into a view and it will display the
|
12
|
+
content. If the builder is a container, it will also allow you to add
|
13
|
+
child views to the container.
|
14
|
+
|
15
|
+
@extends SC.View
|
16
|
+
@author AuthorName
|
17
|
+
@version 0.1
|
18
|
+
*/
|
19
|
+
SC.BuilderView = SC.ButtonView.extend(SC.DesignMode,
|
20
|
+
/** @scope ViewBuilder.BuilderView.prototype */ {
|
21
|
+
|
22
|
+
init: function() {
|
23
|
+
arguments.callee.base.call(this) ;
|
24
|
+
this.set('designModeIsEnabled', YES) ; // activate design mode.
|
25
|
+
}
|
26
|
+
}) ;
|
@@ -0,0 +1,30 @@
|
|
1
|
+
// ==========================================================================
|
2
|
+
// ViewBuilder.PaletteView
|
3
|
+
// ==========================================================================
|
4
|
+
|
5
|
+
require('core');
|
6
|
+
|
7
|
+
/** @class
|
8
|
+
|
9
|
+
(Document Your View Here)
|
10
|
+
|
11
|
+
@extends SC.View
|
12
|
+
@author AuthorName
|
13
|
+
@version 0.1
|
14
|
+
*/
|
15
|
+
ViewBuilder.PaletteView = SC.View.extend(
|
16
|
+
/** @scope ViewBuilder.PaletteView.prototype */ {
|
17
|
+
|
18
|
+
title: 'TITLE',
|
19
|
+
|
20
|
+
emptyElement: '<div class="sc-smoke-theme palette"><div class="titlebar"><div class="label"></div></div><div class="body"></div></div>',
|
21
|
+
|
22
|
+
containerElement: '.body?',
|
23
|
+
|
24
|
+
outlets: ['titleLabelView'],
|
25
|
+
|
26
|
+
titleLabelView: SC.LabelView.extend({
|
27
|
+
valueBinding: '*owner.title'
|
28
|
+
}).outletFor('.titlebar .label?')
|
29
|
+
|
30
|
+
}) ;
|
@@ -127,6 +127,7 @@ Object.extend(SC,{
|
|
127
127
|
|
128
128
|
// call the onloadQueue.
|
129
129
|
var queue ;
|
130
|
+
SC.runLoop.beginRunLoop() ;
|
130
131
|
if (window.callOnLoad) {
|
131
132
|
if (window.callOnLoad instanceof Array) {
|
132
133
|
queue = window.callOnLoad ;
|
@@ -148,7 +149,8 @@ Object.extend(SC,{
|
|
148
149
|
} else if (typeof SC.Routes != 'undefined') {
|
149
150
|
SC.Routes.ping() ; // handle routes, if modules is installed.
|
150
151
|
}
|
151
|
-
|
152
|
+
|
153
|
+
SC.runLoop.endRunLoop();
|
152
154
|
},
|
153
155
|
|
154
156
|
// this will take a URL of any type and convert it to a fully qualified URL.
|
@@ -179,10 +181,10 @@ Object.extend(SC,{
|
|
179
181
|
ret = (item.isClass) ? T_CLASS : T_FUNCTION ;
|
180
182
|
} else if (item instanceof SC.Error) {
|
181
183
|
ret = T_ERROR ;
|
182
|
-
} else if (item.isObject
|
184
|
+
} else if (item.isObject === true) {
|
183
185
|
ret = T_OBJECT ;
|
184
186
|
} else ret = T_HASH ;
|
185
|
-
} else if (ret
|
187
|
+
} else if (ret === T_FUNCTION) ret = (item.isClass) ? T_CLASS : T_FUNCTION;
|
186
188
|
return ret ;
|
187
189
|
},
|
188
190
|
|
@@ -200,7 +202,7 @@ Object.extend(SC,{
|
|
200
202
|
|
201
203
|
isArray: function( obj )
|
202
204
|
{
|
203
|
-
return ($type(obj)
|
205
|
+
return ($type(obj) === T_ARRAY) || (obj && obj.objectAt);
|
204
206
|
},
|
205
207
|
|
206
208
|
_nextGUID: 0,
|