Compare commits

..

93 Commits

Author SHA1 Message Date
John Bintz a36b6d3e76 add unit test for getStyle where passed object does not have style attribute 2010-01-15 14:00:07 -05:00
John Bintz 2ede0b24e2 coding style change 2010-01-12 14:51:36 -05:00
John Bintz 1c21c2f1b6 remaining IE6 fixes for offset positioning where null objects are being returned 2010-01-12 14:46:52 -05:00
John Bintz 8a5b3209f4 add check to getStyle to ensure provided element has a style attribute 2010-01-06 19:43:10 -05:00
John Bintz 5992866e46 Revert "potential workaround for IE 5 issue where element can become something other than a DOM node"
This reverts commit ef78a973ef.
2010-01-06 19:41:33 -05:00
John Bintz ef78a973ef potential workaround for IE 6 issue where element can become something other than a DOM node 2010-01-06 16:52:58 -05:00
Tobie Langel 6839886699 doc: Update PDoc. Default to BlueCloth Markdown parser to avoid Maruku warning. 2009-12-31 19:34:35 +01:00
Juriy Zaytsev 475f1797e1 No need to check for `window.Node`, since `var Node` already declares it if missing. 2009-12-30 01:45:59 -05:00
Juriy Zaytsev e0a102b510 Merge branch 'master' of github.com:sstephenson/prototype 2009-12-30 01:41:27 -05:00
Juriy Zaytsev a260913a30 Remove SETATTRIBUTE_IGNORES_NAME feature test, replacing it with a simpler HAS_EXTENDED_CREATE_ELEMENT_SYNTAX one. This avoids invalid injection of FORM into a root element (HTML). 2009-12-30 01:33:37 -05:00
Tobie Langel 6c1790ac4e doc: Fix Template doc to avoid issues with Sprockets. 2009-12-29 01:54:56 +01:00
Tobie Langel 4cc67f2e8e doc: Minor cleanup. 2009-12-29 01:53:16 +01:00
Tobie Langel 8a8af0a729 doc: Fix documentation for Template. 2009-12-24 07:32:32 +01:00
Tobie Langel 2e3e02d92c doc: Fix documentation errors in Ajax.Response. 2009-12-24 03:19:14 +01:00
Tobie Langel bccb541797 Merge branch 'master' of git@github.com:sstephenson/prototype 2009-12-24 03:18:11 +01:00
Juriy Zaytsev 56fb5b84a1 No need to use expensive try/catch when check for element being orphaned suffices. 2009-12-23 01:54:19 -05:00
Tobie Langel d085d97a56 Revert back to PDoc's default templates. 2009-12-23 06:51:56 +01:00
Tobie Langel fb93b80b59 doc: using pygments for syntax highlighting. 2009-12-23 06:32:59 +01:00
Tobie Langel a7f05ee8b5 doc: Fix a typo in Prototype.Selector.find which prevented proper documentation parsing. Add a default value for the index argument. 2009-12-23 05:52:51 +01:00
Juriy Zaytsev 647d93bcc4 Use native `Array.isArray` when available; currently present in nightly webkit (up to 17x faster) and Opera 10.5 alpha (up to 5x faster). 2009-12-22 18:05:30 -05:00
Andrew Dupont d6ed7efe94 Tweak the PDoc templates. 2009-12-17 14:52:27 -06:00
Andrew Dupont 83b0c153d3 Add examples for String#gsub and String#sub.
(cherry picked from commit 591b25eb2604953754f08c40e9ef99791a6bb51b)
2009-12-04 18:29:40 -06:00
Andrew Dupont c028935279 Add note about mouseenter/leave support to docs.
(cherry picked from commit 1c4c2005341ef587dca7eacc8d347367e3eb7ef7)
2009-12-04 18:28:31 -06:00
Andrew Dupont 0dd600974c Add documentation for event key codes.
(cherry picked from commit 93bd2048e2c106ecc309292be358ef398df05984)
2009-12-04 18:27:49 -06:00
Andrew Dupont e7c9072872 Merge branch 'master' of git@github.com:sstephenson/prototype 2009-12-04 18:25:23 -06:00
Sam Stephenson fa0dce2488 Revert Event#findElement changes from 6bb309a 2009-12-03 00:31:35 -06:00
Sam Stephenson 6bb309afb7 Selector API change: replace Prototype.Selector.filter with Prototype.Selector.find, which works like the old Selector.findElement. 2009-12-02 15:57:58 -06:00
Sam Stephenson 7770ab99dc Fix 'rake' without SELECTOR_ENGINE environment variable set 2009-12-02 15:14:18 -06:00
Tobie Langel a44a8db6ae Avoid automatically fetching the vendor/sizzle git submodule. 2009-12-02 21:41:52 +01:00
Sam Stephenson 797c231bfa Move ext/sizzle into src so it's available in the default Sprockets load path. 2009-12-02 14:18:01 -06:00
Tobie Langel 9d4711281d Fix typo in Rakefile. 2009-12-02 00:47:16 +01:00
Samuel Lebeau 74c5d45511 Fix custom selector engine load path resolution. 2009-11-30 12:45:13 +01:00
Tobie Langel 6b00f24963 Merge branch 'selector_agnostic'
Conflicts:
	src/dom/selector.js
2009-11-30 11:32:09 +01:00
Tobie Langel cdb41a170f Add sizzle to ext/. 2009-11-30 11:12:26 +01:00
Juriy Zaytsev b3fc07922c Avoid object creation and an unnecessary function call in `Class#addMethods`, when working around JScript DontEnum bug. 2009-11-13 15:49:22 -05:00
Juriy Zaytsev 18f2ac65c3 Optimize Element#immediateDescendants. 2009-11-13 14:28:27 -05:00
Juriy Zaytsev 82c9b9c783 Remove unnecessary function object creation and `Number#times` in `Element._getContentFromAnonymousElement`. 2009-11-13 14:21:14 -05:00
Juriy Zaytsev 9ef3f8d2ed Eliminate runtime forking and long method lookup in `Element.hasAttribute`. 2009-11-13 12:27:10 -05:00
Juriy Zaytsev 829800834d Do not create translations object every time method is called. 2009-11-12 21:21:42 -05:00
Juriy Zaytsev c272e40042 Minor optimization in class module. 2009-11-12 21:17:37 -05:00
Juriy Zaytsev f40fd5a7d6 Remove redundant ternary. 2009-11-12 21:15:52 -05:00
Juriy Zaytsev 1f167f8754 `if` should be followed by space. 2009-11-11 17:43:25 -05:00
Juriy Zaytsev 01a229011a Avoid repeating declaration statements. 2009-11-11 17:32:19 -05:00
Andrew Dupont 5d027eb939 Merge branch 'master' of git@github.com:sstephenson/prototype 2009-10-30 02:59:14 -05:00
Tobie Langel 678774cbd6 Minor changes to the Sizzle adapter. 2009-10-26 02:00:55 +01:00
Tobie Langel 74ae0a5537 Renamed Prototype.Legacy to Prototype.LegacySelector by popular request. 2009-10-25 16:35:59 +01:00
Tobie Langel 70c5e98d44 Make the UpdaterHelper function on WebKit-based browsers. 2009-10-25 16:24:51 +01:00
Tobie Langel 24569d1d98 Deprecate the Selector API. 2009-10-25 16:13:11 +01:00
Tobie Langel fdf3424f78 Add unit tests. 2009-10-25 00:40:48 +02:00
Tobie Langel 107f812525 Modify PrototypeHelper.sprocketize to take a hash of options rather than separate arguments. 2009-10-24 22:17:37 +02:00
Tobie Langel 83826829a7 Add Prototype.Selector.engine which simply holds a reference to the actual selector engine used. 2009-10-24 16:12:38 +02:00
Tobie Langel 5f85799c3f Refactor NWMatcher adapter. 2009-10-23 19:29:03 +02:00
Tobie Langel 75aab03eba Repo and Rakefile refactoring. 2009-10-23 18:32:07 +02:00
Tobie Langel 7f5ce1e6c2 Clean-up NWMatcher proxy. 2009-10-23 13:17:53 +02:00
Tobie Langel f6f6955a71 Marked old Selector API as deprecated. 2009-10-23 12:58:10 +02:00
Tobie Langel b0159bdba7 Document Prototype.Selector API. 2009-10-23 12:53:03 +02:00
Tobie Langel af89847a4f Make Event.stopObserving return element in all cases. [#810 state:resolved] 2009-10-23 07:51:50 +02:00
Tobie Langel bf8e404805 Make Event.stopObserving return element in all cases. [#810 state:resolved] 2009-10-23 07:49:57 +02:00
Tobie Langel ed27b225a5 Fix Element extension when using the NWMatcher selector engine. (jddalton) 2009-10-23 07:31:37 +02:00
Tobie Langel 15c323b9ac Include NWMatcher as a submodule. 2009-10-23 07:18:52 +02:00
Tobie Langel 17e8064d8a Add legacy Prototype selector engine. Acessible as Prototype.Legacy. Use SELECTOR_ENGINE=legacy to build. 2009-10-23 06:39:59 +02:00
Tobie Langel cba5468b09 Nitpicking. 2009-10-23 06:38:27 +02:00
Tobie Langel 7762e002cb Reorder repository to allow for custom selector engines to be included instead of Sizzle (the current default). Selector engines belong in the vendor directory and must have a selector_engine.js file. To build a Prototype with your engine of choice just spepcify it at build time using the SELECTOR_ENGINE option. For example, to build a version with NSMatcher: rake dist SELECTOR_ENGINE=nwmatcher. 2009-10-23 05:49:40 +02:00
Tobie Langel 3e19f959a2 Fix Selector#findElements. 2009-10-23 04:42:05 +02:00
Tobie Langel da3e1e361e Clean-up. 2009-10-23 04:10:30 +02:00
Tobie Langel 2d13d45dc8 Remove dependencies to Selector in favor of Prototype.Selector throughout the library. 2009-10-23 01:43:48 +02:00
Tobie Langel caf66395d5 Add Prototype.Selector object with select, match and filter methods as a wraper around Sizzle.Redefine the whole of Selector API in terms of Prototype.Selector. 2009-10-23 01:17:53 +02:00
Yaffle 2d3e423230 Add missing semicolons. [#837 state:resolved] 2009-10-21 18:25:27 +02:00
Tobie Langel f9c680a9ba More nitpicking. 2009-10-21 17:58:09 +02:00
Tobie Langel 8783065b8e Cosmetic rewrite of String#startsWith and String#endsWith with performance-related comments. 2009-10-21 17:24:09 +02:00
Tobie Langel 35ed99ba2e doc: nitpicking. 2009-10-21 17:00:17 +02:00
Tobie Langel 067a0ec364 Update to latest PDoc release. 2009-10-21 16:35:43 +02:00
tjcrowder 859197ca8b doc: Merged/updated old docs for Element.descendants. 2009-10-09 17:20:39 +01:00
tjcrowder d10aad7bfa doc: Merged/updated old docs for Element.descendantOf. 2009-10-09 17:15:15 +01:00
tjcrowder adf80ad1b3 doc: Merged/updated old docs for Element.cumulativeScrollOffset, clarified units, added example. 2009-10-09 17:10:13 +01:00
tjcrowder f1f6fca60b doc: Clarified units in Element.cumulativeOffset and added example. 2009-10-09 17:01:40 +01:00
tjcrowder c448b38f7b doc: Merged/updated old docs for Element.clonePosition. 2009-10-09 16:55:42 +01:00
tjcrowder 9ce1ea06b5 doc: Merged/updated old docs for Element.cleanWhitespace. 2009-10-09 16:10:44 +01:00
tjcrowder 1e29e3c6c9 doc: Merged/updated old docs for Element.classNames, mostly by marking it deprecated. 2009-10-09 15:49:54 +01:00
tjcrowder 892eb9d6b3 doc: Merged/updated old docs for Element.childElements / Element.immediateDescendants. Made immediateDescendants an alias of childElements rather than vice-versa as the latter is depreceated. 2009-10-09 15:34:39 +01:00
tjcrowder e3c89c08c6 doc: Merged/updated old docs for Element.ancestors. 2009-10-09 14:48:47 +01:00
tjcrowder 402a2d408e doc: Merged/updated old docs for Element.adjacent 2009-10-09 14:31:02 +01:00
tjcrowder 77832408bd doc: Merged/updated old docs for Element.addClassName 2009-10-09 14:14:14 +01:00
tjcrowder 7df62ce864 doc: Merged/updated old docs for Element.extend 2009-10-09 13:56:39 +01:00
tjcrowder d6d3ab1fef doc: Merged/updated old docs for Element constructor 2009-10-09 13:36:14 +01:00
tjcrowder 7d073ad56a doc: Merged/updated old docs for Element overview 2009-10-09 13:35:38 +01:00
tjcrowder d2874c0294 doc: Merged old docs for Element.addMethods. 2009-10-08 14:46:14 +01:00
Juriy Zaytsev 3b525f194d String#startsWith, String#endsWith performance optimization [#808 state:resolved] 2009-09-28 19:21:37 -04:00
Samuel Lebeau f4ea4c6ef7 Rewrite `String#camelize` using `String#replace` with a replacement function [#297 state:resolved] 2009-09-26 13:36:42 -04:00
Andrew Dupont 4dedcd3b62 Merge branch 'master' of git@github.com:sstephenson/prototype 2009-09-15 18:27:56 -05:00
Andrew Dupont 58a2f9db28 Update to latest PDoc. 2009-09-15 18:27:46 -05:00
Andrew Dupont 19615e7a00 Cleanup on PDoc templates. 2009-09-15 18:27:35 -05:00
Andrew Dupont 5ccf8cbefd Change all H4s in _method_ documentation blocks to H5s. (Start with H5 when using headings in a method doc block; start with H4 when using headings in a namespace/class doc block.) 2009-09-09 23:18:45 -05:00
80 changed files with 2969 additions and 9970 deletions

8
.gitmodules vendored
View File

@ -11,6 +11,10 @@
path = vendor/sprockets
url = git://github.com/sstephenson/sprockets.git
[submodule "vendor/sizzle"]
path = vendor/sizzle
[submodule "vendor/nwmatcher/repository"]
path = vendor/nwmatcher/repository
url = git://github.com/dperini/nwmatcher.git
[submodule "vendor/sizzle/repository"]
path = vendor/sizzle/repository
url = git://github.com/jeresig/sizzle.git

View File

@ -1,3 +1,21 @@
* Avoid object creation and an unnecessary function call in `Class#addMethods`, when working around JScript DontEnum bug. Replace with feature test and a simple boolean check at runtime. (kangax)
* Optimize Element#immediateDescendants. (kangax, Tobie Langel)
* Remove unnecessary function object creation and `Number#times` in `Element._getContentFromAnonymousElement`. (kangax)
* Eliminate runtime forking and long method lookup in `Element.hasAttribute`. (kangax)
* Remove redundant ternary. (kangax)
* Avoid repeating declaration statements where it makes sense, for slightly better runtime performance and minification. (kangax)
* Make `Event.stopObserving` return element in all cases. [#810 state:resolved] (Yaffle, Tobie Langel)
* String#startsWith, String#endsWith performance optimization (Yaffle, Tobie Langel, kangax)
* Rewrite String#camelize using String#replace with a replacement function (Phred, John-David Dalton, Samuel Lebeau, kangax)
*1.6.1* (August 24, 2009)
* Avoid triggering a warning when Java is disabled in IE8. [#668 state:resolved] (orv, kangax, Andrew Dupont, Tobie Langel)

View File

@ -9,13 +9,13 @@ module PrototypeHelper
DOC_DIR = File.join(ROOT_DIR, 'doc')
TEMPLATES_DIR = File.join(ROOT_DIR, 'templates')
PKG_DIR = File.join(ROOT_DIR, 'pkg')
SIZZLE_DIR = File.join(ROOT_DIR, 'vendor', 'sizzle')
TEST_DIR = File.join(ROOT_DIR, 'test')
TEST_UNIT_DIR = File.join(TEST_DIR, 'unit')
TMP_DIR = File.join(TEST_UNIT_DIR, 'tmp')
VERSION = YAML.load(IO.read(File.join(SRC_DIR, 'constants.yml')))['PROTOTYPE_VERSION']
DEFAULT_SELECTOR_ENGINE = 'sizzle'
%w[sprockets pdoc unittest_js caja_builder sizzle].each do |name|
%w[sprockets pdoc unittest_js caja_builder].each do |name|
$:.unshift File.join(PrototypeHelper::ROOT_DIR, 'vendor', name, 'lib')
end
@ -37,31 +37,48 @@ module PrototypeHelper
exit
end
def self.sprocketize(path, source, destination = nil, strip_comments = true)
def self.sprocketize(options = {})
options = {
:destination => File.join(DIST_DIR, options[:source]),
:strip_comments => true
}.merge(options)
require_sprockets
require_sizzle
load_path = [SRC_DIR]
if selector_path = get_selector_engine(options[:selector_engine])
load_path << selector_path
end
secretary = Sprockets::Secretary.new(
:root => File.join(ROOT_DIR, path),
:load_path => [SRC_DIR, SIZZLE_DIR],
:source_files => [source],
:strip_comments => strip_comments
:root => File.join(ROOT_DIR, options[:path]),
:load_path => load_path,
:source_files => [options[:source]],
:strip_comments => options[:strip_comments]
)
destination = File.join(DIST_DIR, source) unless destination
secretary.concatenation.save_to(destination)
secretary.concatenation.save_to(options[:destination])
end
def self.build_doc_for(file)
mkdir_p TMP_DIR
temp_path = File.join(TMP_DIR, "prototype.temp.js")
sprocketize('src', file, temp_path, false)
sprocketize(
:path => 'src',
:source => file,
:destination => temp_path,
:selector_engine => ENV['SELECTOR_ENGINE'] || DEFAULT_SELECTOR_ENGINE,
:strip_comments => false
)
rm_rf DOC_DIR
PDoc::Runner.new(temp_path, {
:output => DOC_DIR,
:templates => File.join(TEMPLATES_DIR, "html"),
:index_page => 'README.markdown'
}).run
PDoc.run({
:source_files => [temp_path],
:destination => DOC_DIR,
:index_page => 'README.markdown',
:syntax_highlighter => :pygments,
:markdown_parser => :bluecloth
})
rm_rf temp_path
end
@ -82,9 +99,15 @@ module PrototypeHelper
require_submodule('CajaBuilder', 'caja_builder')
end
def self.require_sizzle
if !File.exists?(File.join(SIZZLE_DIR, 'sizzle.js'))
exit unless get_submodule("Sizzle", "sizzle")
def self.get_selector_engine(name)
return if name == DEFAULT_SELECTOR_ENGINE || !name
submodule_path = File.join(ROOT_DIR, "vendor", name)
return submodule_path if File.exist?(File.join(submodule_path, "repository", ".git"))
get_submodule('the required selector engine', "#{name}/repository")
unless File.exist?(submodule_path)
puts "The selector engine you required isn't available at vendor/#{name}.\n\n"
exit
end
end
@ -94,7 +117,6 @@ module PrototypeHelper
Kernel.system("git submodule init")
return true if Kernel.system("git submodule update vendor/#{path}")
# If we got this far, something went wrong.
puts "\nLooks like it didn't work. Try it manually:\n\n"
puts " $ git submodule init"
@ -128,7 +150,11 @@ task :default => [:dist, :dist_helper, :package, :clean_package_source]
desc "Builds the distribution."
task :dist do
PrototypeHelper.sprocketize("src", "prototype.js")
PrototypeHelper.sprocketize(
:path => 'src',
:source => 'prototype.js',
:selector_engine => ENV['SELECTOR_ENGINE'] || PrototypeHelper::DEFAULT_SELECTOR_ENGINE
)
end
namespace :doc do
@ -146,7 +172,7 @@ task :doc => ['doc:build']
desc "Builds the updating helper."
task :dist_helper do
PrototypeHelper.sprocketize("ext/update_helper", "prototype_update_helper.js")
PrototypeHelper.sprocketize(:path => 'ext/update_helper', :source => 'prototype_update_helper.js')
end
Rake::PackageTask.new('prototype', PrototypeHelper::VERSION) do |package|

View File

@ -81,7 +81,12 @@
new Test.Unit.Runner({
testGetStack: function() {
this.assertMatch(/prototype_update_helper\.html:\d+\n$/, prototypeUpdateHelper.getStack());
var stack = prototypeUpdateHelper.getStack();
if (stack === '') {
this.info('UpdaterHelper#getStack is currently not supported on this browser.')
} else {
this.assertMatch(/prototype_update_helper\.html:\d+\n$/, prototypeUpdateHelper.getStack());
}
},
testDisplay: function() {
@ -280,6 +285,38 @@
this.assertNotNotified();
},
testSelectorInstanceMethods: function() {
var selector = new Selector('div');
this.assertWarnNotified('The Selector class has been deprecated. Please use the new Prototype.Selector API instead.');
selector.findElements(document);
this.assertWarnNotified('Selector#findElements has been deprecated. Please use the new Prototype.Selector API instead.');
selector.match(document.documentElement);
this.assertWarnNotified('Selector#match has been deprecated. Please use the new Prototype.Selector API instead.');
selector.toString();
this.assertWarnNotified('Selector#toString has been deprecated. Please use the new Prototype.Selector API instead.');
selector.inspect();
this.assertWarnNotified('Selector#inspect has been deprecated. Please use the new Prototype.Selector API instead.');
},
testSelectorMatchElements: function() {
Selector.matchElements([], 'div');
this.assertWarnNotified('Selector.matchElements has been deprecated. Please use the new Prototype.Selector API instead.');
},
testSelectorFindElement: function() {
Selector.findElement([], 'div');
this.assertWarnNotified('Selector.findElement has been deprecated. Please use the new Prototype.Selector API instead.');
},
testSelectorFindChildElements: function() {
Selector.findChildElements(document, 'div');
this.assertWarnNotified('Selector.findChildElements has been deprecated. Please use the new Prototype.Selector API instead.');
},
testLogDeprecationOption: function() {
prototypeUpdateHelper.logLevel = UpdateHelper.Warn;
var h = $H({ foo: 2 });

View File

@ -1,6 +1,6 @@
//= require "update_helper"
/* UpdateHelper for Prototype <%= PROTOTYPE_VERSION %> (c) 2008 Tobie Langel
/* UpdateHelper for Prototype <%= PROTOTYPE_VERSION %> (c) 2008-2009 Tobie Langel
*
* UpdateHelper for Prototype is freely distributable under the same
* terms as Prototype (MIT-style license).
@ -17,7 +17,7 @@
*
* This, for example, will prevent deprecation messages from being logged.
*
* THIS SCRIPT WORKS IN FIREFOX ONLY
* THIS SCRIPT DOES NOT WORK IN INTERNET EXPLORER
*--------------------------------------------------------------------------*/
var prototypeUpdateHelper = new UpdateHelper([
@ -275,6 +275,62 @@ var prototypeUpdateHelper = new UpdateHelper([
message: 'The class API has been fully revised and now allows for mixins and inheritance.\n' +
'You can find more about it here: http://prototypejs.org/learn/class-inheritance',
condition: function() { return !arguments.length }
},
{
methodName: 'initialize',
namespace: Selector.prototype,
message: 'The Selector class has been deprecated. Please use the new Prototype.Selector API instead.',
type: 'warn'
},
{
methodName: 'findElements',
namespace: Selector.prototype,
message: 'Selector#findElements has been deprecated. Please use the new Prototype.Selector API instead.',
type: 'warn'
},
{
methodName: 'match',
namespace: Selector.prototype,
message: 'Selector#match has been deprecated. Please use the new Prototype.Selector API instead.',
type: 'warn'
},
{
methodName: 'toString',
namespace: Selector.prototype,
message: 'Selector#toString has been deprecated. Please use the new Prototype.Selector API instead.',
type: 'warn'
},
{
methodName: 'inspect',
namespace: Selector.prototype,
message: 'Selector#inspect has been deprecated. Please use the new Prototype.Selector API instead.',
type: 'warn'
},
{
methodName: 'matchElements',
namespace: Selector,
message: 'Selector.matchElements has been deprecated. Please use the new Prototype.Selector API instead.',
type: 'warn'
},
{
methodName: 'findElement',
namespace: Selector,
message: 'Selector.findElement has been deprecated. Please use the new Prototype.Selector API instead.',
type: 'warn'
},
{
methodName: 'findChildElements',
namespace: Selector,
message: 'Selector.findChildElements has been deprecated. Please use the new Prototype.Selector API instead.',
type: 'warn'
}
]);

View File

@ -1,4 +1,4 @@
/* Update Helper (c) 2008 Tobie Langel
/* Update Helper (c) 2008-2009 Tobie Langel
*
* Requires Prototype >= 1.6.0
*
@ -54,9 +54,12 @@ var UpdateHelper = Class.create({
try {
throw new Error("stack");
} catch(e) {
return (e.stack || '').match(this.Regexp).reject(function(path) {
return /(prototype|unittest|update_helper)\.js/.test(path);
}).join("\n");
var match = (e.stack || '').match(this.Regexp);
if (match) {
return match.reject(function(path) {
return (/(prototype|unittest|update_helper)\.js/).test(path);
}).join("\n");
} else { return ''; }
}
},

View File

@ -64,14 +64,14 @@ Ajax.Response = Class.create({
var transport = this.transport = request.transport,
readyState = this.readyState = transport.readyState;
if((readyState > 2 && !Prototype.Browser.IE) || readyState == 4) {
if ((readyState > 2 && !Prototype.Browser.IE) || readyState == 4) {
this.status = this.getStatus();
this.statusText = this.getStatusText();
this.responseText = String.interpret(transport.responseText);
this.headerJSON = this._getHeaderJSON();
}
if(readyState == 4) {
if (readyState == 4) {
var xml = transport.responseXML;
this.responseXML = Object.isUndefined(xml) ? null : xml;
this.responseJSON = this._getResponseJSON();
@ -121,7 +121,7 @@ Ajax.Response = Class.create({
},
/**
* Ajax.Response.getResponseHeader(name) -> String
* Ajax.Response#getResponseHeader(name) -> String
*
* Returns the value of the requested header if present; throws an error
* otherwise. This is just a wrapper around the `XmlHttpRequest` method of
@ -132,7 +132,7 @@ Ajax.Response = Class.create({
},
/**
* Ajax.Response.getAllResponseHeaders() -> String
* Ajax.Response#getAllResponseHeaders() -> String
*
* Returns a string containing all headers separated by line breaks; throws
* an error if no headers exist. This is just a wrapper around the

View File

@ -184,3 +184,95 @@ Element.ClassNames.prototype = {
Object.extend(Element.ClassNames.prototype, Enumerable);
/*--------------------------------------------------------------------------*/
/** deprecated, section: DOM
* class Selector
*
* A class that queries the document for elements that match a given CSS
* selector.
**/
(function() {
window.Selector = Class.create({
/** deprecated
* new Selector(expression)
* - expression (String): A CSS selector.
*
* Creates a `Selector` with the given CSS selector.
**/
initialize: function(expression) {
this.expression = expression.strip();
},
/** deprecated
* Selector#findElements(root) -> [Element...]
* - root (Element | document): A "scope" to search within. All results will
* be descendants of this node.
*
* Searches the document for elements that match the instance's CSS
* selector.
**/
findElements: function(rootElement) {
return Prototype.Selector.select(this.expression, rootElement);
},
/** deprecated
* Selector#match(element) -> Boolean
*
* Tests whether a `element` matches the instance's CSS selector.
**/
match: function(element) {
return Prototype.Selector.match(element, this.expression);
},
toString: function() {
return this.expression;
},
inspect: function() {
return "#<Selector: " + this.expression + ">";
}
});
Object.extend(Selector, {
/** deprecated
* Selector.matchElements(elements, expression) -> [Element...]
*
* Filters the given collection of elements with `expression`.
*
* The only nodes returned will be those that match the given CSS selector.
**/
matchElements: Prototype.Selector.filter,
/** deprecated
* Selector.findElement(elements, expression[, index = 0]) -> Element
* Selector.findElement(elements[, index = 0]) -> Element
*
* Returns the `index`th element in the collection that matches
* `expression`.
*
* Returns the `index`th element overall if `expression` is not given.
**/
findElement: function(elements, expression, index) {
index = index || 0;
var matchIndex = 0, element;
// Match each element individually, since Sizzle.matches does not preserve order
for (var i = 0, length = elements.length; i < length; i++) {
element = elements[i];
if (Prototype.Selector.match(element, expression) && index === matchIndex++) {
return Element.extend(element);
}
}
},
/** deprecated
* Selector.findChildElements(element, expressions) -> [Element...]
*
* Searches beneath `element` for any elements that match the selector
* (or selectors) specified in `expressions`.
**/
findChildElements: function(element, expressions) {
var selector = expressions.toArray().join(', ');
return Prototype.Selector.select(selector, element || document);
}
});
})();

View File

@ -19,8 +19,15 @@
*
**/
/** section: DOM
* Prototype
*
* The Prototype namespace.
*
**/
//= require "dom/dom"
//= require <selector_engine>
//= require "dom/selector"
//= require "dom/form"
//= require "dom/event"

File diff suppressed because it is too large Load Diff

View File

@ -25,7 +25,10 @@
* browsers.
*
* `Event` also provides a standardized list of key codes you can use with
* keyboard-related events.
* keyboard-related events, including `KEY_BACKSPACE`, `KEY_TAB`,
* `KEY_RETURN`, `KEY_ESC`, `KEY_LEFT`, `KEY_UP`, `KEY_RIGHT`, `KEY_DOWN`,
* `KEY_DELETE`, `KEY_HOME`, `KEY_END`, `KEY_PAGEUP`, `KEY_PAGEDOWN` and
* `KEY_INSERT`.
*
* The functions you're most likely to use a lot are [[Event.observe]],
* [[Event.element]] and [[Event.stop]]. If your web app uses custom events,
@ -149,10 +152,14 @@
function findElement(event, expression) {
var element = Event.element(event);
if (!expression) return element;
var elements = [element].concat(element.ancestors());
return Selector.findElement(elements, expression, 0);
while (element) {
if (Prototype.Selector.match(element, expression)) {
return Element.extend(element);
}
element = element.parentNode;
}
}
/**
* Event.pointer(@event) -> Object
*
@ -379,12 +386,12 @@
window.addEventListener('unload', Prototype.emptyFunction, false);
var _getDOMEventName = Prototype.K;
var _getDOMEventName = Prototype.K,
translations = { mouseenter: "mouseover", mouseleave: "mouseout" };
if (!MOUSEENTER_MOUSELEAVE_EVENTS_SUPPORTED) {
_getDOMEventName = function(eventName) {
var translations = { mouseenter: "mouseover", mouseleave: "mouseout" };
return eventName in translations ? translations[eventName] : eventName;
return (translations[eventName] || eventName);
};
}
@ -408,6 +415,7 @@
* * Prototype handles cleaning up the handler when leaving the page (important for MSIE memory
* leak prevention).
* * `observe` makes it possible to stop observing the event easily via [[Event.stopObserving]].
* * Adds support for `mouseenter` / `mouseleave` in all browsers.
*
* Although you can use `Event.observe` directly and there are times when that's the most
* convenient or direct way, it's more common to use its alias [[Element#observe]]. These two
@ -613,48 +621,39 @@
* ...and then to remove:
*
* $('foo').stopObserving('click', this.boundHandlerMethod); // <== Right
*
**/
function stopObserving(element, eventName, handler) {
element = $(element);
var registry = Element.retrieve(element, 'prototype_event_registry');
if (!registry) return element;
if (Object.isUndefined(registry)) return element;
if (eventName && !handler) {
// If an event name is passed without a handler, we stop observing all
// handlers of that type.
var responders = registry.get(eventName);
if (Object.isUndefined(responders)) return element;
responders.each( function(r) {
Element.stopObserving(element, eventName, r.handler);
});
return element;
} else if (!eventName) {
// If both the event name and the handler are omitted, we stop observing
// _all_ handlers on the element.
if (!eventName) {
// We stop observing all events.
// e.g.: $(element).stopObserving();
registry.each( function(pair) {
var eventName = pair.key, responders = pair.value;
responders.each( function(r) {
Element.stopObserving(element, eventName, r.handler);
});
var eventName = pair.key;
stopObserving(element, eventName);
});
return element;
}
var responders = registry.get(eventName);
if (!responders) return element;
// Fail gracefully if there are no responders assigned.
if (!responders) return;
if (!handler) {
// We stop observing all handlers for the given eventName.
// e.g.: $(element).stopObserving('click');
responders.each(function(r) {
stopObserving(element, eventName, r.handler);
});
return element;
}
var responder = responders.find( function(r) { return r.handler === handler; });
if (!responder) return element;
var actualEventName = _getDOMEventName(eventName);
if (eventName.include(':')) {
// Custom event.
if (element.removeEventListener)
@ -665,6 +664,7 @@
}
} else {
// Ordinary event.
var actualEventName = _getDOMEventName(eventName);
if (element.removeEventListener)
element.removeEventListener(actualEventName, responder, false);
else
@ -745,7 +745,7 @@
});
/** section: DOM
* document
* document
*
* Prototype extends the built-in `document` object with several convenience
* methods related to events.

View File

@ -46,7 +46,7 @@ var Form = {
* fields are included in that object or string.
*
* If you do not supply an `options` object _at all_, the options
* `{hash: false}` are used.
* `{ hash: false }` are used.
*
* If you supply an `options` object, it may have the following options:
* - `hash` ([[Boolean]]): `true` to return a plain object with keys and values
@ -248,7 +248,7 @@ Form.Methods = {
/*--------------------------------------------------------------------------*/
/** section: DOM
/**
* Form.Element
*
* Utilities for dealing with form controls in the DOM.
@ -359,7 +359,7 @@ Form.Element.Methods = {
},
/**
* Form.Element#activate(element) -> Element
* Form.Element.activate(@element) -> Element
*
* Gives focus to a form control and selects its contents if it is a text
* input.
@ -479,7 +479,7 @@ Form.Element.Serializers = {
* Abstract
**/
/** section: DOM
/**
* class Abstract.TimedObserver
*
* An abstract DOM element observer class, subclasses of which can be used to periodically
@ -528,7 +528,7 @@ Abstract.TimedObserver = Class.create(PeriodicalExecuter, {
}
});
/** section: DOM
/**
* class Form.Element.Observer < Abstract.TimedObserver
*
* An [[Abstract.TimedObserver]] subclass that watches for changes to a form field's value.
@ -551,7 +551,7 @@ Form.Element.Observer = Class.create(Abstract.TimedObserver, {
}
});
/** section: DOM
/**
* class Form.Observer < Abstract.TimedObserver
*
* An [[Abstract.TimedObserver]] subclass that watches for changes to a form.
@ -577,7 +577,7 @@ Form.Observer = Class.create(Abstract.TimedObserver, {
/*--------------------------------------------------------------------------*/
/** section: DOM
/**
* class Abstract.EventObserver
**/
Abstract.EventObserver = Class.create({
@ -619,7 +619,7 @@ Abstract.EventObserver = Class.create({
}
});
/** section: DOM
/**
* class Form.Element.EventObserver < Abstract.EventObserver
**/
Form.Element.EventObserver = Class.create(Abstract.EventObserver, {
@ -628,8 +628,8 @@ Form.Element.EventObserver = Class.create(Abstract.EventObserver, {
}
});
/** section: DOM
* class Form.Element.EventObserver < Abstract.EventObserver
/**
* class Form.EventObserver < Abstract.EventObserver
**/
Form.EventObserver = Class.create(Abstract.EventObserver, {
getValue: function() {

View File

@ -1,111 +1,66 @@
//= require <sizzle>
/** section: DOM
* class Selector
/** section: DOM, related to: Prototype.Selector
* $$(expression...) -> [Element...]
*
* A class that queries the document for elements that match a given CSS
* selector.
* Returns all elements in the document that match the provided CSS selectors.
**/
(function() {
function extend(elements) {
for (var i = 0, length = elements.length; i < length; i++)
elements[i] = Element.extend(elements[i]);
return elements;
}
window.Selector = Class.create({
/**
* new Selector(expression)
* - expression (String): A CSS selector.
*
* Creates a `Selector` with the given CSS selector.
**/
initialize: function(expression) {
this.expression = expression.strip();
},
/**
* Selector#findElements(root) -> [Element...]
* - root (Element || document): A "scope" to search within. All results will
* be descendants of this node.
*
* Searches the document for elements that match the instance's CSS
* selector.
**/
findElements: function(rootElement) {
return extend(Sizzle(this.expression, rootElement || document));
},
/**
* Selector#match(element) -> Boolean
*
* Tests whether a `element` matches the instance's CSS selector.
**/
match: function(element) {
return Sizzle.matches(this.expression, [element]).length == 1;
},
toString: function() {
return this.expression;
},
inspect: function() {
return "#<Selector: " + this.expression + ">";
}
});
window.$$ = function() {
var expression = $A(arguments).join(', ');
return Prototype.Selector.select(expression, document);
};
Object.extend(Selector, {
/**
* Selector.matchElements(elements, expression) -> [Element...]
*
* Filters the given collection of elements with `expression`.
*
* The only nodes returned will be those that match the given CSS selector.
**/
matchElements: function(elements, expression) {
return extend(Sizzle.matches(expression, elements));
},
/**
* Prototype.Selector
*
* A namespace that acts as a wrapper around
* the choosen selector engine (Sizzle by default).
*
**/
/**
* Selector.findElement(elements, expression[, index = 0]) -> Element
* Selector.findElement(elements[, index = 0]) -> Element
*
* Returns the `index`th element in the collection that matches
* `expression`.
*
* Returns the `index`th element overall if `expression` is not given.
**/
findElement: function(elements, expression, index) {
if (Object.isUndefined(index)) index = 0;
var selector = new Selector(expression), length = elements.length, matchIndex = 0, i;
// Implementation provided by selector engine.
// Match each element individually, since Sizzle.matches does not preserve order
for (i = 0; i < length; i++) {
if (selector.match(elements[i]) && index == matchIndex++) {
return Element.extend(elements[i]);
}
/**
* Prototype.Selector.select(expression[, root = document]) -> [Element...]
* - expression (String): A CSS selector.
* - root (Element | document): A "scope" to search within. All results will
* be descendants of this node.
*
* Searches `root` for elements that match the provided CSS selector and returns an
* array of extended [[Element]] objects.
**/
// Implementation provided by selector engine.
/**
* Prototype.Selector.match(element, expression) -> Boolean
* - element (Element): a DOM element.
* - expression (String): A CSS selector.
*
* Tests whether `element` matches the CSS selector.
**/
// Implementation provided by selector engine.
/**
* Prototype.Selector.find(elements, expression[, index = 0]) -> Element
* - elements (Enumerable): a collection of DOM elements.
* - expression (String): A CSS selector.
* - index: Numeric index of the match to return, defaults to 0.
*
* Filters the given collection of elements with `expression` and returns the
* first matching element (or the `index`th matching element if `index` is
* specified).
**/
if (!Prototype.Selector.find) {
Prototype.Selector.find = function(elements, expression, index) {
if (Object.isUndefined(index)) index = 0;
var match = Prototype.Selector.match, length = elements.length, matchIndex = 0, i;
for (i = 0; i < length; i++) {
if (match(elements[i], expression) && index == matchIndex++) {
return Element.extend(elements[i]);
}
},
/**
* Selector.findChildElements(element, expressions) -> [Element...]
*
* Searches beneath `element` for any elements that match the selector
* (or selectors) specified in `expressions`.
**/
findChildElements: function(element, expressions) {
var results = [], exprs = expressions.toArray();
while (exprs.length) Sizzle(exprs.shift(), element || document, results);
return extend(results);
}
});
/** related to: Selector
* $$(expression...) -> [Element...]
*
* Returns all elements in the document that match the provided CSS selectors.
**/
window.$$ = function() {
return Selector.findChildElements(document, $A(arguments));
}
})();
}

View File

@ -9,6 +9,17 @@
* inheritance](http://prototypejs.org/learn/class-inheritance).
**/
var Class = (function() {
// Some versions of JScript fail to enumerate over properties, names of which
// correspond to non-enumerable properties in the prototype chain
var IS_DONTENUM_BUGGY = (function(){
for (var p in { toString: 1 }) {
// check actual property name, so that it works with augmented Object.prototype
if (p === 'toString') return false;
}
return true;
})();
/**
* Class.create([superclass][, methods...]) -> Class
* - superclass (Class): The optional superclass to inherit methods from.
@ -59,7 +70,7 @@ var Class = (function() {
parent.subclasses.push(klass);
}
for (var i = 0; i < properties.length; i++)
for (var i = 0, length = properties.length; i < length; i++)
klass.addMethods(properties[i]);
if (!klass.prototype.initialize)
@ -135,12 +146,13 @@ var Class = (function() {
* //-> alerts "You should probably run. He looks really mad."
**/
function addMethods(source) {
var ancestor = this.superclass && this.superclass.prototype;
var properties = Object.keys(source);
var ancestor = this.superclass && this.superclass.prototype,
properties = Object.keys(source);
// IE6 doesn't enumerate toString and valueOf properties,
// Force copy if they're not coming from Object.prototype.
if (!Object.keys({ toString: true }).length) {
// IE6 doesn't enumerate `toString` and `valueOf` (among other built-in `Object.prototype`) properties,
// Force copy if they're not Object.prototype ones.
// Do not copy other Object.prototype.* for performance reasons
if (IS_DONTENUM_BUGGY) {
if (source.toString != Object.prototype.toString)
properties.push("toString");
if (source.valueOf != Object.prototype.valueOf)
@ -150,7 +162,7 @@ var Class = (function() {
for (var i = 0, length = properties.length; i < length; i++) {
var property = properties[i], value = source[property];
if (ancestor && Object.isFunction(value) &&
value.argumentNames().first() == "$super") {
value.argumentNames()[0] == "$super") {
var method = value;
value = (function(m) {
return function() { return ancestor[m].apply(this, arguments); };

View File

@ -217,7 +217,13 @@
function isArray(object) {
return _toString.call(object) == "[object Array]";
}
var hasNativeIsArray = (typeof Array.isArray == 'function')
&& Array.isArray([]) && !Array.isArray({});
if (hasNativeIsArray) {
isArray = Array.isArray;
}
/**
* Object.isHash(object) -> Boolean

View File

@ -42,6 +42,11 @@ Object.extend(String.prototype, (function() {
* Returns the string with every occurence of a given pattern replaced by either
* a regular string, the returned value of a function or a [[Template]] string.
* The pattern can be a string or a regular expression.
*
* <h5>Example</h5>
*
* ""hello".gsub(/([aeiou])/, '<#{1}>');
* // => "h<e>ll<o>"
**/
function gsub(pattern, replacement) {
var result = '', source = this, match;
@ -73,6 +78,11 @@ Object.extend(String.prototype, (function() {
* Returns a string with the first count occurrences of pattern replaced by either
* a regular string, the returned value of a function or a [[Template]] string.
* The pattern can be a string or a regular expression.
*
* <h5>Example</h5>
*
* "20091201".sub(/^(\d{4})(\d{2})(\d{2})$/, "#{1}-#{2}-#{3}");
* // => "2009-12-01"
**/
function sub(pattern, replacement, count) {
replacement = prepareReplacement(replacement);
@ -131,7 +141,7 @@ Object.extend(String.prototype, (function() {
*
* Note that the processing `stripTags` does is good enough for most purposes, but
* you cannot rely on it for security purposes. If you're processing end-user-supplied
* content, `stripTags` is probably _not_ sufficiently robust to ensure that the content
* content, `stripTags` is _not_ sufficiently robust to ensure that the content
* is completely devoid of HTML tags in the case of a user intentionally trying to circumvent
* tag restrictions. But then, you'll be running them through [[String#escapeHTML]] anyway,
* won't you?
@ -167,8 +177,8 @@ Object.extend(String.prototype, (function() {
* returns them as an array of strings.
**/
function extractScripts() {
var matchAll = new RegExp(Prototype.ScriptFragment, 'img');
var matchOne = new RegExp(Prototype.ScriptFragment, 'im');
var matchAll = new RegExp(Prototype.ScriptFragment, 'img'),
matchOne = new RegExp(Prototype.ScriptFragment, 'im');
return (this.match(matchAll) || []).map(function(scriptTag) {
return (scriptTag.match(matchOne) || ['', ''])[1];
});
@ -251,8 +261,9 @@ Object.extend(String.prototype, (function() {
return match[1].split(separator || '&').inject({ }, function(hash, pair) {
if ((pair = pair.split('='))[0]) {
var key = decodeURIComponent(pair.shift());
var value = pair.length > 1 ? pair.join('=') : pair[0];
var key = decodeURIComponent(pair.shift()),
value = pair.length > 1 ? pair.join('=') : pair[0];
if (value != undefined) value = decodeURIComponent(value);
if (key in hash) {
@ -311,17 +322,9 @@ Object.extend(String.prototype, (function() {
* // -> 'MozBinding'
**/
function camelize() {
var parts = this.split('-'), len = parts.length;
if (len == 1) return parts[0];
var camelized = this.charAt(0) == '-'
? parts[0].charAt(0).toUpperCase() + parts[0].substring(1)
: parts[0];
for (var i = 1; i < len; i++)
camelized += parts[i].charAt(0).toUpperCase() + parts[i].substring(1);
return camelized;
return this.replace(/-+(.)?/g, function(match, chr) {
return chr ? chr.toUpperCase() : '';
});
}
/**
@ -437,7 +440,9 @@ Object.extend(String.prototype, (function() {
* Checks if the string starts with `substring`.
**/
function startsWith(pattern) {
return this.indexOf(pattern) === 0;
// We use `lastIndexOf` instead of `indexOf` to avoid tying execution
// time to string length when string doesn't start with pattern.
return this.lastIndexOf(pattern, 0) === 0;
}
/**
@ -447,7 +452,9 @@ Object.extend(String.prototype, (function() {
**/
function endsWith(pattern) {
var d = this.length - pattern.length;
return d >= 0 && this.lastIndexOf(pattern) === d;
// We use `indexOf` instead of `lastIndexOf` to avoid tying execution
// time to string length when string doesn't end with pattern.
return d >= 0 && this.indexOf(pattern, d) === d;
}
/**
@ -486,7 +493,7 @@ Object.extend(String.prototype, (function() {
truncate: truncate,
// Firefox 3.5+ supports String.prototype.trim
// (`trim` is ~ 5x faster than `strip` in FF3.5)
strip: String.prototype.trim ? String.prototype.trim : strip,
strip: String.prototype.trim || strip,
stripTags: stripTags,
stripScripts: stripScripts,
extractScripts: extractScripts,

View File

@ -82,14 +82,14 @@
* inadequate, there's a provision for customization. `Template`'s
* constructor accepts an optional second argument that is a regular expression
* object to match the replaceable symbols in the template string. Let's put
* together a template that uses a syntax similar to the ubiquitous `<&#38;= %>`
* together a template that uses a syntax similar to the now ubiquitous `{{ }}`
* constructs:
*
* // matches symbols like '<&#38;= field %>'
* var syntax = /(^|.|\r|\n)(\<%=\s*(\w+)\s*%\>)/;
* // matches symbols like '{{ field }}'
* var syntax = /(^|.|\r|\n)(\{{\s*(\w+)\s*}})/;
*
* var t = new Template(
* '<div>Name: <b><&#38;= name %></b>, Age: <b><&#38;=age%></b></div>',
* '<div>Name: <b>{{ name }}</b>, Age: <b>{{ age }}</b></div>',
* syntax);
* t.evaluate( {name: 'John Smith', age: 26} );
* // -> <div>Name: <b>John Smith</b>, Age: <b>26</b></div>
@ -133,8 +133,9 @@ var Template = Class.create({
var before = match[1] || '';
if (before == '\\') return match[2];
var ctx = object, expr = match[3];
var pattern = /^([^.[]+|\[((?:.*?[^\\])?)\])(\.|\[|$)/;
var ctx = object, expr = match[3],
pattern = /^([^.[]+|\[((?:.*?[^\\])?)\])(\.|\[|$)/;
match = pattern.exec(expr);
if (match == null) return before;

6
src/prototype.js vendored
View File

@ -35,9 +35,9 @@ var Prototype = {
if (typeof window.HTMLDivElement !== 'undefined')
return true;
var div = document.createElement('div');
var form = document.createElement('form');
var isSupported = false;
var div = document.createElement('div'),
form = document.createElement('form'),
isSupported = false;
if (div['__proto__'] && (div['__proto__'] !== form['__proto__'])) {
isSupported = true;

29
src/selector_engine.js Normal file
View File

@ -0,0 +1,29 @@
Prototype._original_property = window.Sizzle;
//= require "sizzle"
Prototype.Selector = (function(engine) {
function extend(elements) {
for (var i = 0, length = elements.length; i < length; i++) {
Element.extend(elements[i]);
}
return elements;
}
function select(selector, scope) {
return extend(engine(selector, scope || document));
}
function match(element, selector) {
return engine.matches(selector, [element]).length == 1;
}
return {
engine: engine,
select: select,
match: match
};
})(Sizzle);
// Restore globals.
window.Sizzle = Prototype._original_property;
delete Prototype._original_property;

1015
src/sizzle.js Normal file

File diff suppressed because it is too large Load Diff

Binary file not shown.

Before

Width:  |  Height:  |  Size: 733 B

Binary file not shown.

Before

Width:  |  Height:  |  Size: 1.5 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 1.2 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 857 B

Binary file not shown.

Before

Width:  |  Height:  |  Size: 599 B

Binary file not shown.

Before

Width:  |  Height:  |  Size: 981 B

Binary file not shown.

Before

Width:  |  Height:  |  Size: 584 B

Binary file not shown.

Before

Width:  |  Height:  |  Size: 786 B

Binary file not shown.

Before

Width:  |  Height:  |  Size: 125 B

Binary file not shown.

Before

Width:  |  Height:  |  Size: 4.0 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 18 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 1.6 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 3.9 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 778 B

Binary file not shown.

Before

Width:  |  Height:  |  Size: 853 B

Binary file not shown.

Before

Width:  |  Height:  |  Size: 613 B

Binary file not shown.

Before

Width:  |  Height:  |  Size: 6.7 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 1.6 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 1.3 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 1.1 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 970 B

Binary file not shown.

Before

Width:  |  Height:  |  Size: 599 B

Binary file not shown.

Before

Width:  |  Height:  |  Size: 343 B

Binary file not shown.

Before

Width:  |  Height:  |  Size: 946 B

Binary file not shown.

Before

Width:  |  Height:  |  Size: 764 B

Binary file not shown.

Before

Width:  |  Height:  |  Size: 764 B

Binary file not shown.

Before

Width:  |  Height:  |  Size: 1.9 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 630 B

View File

@ -1,389 +0,0 @@
if (typeof PDoc === "undefined") window.PDoc = {};
// Poor-man's history manager. Polls for changes to the hash.
(function() {
var PREVIOUS_HASH = null;
Event.observe(window, "load", function() {
var hash = window.location.hash;
if (hash && hash !== PREVIOUS_HASH) {
document.fire("hash:changed",
{ previous: PREVIOUS_HASH, current: hash });
PREVIOUS_HASH = hash;
}
window.setTimeout(arguments.callee, 100);
});
})();
// Place a "frame" around the element described by the hash.
// Update the frame when the hash changes.
PDoc.highlightSelected = function() {
if (!window.location.hash) return;
element = $(window.location.hash.substr(1));
if (element) PDoc.highlight(element.up('li, div'));
};
document.observe("hash:changed", PDoc.highlightSelected);
PDoc.highlight = function(element) {
var self = arguments.callee;
if (!self.frame) {
self.frame = new Element('div', { 'class': 'highlighter' });
document.body.appendChild(self.frame);
}
var frame = self.frame;
element.getOffsetParent().appendChild(frame);
var offset = element.positionedOffset();
var w = parseFloat(element.getStyle('width')),
h = parseFloat(element.getStyle('height'));
frame.setStyle({
position: 'absolute',
top: (offset.top - 15) + 'px',
left: (offset.left - 12) + 'px',
width: (w + 20) + 'px',
height: (h + 30) + 'px'
});
// Defer this call because Safari hasn't yet scrolled the viewport.
(function() {
var frameOffset = frame.viewportOffset(frame);
if (frameOffset.top < 0) {
window.scrollBy(0, frameOffset.top - 10);
}
}).defer();
};
// Live API search.
var Filterer = Class.create({
initialize: function(element, options) {
this.element = $(element);
this.options = Object.extend({
interval: 0.1,
resultsElement: '.search-results'
}, options || {});
this.element.writeAttribute("autocomplete", "off");
this.element.up('form').observe("submit", Event.stop);
// // The Safari-only "search" input type is prettier
// if (Prototype.Browser.WebKit)
// this.element.type = "search";
this.menu = this.options.menu;
this.links = this.menu.select('a');
this.resultsElement = this.options.resultsElement;
this.resultsElement.setStyle({
overflowX: 'hidden'
});
this.events = {
filter: this.filter.bind(this),
keydown: this.keydown.bind(this)
};
this.menu.setStyle({ opacity: 0.9 });
this.addObservers();
this.element.value = '';
},
addObservers: function() {
this.element.observe('keyup', this.events.filter);
},
filter: function(event) {
if (this._timer) window.clearTimeout(this._timer);
// Clear the text box on ESC
if (event.keyCode && event.keyCode === Event.KEY_ESC) {
this.element.value = '';
}
if ([Event.KEY_UP, Event.KEY_DOWN, Event.KEY_RETURN].include(event.keyCode))
return;
var value = $F(this.element).strip().toLowerCase();
if (value === "") {
this.onEmpty();
return;
}
var urls = this.findURLs(value);
this.buildResults(urls);
},
keydown: function(event) {
if (![Event.KEY_UP, Event.KEY_DOWN, Event.KEY_RETURN].include(event.keyCode))
return;
// ignore if any modifier keys are present
if (event.shiftKey || event.ctrlKey || event.altKey || event.metaKey)
return;
event.stop();
var highlighted = this.resultsElement.down('.highlighted');
if (event.keyCode === Event.KEY_RETURN) {
// Follow the highlighted item.
if (!highlighted) return;
window.location.href = highlighted.down('a').href;
} else {
var direction = (Event.KEY_DOWN === event.keyCode) ? 1 : -1;
highlighted = this.moveHighlight(direction);
}
if ([Event.KEY_UP, Event.KEY_DOWN].include(event.keyCode) &&
!Prototype.Browser.WebKit) {
// If up/down key is held down, list should keep scrolling.
// Safari does this automatically because it fires the keydown
// event over and over.
this._timer = window.setTimeout(this.scrollList.bind(this, direction), 1000);
}
},
moveHighlight: function(direction) {
var highlighted = this.resultsElement.down('.highlighted');
// move the focus
if (!highlighted) {
// if there is none, highlight the first result
var highlighted = this.resultsElement.down('li').addClassName('highlighted');
} else {
var method = (direction === 1) ? 'next' : 'previous';
highlighted.removeClassName('highlighted');
var adjacent = highlighted[method]('li');
if (!adjacent) {
adjacent = method == 'next' ? this.resultsElement.down('li') :
this.resultsElement.down('li:last-of-type');
}
adjacent.addClassName('highlighted');
highlighted = adjacent;
}
// Adjust the scroll offset of the container so that the highlighted
// item is always in view.
var distanceToBottom = highlighted.offsetTop + highlighted.offsetHeight;
if (distanceToBottom > this.resultsElement.offsetHeight + this.resultsElement.scrollTop) {
// item is too low
this.resultsElement.scrollTop = distanceToBottom - this.resultsElement.offsetHeight;
} else if (highlighted.offsetTop < this.resultsElement.scrollTop) {
// item is too high
this.resultsElement.scrollTop = highlighted.offsetTop;
}
return highlighted;
},
scrollList: function(direction) {
this.moveHighlight(direction);
this._timer = window.setTimeout(this.scrollList.bind(this, direction), 100);
},
// Given a path with any number of `../`s in front of it, remove them all.
// TODO: Fix this a better way.
_fixPath: function(path) {
return path.replace('../', '');
},
buildResults: function(urls) {
this.resultsElement.update();
var ul = this.resultsElement;
urls.each( function(url) {
var a = new Element('a', {
'class': url.type.gsub(/\s/, '_'),
href: PDoc.pathPrefix + this._fixPath(url.path)
}).update(url.name);
var li = new Element('li', { 'class': 'menu-item' });
li.appendChild(a);
ul.appendChild(li);
}, this);
this.showResults();
},
findURLs: function(str) {
var results = [];
for (var i in PDoc.elements) {
if (i.toLowerCase().include(str)) results.push(PDoc.elements[i]);
}
return results;
},
onEmpty: function() {
this.hideResults();
},
showResults: function() {
this.resultsElement.show();
document.stopObserving("keydown", this.events.keydown);
document.observe("keydown", this.events.keydown);
},
hideResults: function() {
this.resultsElement.hide();
document.stopObserving("keydown", this.events.keydown);
}
});
document.observe('dom:loaded', function() {
new Filterer($('search'), {
menu: $('api_menu'),
resultsElement: $('search_results')
});
});
Event.observe(window, 'load', function() {
var menu = $('menu');
var OFFSET = menu.viewportOffset().top;
Event.observe(window, 'scroll', function() {
var sOffset = document.viewport.getScrollOffsets();
if (sOffset.top > OFFSET) {
menu.addClassName('fixed');
} else menu.removeClassName('fixed');
});
});
(function() {
function menuButtonMouseOver(event) {
var menuButton = $('api_menu_button');
var target = event.element();
if (target === menuButton || target.descendantOf(menuButton)) {
$('api_menu').show();
}
}
function menuButtonMouseOut(event) {
var menuButton = $('api_menu_button');
var menu = $('api_menu');
var target = event.element(), related = event.relatedTarget || event.toElement;
if (related && (related === menu || related.descendantOf(menu))) return;
menu.hide();
}
function menuMouseOut(event) {
var menu = $('api_menu'), related = event.relatedTarget || event.toElement;
if (related && !related.descendantOf(menu)) {
arguments.callee.timer = Element.hide.delay(0.5, menu);
} else {
window.clearTimeout(arguments.callee.timer);
}
}
function menuItemMouseOver(event) {
var element = event.element();
if (element.tagName.toLowerCase() === 'a') {
element.addClassName('highlighted');
}
}
function menuItemMouseOut(event) {
var element = event.element();
if (element.tagName.toLowerCase() === 'a') {
element.removeClassName('highlighted');
}
}
var MENU_ITEMS;
document.observe('dom:loaded', function() {
MENU_ITEMS = $$('.api-box .menu-item a');
$('api_menu_button').observe('mouseenter', menuButtonMouseOver);
$('api_menu_button').observe('mouseleave', menuButtonMouseOut );
$('api_menu').observe('mouseleave', menuMouseOut);
if (Prototype.Browser.IE) {
$('api_menu').observe('mouseover', menuItemMouseOver);
$('api_menu').observe('mouseout', menuItemMouseOut);
}
});
})();
Form.GhostedField = Class.create({
initialize: function(element, title, options) {
this.element = $(element);
this.title = title;
options = options || {};
this.isGhosted = true;
if (options.cloak) {
// Wrap the native getValue function so that it never returns the
// ghosted value. This is optional because it presumes the ghosted
// value isn't valid input for the field.
this.element.getValue = this.element.getValue.wrap(this.wrappedGetValue.bind(this));
}
this.addObservers();
this.onBlur();
},
wrappedGetValue: function($proceed) {
var value = $proceed();
return value === this.title ? "" : value;
},
addObservers: function() {
this.element.observe('focus', this.onFocus.bind(this));
this.element.observe('blur', this.onBlur.bind(this));
var form = this.element.up('form');
if (form) {
form.observe('submit', this.onSubmit.bind(this));
}
// Firefox's bfcache means that form fields need to be re-initialized
// when you hit the "back" button to return to the page.
if (Prototype.Browser.Gecko) {
window.addEventListener('pageshow', this.onBlur.bind(this), false);
}
},
onFocus: function() {
if (this.isGhosted) {
this.element.setValue('');
this.setGhosted(false);
}
},
onBlur: function() {
var value = this.element.getValue();
if (value.blank() || value == this.title) {
this.setGhosted(true);
} else {
this.setGhosted(false);
}
},
setGhosted: function(isGhosted) {
this.isGhosted = isGhosted;
this.element[isGhosted ? 'addClassName' : 'removeClassName']('ghosted');
if (isGhosted) {
this.element.setValue(this.title);
}
},
// Hook into the enclosing form's `onsubmit` event so that we clear any
// ghosted text before the form is sent.
onSubmit: function() {
if (this.isGhosted) {
this.element.setValue('');
}
}
});
document.observe("dom:loaded", function() {
new Form.GhostedField($('search'), "Search");
});

View File

@ -1,251 +0,0 @@
/* Unobtrustive Code Highlighter By Dan Webb 11/2005
Version: 0.4
Usage:
Add a script tag for this script and any stylesets you need to use
to the page in question, add correct class names to CODE elements,
define CSS styles for elements. That's it!
Known to work on:
IE 5.5+ PC
Firefox/Mozilla PC/Mac
Opera 7.23 + PC
Safari 2
Known to degrade gracefully on:
IE5.0 PC
Note: IE5.0 fails due to the use of lookahead in some stylesets. To avoid script errors
in older browsers use expressions that use lookahead in string format when defining stylesets.
This script is inspired by star-light by entirely cunning Dean Edwards
http://dean.edwards.name/star-light/.
*/
// replace callback support for safari.
if ("a".replace(/a/, function() {return "b"}) != "b") (function(){
var default_replace = String.prototype.replace;
String.prototype.replace = function(search,replace){
// replace is not function
if(typeof replace != "function"){
return default_replace.apply(this,arguments)
}
var str = "" + this;
var callback = replace;
// search string is not RegExp
if(!(search instanceof RegExp)){
var idx = str.indexOf(search);
return (
idx == -1 ? str :
default_replace.apply(str,[search,callback(search, idx, str)])
)
}
var reg = search;
var result = [];
var lastidx = reg.lastIndex;
var re;
while((re = reg.exec(str)) != null){
var idx = re.index;
var args = re.concat(idx, str);
result.push(
str.slice(lastidx,idx),
callback.apply(null,args).toString()
);
if(!reg.global){
lastidx += RegExp.lastMatch.length;
break
}else{
lastidx = reg.lastIndex;
}
}
result.push(str.slice(lastidx));
return result.join("")
}
})();
var CodeHighlighter = { styleSets : new Array };
CodeHighlighter.addStyle = function(name, rules) {
// using push test to disallow older browsers from adding styleSets
if ([].push) this.styleSets.push({
name : name,
rules : rules,
ignoreCase : arguments[2] || false
})
function setEvent() {
// set highlighter to run on load (use LowPro if present)
if (typeof Event != 'undefined' && typeof Event.onReady == 'function')
return Event.onReady(CodeHighlighter.init.bind(CodeHighlighter));
var old = window.onload;
if (typeof window.onload != 'function') {
window.onload = function() { CodeHighlighter.init() };
} else {
window.onload = function() {
old();
CodeHighlighter.init();
}
}
}
// only set the event when the first style is added
if (this.styleSets.length==1) setEvent();
}
CodeHighlighter.init = function() {
if (!document.getElementsByTagName) return;
if ("a".replace(/a/, function() {return "b"}) != "b") return; // throw out Safari versions that don't support replace function
// throw out older browsers
var codeEls = document.getElementsByTagName("CODE");
// collect array of all pre elements
codeEls.filter = function(f) {
var a = new Array;
for (var i = 0; i < this.length; i++) if (f(this[i])) a[a.length] = this[i];
return a;
}
var rules = new Array;
rules.toString = function() {
// joins regexes into one big parallel regex
var exps = new Array;
for (var i = 0; i < this.length; i++) exps.push(this[i].exp);
return exps.join("|");
}
function addRule(className, rule) {
// add a replace rule
var exp = (typeof rule.exp != "string")?String(rule.exp).substr(1, String(rule.exp).length-2):rule.exp;
// converts regex rules to strings and chops of the slashes
rules.push({
className : className,
exp : "(" + exp + ")",
length : (exp.match(/(^|[^\\])\([^?]/g) || "").length + 1, // number of subexps in rule
replacement : rule.replacement || null
});
}
function parse(text, ignoreCase) {
// main text parsing and replacement
return text.replace(new RegExp(rules, (ignoreCase)?"gi":"g"), function() {
var i = 0, j = 1, rule;
while (rule = rules[i++]) {
if (arguments[j]) {
// if no custom replacement defined do the simple replacement
if (!rule.replacement) return "<span class=\"" + rule.className + "\">" + arguments[0] + "</span>";
else {
// replace $0 with the className then do normal replaces
var str = rule.replacement.replace("$0", rule.className);
for (var k = 1; k <= rule.length - 1; k++) str = str.replace("$" + k, arguments[j + k]);
return str;
}
} else j+= rule.length;
}
});
}
function highlightCode(styleSet) {
// clear rules array
var parsed;
rules.length = 0;
// get stylable elements by filtering out all code elements without the correct className
var stylableEls = codeEls.filter(function(item) {return (item.className.indexOf(styleSet.name)>=0)});
// add style rules to parser
for (var className in styleSet.rules) addRule(className, styleSet.rules[className]);
// replace for all elements
for (var i = 0; i < stylableEls.length; i++) {
// EVIL hack to fix IE whitespace badness if it's inside a <pre>
if (/MSIE/.test(navigator.appVersion) && stylableEls[i].parentNode.nodeName == 'PRE') {
stylableEls[i] = stylableEls[i].parentNode;
parsed = stylableEls[i].innerHTML.replace(/(<code[^>]*>)([^<]*)<\/code>/i, function() {
return arguments[1] + parse(arguments[2], styleSet.ignoreCase) + "</code>"
});
parsed = parsed.replace(/\n( *)/g, function() {
var spaces = "";
for (var i = 0; i < arguments[1].length; i++) spaces+= "&nbsp;";
return "\n" + spaces;
});
parsed = parsed.replace(/\t/g, "&nbsp;&nbsp;&nbsp;&nbsp;");
parsed = parsed.replace(/\n(<\/\w+>)?/g, "<br />$1").replace(/<br \/>[\n\r\s]*<br \/>/g, "<p><br></p>");
} else parsed = parse(stylableEls[i].innerHTML, styleSet.ignoreCase);
stylableEls[i].innerHTML = parsed;
}
}
// run highlighter on all stylesets
for (var i=0; i < this.styleSets.length; i++) {
highlightCode(this.styleSets[i]);
}
};
CodeHighlighter.addStyle("css", {
comment : {
exp : /\/\*[^*]*\*+([^\/][^*]*\*+)*\//
},
keywords : {
exp : /@\w[\w\s]*/
},
selectors : {
exp : "([\\w-:\\[.#][^{};>]*)(?={)"
},
properties : {
exp : "([\\w-]+)(?=\\s*:)"
},
units : {
exp : /([0-9])(em|en|px|%|pt)\b/,
replacement : "$1<span class=\"$0\">$2</span>"
},
urls : {
exp : /url\([^\)]*\)/
}
});
CodeHighlighter.addStyle("html", {
comment : {
exp: /&lt;!\s*(--([^-]|[\r\n]|-[^-])*--\s*)&gt;/
},
tag : {
exp: /(&lt;\/?)([a-zA-Z]+\s?)/,
replacement: "$1<span class=\"$0\">$2</span>"
},
string : {
exp : /'[^']*'|"[^"]*"/
},
attribute : {
exp: /\b([a-zA-Z-:]+)(=)/,
replacement: "<span class=\"$0\">$1</span>$2"
},
doctype : {
exp: /&lt;!DOCTYPE([^&]|&[^g]|&g[^t])*&gt;/
}
});
CodeHighlighter.addStyle("javascript",{
comment : {
exp : /(\/\/[^\n]*(\n|$))|(\/\*[^*]*\*+([^\/][^*]*\*+)*\/)/
},
brackets : {
exp : /\(|\)/
},
regex : {
exp : /\/(.*?)[g|s|m]?\/[;|\n]/
},
string : {
exp : /'(?:\.|(\\\')|[^\''])*'|"(?:\.|(\\\")|[^\""])*"/
},
keywords : {
exp : /\b(arguments|break|case|continue|default|delete|do|else|false|for|function|if|in|instanceof|new|null|return|switch|this|true|typeof|var|void|while|with)\b/
},
global : {
exp : /\b(toString|valueOf|window|element|prototype|constructor|document|escape|unescape|parseInt|parseFloat|setTimeout|clearTimeout|setInterval|clearInterval|NaN|isNaN|Infinity|alert|prompt|confirm)\b/
}
});

View File

@ -1,963 +0,0 @@
// Copyright (c) 2005-2007 Thomas Fuchs (http://script.aculo.us, http://mir.aculo.us)
// (c) 2005-2007 Ivan Krstic (http://blogs.law.harvard.edu/ivan)
// (c) 2005-2007 Jon Tirsen (http://www.tirsen.com)
// Contributors:
// Richard Livsey
// Rahul Bhargava
// Rob Wills
//
// script.aculo.us is freely distributable under the terms of an MIT-style license.
// For details, see the script.aculo.us web site: http://script.aculo.us/
// Autocompleter.Base handles all the autocompletion functionality
// that's independent of the data source for autocompletion. This
// includes drawing the autocompletion menu, observing keyboard
// and mouse events, and similar.
//
// Specific autocompleters need to provide, at the very least,
// a getUpdatedChoices function that will be invoked every time
// the text inside the monitored textbox changes. This method
// should get the text for which to provide autocompletion by
// invoking this.getToken(), NOT by directly accessing
// this.element.value. This is to allow incremental tokenized
// autocompletion. Specific auto-completion logic (AJAX, etc)
// belongs in getUpdatedChoices.
//
// Tokenized incremental autocompletion is enabled automatically
// when an autocompleter is instantiated with the 'tokens' option
// in the options parameter, e.g.:
// new Ajax.Autocompleter('id','upd', '/url/', { tokens: ',' });
// will incrementally autocomplete with a comma as the token.
// Additionally, ',' in the above example can be replaced with
// a token array, e.g. { tokens: [',', '\n'] } which
// enables autocompletion on multiple tokens. This is most
// useful when one of the tokens is \n (a newline), as it
// allows smart autocompletion after linebreaks.
if(typeof Effect == 'undefined')
throw("controls.js requires including script.aculo.us' effects.js library");
var Autocompleter = { }
Autocompleter.Base = Class.create({
baseInitialize: function(element, update, options) {
element = $(element)
this.element = element;
this.update = $(update);
this.hasFocus = false;
this.changed = false;
this.active = false;
this.index = 0;
this.entryCount = 0;
this.oldElementValue = this.element.value;
if(this.setOptions)
this.setOptions(options);
else
this.options = options || { };
this.options.paramName = this.options.paramName || this.element.name;
this.options.tokens = this.options.tokens || [];
this.options.frequency = this.options.frequency || 0.4;
this.options.minChars = this.options.minChars || 1;
this.options.onShow = this.options.onShow ||
function(element, update){
if(!update.style.position || update.style.position=='absolute') {
update.style.position = 'absolute';
Position.clone(element, update, {
setHeight: false,
offsetTop: element.offsetHeight
});
}
Effect.Appear(update,{duration:0.15});
};
this.options.onHide = this.options.onHide ||
function(element, update){ new Effect.Fade(update,{duration:0.15}) };
if(typeof(this.options.tokens) == 'string')
this.options.tokens = new Array(this.options.tokens);
// Force carriage returns as token delimiters anyway
if (!this.options.tokens.include('\n'))
this.options.tokens.push('\n');
this.observer = null;
this.element.setAttribute('autocomplete','off');
Element.hide(this.update);
Event.observe(this.element, 'blur', this.onBlur.bindAsEventListener(this));
Event.observe(this.element, 'keydown', this.onKeyPress.bindAsEventListener(this));
},
show: function() {
if(Element.getStyle(this.update, 'display')=='none') this.options.onShow(this.element, this.update);
if(!this.iefix &&
(Prototype.Browser.IE) &&
(Element.getStyle(this.update, 'position')=='absolute')) {
new Insertion.After(this.update,
'<iframe id="' + this.update.id + '_iefix" '+
'style="display:none;position:absolute;filter:progid:DXImageTransform.Microsoft.Alpha(opacity=0);" ' +
'src="javascript:false;" frameborder="0" scrolling="no"></iframe>');
this.iefix = $(this.update.id+'_iefix');
}
if(this.iefix) setTimeout(this.fixIEOverlapping.bind(this), 50);
},
fixIEOverlapping: function() {
Position.clone(this.update, this.iefix, {setTop:(!this.update.style.height)});
this.iefix.style.zIndex = 1;
this.update.style.zIndex = 2;
Element.show(this.iefix);
},
hide: function() {
this.stopIndicator();
if(Element.getStyle(this.update, 'display')!='none') this.options.onHide(this.element, this.update);
if(this.iefix) Element.hide(this.iefix);
},
startIndicator: function() {
if(this.options.indicator) Element.show(this.options.indicator);
},
stopIndicator: function() {
if(this.options.indicator) Element.hide(this.options.indicator);
},
onKeyPress: function(event) {
if(this.active)
switch(event.keyCode) {
case Event.KEY_TAB:
case Event.KEY_RETURN:
this.selectEntry();
Event.stop(event);
case Event.KEY_ESC:
this.hide();
this.active = false;
Event.stop(event);
return;
case Event.KEY_LEFT:
case Event.KEY_RIGHT:
return;
case Event.KEY_UP:
this.markPrevious();
this.render();
Event.stop(event);
return;
case Event.KEY_DOWN:
this.markNext();
this.render();
Event.stop(event);
return;
}
else
if(event.keyCode==Event.KEY_TAB || event.keyCode==Event.KEY_RETURN ||
(Prototype.Browser.WebKit > 0 && event.keyCode == 0)) return;
this.changed = true;
this.hasFocus = true;
if(this.observer) clearTimeout(this.observer);
this.observer =
setTimeout(this.onObserverEvent.bind(this), this.options.frequency*1000);
},
activate: function() {
this.changed = false;
this.hasFocus = true;
this.getUpdatedChoices();
},
onHover: function(event) {
var element = Event.findElement(event, 'LI');
if(this.index != element.autocompleteIndex)
{
this.index = element.autocompleteIndex;
this.render();
}
Event.stop(event);
},
onClick: function(event) {
var element = Event.findElement(event, 'LI');
this.index = element.autocompleteIndex;
this.selectEntry();
this.hide();
},
onBlur: function(event) {
// needed to make click events working
setTimeout(this.hide.bind(this), 250);
this.hasFocus = false;
this.active = false;
},
render: function() {
if(this.entryCount > 0) {
for (var i = 0; i < this.entryCount; i++)
this.index==i ?
Element.addClassName(this.getEntry(i),"selected") :
Element.removeClassName(this.getEntry(i),"selected");
if(this.hasFocus) {
this.show();
this.active = true;
}
} else {
this.active = false;
this.hide();
}
},
markPrevious: function() {
if(this.index > 0) this.index--
else this.index = this.entryCount-1;
this.getEntry(this.index).scrollIntoView(true);
},
markNext: function() {
if(this.index < this.entryCount-1) this.index++
else this.index = 0;
this.getEntry(this.index).scrollIntoView(false);
},
getEntry: function(index) {
return this.update.firstChild.childNodes[index];
},
getCurrentEntry: function() {
return this.getEntry(this.index);
},
selectEntry: function() {
this.active = false;
this.updateElement(this.getCurrentEntry());
},
updateElement: function(selectedElement) {
if (this.options.updateElement) {
this.options.updateElement(selectedElement);
return;
}
var value = '';
if (this.options.select) {
var nodes = $(selectedElement).select('.' + this.options.select) || [];
if(nodes.length>0) value = Element.collectTextNodes(nodes[0], this.options.select);
} else
value = Element.collectTextNodesIgnoreClass(selectedElement, 'informal');
var bounds = this.getTokenBounds();
if (bounds[0] != -1) {
var newValue = this.element.value.substr(0, bounds[0]);
var whitespace = this.element.value.substr(bounds[0]).match(/^\s+/);
if (whitespace)
newValue += whitespace[0];
this.element.value = newValue + value + this.element.value.substr(bounds[1]);
} else {
this.element.value = value;
}
this.oldElementValue = this.element.value;
this.element.focus();
if (this.options.afterUpdateElement)
this.options.afterUpdateElement(this.element, selectedElement);
},
updateChoices: function(choices) {
if(!this.changed && this.hasFocus) {
this.update.innerHTML = choices;
Element.cleanWhitespace(this.update);
Element.cleanWhitespace(this.update.down());
if(this.update.firstChild && this.update.down().childNodes) {
this.entryCount =
this.update.down().childNodes.length;
for (var i = 0; i < this.entryCount; i++) {
var entry = this.getEntry(i);
entry.autocompleteIndex = i;
this.addObservers(entry);
}
} else {
this.entryCount = 0;
}
this.stopIndicator();
this.index = 0;
if(this.entryCount==1 && this.options.autoSelect) {
this.selectEntry();
this.hide();
} else {
this.render();
}
}
},
addObservers: function(element) {
Event.observe(element, "mouseover", this.onHover.bindAsEventListener(this));
Event.observe(element, "click", this.onClick.bindAsEventListener(this));
},
onObserverEvent: function() {
this.changed = false;
this.tokenBounds = null;
if(this.getToken().length>=this.options.minChars) {
this.getUpdatedChoices();
} else {
this.active = false;
this.hide();
}
this.oldElementValue = this.element.value;
},
getToken: function() {
var bounds = this.getTokenBounds();
return this.element.value.substring(bounds[0], bounds[1]).strip();
},
getTokenBounds: function() {
if (null != this.tokenBounds) return this.tokenBounds;
var value = this.element.value;
if (value.strip().empty()) return [-1, 0];
var diff = arguments.callee.getFirstDifferencePos(value, this.oldElementValue);
var offset = (diff == this.oldElementValue.length ? 1 : 0);
var prevTokenPos = -1, nextTokenPos = value.length;
var tp;
for (var index = 0, l = this.options.tokens.length; index < l; ++index) {
tp = value.lastIndexOf(this.options.tokens[index], diff + offset - 1);
if (tp > prevTokenPos) prevTokenPos = tp;
tp = value.indexOf(this.options.tokens[index], diff + offset);
if (-1 != tp && tp < nextTokenPos) nextTokenPos = tp;
}
return (this.tokenBounds = [prevTokenPos + 1, nextTokenPos]);
}
});
Autocompleter.Base.prototype.getTokenBounds.getFirstDifferencePos = function(newS, oldS) {
var boundary = Math.min(newS.length, oldS.length);
for (var index = 0; index < boundary; ++index)
if (newS[index] != oldS[index])
return index;
return boundary;
};
Ajax.Autocompleter = Class.create(Autocompleter.Base, {
initialize: function(element, update, url, options) {
this.baseInitialize(element, update, options);
this.options.asynchronous = true;
this.options.onComplete = this.onComplete.bind(this);
this.options.defaultParams = this.options.parameters || null;
this.url = url;
},
getUpdatedChoices: function() {
this.startIndicator();
var entry = encodeURIComponent(this.options.paramName) + '=' +
encodeURIComponent(this.getToken());
this.options.parameters = this.options.callback ?
this.options.callback(this.element, entry) : entry;
if(this.options.defaultParams)
this.options.parameters += '&' + this.options.defaultParams;
new Ajax.Request(this.url, this.options);
},
onComplete: function(request) {
this.updateChoices(request.responseText);
}
});
// The local array autocompleter. Used when you'd prefer to
// inject an array of autocompletion options into the page, rather
// than sending out Ajax queries, which can be quite slow sometimes.
//
// The constructor takes four parameters. The first two are, as usual,
// the id of the monitored textbox, and id of the autocompletion menu.
// The third is the array you want to autocomplete from, and the fourth
// is the options block.
//
// Extra local autocompletion options:
// - choices - How many autocompletion choices to offer
//
// - partialSearch - If false, the autocompleter will match entered
// text only at the beginning of strings in the
// autocomplete array. Defaults to true, which will
// match text at the beginning of any *word* in the
// strings in the autocomplete array. If you want to
// search anywhere in the string, additionally set
// the option fullSearch to true (default: off).
//
// - fullSsearch - Search anywhere in autocomplete array strings.
//
// - partialChars - How many characters to enter before triggering
// a partial match (unlike minChars, which defines
// how many characters are required to do any match
// at all). Defaults to 2.
//
// - ignoreCase - Whether to ignore case when autocompleting.
// Defaults to true.
//
// It's possible to pass in a custom function as the 'selector'
// option, if you prefer to write your own autocompletion logic.
// In that case, the other options above will not apply unless
// you support them.
Autocompleter.Local = Class.create(Autocompleter.Base, {
initialize: function(element, update, array, options) {
this.baseInitialize(element, update, options);
this.options.array = array;
},
getUpdatedChoices: function() {
this.updateChoices(this.options.selector(this));
},
setOptions: function(options) {
this.options = Object.extend({
choices: 10,
partialSearch: true,
partialChars: 2,
ignoreCase: true,
fullSearch: false,
selector: function(instance) {
var ret = []; // Beginning matches
var partial = []; // Inside matches
var entry = instance.getToken();
var count = 0;
for (var i = 0; i < instance.options.array.length &&
ret.length < instance.options.choices ; i++) {
var elem = instance.options.array[i];
var foundPos = instance.options.ignoreCase ?
elem.toLowerCase().indexOf(entry.toLowerCase()) :
elem.indexOf(entry);
while (foundPos != -1) {
if (foundPos == 0 && elem.length != entry.length) {
ret.push("<li><strong>" + elem.substr(0, entry.length) + "</strong>" +
elem.substr(entry.length) + "</li>");
break;
} else if (entry.length >= instance.options.partialChars &&
instance.options.partialSearch && foundPos != -1) {
if (instance.options.fullSearch || /\s/.test(elem.substr(foundPos-1,1))) {
partial.push("<li>" + elem.substr(0, foundPos) + "<strong>" +
elem.substr(foundPos, entry.length) + "</strong>" + elem.substr(
foundPos + entry.length) + "</li>");
break;
}
}
foundPos = instance.options.ignoreCase ?
elem.toLowerCase().indexOf(entry.toLowerCase(), foundPos + 1) :
elem.indexOf(entry, foundPos + 1);
}
}
if (partial.length)
ret = ret.concat(partial.slice(0, instance.options.choices - ret.length))
return "<ul>" + ret.join('') + "</ul>";
}
}, options || { });
}
});
// AJAX in-place editor and collection editor
// Full rewrite by Christophe Porteneuve <tdd@tddsworld.com> (April 2007).
// Use this if you notice weird scrolling problems on some browsers,
// the DOM might be a bit confused when this gets called so do this
// waits 1 ms (with setTimeout) until it does the activation
Field.scrollFreeActivate = function(field) {
setTimeout(function() {
Field.activate(field);
}, 1);
}
Ajax.InPlaceEditor = Class.create({
initialize: function(element, url, options) {
this.url = url;
this.element = element = $(element);
this.prepareOptions();
this._controls = { };
arguments.callee.dealWithDeprecatedOptions(options); // DEPRECATION LAYER!!!
Object.extend(this.options, options || { });
if (!this.options.formId && this.element.id) {
this.options.formId = this.element.id + '-inplaceeditor';
if ($(this.options.formId))
this.options.formId = '';
}
if (this.options.externalControl)
this.options.externalControl = $(this.options.externalControl);
if (!this.options.externalControl)
this.options.externalControlOnly = false;
this._originalBackground = this.element.getStyle('background-color') || 'transparent';
this.element.title = this.options.clickToEditText;
this._boundCancelHandler = this.handleFormCancellation.bind(this);
this._boundComplete = (this.options.onComplete || Prototype.emptyFunction).bind(this);
this._boundFailureHandler = this.handleAJAXFailure.bind(this);
this._boundSubmitHandler = this.handleFormSubmission.bind(this);
this._boundWrapperHandler = this.wrapUp.bind(this);
this.registerListeners();
},
checkForEscapeOrReturn: function(e) {
if (!this._editing || e.ctrlKey || e.altKey || e.shiftKey) return;
if (Event.KEY_ESC == e.keyCode)
this.handleFormCancellation(e);
else if (Event.KEY_RETURN == e.keyCode)
this.handleFormSubmission(e);
},
createControl: function(mode, handler, extraClasses) {
var control = this.options[mode + 'Control'];
var text = this.options[mode + 'Text'];
if ('button' == control) {
var btn = document.createElement('input');
btn.type = 'submit';
btn.value = text;
btn.className = 'editor_' + mode + '_button';
if ('cancel' == mode)
btn.onclick = this._boundCancelHandler;
this._form.appendChild(btn);
this._controls[mode] = btn;
} else if ('link' == control) {
var link = document.createElement('a');
link.href = '#';
link.appendChild(document.createTextNode(text));
link.onclick = 'cancel' == mode ? this._boundCancelHandler : this._boundSubmitHandler;
link.className = 'editor_' + mode + '_link';
if (extraClasses)
link.className += ' ' + extraClasses;
this._form.appendChild(link);
this._controls[mode] = link;
}
},
createEditField: function() {
var text = (this.options.loadTextURL ? this.options.loadingText : this.getText());
var fld;
if (1 >= this.options.rows && !/\r|\n/.test(this.getText())) {
fld = document.createElement('input');
fld.type = 'text';
var size = this.options.size || this.options.cols || 0;
if (0 < size) fld.size = size;
} else {
fld = document.createElement('textarea');
fld.rows = (1 >= this.options.rows ? this.options.autoRows : this.options.rows);
fld.cols = this.options.cols || 40;
}
fld.name = this.options.paramName;
fld.value = text; // No HTML breaks conversion anymore
fld.className = 'editor_field';
if (this.options.submitOnBlur)
fld.onblur = this._boundSubmitHandler;
this._controls.editor = fld;
if (this.options.loadTextURL)
this.loadExternalText();
this._form.appendChild(this._controls.editor);
},
createForm: function() {
var ipe = this;
function addText(mode, condition) {
var text = ipe.options['text' + mode + 'Controls'];
if (!text || condition === false) return;
ipe._form.appendChild(document.createTextNode(text));
};
this._form = $(document.createElement('form'));
this._form.id = this.options.formId;
this._form.addClassName(this.options.formClassName);
this._form.onsubmit = this._boundSubmitHandler;
this.createEditField();
if ('textarea' == this._controls.editor.tagName.toLowerCase())
this._form.appendChild(document.createElement('br'));
if (this.options.onFormCustomization)
this.options.onFormCustomization(this, this._form);
addText('Before', this.options.okControl || this.options.cancelControl);
this.createControl('ok', this._boundSubmitHandler);
addText('Between', this.options.okControl && this.options.cancelControl);
this.createControl('cancel', this._boundCancelHandler, 'editor_cancel');
addText('After', this.options.okControl || this.options.cancelControl);
},
destroy: function() {
if (this._oldInnerHTML)
this.element.innerHTML = this._oldInnerHTML;
this.leaveEditMode();
this.unregisterListeners();
},
enterEditMode: function(e) {
if (this._saving || this._editing) return;
this._editing = true;
this.triggerCallback('onEnterEditMode');
if (this.options.externalControl)
this.options.externalControl.hide();
this.element.hide();
this.createForm();
this.element.parentNode.insertBefore(this._form, this.element);
if (!this.options.loadTextURL)
this.postProcessEditField();
if (e) Event.stop(e);
},
enterHover: function(e) {
if (this.options.hoverClassName)
this.element.addClassName(this.options.hoverClassName);
if (this._saving) return;
this.triggerCallback('onEnterHover');
},
getText: function() {
return this.element.innerHTML;
},
handleAJAXFailure: function(transport) {
this.triggerCallback('onFailure', transport);
if (this._oldInnerHTML) {
this.element.innerHTML = this._oldInnerHTML;
this._oldInnerHTML = null;
}
},
handleFormCancellation: function(e) {
this.wrapUp();
if (e) Event.stop(e);
},
handleFormSubmission: function(e) {
var form = this._form;
var value = $F(this._controls.editor);
this.prepareSubmission();
var params = this.options.callback(form, value) || '';
if (Object.isString(params))
params = params.toQueryParams();
params.editorId = this.element.id;
if (this.options.htmlResponse) {
var options = Object.extend({ evalScripts: true }, this.options.ajaxOptions);
Object.extend(options, {
parameters: params,
onComplete: this._boundWrapperHandler,
onFailure: this._boundFailureHandler
});
new Ajax.Updater({ success: this.element }, this.url, options);
} else {
var options = Object.extend({ method: 'get' }, this.options.ajaxOptions);
Object.extend(options, {
parameters: params,
onComplete: this._boundWrapperHandler,
onFailure: this._boundFailureHandler
});
new Ajax.Request(this.url, options);
}
if (e) Event.stop(e);
},
leaveEditMode: function() {
this.element.removeClassName(this.options.savingClassName);
this.removeForm();
this.leaveHover();
this.element.style.backgroundColor = this._originalBackground;
this.element.show();
if (this.options.externalControl)
this.options.externalControl.show();
this._saving = false;
this._editing = false;
this._oldInnerHTML = null;
this.triggerCallback('onLeaveEditMode');
},
leaveHover: function(e) {
if (this.options.hoverClassName)
this.element.removeClassName(this.options.hoverClassName);
if (this._saving) return;
this.triggerCallback('onLeaveHover');
},
loadExternalText: function() {
this._form.addClassName(this.options.loadingClassName);
this._controls.editor.disabled = true;
var options = Object.extend({ method: 'get' }, this.options.ajaxOptions);
Object.extend(options, {
parameters: 'editorId=' + encodeURIComponent(this.element.id),
onComplete: Prototype.emptyFunction,
onSuccess: function(transport) {
this._form.removeClassName(this.options.loadingClassName);
var text = transport.responseText;
if (this.options.stripLoadedTextTags)
text = text.stripTags();
this._controls.editor.value = text;
this._controls.editor.disabled = false;
this.postProcessEditField();
}.bind(this),
onFailure: this._boundFailureHandler
});
new Ajax.Request(this.options.loadTextURL, options);
},
postProcessEditField: function() {
var fpc = this.options.fieldPostCreation;
if (fpc)
$(this._controls.editor)['focus' == fpc ? 'focus' : 'activate']();
},
prepareOptions: function() {
this.options = Object.clone(Ajax.InPlaceEditor.DefaultOptions);
Object.extend(this.options, Ajax.InPlaceEditor.DefaultCallbacks);
[this._extraDefaultOptions].flatten().compact().each(function(defs) {
Object.extend(this.options, defs);
}.bind(this));
},
prepareSubmission: function() {
this._saving = true;
this.removeForm();
this.leaveHover();
this.showSaving();
},
registerListeners: function() {
this._listeners = { };
var listener;
$H(Ajax.InPlaceEditor.Listeners).each(function(pair) {
listener = this[pair.value].bind(this);
this._listeners[pair.key] = listener;
if (!this.options.externalControlOnly)
this.element.observe(pair.key, listener);
if (this.options.externalControl)
this.options.externalControl.observe(pair.key, listener);
}.bind(this));
},
removeForm: function() {
if (!this._form) return;
this._form.remove();
this._form = null;
this._controls = { };
},
showSaving: function() {
this._oldInnerHTML = this.element.innerHTML;
this.element.innerHTML = this.options.savingText;
this.element.addClassName(this.options.savingClassName);
this.element.style.backgroundColor = this._originalBackground;
this.element.show();
},
triggerCallback: function(cbName, arg) {
if ('function' == typeof this.options[cbName]) {
this.options[cbName](this, arg);
}
},
unregisterListeners: function() {
$H(this._listeners).each(function(pair) {
if (!this.options.externalControlOnly)
this.element.stopObserving(pair.key, pair.value);
if (this.options.externalControl)
this.options.externalControl.stopObserving(pair.key, pair.value);
}.bind(this));
},
wrapUp: function(transport) {
this.leaveEditMode();
// Can't use triggerCallback due to backward compatibility: requires
// binding + direct element
this._boundComplete(transport, this.element);
}
});
Object.extend(Ajax.InPlaceEditor.prototype, {
dispose: Ajax.InPlaceEditor.prototype.destroy
});
Ajax.InPlaceCollectionEditor = Class.create(Ajax.InPlaceEditor, {
initialize: function($super, element, url, options) {
this._extraDefaultOptions = Ajax.InPlaceCollectionEditor.DefaultOptions;
$super(element, url, options);
},
createEditField: function() {
var list = document.createElement('select');
list.name = this.options.paramName;
list.size = 1;
this._controls.editor = list;
this._collection = this.options.collection || [];
if (this.options.loadCollectionURL)
this.loadCollection();
else
this.checkForExternalText();
this._form.appendChild(this._controls.editor);
},
loadCollection: function() {
this._form.addClassName(this.options.loadingClassName);
this.showLoadingText(this.options.loadingCollectionText);
var options = Object.extend({ method: 'get' }, this.options.ajaxOptions);
Object.extend(options, {
parameters: 'editorId=' + encodeURIComponent(this.element.id),
onComplete: Prototype.emptyFunction,
onSuccess: function(transport) {
var js = transport.responseText.strip();
if (!/^\[.*\]$/.test(js)) // TODO: improve sanity check
throw 'Server returned an invalid collection representation.';
this._collection = eval(js);
this.checkForExternalText();
}.bind(this),
onFailure: this.onFailure
});
new Ajax.Request(this.options.loadCollectionURL, options);
},
showLoadingText: function(text) {
this._controls.editor.disabled = true;
var tempOption = this._controls.editor.firstChild;
if (!tempOption) {
tempOption = document.createElement('option');
tempOption.value = '';
this._controls.editor.appendChild(tempOption);
tempOption.selected = true;
}
tempOption.update((text || '').stripScripts().stripTags());
},
checkForExternalText: function() {
this._text = this.getText();
if (this.options.loadTextURL)
this.loadExternalText();
else
this.buildOptionList();
},
loadExternalText: function() {
this.showLoadingText(this.options.loadingText);
var options = Object.extend({ method: 'get' }, this.options.ajaxOptions);
Object.extend(options, {
parameters: 'editorId=' + encodeURIComponent(this.element.id),
onComplete: Prototype.emptyFunction,
onSuccess: function(transport) {
this._text = transport.responseText.strip();
this.buildOptionList();
}.bind(this),
onFailure: this.onFailure
});
new Ajax.Request(this.options.loadTextURL, options);
},
buildOptionList: function() {
this._form.removeClassName(this.options.loadingClassName);
this._collection = this._collection.map(function(entry) {
return 2 === entry.length ? entry : [entry, entry].flatten();
});
var marker = ('value' in this.options) ? this.options.value : this._text;
var textFound = this._collection.any(function(entry) {
return entry[0] == marker;
}.bind(this));
this._controls.editor.update('');
var option;
this._collection.each(function(entry, index) {
option = document.createElement('option');
option.value = entry[0];
option.selected = textFound ? entry[0] == marker : 0 == index;
option.appendChild(document.createTextNode(entry[1]));
this._controls.editor.appendChild(option);
}.bind(this));
this._controls.editor.disabled = false;
Field.scrollFreeActivate(this._controls.editor);
}
});
//**** DEPRECATION LAYER FOR InPlace[Collection]Editor! ****
//**** This only exists for a while, in order to let ****
//**** users adapt to the new API. Read up on the new ****
//**** API and convert your code to it ASAP! ****
Ajax.InPlaceEditor.prototype.initialize.dealWithDeprecatedOptions = function(options) {
if (!options) return;
function fallback(name, expr) {
if (name in options || expr === undefined) return;
options[name] = expr;
};
fallback('cancelControl', (options.cancelLink ? 'link' : (options.cancelButton ? 'button' :
options.cancelLink == options.cancelButton == false ? false : undefined)));
fallback('okControl', (options.okLink ? 'link' : (options.okButton ? 'button' :
options.okLink == options.okButton == false ? false : undefined)));
fallback('highlightColor', options.highlightcolor);
fallback('highlightEndColor', options.highlightendcolor);
};
Object.extend(Ajax.InPlaceEditor, {
DefaultOptions: {
ajaxOptions: { },
autoRows: 3, // Use when multi-line w/ rows == 1
cancelControl: 'link', // 'link'|'button'|false
cancelText: 'cancel',
clickToEditText: 'Click to edit',
externalControl: null, // id|elt
externalControlOnly: false,
fieldPostCreation: 'activate', // 'activate'|'focus'|false
formClassName: 'inplaceeditor-form',
formId: null, // id|elt
highlightColor: '#ffff99',
highlightEndColor: '#ffffff',
hoverClassName: '',
htmlResponse: true,
loadingClassName: 'inplaceeditor-loading',
loadingText: 'Loading...',
okControl: 'button', // 'link'|'button'|false
okText: 'ok',
paramName: 'value',
rows: 1, // If 1 and multi-line, uses autoRows
savingClassName: 'inplaceeditor-saving',
savingText: 'Saving...',
size: 0,
stripLoadedTextTags: false,
submitOnBlur: false,
textAfterControls: '',
textBeforeControls: '',
textBetweenControls: ''
},
DefaultCallbacks: {
callback: function(form) {
return Form.serialize(form);
},
onComplete: function(transport, element) {
// For backward compatibility, this one is bound to the IPE, and passes
// the element directly. It was too often customized, so we don't break it.
new Effect.Highlight(element, {
startcolor: this.options.highlightColor, keepBackgroundImage: true });
},
onEnterEditMode: null,
onEnterHover: function(ipe) {
ipe.element.style.backgroundColor = ipe.options.highlightColor;
if (ipe._effect)
ipe._effect.cancel();
},
onFailure: function(transport, ipe) {
alert('Error communication with the server: ' + transport.responseText.stripTags());
},
onFormCustomization: null, // Takes the IPE and its generated form, after editor, before controls.
onLeaveEditMode: null,
onLeaveHover: function(ipe) {
ipe._effect = new Effect.Highlight(ipe.element, {
startcolor: ipe.options.highlightColor, endcolor: ipe.options.highlightEndColor,
restorecolor: ipe._originalBackground, keepBackgroundImage: true
});
}
},
Listeners: {
click: 'enterEditMode',
keydown: 'checkForEscapeOrReturn',
mouseover: 'enterHover',
mouseout: 'leaveHover'
}
});
Ajax.InPlaceCollectionEditor.DefaultOptions = {
loadingCollectionText: 'Loading options...'
};
// Delayed observer, like Form.Element.Observer,
// but waits for delay after last key input
// Ideal for live-search fields
Form.Element.DelayedObserver = Class.create({
initialize: function(element, delay, callback) {
this.delay = delay || 0.5;
this.element = $(element);
this.callback = callback;
this.timer = null;
this.lastValue = $F(this.element);
Event.observe(this.element,'keyup',this.delayedListener.bindAsEventListener(this));
},
delayedListener: function(event) {
if(this.lastValue == $F(this.element)) return;
if(this.timer) clearTimeout(this.timer);
this.timer = setTimeout(this.onTimerEvent.bind(this), this.delay * 1000);
this.lastValue = $F(this.element);
},
onTimerEvent: function() {
this.timer = null;
this.callback(this.element, $F(this.element));
}
});

File diff suppressed because it is too large Load Diff

File diff suppressed because it is too large Load Diff

View File

@ -1,487 +0,0 @@
/*
* API STYLES
*/
/* tag styles */
pre {
padding: 0;
}
code {
font-family: Monaco, "Bitstream Vera Sans Mono", "Lucida Console", monospace;
font-size: 12px;
}
/* masthead */
div#masthead {
background: url(../images/header-stripe-small.png) repeat-x top left;
height: 76px;
}
div#masthead div#masthead_content {
margin: 0 auto;
width: 835px;
position: relative;
}
div#masthead h1#logo {
background: url(../images/header-logo-small.png) no-repeat 0 1px;
width: 118px;
height: 76px;
position: relative;
left: 60px;
}
/* footer */
div#footer {
width: 960px;
margin: 0 auto;
}
div.about {
margin-top: 20px;
padding-top: 20px;
width: 835px;
margin-left: 120px;
border-top: 1px solid #aaa;
color: #aaa;
}
div.about a,
div.about a:link {
color: #aaa;
text-decoration: underline;
border: 0;
}
div.copyright,
div.credits {
width: 360px;
float: left;
}
div.copyright .cc {
width: 115px;
margin-right: 5px;
text-align: center;
float: left;
}
div.copyright .copyright-about {
width: 235px;
float: left;
}
div.credits {
margin-left: 115px;
}
.page-title span.type {
display: block;
text-transform: uppercase;
font-size: 14px;
color: #aaa;
letter-spacing: 0;
}
h2.page-title {
margin-top: 0;
line-height: 100%;
}
ul.breadcrumbs {
margin-left: 120px;
}
ul.breadcrumbs li {
float: left;
list-style-type: none;
margin-right: 10px;
margin-left: 0;
}
ul.method-list {
margin-top: 0;
}
ul.method-list li {
margin-top: 0;
float: left;
margin-right: 5px;
margin-left: 0;
list-style-type: none;
}
ul.method-list li a,
ul.method-list li a:link {
text-decoration: none;
border: 0;
}
ul.method-details-list {
margin-top: 0;
}
ul.method-details-list li.method-description {
margin-top: 0;
margin-bottom: 3.0em;
margin-left: 0;
list-style-type: none;
}
ul.method-details-list li h4 {
margin: 0 0 0.6em;
line-height: 90%;
}
ul.method-details-list li pre {
margin-top: 0;
}
ul.method-details-list li pre code {
font-size: 13px;
}
ul.method-details-list li code {
font-size: 12px;
}
h4.inherited {
padding-top: 5px;
clear: left;
font-style: italic;
font-weight: bold;
font-size: 14px;
}
.method-description h4 .method-permalink a {
color: #aaa;
text-decoration: none;
border: 0;
font-size: 14px;
}
ul.argument-list {
margin-top: -5px;
list-style-type: disc;
margin-left: 20px;
}
ul.argument-list li {
list-style-type: disc;
font-size: 90%;
margin-bottom: 0;
}
ul.argument-list li code {
font-size: 11px;
}
ul.section-list {
margin-top: 0;
}
ul.section-list li {
margin-top: 0;
margin-left: 0;
list-style-type: none;
}
ul.section-list li h4 {
margin-top: 0;
}
/* Aliases */
.alias,
.related-to {
font-style: italic;
}
.alias code,
.related-to code {
font-style: normal;
}
/* Section icons */
.page-content .section .section-title h3 {
padding-right: 24px;
background-position: right 0;
background-repeat: no-repeat;
}
.section-constructor .section-title h3 {
background-image: url(../images/constructor.png);
}
.section-method-list .section-title h3 {
background-image: url(../images/method.png);
}
.section-klass_methods .section-title h3 {
background-image: url(../images/class_method.png);
}
.section-klass_properties .section-title h3 {
background-image: url(../images/class_property.png);
}
.section-instance_methods .section-title h3 {
background-image: url(../images/instance_method.png);
}
.section-instance_properties .section-title h3 {
background-image: url(../images/instance_property.png);
}
.section-mixins .section-title h3 {
background-image: url(../images/mixin.png);
}
.section-classes .section-title h3 {
background-image: url(../images/class.png);
}
.section-namespaces .section-title h3 {
background-image: url(../images/namespace.png);
}
.section-sections .section-title h3 {
background-image: url(../images/section.png);
}
.section-utilities .section-title h3 {
background-image: url(../images/utility.png);
}
.section-description .section-title h3 {
background-image: url(../images/description.png);
}
.section-subclasses .section-title h3 {
background-image: url(../images/subclass.png);
}
.section-superclass .section-title h3 {
background-image: url(../images/superclass.png);
}
/* search box */
.search-results {
position: absolute;
background-color: #fff;
height: 200px;
width: 233px;
overflow: auto;
overflow-y: scroll;
overflow-x: hidden;
margin: 7px -11px 0;
border: 1px solid #999;
top: 28px;
}
* html .search-results {
left: 486px;
top: 30px;
}
/* search result types */
.menu-item a,
.menu-item a:link {
display: block;
padding: 3px 10px 3px 28px;
background-position: 6px 50%;
background-repeat: no-repeat;
text-align: left;
text-decoration: none;
color: #333;
border-top: 1px solid #fff;
border-bottom: 1px solid #fff;
white-space: nowrap;
}
.menu-item a:hover,
.menu-item a.highlighted,
#menu .highlighted a {
border-top: 1px solid #69f;
border-bottom: 1px solid #69f;
background-color: #f0f0ff;
}
.menu-item a.section {
font-weight: bold;
background-image: url(../images/section.png);
}
.menu-item a.class_method,
.menu-item a.instance_method {
background-image: url(../images/method.png);
}
.menu-item a.class {
background-image: url(../images/class.png);
}
.menu-item a.constructor {
background-image: url(../images/constructor.png);
}
.menu-item a.class_property {
background-image: url(../images/class_property.png);
}
.menu-item a.instance_property {
background-image: url(../images/instance_property.png);
}
.menu-item a.namespace {
background-image: url(../images/namespace.png);
}
.menu-item a.utility {
background-image: url(../images/utility.png);
}
/* halo around selected method */
.highlighter {
border: 3px solid #69f;
z-index: -1;
-webkit-border-radius: 15px;
-moz-border-radius: 15px;
border-radius: 15px;
}
/* MENU */
div#menu {
width: 960px;
margin: 0 auto;
position: relative;
}
#menu .api-box h2 a,
#menu .search-box {
width: 213px;
height: 25px;
line-height: 25px;
padding: 5px 10px;
margin-right: 5px;
text-align: center;
float: right;
}
* html #menu .api-box h2 a,
* html #menu .search-box {
height: 30px;
line-height: 30px;
}
#menu .api-box {
}
#menu .api-box h2 a {
font-size: 14px;
font-weight: normal;
font-family: Verdana, sans-serif;
display: block;
background-color: #cde0fb;
border: 1px solid #669;
border-top: 0;
text-decoration: none;
color: #222;
}
#menu .api-box .menu-items {
position: absolute;
background-color: #fff;
height: 200px;
width: 233px;
overflow: auto;
overflow-y: scroll;
overflow-x: hidden;
top: 35px;
border: 1px solid #999;
right: 5px;
}
* html #menu .api-box .menu-items {
right: 10px;
top: 37px;
}
#menu .api-box ul,
#menu .api-box li {
margin: 0;
padding: 0;
}
#menu .api-box .menu-item a {
}
#menu .search-box {
background-color: #cee8c3;
border: 1px solid #696;
border-top: 0;
}
#menu .search-box input {
width: 150px;
padding: 3px 10px;
margin-top: 2px;
border: 1px solid #999;
border-radius: 10px;
-webkit-border-radius: 10px;
-moz-border-radius: 10px;
}
#menu #search.ghosted {
color: #aaa;
text-align: left;
}
/* notes */
p.note,
p.alias,
p.related-to {
font-size: 11px;
line-height: 14px;
padding: 5px 5px 5px 60px;
background-repeat: no-repeat;
background-position: 20px 50%;
border: 1px solid #000;
}
p.note {
background-color: #f0f0f4;
background-image: url(../images/information.png);
border-color: #69c;
}
p.alias {
background-color: #fff6de;
background-image: url(../images/alias.png);
border-color: #cc9;
}
p.related-to {
background-color: #f4f0f4;
background-image: url(../images/related_to.png);
border-color: #c9c;
}

View File

@ -1,415 +0,0 @@
/* The "section" class implicitly needs a clearfix; adding it here for convenience. */
.clearfix:after,
.section:after {
content: ".";
display: block;
clear: both;
visibility: hidden;
line-height: 0;
height: 0;
}
.clearfix, .section {
display: inline-block;
}
html[xmlns] .clearfix,
html[xmlns] .section {
display: block;
}
* html .clearfix,
* html .section {
height: 1%;
}
span.replaced { visibility: hidden; }
span.hidden { display: none; }
body {
font-family: Verdana, sans-serif;
font-size: 82.5%;
line-height: 1.5em;
margin: 0;
padding: 0;
}
body * {
margin: 0;
padding: 0;
}
h1, h2, h3, h4, h5, h6 {
font-family: "Helvetica Neue", Arial, Helvetica, sans-serif;
}
h4 {
font-size: 17px;
color: #555;
margin: 1.0em 0 0.6em;
}
h5 {
font-size: 15px;
color: #2a2a2a;
margin: 1.0em 0 0.6em;
}
h6 {
font-size: 14px;
color: #000;
margin: 1.0em 0 0.6em;
}
a img {
border: 0;
}
ul, li {
list-style-type: none;
}
ol, ul {
margin: 0 0 15px;
}
#page a.img,
#page a.img:link,
#page a.img:visited {
border: none;
}
/* Link bar */
div#links {
margin: 0 auto;
width: 835px;
padding: 16px 0;
height: 16px;
overflow: hidden;
}
div#links_wrapper {
background: #fff;
}
div#links li {
display: inline;
}
div#links li a {
color: #666;
}
div#links li.selected a {
color: #000;
font-weight: bold;
text-decoration: none;
}
ul#internal_links {
float: left;
}
ul#internal_links li {
margin-right: 25px;
}
ul#external_links {
float: right;
}
ul#external_links li {
margin-left: 25px;
padding-left: 21px;
}
li#scripty_link {
background: url(http://prototype.conio.net/new/images/link-logo-scripty.png) no-repeat center left;
}
li#rails_link {
background: url(http://prototype.conio.net/new/images/link-logo-rails.png) no-repeat center left;
}
p a, p a:link,
h1 a, h1 a:link,
h2 a, h2 a:link,
h3 a, h3 a:link,
h4 a, h4 a:link,
h5 a, h5 a:link,
h6 a, h6 a:link {
color: #036;
border-bottom: 1px solid #036;
text-decoration: none;
}
p a:visited {
border-bottom: 1px solid #666;
}
code {
font-family: "Panic Sans", "Bitstream Vera Sans Mono", Monaco, Consolas, Andale Mono, monospace;
font-size: 13px;
}
p code,
li code {
background-color: #f0f0f0;
border: 1px solid #ccc;
border-radius: 3px;
-webkit-border-radius: 3px;
padding: 0 3px;
}
pre code {
background-color: transparent;
border: 0;
padding: 0;
}
#page {
margin: 0 auto;
padding-bottom: 100px; /* FIXME: Temporary as pages are built */
}
/* top */
.related-links {
width: 835px;
font-size: 0.9em;
margin: 0 auto 10px;
padding: 10px 0 0;
}
.related-links a {
color: #000;
text-decoration: none;
}
.related-links ul {
list-style-type: none;
}
.related-links ul.internal {
float: left;
width: 355px;
}
.related-links ul.internal li {
text-align: center;
}
.related-links ul.external {
float: right;
width: 295px;
}
.related-links li {
float: left;
padding: 0 15px;
width: 85px;
margin-right: 5px;
}
.related-links li.last {
margin-right: 0;
}
.related-links ul.external li.scripty {
padding: 0 8px 0 22px;
background: url(../images/icon-scripty.png) no-repeat;
margin-right: 65px;
}
.related-links ul.external li.rails {
padding: 0 8px 0 22px;
background: url(../images/icon-rails.png) no-repeat;
}
.banner {
height: 152px;
padding: 1px 0;
background: url(../images/header-stripe.png) repeat-x;
}
.banner-content {
width: 835px;
margin: 0 auto;
}
.banner h1 {
width: 236px;
height: 150px;
background: url(../images/header-logo.png) no-repeat;
}
.banner h1 span {
display: none;
}
.banner-small {
height: 75px;
padding: 1px 0;
background: url(../images/header-stripe-small.png) repeat-x;
}
.banner-small h1 {
width: 118px;
height: 75px;
background: url(../images/header-logo-small.png) no-repeat;
margin-left: 60px;
}
.banner-small h1 span {
display: none;
}
/* PAGE CONTENT */
.page-content {
width: 955px;
margin: 30px auto 0;
}
.page-content .page-title {
margin-left: 120px;
margin-bottom: 15px;
font-size: 27px;
letter-spacing: -1px;
color: #444;
}
.page-content .page-introduction {
margin-left: 120px;
margin-bottom: 25px;
}
.page-content .section {
width: 955px;
margin: 10px 0 20px;
}
.page-content .section .section-title {
width: 110px;
margin-right: 10px;
padding-right: 0;
float: left;
text-align: right;
overflow: hidden;
}
.page-content .section .section-title h3 {
color: #999;
font-size: 14px;
line-height: 110%;
padding-right: 10px;
padding-bottom: 5px;
}
.page-content .section .section-content {
width: 835px;
float: left;
}
.page-content a,
.page-content a:link {
color: #036;
border-bottom: 1px solid #036;
text-decoration: none;
}
.page-content a:visited {
border-bottom: 1px solid #bbb;
}
.page-content ul,
.page-content ol {
margin: 10px 0;
}
.page-content li {
margin: 5px 0 8px 20px;
list-style-type: disc;
}
.page-content p {
margin: 0 0 0.8em;
}
.page-content pre {
color: #333;
background-color: #f0f0ff;
border: 1px solid #dde;
padding: 3px 5px;
margin: 0 0 1em;
}
.page-content .two-column {
}
.page-content .two-column-left,
.page-content .two-column-right {
width: 475px;
margin-right: 5px;
float: left;
}
.page-content .two-column-right {
margin-right: 0;
}
.page-content .two-column .section {
width: 475px;
}
.page-content .two-column .section-content {
width: 345px;
padding-right: 10px;
}
.smallcaps {
font-size: 0.85em;
text-transform: uppercase;
letter-spacing: 1px;
}
/* MASTHEAD */
div#masthead {
margin-top: 50px;
background: url(../images/header-stripe-small.png) repeat-x top left;
height: 76px;
}
div#masthead div#masthead_content {
margin: 0 auto;
width: 835px;
position: relative;
}
div#masthead h1#logo {
background: url(../images/header-logo-small.png) no-repeat 0 1px;
width: 118px;
height: 76px;
position: relative;
left: 60px;
}
div#masthead a {
text-decoration: none;
}

View File

@ -1,13 +0,0 @@
body.grid {
width: 955px;
margin: auto;
}
body.grid div#page {
overflow: hidden;
background: url(../images/grid.png);
}
body.grid div#page * {
opacity: .9;
}

View File

@ -1,116 +0,0 @@
/* See license.txt for terms of usage */
.firebugHighlight {
z-index: 2147483647;
position: absolute;
background-color: #3875d7;
}
.firebugLayoutBoxParent {
z-index: 2147483647;
position: absolute;
border-right: 1px dashed #BBBBBB;
border-bottom: 1px dashed #BBBBBB;
}
.firebugRulerH {
position: absolute;
top: -15px;
left: 0;
width: 100%;
height: 14px;
background: url(chrome://firebug/skin/rulerH.png) repeat-x;
border-top: 1px solid #BBBBBB;
border-right: 1px dashed #BBBBBB;
border-bottom: 1px solid #000000;
}
.firebugRulerV {
position: absolute;
top: 0;
left: -15px;
width: 14px;
height: 100%;
background: url(chrome://firebug/skin/rulerV.png) repeat-y;
border-left: 1px solid #BBBBBB;
border-right: 1px solid #000000;
border-bottom: 1px dashed #BBBBBB;
}
.overflowRulerX > .firebugRulerV {
left: 0;
}
.overflowRulerY > .firebugRulerH {
top: 0;
}
/* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * */
.firebugLayoutBoxOffset {
z-index: 2147483647;
position: absolute;
opacity: 0.8;
}
.firebugLayoutBoxMargin {
background-color: #EDFF64;
}
.firebugLayoutBoxBorder {
background-color: #666666;
}
.firebugLayoutBoxPadding {
background-color: SlateBlue;
}
.firebugLayoutBoxContent {
background-color: SkyBlue;
}
/*.firebugHighlightGroup .firebugLayoutBox {
background-color: transparent;
}
.firebugHighlightBox {
background-color: Blue !important;
}*/
.firebugLayoutLine {
z-index: 2147483647;
background-color: #000000;
opacity: 0.4;
}
.firebugLayoutLineLeft,
.firebugLayoutLineRight {
position: fixed;
width: 1px;
height: 100%;
}
.firebugLayoutLineTop,
.firebugLayoutLineBottom {
position: absolute;
width: 100%;
height: 1px;
}
.firebugLayoutLineTop {
margin-top: -1px;
border-top: 1px solid #999999;
}
.firebugLayoutLineRight {
border-right: 1px solid #999999;
}
.firebugLayoutLineBottom {
border-bottom: 1px solid #999999;
}
.firebugLayoutLineLeft {
margin-left: -1px;
border-left: 1px solid #999999;
}

View File

@ -1,443 +0,0 @@
/* @group Tags */
body {
font-family: Verdana, sans-serif;
}
form {
margin: 0;
padding: 0;
}
a {
color: #036;
text-decoration: none;
}
p a {
border-bottom: 1px solid #999;
padding: 0 1px;
}
p a:hover {
background-color: #036;
color: #fff;
border-bottom: 1px solid #036;
}
h1, h2, h3, h4, h5, h6 {
font-family: "Helvetica Neue", Helvetica, Arial, sans-serif;
margin: 0;
padding: 0;
}
pre {
padding: 0;
}
code {
font-family: Monaco, "Bitstream Vera Sans Mono", "Lucida Console", monospace;
font-size: 11px;
}
/* @end */
/* @group Masthead */
div#masthead {
background: url(../images/header-stripe-small.png) repeat-x top left;
height: 76px;
}
div#masthead div#masthead_content {
margin: 0 auto;
width: 835px;
position: relative;
}
div#masthead h1#logo {
background: url(../images/header-logo-small.png) no-repeat 0 1px;
width: 118px;
height: 76px;
position: relative;
left: 60px;
}
/* @end */
/* @group Main */
#main {
width: 840px;
margin: 20px auto;
position: relative;
}
#main h2 {
color: #444;
font-size: 22px;
padding-left: 69px;
margin-top: 0;
}
#main h2 span {
color: #ccc;
display: block;
text-transform: uppercase;
font-size: 13px;
margin-bottom: -10px;
padding-left: 2px;
}
#main h2 a {
color: #444;
text-decoration: none;
}
#main h2 a:hover {
color: #222;
border-bottom: 1px solid #999;
}
#main h4, h5, h6 {
padding-left: 4px;
}
#main li h4,
#main li h5,
#main li h6 {
padding-left: 0;
}
#main h4.inherited {
color: #888 !important;
}
#main .section {
overflow: hidden;
padding-left: 65px;
padding-bottom: 0;
margin: 5px 0 0;
}
#main .section h3 {
position: absolute;
left: -85px;
width: 110px;
text-align: right;
font-size: 13px;
padding-top: 3px;
color: #999;
line-height: 100%;
min-height: 30px;
}
#main .section h4 {
font-size: 15px;
color: #444;
margin: 0 0 0.3em;
}
#main .section h4.inherited {
color: #888;
}
#main .section h4.inherited a {
color: #49B;
}
#main p {
margin: 0 0 1.1em;
}
#main pre {
background-color: #000;
color: #fff;
padding: 5px 10px;
margin: 0 0 5px;
}
#main pre.syntax {
background-color: #f5f5f5;
color: #000;
padding: 3px 5px;
}
#main .section p.purpose {
background-color: #CDE0FB;
padding: 3px 5px;
}
#main .section p {
padding: 0 5px;
}
#main ul, #main ol {
padding-left: 5px;
margin: 0 0 10px;
}
#main ul, #main ul li {
list-style-type: none;
}
#main #excerpt p {
color: #000;
border-left: 3px solid #bbb;
padding: 0;
margin-left: -10px;
font-size: 94%;
padding-left: 10px;
}
#main .meta {
position: absolute;
width: 108px;
left: -60px;
text-align: right;
font-family: "Helvetica Neue", Helvetica, Arial, sans-serif;
font-size: 14px;
font-weight: bold;
color: #888;
}
/* @end */
/* @group Method List */
ul.method-list li {
display: inline;
border-top: 1px solid #ccc;
}
ul.method-list li a {
background-color: #eee;
padding: 2px 3px;
border: 1px solid #ccc;
}
ul.method-list li a:hover {
background-color: #ddd;
}
/* @end */
/* @group Menu */
#menu {
width: 840px;
margin: 0 auto;
position: relative;
height: 25px;
}
#menu div {
width: 234px;
float: right;
margin: 0 3px;
}
#menu div.search-box {
width: 222px;
background-color: #cee8c3;
font-size: 13px;
height: 25px;
line-height: 25px;
padding: 2px 6px;
}
#menu div.search-box label {
color: #555;
}
#menu div.search-box input {
border: 1px solid #bbb;
padding: 2px;
width: 163px;
}
#menu h2 {
font-size: 13px;
font-weight: normal;
}
#menu h2 a {
height: 25px;
line-height: 25px;
display: block;
text-align: center;
background-color: #CDE0FB;
font-family: Verdana, sans-serif;
padding: 2px 6px;
}
#menu h2 a:hover {
background-color: #a4c8fb;
}
#menu #api_menu,
#menu #search_results {
border: 1px solid #ddd;
background: #fff;
position: absolute;
width: 232px;
top: 26px;
z-index: 1500;
max-height: 200px;
overflow: auto;
}
#menu #api_menu {
right: 3px;
}
#menu #search_results {
right: 243px;
}
#menu .menu-items li {
background-color: #fff;
}
#menu .menu-items li a {
display: block;
color: #333;
background-color: #fff;
padding: 2px 6px;
border-top: 1px solid #fff;
border-bottom: 1px solid #fff;
}
#menu .menu-items li a:hover,
#menu .menu-items li.highlighted a {
background-color: #CDE0FB;
border-top-color: #a4c8fb;
border-bottom-color: #a4c8fb;
}
#menu .menu-items ul {
margin: 0;
padding: 0;
}
#menu .menu-items li a {
background-repeat: no-repeat;
background-position: 6px 3px;
padding: 3px 5px 3px 30px;
font-size: 12px;
}
#menu .menu-items li a.class {
background-image: url(../images/class.png);
}
#menu .menu-items li a.namespace {
background-image: url(../images/namespace.png);
}
#menu .menu-items li a.mixin {
background-image: url(../images/mixin.png);
}
#menu .menu-items li a.section {
text-transform: uppercase;
color: #777;
background-image: url(../images/section.png);
}
#menu .menu-items li a.class_method,
#menu .menu-items li a.instance_method,
#menu .menu-items li a.utility {
background-image: url(../images/method.png);
}
#menu .menu-items li a.class_property,
#menu .menu-items li a.instance_property {
background-image: url(../images/property.png);
}
#menu .menu-items li a.constructor {
background-image: url(../images/constructor.png);
}
#menu .menu-items li a.constant {
background-image: url(../images/constant.png);
}
/* @end */
/* @group Section Headings (H3s) */
.section h3 {
padding-right: 25px;
background-repeat: no-repeat;
background-position: right 4px;
}
.section-superclass h3 {
background-image: url(../images/class.png);
}
.section-method-list h3,
.section-instance_methods h3,
.section-klass_methods h3 {
background-image: url(../images/method.png);
}
.section-klass_properties h3,
.section-instance_properties h3 {
background-image: url(../images/property.png);
}
.section-constructor h3 {
background-image: url(../images/constructor.png);
}
.section-constants h3 {
background-image: url(../images/constant.png);
}
.section-mixins h3 {
background-image: url(../images/mixin.png);
}
/* @end */
/* @group Method Details List */
ul.method-details-list li {
border: 2px solid #fff;
}
ul.method-details-list li.highlighted {
border: 2px solid #CDE0FB;
}
/* @end */
/* floating menu */
#menu.fixed {
position: fixed;
top: 0;
z-index: 1000;
left: 232px;
}

View File

@ -1,244 +0,0 @@
/* Masthead */
div#masthead {
background: url(http://prototype.conio.net/new/images/header-stripe.png) repeat-x top left;
height: 152px;
}
div#masthead div#masthead_content {
margin: 0 auto;
width: 835px;
position: relative;
}
div#masthead h1#logo {
background: url(http://prototype.conio.net/new/images/header-logo.png) no-repeat 0 1px;
width: 236px;
height: 152px;
}
div#masthead div#pitch {
position: absolute;
background: url(http://prototype.conio.net/new/images/header-copy.png) no-repeat 0 1px;
top: 0;
left: 300px;
width: 535px;
height: 152px;
}
div#masthead h1#logo *,
div#masthead div#pitch * {
display: none;
}
/* Buttons */
div#buttons, div#more {
overflow: hidden;
width: 840px;
margin: -1px auto 0 auto;
padding: 0 0 0 5px;
}
div#more {
margin-top: 35px;
}
div#buttons li {
display: block;
float: left;
border-top: 1px solid #929fb3;
margin: 0 5px 0 0;
width: 175px;
height: 100px;
}
div#more li {
height: 50px;
}
div#buttons li a {
display: block;
position: relative;
width: 175px;
height: 100px;
text-decoration: none;
background: #cde0fb no-repeat center 30px;
}
div#buttons li a:hover {
background-color: #a4c8fb;
}
div#buttons li a span.title {
display: none;
}
div#buttons li a span.description {
position: absolute;
display: block;
width: 175px;
top: 55px;
text-align: center;
color: #666;
}
div#more li a span.title {
position: absolute;
display: block;
width: 175px;
top: 15px;
text-align: center;
color: #666;
}
div#buttons li a:hover span.description {
color: #333;
}
div#buttons li#download_button {
width: 295px;
}
div#buttons li#download_button a,
div#buttons li#download_button a span.description {
width: 295px;
}
div#buttons li#download_button a {
background-color: #cee8c3;
background-image: url(http://prototype.conio.net/new/images/button-download.png);
}
div#buttons li#download_button a:hover {
background-color: #a4e289;
}
div#buttons li#learn_button a {
background-image: url(http://prototype.conio.net/new/images/button-learn.png);
}
div#buttons li#discuss_button a {
background-image: url(http://prototype.conio.net/new/images/button-discuss.png);
}
div#buttons li#contribute_button a {
background-image: url(http://prototype.conio.net/new/images/button-contribute.png);
}
div#more {
position: relative;
height: 400px;
margin: 15px 60px;
color: #444;
}
div#more .column {
display: block;
float: left;
margin: 0 5px 0 0;
padding-left: 5px;
min-height: 300px;
}
div#more h3 {
font-family: "Helvetica Neue", Helvetica, Arial, sans-serif;
letter-spacing: -1px;
font-weight: bold;
color: #444;
font-size: 18px;
margin: 0 0 5px;
}
.column {
width: 175px;
}
.wide-column {
width: 295px;
}
.medium-column {
width: 235px;
}
.main-column {
width: 530px;
}
.sidebar-column {
width: 290px;
}
div#more {
width: 840px;
margin: 25px auto 0;
}
/*#buttons_wrapper {
background-color: #0E4FAF;
}
#page {
background-color: #292929;
}
*/
div#more div.main-column p {
font-size: 16px;
margin-right: 10px;
}
div#more h3.tagline {
height: 23px;
background: url(../images/tagline.png) no-repeat top left;
width: 530px;
}
div#more h3.tagline span { display: none; }
.view-master {
text-align: center;
font-family: Verdana;
color: #ccc;
font-size: 18px;
padding: 35px 0;
margin: 10px 0;
}
.using-prototype {
border-top: 2px solid #ddd;
border-bottom: 2px solid #ddd;
margin: 25px 10px 10px 0;
padding: 5px 0;
}
.sidebar-column h4 {
font-family: "Helvetica Neue", Helvetica, Arial, sans-serif;
font-size: 14px;
font-weight: bold;
margin: 0;
}
.sidebar-column p {
margin-bottom: 15px;
}
ol, ol li {
list-style-type: decimal;
line-height: 160%;
}
ol li {
margin: 0 0 2px;
}
ol, ul {
margin: 0 0 15px;
padding-left: 0;
font-family: "Helvetica Neue", Helvetica, Arial, sans-serif;
}

View File

@ -1,19 +0,0 @@
module PDoc
module Generators
module Html
module Helpers
module BaseHelper
end
module LinkHelper
end
module CodeHelper
end
module MenuHelper
end
end
end
end
end

View File

@ -1,24 +0,0 @@
<% @title = "Home" %>
<div class="page-introduction">
<%= @index_page_content %>
</div> <!-- .section -->
<div class="section section-sections">
<div class="section-title">
<h3>Sections</h3>
</div> <!-- .section-title -->
<div class="section-content">
<ul class="section-list">
<% @root.sections.each do |section| %>
<li>
<h4>
<a href="<%= path_to_section(section) %>"><%= section.name %></a>
</h4>
<p><%= htmlize(section.short_description) %></p>
</li>
<% end %>
</ul>
</div> <!-- .section-content -->
</div> <!-- .section clearfix -->

View File

@ -1,6 +0,0 @@
if (!window.PDoc) window.PDoc = {};
PDoc.elements = {
<%= @root.map { |e, i|
"'#{e.full_name}': { 'name': '#{e.full_name}', 'type': '#{e.type}', 'path': '#{path_to(e)}' }" }.join(",\n")
%>
};

View File

@ -1,79 +0,0 @@
<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN" "http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd">
<html xmlns="http://www.w3.org/1999/xhtml" xml:lang="en" lang="en">
<head>
<meta http-equiv="Content-Type" content="text/html; charset=utf-8" />
<title>Prototype API documentation | <%= @title %></title>
<meta name="generator" content="PDoc" />
<%= javascript_include_tag "prototype", "effects", "controls" %>
<%= javascript_include_tag "application", "code_highlighter" %>
<%= javascript_include_tag "item_index" %>
<%= stylesheet_link_tag "core", "api" %>
<script type="text/javascript">PDoc.pathPrefix = '<%= path_prefix %>';</script>
</head>
<body class="">
<div id="page">
<div id="masthead">
<div id="masthead_content">
<a href="http://prototypejs.org">
<h1 id="logo"><span class="replaced">Prototype JavaScript framework</span></h1>
</a>
</div> <!-- #masthead_content -->
</div> <!-- #masthead -->
<div id="menu" class="clearfix">
<div class="api-box">
<h2><a href="#" id="api_menu_button">Menu &darr;</a></h2>
<ul id="api_menu" class="menu-items" style="display: none">
<% @root.sections.each do |section| %>
<%= menu(section) %>
<% end %>
</ul>
</div> <!-- .api-box -->
<div class="search-box">
<form>
<label><span class="hidden">Search </span><input type="text" id="search" size="20" /></label>
</form>
<ul id="search_results" class="search-results menu-items" style="display:none"></ul>
</div> <!-- .search-box -->
</div> <!-- #menu -->
<div id="main" class="page-content">
<%= @content_for_layout %>
</div> <!-- #main -->
<div id="footer">
<div class="about clearfix">
<div class="copyright clearfix">
<div class="cc">
<a rel="license" href="http://creativecommons.org/licenses/by-sa/3.0/"><img alt="Creative Commons License" style="border-width:0" src="http://creativecommons.org/images/public/somerights20.png" /></a>
</div> <!-- .cc -->
<div class="copyright-about">
This work is licensed under a <a rel="license" href="http://creativecommons.org/licenses/by-sa/3.0/">Creative Commons Attribution-Share Alike 3.0 Unported License</a>.
</div> <!-- .copyright-about -->
</div> <!-- .copyright -->
<div class="credits">
<p>Generated by <a href="http://pdoc.org">PDoc</a>. Uses <a href="http://famfamfam.com/lab/icons/silk/" title="famfamfam.com: Silk Icons">Silk Icons</a>.</p>
</div> <!-- .credits -->
</div> <!-- .about -->
</div> <!-- #footer -->
</div> <!-- #page -->
</body>
</html>

View File

@ -1,171 +0,0 @@
<% d = @doc_instance %>
<% @title = "#{d.full_name} #{d.type}" %>
<%= include "partials/breadcrumbs", :object => d %>
<h2 class="page-title <%= class_names_for(d) %>">
<span class="type"><%= d.type %> </span><%= d.full_name %>
</h2>
<% # Does it have a description? %>
<% if d.description && !d.description.empty? %>
<div class="section section-description">
<div class="section-title">
<h3>Description</h3>
</div> <!-- .section-title -->
<div class="section-content">
<%= htmlize(d.description) %>
</div> <!-- .section-content -->
</div> <!--.section -->
<% end %>
<% # Is it a CLASS? %>
<% if d.is_a?(Documentation::Klass) %>
<% if d.superklass %>
<div class="section section-superclass">
<div class="section-title">
<h3>Superclass</h3>
</div> <!-- .section-title -->
<div class="section-content">
<p><%= auto_link_code(d.superklass, false) %></p>
</div> <!-- .section-content -->
</div> <!-- .section -->
<% end %>
<% unless d.subklasses.empty? %>
<div class="section section-subclasses">
<div class="section-title">
<h3>Subclasses</h3>
</div> <!-- .section-title -->
<div class="section-content">
<p><%= d.subklasses.map { |s| auto_link_code(s, false) }.join(', ') %></p>
</div> <!-- .section-content -->
</div> <!-- .section -->
<% end %>
<% end %>
<% # Does it have MIXINS? %>
<% unless d.mixins.compact.empty? %>
<div class="section section-mixins">
<div class="section-title">
<h3>Includes</h3>
</div> <!-- .section-title -->
<div class="section-content">
<p><%= d.mixins.map { |m| auto_link_code(m, false) }.join(', ') %></p>
</div> <!-- .section-content -->
</div> <!-- .section -->
<% end %>
<% # Are there related utilities? %>
<% unless d.related_utilities.empty? %>
<div class="section section-utilities">
<div class="section-title">
<h3>Related utilities</h3>
</div> <!-- .section-title -->
<div class="section-content">
<p><%= d.related_utilities.map { |u| auto_link_code(u, false) }.join(', ') %></p>
</div> <!-- .section-content -->
</div> <!-- .section -->
<% end %>
<% # List its methods. %>
<% unless d.all_methods.empty? && d.mixins.empty? %>
<div class="section section-method-list">
<div class="section-title">
<h3>Methods</h3>
</div> <!-- .section-title -->
<div class="section-content">
<ul class="method-list">
<% d.all_methods.each do |method| %>
<li><%= auto_link_code(method, true, :class => class_names_for(method)) %></li>
<% end %>
</ul>
<% unless d.mixins.compact.empty? %>
<% d.mixins.each do |mixin| %>
<h4 class="inherited">Inherited from <%= auto_link(mixin) %></h4>
<ul class="method-list">
<% mixin.all_methods.each do |method| %>
<li><%= auto_link_code(method, true, :class => class_names_for(method)) %></li>
<% end %>
</ul>
<% end %>
<% end %>
</div> <!-- .section-content -->
</div> <!-- .section -->
<% end %>
<% if d.is_a?(Documentation::Klass) && d.constructor %>
<div class="section section-constructor">
<div class="section-title">
<h3>Constructor</h3>
</div> <!-- .section-title -->
<div class="section-content">
<pre id="<%= dom_id(d.constructor) %>" class="syntax"><code><%= d.constructor.ebnf_expressions.join("\n").strip %></code></pre>
<% unless d.constructor.arguments.empty? %>
<ul class="argument-list">
<% d.constructor.arguments.each do |arg| %>
<li>
<code><%= arg.name %></code>
<% unless arg.types.empty? %>
(<%= arg.types.map { |t| auto_link_code(t, false) }.join(' | ') %>)
<% end %>
<%= ' &ndash; ' + inline_htmlize(arg.description) unless arg.description.empty? %>
</li>
<% end %>
</ul> <!-- .argument-list -->
<% end %>
<p><%= htmlize(d.constructor.description) %></p>
</div> <!-- .section-content -->
</div> <!-- .section -->
<% end %>
<%
types = {
:constants => "Constants",
:klass_methods => "Class methods",
:klass_properties => "Class properties",
:instance_methods => "Instance methods",
:instance_properties => "Instance properties"
}
%>
<% types.each do |method, title| %>
<% methods = d.send(method) %>
<% unless methods.empty? %>
<div class="section section-<%= method.to_s %>">
<div class="section-title">
<h3><%= title %></h3>
</div> <!-- .section-title -->
<div class="section-content">
<ul class="method-details-list">
<%= include "partials/short_description", :collection => methods %>
</ul>
</div> <!-- .section-content -->
</div> <!-- .section -->
<% end %>
<% end %>

View File

@ -1,6 +0,0 @@
<ul class="breadcrumbs clearfix">
<li><a href="<%= path_prefix %>index.html">Home</a> &rarr;</li>
<% unless object.is_a?(Documentation::Section) %>
<li><a href="<%= path_to(object.section) %>"><%= object.section.name %></a> &rarr;</li>
<% end %>
</ul>

View File

@ -1,48 +0,0 @@
<li class="method-description">
<h4 id="<%= dom_id(object) %>"><%= object.name %>
<span class="method-permalink"><a href="<%= path_to(object) %>">#</a></span></h4>
<% if object.signature %>
<%= method_synopsis(object) %>
<% end %>
<% if object.is_a?(Documentation::Method) %>
<% unless object.arguments.empty? %>
<ul class="argument-list">
<% object.arguments.each do |arg| %>
<li>
<code><%= arg.name %></code>
<% unless arg.types.empty? %>
(<%= arg.types.map { |t| auto_link_code(t, false) }.join(' | ') %>)
<% end %>
<%= ' &ndash; ' + inline_htmlize(arg.description) unless arg.description.empty? %>
</li>
<% end %>
</ul> <!-- .argument-list -->
<% end %>
<% end %>
<%= htmlize(object.description) %>
<% # Does it have an alias? %>
<% unless object.aliases.empty? %>
<p class="alias aliases">Aliased as: <%= object.aliases.map { |a| auto_link_code(a, false) }.join(', ') %></p>
<% end %>
<% # Is it an alias of something else? %>
<% if object.alias? %>
<p class="alias alias-of">Alias of: <%= auto_link_code(object.alias_of, false) %></p>
<% end %>
<% # Is it related to something? %>
<% if object.is_a?(Documentation::Utility) && object.related_to %>
<p class="related-to">Related to:
<%= auto_link_code(object.related_to, false) %></p>
<% end %>
<% # Is it methodized? %>
<% if object.is_a?(Documentation::Method) && object.methodized? %>
<p class="note">This method can be called <em>either</em> as an instance method <em>or</em> as a generic method. If calling as a generic, pass the instance in as the first argument.</p>
<% end %>
</li>

View File

@ -1,99 +0,0 @@
<% @title = "#{@doc_instance.full_name}" %>
<% section = @doc_instance %>
<%= include "partials/breadcrumbs", :object => section %>
<h2 class="page-title">
<span class="type">Section </span><%= section.name %>
</h2>
<div class="section section-description">
<div class="section-title">
<h3>Description</h3>
</div> <!-- .section-title -->
<div class="section-content">
<%= htmlize(section.description) %>
</div> <!-- .section-content -->
</div> <!--.section -->
<% # Iterate over the items in this section. %>
<% utilities = section.utilities %>
<% unless utilities.empty? %>
<div class="section section-utilities">
<div class="section-title">
<h3>Utilities</h3>
</div> <!-- .section-title -->
<div class="section-content">
<ul class="method-list">
<% utilities.each do |utility| %>
<li><%= auto_link_code(utility) %></li>
<% end %>
</ul>
</div> <!-- .section-content -->
</div> <!-- .section -->
<% end %>
<% namespaces = section.namespaces %>
<% unless namespaces.empty? %>
<div class="section section-namespaces">
<div class="section-title">
<h3>Namespaces</h3>
</div> <!-- .section-title -->
<div class="section-content">
<ul class="method-details-list">
<% namespaces.each do |namespace| %>
<li class="method-description">
<h4>
<a href="<%= path_to(namespace) %>"><%= namespace.full_name %></a>
</h4>
<% unless namespace.short_description.nil? %>
<p><%= htmlize(namespace.short_description) %></p>
<% end %>
</li>
<% end %>
</ul>
</div> <!-- .section-content -->
</div> <!-- .section -->
<% end %>
<% klasses = section.klasses %>
<% unless klasses.empty? %>
<div class="section section-classes">
<div class="section-title">
<h3>Classes</h3>
</div> <!-- .section-title -->
<div class="section-content">
<ul class="method-details-list">
<% klasses.each do |klass| %>
<li class="method-description">
<h4>
<a href="<%= path_to(klass) %>"><%= klass.full_name %></a>
</h4>
<% unless klass.short_description.nil? %>
<p><%= htmlize(klass.short_description) %></p>
<% end %>
</li>
<% end %>
</ul>
</div> <!-- .section-content -->
</div> <!--.section -->
<% end %>

View File

@ -1,21 +0,0 @@
<% d = @doc_instance %>
<% @title = "#{@doc_instance.full_name} utility" %>
<%= include "partials/breadcrumbs", :object => d %>
<h2 class="page-title">
<span class="type">utility </span><%= @doc_instance.name %>
</h2>
<div class="section">
<div class="section-title">
<h3>Description</h3>
</div> <!-- .section-title -->
<div class="section-content">
<ul class="method-details-list">
<%= include "partials/short_description", :collection => [@doc_instance] %>
</ul>
</div> <!-- .section-content -->
</div> <!-- .section -->

View File

@ -951,6 +951,9 @@ new Test.Unit.Runner({
// height/width could always be calculated if it's set to "auto" (Firefox)
this.assertNotNull($('auto_dimensions').getStyle('height'));
this.assertNotNull($('auto_dimensions').getStyle('width'));
// assert that using getStyle on an object without a style property returns null
this.assertNull(Element.Methods.getStyle({}, 'width'));
},
testElementGetOpacity: function() {
@ -1322,6 +1325,10 @@ new Test.Unit.Runner({
this.assertEnumEqual([0,0], offset);
this.assertIdentical(0, offset.top);
this.assertIdentical(0, offset.left);
var innerEl = new Element('div'), outerEl = new Element('div');
outerEl.appendChild(innerEl);
this.assertEnumEqual([0,0], innerEl.cumulativeOffset());
},
testViewportOffset: function() {

View File

@ -184,6 +184,8 @@ new Test.Unit.Runner({
span.observe("test:somethingHappened", observer);
this.assertEqual(span, span.stopObserving("test:somethingHappened"));
this.assertEqual(span, span.stopObserving("test:somethingOtherHappened", observer));
span.observe("test:somethingHappened", observer);
this.assertEqual(span, span.stopObserving());
this.assertEqual(span, span.stopObserving()); // assert it again, after there are no observers

View File

@ -0,0 +1,4 @@
<div id="test_div_parent" class="test_class">
<div id="test_div_child" class="test_class">
</div>
</div>

View File

@ -0,0 +1,50 @@
/*
<div id="test_div_parent" class="test_class">
<div id="test_div_child" class="test_class">
</div>
</div>
*/
new Test.Unit.Runner({
testEngine: function() {
this.assert(Prototype.Selector.engine);
},
testSelect: function() {
var elements = Prototype.Selector.select('.test_class');
this.assert(Object.isArray(elements));
this.assertEqual(2, elements.length);
this.assertEqual('test_div_parent', elements[0].id);
this.assertEqual('test_div_child', elements[1].id);
},
testSelectWithContext: function() {
var elements = Prototype.Selector.select('.test_class', $('test_div_parent'));
this.assert(Object.isArray(elements));
this.assertEqual(1, elements.length);
this.assertEqual('test_div_child', elements[0].id);
},
testSelectWithEmptyResult: function() {
var elements = Prototype.Selector.select('.non_existent');
this.assert(Object.isArray(elements));
this.assertEqual(0, elements.length);
},
testMatch: function() {
var element = $('test_div_parent');
this.assertEqual(true, Prototype.Selector.match(element, '.test_class'));
this.assertEqual(false, Prototype.Selector.match(element, '.non_existent'));
},
testFind: function() {
var elements = document.getElementsByTagName('*'),
expression = '.test_class';
this.assertEqual('test_div_parent', Prototype.Selector.find(elements, expression).id);
this.assertEqual('test_div_child', Prototype.Selector.find(elements, expression, 1).id);
}
});

View File

@ -0,0 +1,803 @@
/* Portions of the Prototype.LegacySelector class are derived from Jack Slocum's DomQuery,
* part of YUI-Ext version 0.40, distributed under the terms of an MIT-style
* license. Please see http://www.yui-ext.com/ for more information. */
Prototype.LegacySelector = Class.create({
initialize: function(expression) {
this.expression = expression.strip();
if (this.shouldUseSelectorsAPI()) {
this.mode = 'selectorsAPI';
} else if (this.shouldUseXPath()) {
this.mode = 'xpath';
this.compileXPathMatcher();
} else {
this.mode = "normal";
this.compileMatcher();
}
},
shouldUseXPath: (function() {
// Some versions of Opera 9.x produce incorrect results when using XPath
// with descendant combinators.
// see: http://opera.remcol.ath.cx/bugs/index.php?action=bug&id=652
var IS_DESCENDANT_SELECTOR_BUGGY = (function(){
var isBuggy = false;
if (document.evaluate && window.XPathResult) {
var el = document.createElement('div');
el.innerHTML = '<ul><li></li></ul><div><ul><li></li></ul></div>';
var xpath = ".//*[local-name()='ul' or local-name()='UL']" +
"//*[local-name()='li' or local-name()='LI']";
var result = document.evaluate(xpath, el, null,
XPathResult.ORDERED_NODE_SNAPSHOT_TYPE, null);
isBuggy = (result.snapshotLength !== 2);
el = null;
}
return isBuggy;
})();
return function() {
if (!Prototype.BrowserFeatures.XPath) return false;
var e = this.expression;
// Safari 3 chokes on :*-of-type and :empty
if (Prototype.Browser.WebKit &&
(e.include("-of-type") || e.include(":empty")))
return false;
// XPath can't do namespaced attributes, nor can it read
// the "checked" property from DOM nodes
if ((/(\[[\w-]*?:|:checked)/).test(e))
return false;
if (IS_DESCENDANT_SELECTOR_BUGGY) return false;
return true;
}
})(),
shouldUseSelectorsAPI: function() {
if (!Prototype.BrowserFeatures.SelectorsAPI) return false;
if (Prototype.LegacySelector.CASE_INSENSITIVE_CLASS_NAMES) return false;
if (!Prototype.LegacySelector._div) Prototype.LegacySelector._div = new Element('div');
// Make sure the browser treats the selector as valid. Test on an
// isolated element to minimize cost of this check.
try {
Prototype.LegacySelector._div.querySelector(this.expression);
} catch(e) {
return false;
}
return true;
},
compileMatcher: function() {
var e = this.expression, ps = Prototype.LegacySelector.patterns, h = Prototype.LegacySelector.handlers,
c = Prototype.LegacySelector.criteria, le, p, m, len = ps.length, name;
if (Prototype.LegacySelector._cache[e]) {
this.matcher = Prototype.LegacySelector._cache[e];
return;
}
this.matcher = ["this.matcher = function(root) {",
"var r = root, h = Prototype.LegacySelector.handlers, c = false, n;"];
while (e && le != e && (/\S/).test(e)) {
le = e;
for (var i = 0; i<len; i++) {
p = ps[i].re;
name = ps[i].name;
if (m = e.match(p)) {
this.matcher.push(Object.isFunction(c[name]) ? c[name](m) :
new Template(c[name]).evaluate(m));
e = e.replace(m[0], '');
break;
}
}
}
this.matcher.push("return h.unique(n);\n}");
eval(this.matcher.join('\n'));
Prototype.LegacySelector._cache[this.expression] = this.matcher;
},
compileXPathMatcher: function() {
var e = this.expression, ps = Prototype.LegacySelector.patterns,
x = Prototype.LegacySelector.xpath, le, m, len = ps.length, name;
if (Prototype.LegacySelector._cache[e]) {
this.xpath = Prototype.LegacySelector._cache[e]; return;
}
this.matcher = ['.//*'];
while (e && le != e && (/\S/).test(e)) {
le = e;
for (var i = 0; i<len; i++) {
name = ps[i].name;
if (m = e.match(ps[i].re)) {
this.matcher.push(Object.isFunction(x[name]) ? x[name](m) :
new Template(x[name]).evaluate(m));
e = e.replace(m[0], '');
break;
}
}
}
this.xpath = this.matcher.join('');
Prototype.LegacySelector._cache[this.expression] = this.xpath;
},
findElements: function(root) {
root = root || document;
var e = this.expression, results;
switch (this.mode) {
case 'selectorsAPI':
// querySelectorAll queries document-wide, then filters to descendants
// of the context element. That's not what we want.
// Add an explicit context to the selector if necessary.
if (root !== document) {
var oldId = root.id, id = $(root).identify();
// Escape special characters in the ID.
id = id.replace(/([\.:])/g, "\\$1");
e = "#" + id + " " + e;
}
results = $A(root.querySelectorAll(e)).map(Element.extend);
root.id = oldId;
return results;
case 'xpath':
return document._getElementsByXPath(this.xpath, root);
default:
return this.matcher(root);
}
},
match: function(element) {
this.tokens = [];
var e = this.expression, ps = Prototype.LegacySelector.patterns, as = Prototype.LegacySelector.assertions;
var le, p, m, len = ps.length, name;
while (e && le !== e && (/\S/).test(e)) {
le = e;
for (var i = 0; i<len; i++) {
p = ps[i].re;
name = ps[i].name;
if (m = e.match(p)) {
// use the Prototype.LegacySelector.assertions methods unless the selector
// is too complex.
if (as[name]) {
this.tokens.push([name, Object.clone(m)]);
e = e.replace(m[0], '');
} else {
// reluctantly do a document-wide search
// and look for a match in the array
return this.findElements(document).include(element);
}
}
}
}
var match = true, name, matches;
for (var i = 0, token; token = this.tokens[i]; i++) {
name = token[0], matches = token[1];
if (!Prototype.LegacySelector.assertions[name](element, matches)) {
match = false; break;
}
}
return match;
},
toString: function() {
return this.expression;
},
inspect: function() {
return "#<Prototype.LegacySelector:" + this.expression.inspect() + ">";
}
});
if (Prototype.BrowserFeatures.SelectorsAPI &&
document.compatMode === 'BackCompat') {
// Versions of Safari 3 before 3.1.2 treat class names case-insensitively in
// quirks mode. If we detect this behavior, we should use a different
// approach.
Prototype.LegacySelector.CASE_INSENSITIVE_CLASS_NAMES = (function(){
var div = document.createElement('div'),
span = document.createElement('span');
div.id = "prototype_test_id";
span.className = 'Test';
div.appendChild(span);
var isIgnored = (div.querySelector('#prototype_test_id .test') !== null);
div = span = null;
return isIgnored;
})();
}
Object.extend(Prototype.LegacySelector, {
_cache: { },
xpath: {
descendant: "//*",
child: "/*",
adjacent: "/following-sibling::*[1]",
laterSibling: '/following-sibling::*',
tagName: function(m) {
if (m[1] == '*') return '';
return "[local-name()='" + m[1].toLowerCase() +
"' or local-name()='" + m[1].toUpperCase() + "']";
},
className: "[contains(concat(' ', @class, ' '), ' #{1} ')]",
id: "[@id='#{1}']",
attrPresence: function(m) {
m[1] = m[1].toLowerCase();
return new Template("[@#{1}]").evaluate(m);
},
attr: function(m) {
m[1] = m[1].toLowerCase();
m[3] = m[5] || m[6];
return new Template(Prototype.LegacySelector.xpath.operators[m[2]]).evaluate(m);
},
pseudo: function(m) {
var h = Prototype.LegacySelector.xpath.pseudos[m[1]];
if (!h) return '';
if (Object.isFunction(h)) return h(m);
return new Template(Prototype.LegacySelector.xpath.pseudos[m[1]]).evaluate(m);
},
operators: {
'=': "[@#{1}='#{3}']",
'!=': "[@#{1}!='#{3}']",
'^=': "[starts-with(@#{1}, '#{3}')]",
'$=': "[substring(@#{1}, (string-length(@#{1}) - string-length('#{3}') + 1))='#{3}']",
'*=': "[contains(@#{1}, '#{3}')]",
'~=': "[contains(concat(' ', @#{1}, ' '), ' #{3} ')]",
'|=': "[contains(concat('-', @#{1}, '-'), '-#{3}-')]"
},
pseudos: {
'first-child': '[not(preceding-sibling::*)]',
'last-child': '[not(following-sibling::*)]',
'only-child': '[not(preceding-sibling::* or following-sibling::*)]',
'empty': "[count(*) = 0 and (count(text()) = 0)]",
'checked': "[@checked]",
'disabled': "[(@disabled) and (@type!='hidden')]",
'enabled': "[not(@disabled) and (@type!='hidden')]",
'not': function(m) {
var e = m[6], p = Prototype.LegacySelector.patterns,
x = Prototype.LegacySelector.xpath, le, v, len = p.length, name;
var exclusion = [];
while (e && le != e && (/\S/).test(e)) {
le = e;
for (var i = 0; i<len; i++) {
name = p[i].name;
if (m = e.match(p[i].re)) {
v = Object.isFunction(x[name]) ? x[name](m) : new Template(x[name]).evaluate(m);
exclusion.push("(" + v.substring(1, v.length - 1) + ")");
e = e.replace(m[0], '');
break;
}
}
}
return "[not(" + exclusion.join(" and ") + ")]";
},
'nth-child': function(m) {
return Prototype.LegacySelector.xpath.pseudos.nth("(count(./preceding-sibling::*) + 1) ", m);
},
'nth-last-child': function(m) {
return Prototype.LegacySelector.xpath.pseudos.nth("(count(./following-sibling::*) + 1) ", m);
},
'nth-of-type': function(m) {
return Prototype.LegacySelector.xpath.pseudos.nth("position() ", m);
},
'nth-last-of-type': function(m) {
return Prototype.LegacySelector.xpath.pseudos.nth("(last() + 1 - position()) ", m);
},
'first-of-type': function(m) {
m[6] = "1"; return Prototype.LegacySelector.xpath.pseudos['nth-of-type'](m);
},
'last-of-type': function(m) {
m[6] = "1"; return Prototype.LegacySelector.xpath.pseudos['nth-last-of-type'](m);
},
'only-of-type': function(m) {
var p = Prototype.LegacySelector.xpath.pseudos; return p['first-of-type'](m) + p['last-of-type'](m);
},
nth: function(fragment, m) {
var mm, formula = m[6], predicate;
if (formula == 'even') formula = '2n+0';
if (formula == 'odd') formula = '2n+1';
if (mm = formula.match(/^(\d+)$/)) // digit only
return '[' + fragment + "= " + mm[1] + ']';
if (mm = formula.match(/^(-?\d*)?n(([+-])(\d+))?/)) { // an+b
if (mm[1] == "-") mm[1] = -1;
var a = mm[1] ? Number(mm[1]) : 1;
var b = mm[2] ? Number(mm[2]) : 0;
predicate = "[((#{fragment} - #{b}) mod #{a} = 0) and " +
"((#{fragment} - #{b}) div #{a} >= 0)]";
return new Template(predicate).evaluate({
fragment: fragment, a: a, b: b });
}
}
}
},
criteria: {
tagName: 'n = h.tagName(n, r, "#{1}", c); c = false;',
className: 'n = h.className(n, r, "#{1}", c); c = false;',
id: 'n = h.id(n, r, "#{1}", c); c = false;',
attrPresence: 'n = h.attrPresence(n, r, "#{1}", c); c = false;',
attr: function(m) {
m[3] = (m[5] || m[6]);
return new Template('n = h.attr(n, r, "#{1}", "#{3}", "#{2}", c); c = false;').evaluate(m);
},
pseudo: function(m) {
if (m[6]) m[6] = m[6].replace(/"/g, '\\"');
return new Template('n = h.pseudo(n, "#{1}", "#{6}", r, c); c = false;').evaluate(m);
},
descendant: 'c = "descendant";',
child: 'c = "child";',
adjacent: 'c = "adjacent";',
laterSibling: 'c = "laterSibling";'
},
patterns: [
// combinators must be listed first
// (and descendant needs to be last combinator)
{ name: 'laterSibling', re: /^\s*~\s*/ },
{ name: 'child', re: /^\s*>\s*/ },
{ name: 'adjacent', re: /^\s*\+\s*/ },
{ name: 'descendant', re: /^\s/ },
// selectors follow
{ name: 'tagName', re: /^\s*(\*|[\w\-]+)(\b|$)?/ },
{ name: 'id', re: /^#([\w\-\*]+)(\b|$)/ },
{ name: 'className', re: /^\.([\w\-\*]+)(\b|$)/ },
{ name: 'pseudo', re: /^:((first|last|nth|nth-last|only)(-child|-of-type)|empty|checked|(en|dis)abled|not)(\((.*?)\))?(\b|$|(?=\s|[:+~>]))/ },
{ name: 'attrPresence', re: /^\[((?:[\w-]+:)?[\w-]+)\]/ },
{ name: 'attr', re: /\[((?:[\w-]*:)?[\w-]+)\s*(?:([!^$*~|]?=)\s*((['"])([^\4]*?)\4|([^'"][^\]]*?)))?\]/ }
],
// for Prototype.LegacySelector.match and Element#match
assertions: {
tagName: function(element, matches) {
return matches[1].toUpperCase() == element.tagName.toUpperCase();
},
className: function(element, matches) {
return Element.hasClassName(element, matches[1]);
},
id: function(element, matches) {
return element.id === matches[1];
},
attrPresence: function(element, matches) {
return Element.hasAttribute(element, matches[1]);
},
attr: function(element, matches) {
var nodeValue = Element.readAttribute(element, matches[1]);
return nodeValue && Prototype.LegacySelector.operators[matches[2]](nodeValue, matches[5] || matches[6]);
}
},
handlers: {
// UTILITY FUNCTIONS
// joins two collections
concat: function(a, b) {
for (var i = 0, node; node = b[i]; i++)
a.push(node);
return a;
},
// marks an array of nodes for counting
mark: function(nodes) {
var _true = Prototype.emptyFunction;
for (var i = 0, node; node = nodes[i]; i++)
node._countedByPrototype = _true;
return nodes;
},
unmark: (function(){
// IE improperly serializes _countedByPrototype in (inner|outer)HTML
// due to node properties being mapped directly to attributes
var PROPERTIES_ATTRIBUTES_MAP = (function(){
var el = document.createElement('div'),
isBuggy = false,
propName = '_countedByPrototype',
value = 'x';
el[propName] = value;
isBuggy = (el.getAttribute(propName) === value);
el = null;
return isBuggy;
})();
return PROPERTIES_ATTRIBUTES_MAP ?
function(nodes) {
for (var i = 0, node; node = nodes[i]; i++)
node.removeAttribute('_countedByPrototype');
return nodes;
} :
function(nodes) {
for (var i = 0, node; node = nodes[i]; i++)
node._countedByPrototype = void 0;
return nodes;
}
})(),
// mark each child node with its position (for nth calls)
// "ofType" flag indicates whether we're indexing for nth-of-type
// rather than nth-child
index: function(parentNode, reverse, ofType) {
parentNode._countedByPrototype = Prototype.emptyFunction;
if (reverse) {
for (var nodes = parentNode.childNodes, i = nodes.length - 1, j = 1; i >= 0; i--) {
var node = nodes[i];
if (node.nodeType == 1 && (!ofType || node._countedByPrototype)) node.nodeIndex = j++;
}
} else {
for (var i = 0, j = 1, nodes = parentNode.childNodes; node = nodes[i]; i++)
if (node.nodeType == 1 && (!ofType || node._countedByPrototype)) node.nodeIndex = j++;
}
},
// filters out duplicates and extends all nodes
unique: function(nodes) {
if (nodes.length == 0) return nodes;
var results = [], n;
for (var i = 0, l = nodes.length; i < l; i++)
// use `typeof` operator to prevent errors
if (typeof (n = nodes[i])._countedByPrototype == 'undefined') {
n._countedByPrototype = Prototype.emptyFunction;
results.push(Element.extend(n));
}
return Prototype.LegacySelector.handlers.unmark(results);
},
// COMBINATOR FUNCTIONS
descendant: function(nodes) {
var h = Prototype.LegacySelector.handlers;
for (var i = 0, results = [], node; node = nodes[i]; i++)
h.concat(results, node.getElementsByTagName('*'));
return results;
},
child: function(nodes) {
var h = Prototype.LegacySelector.handlers;
for (var i = 0, results = [], node; node = nodes[i]; i++) {
for (var j = 0, child; child = node.childNodes[j]; j++)
if (child.nodeType == 1 && child.tagName != '!') results.push(child);
}
return results;
},
adjacent: function(nodes) {
for (var i = 0, results = [], node; node = nodes[i]; i++) {
var next = this.nextElementSibling(node);
if (next) results.push(next);
}
return results;
},
laterSibling: function(nodes) {
var h = Prototype.LegacySelector.handlers;
for (var i = 0, results = [], node; node = nodes[i]; i++)
h.concat(results, Element.nextSiblings(node));
return results;
},
nextElementSibling: function(node) {
while (node = node.nextSibling)
if (node.nodeType == 1) return node;
return null;
},
previousElementSibling: function(node) {
while (node = node.previousSibling)
if (node.nodeType == 1) return node;
return null;
},
// TOKEN FUNCTIONS
tagName: function(nodes, root, tagName, combinator) {
var uTagName = tagName.toUpperCase();
var results = [], h = Prototype.LegacySelector.handlers;
if (nodes) {
if (combinator) {
// fastlane for ordinary descendant combinators
if (combinator == "descendant") {
for (var i = 0, node; node = nodes[i]; i++)
h.concat(results, node.getElementsByTagName(tagName));
return results;
} else nodes = this[combinator](nodes);
if (tagName == "*") return nodes;
}
for (var i = 0, node; node = nodes[i]; i++)
if (node.tagName.toUpperCase() === uTagName) results.push(node);
return results;
} else return root.getElementsByTagName(tagName);
},
id: function(nodes, root, id, combinator) {
var targetNode = $(id), h = Prototype.LegacySelector.handlers;
if (root == document) {
// We don't have to deal with orphan nodes. Easy.
if (!targetNode) return [];
if (!nodes) return [targetNode];
} else {
// In IE, we can check sourceIndex to see if root is attached
// to the document. If not (or if sourceIndex is not present),
// we do it the hard way.
if (!root.sourceIndex || root.sourceIndex < 1) {
var nodes = root.getElementsByTagName('*');
for (var j = 0, node; node = nodes[j]; j++) {
if (node.id === id) return [node];
}
}
}
if (nodes) {
if (combinator) {
if (combinator == 'child') {
for (var i = 0, node; node = nodes[i]; i++)
if (targetNode.parentNode == node) return [targetNode];
} else if (combinator == 'descendant') {
for (var i = 0, node; node = nodes[i]; i++)
if (Element.descendantOf(targetNode, node)) return [targetNode];
} else if (combinator == 'adjacent') {
for (var i = 0, node; node = nodes[i]; i++)
if (Prototype.LegacySelector.handlers.previousElementSibling(targetNode) == node)
return [targetNode];
} else nodes = h[combinator](nodes);
}
for (var i = 0, node; node = nodes[i]; i++)
if (node == targetNode) return [targetNode];
return [];
}
return (targetNode && Element.descendantOf(targetNode, root)) ? [targetNode] : [];
},
className: function(nodes, root, className, combinator) {
if (nodes && combinator) nodes = this[combinator](nodes);
return Prototype.LegacySelector.handlers.byClassName(nodes, root, className);
},
byClassName: function(nodes, root, className) {
if (!nodes) nodes = Prototype.LegacySelector.handlers.descendant([root]);
var needle = ' ' + className + ' ';
for (var i = 0, results = [], node, nodeClassName; node = nodes[i]; i++) {
nodeClassName = node.className;
if (nodeClassName.length == 0) continue;
if (nodeClassName == className || (' ' + nodeClassName + ' ').include(needle))
results.push(node);
}
return results;
},
attrPresence: function(nodes, root, attr, combinator) {
if (!nodes) nodes = root.getElementsByTagName("*");
if (nodes && combinator) nodes = this[combinator](nodes);
var results = [];
for (var i = 0, node; node = nodes[i]; i++)
if (Element.hasAttribute(node, attr)) results.push(node);
return results;
},
attr: function(nodes, root, attr, value, operator, combinator) {
if (!nodes) nodes = root.getElementsByTagName("*");
if (nodes && combinator) nodes = this[combinator](nodes);
var handler = Prototype.LegacySelector.operators[operator], results = [];
for (var i = 0, node; node = nodes[i]; i++) {
var nodeValue = Element.readAttribute(node, attr);
if (nodeValue === null) continue;
if (handler(nodeValue, value)) results.push(node);
}
return results;
},
pseudo: function(nodes, name, value, root, combinator) {
if (nodes && combinator) nodes = this[combinator](nodes);
if (!nodes) nodes = root.getElementsByTagName("*");
return Prototype.LegacySelector.pseudos[name](nodes, value, root);
}
},
pseudos: {
'first-child': function(nodes, value, root) {
for (var i = 0, results = [], node; node = nodes[i]; i++) {
if (Prototype.LegacySelector.handlers.previousElementSibling(node)) continue;
results.push(node);
}
return results;
},
'last-child': function(nodes, value, root) {
for (var i = 0, results = [], node; node = nodes[i]; i++) {
if (Prototype.LegacySelector.handlers.nextElementSibling(node)) continue;
results.push(node);
}
return results;
},
'only-child': function(nodes, value, root) {
var h = Prototype.LegacySelector.handlers;
for (var i = 0, results = [], node; node = nodes[i]; i++)
if (!h.previousElementSibling(node) && !h.nextElementSibling(node))
results.push(node);
return results;
},
'nth-child': function(nodes, formula, root) {
return Prototype.LegacySelector.pseudos.nth(nodes, formula, root);
},
'nth-last-child': function(nodes, formula, root) {
return Prototype.LegacySelector.pseudos.nth(nodes, formula, root, true);
},
'nth-of-type': function(nodes, formula, root) {
return Prototype.LegacySelector.pseudos.nth(nodes, formula, root, false, true);
},
'nth-last-of-type': function(nodes, formula, root) {
return Prototype.LegacySelector.pseudos.nth(nodes, formula, root, true, true);
},
'first-of-type': function(nodes, formula, root) {
return Prototype.LegacySelector.pseudos.nth(nodes, "1", root, false, true);
},
'last-of-type': function(nodes, formula, root) {
return Prototype.LegacySelector.pseudos.nth(nodes, "1", root, true, true);
},
'only-of-type': function(nodes, formula, root) {
var p = Prototype.LegacySelector.pseudos;
return p['last-of-type'](p['first-of-type'](nodes, formula, root), formula, root);
},
// handles the an+b logic
getIndices: function(a, b, total) {
if (a == 0) return b > 0 ? [b] : [];
return $R(1, total).inject([], function(memo, i) {
if (0 == (i - b) % a && (i - b) / a >= 0) memo.push(i);
return memo;
});
},
// handles nth(-last)-child, nth(-last)-of-type, and (first|last)-of-type
nth: function(nodes, formula, root, reverse, ofType) {
if (nodes.length == 0) return [];
if (formula == 'even') formula = '2n+0';
if (formula == 'odd') formula = '2n+1';
var h = Prototype.LegacySelector.handlers, results = [], indexed = [], m;
h.mark(nodes);
for (var i = 0, node; node = nodes[i]; i++) {
if (!node.parentNode._countedByPrototype) {
h.index(node.parentNode, reverse, ofType);
indexed.push(node.parentNode);
}
}
if (formula.match(/^\d+$/)) { // just a number
formula = Number(formula);
for (var i = 0, node; node = nodes[i]; i++)
if (node.nodeIndex == formula) results.push(node);
} else if (m = formula.match(/^(-?\d*)?n(([+-])(\d+))?/)) { // an+b
if (m[1] == "-") m[1] = -1;
var a = m[1] ? Number(m[1]) : 1;
var b = m[2] ? Number(m[2]) : 0;
var indices = Prototype.LegacySelector.pseudos.getIndices(a, b, nodes.length);
for (var i = 0, node, l = indices.length; node = nodes[i]; i++) {
for (var j = 0; j < l; j++)
if (node.nodeIndex == indices[j]) results.push(node);
}
}
h.unmark(nodes);
h.unmark(indexed);
return results;
},
'empty': function(nodes, value, root) {
for (var i = 0, results = [], node; node = nodes[i]; i++) {
// IE treats comments as element nodes
if (node.tagName == '!' || node.firstChild) continue;
results.push(node);
}
return results;
},
'not': function(nodes, selector, root) {
var h = Prototype.LegacySelector.handlers, selectorType, m;
var exclusions = new Prototype.LegacySelector(selector).findElements(root);
h.mark(exclusions);
for (var i = 0, results = [], node; node = nodes[i]; i++)
if (!node._countedByPrototype) results.push(node);
h.unmark(exclusions);
return results;
},
'enabled': function(nodes, value, root) {
for (var i = 0, results = [], node; node = nodes[i]; i++)
if (!node.disabled && (!node.type || node.type !== 'hidden'))
results.push(node);
return results;
},
'disabled': function(nodes, value, root) {
for (var i = 0, results = [], node; node = nodes[i]; i++)
if (node.disabled) results.push(node);
return results;
},
'checked': function(nodes, value, root) {
for (var i = 0, results = [], node; node = nodes[i]; i++)
if (node.checked) results.push(node);
return results;
}
},
operators: {
'=': function(nv, v) { return nv == v; },
'!=': function(nv, v) { return nv != v; },
'^=': function(nv, v) { return nv == v || nv && nv.startsWith(v); },
'$=': function(nv, v) { return nv == v || nv && nv.endsWith(v); },
'*=': function(nv, v) { return nv == v || nv && nv.include(v); },
'~=': function(nv, v) { return (' ' + nv + ' ').include(' ' + v + ' '); },
'|=': function(nv, v) { return ('-' + (nv || "").toUpperCase() +
'-').include('-' + (v || "").toUpperCase() + '-'); }
},
split: function(expression) {
var expressions = [];
expression.scan(/(([\w#:.~>+()\s-]+|\*|\[.*?\])+)\s*(,|$)/, function(m) {
expressions.push(m[1].strip());
});
return expressions;
},
matchElements: function(elements, expression) {
var matches = $$(expression), h = Prototype.LegacySelector.handlers;
h.mark(matches);
for (var i = 0, results = [], element; element = elements[i]; i++)
if (element._countedByPrototype) results.push(element);
h.unmark(matches);
return results;
},
findElement: function(elements, expression, index) {
if (Object.isNumber(expression)) {
index = expression; expression = false;
}
return Prototype.LegacySelector.matchElements(elements, expression || '*')[index || 0];
},
findChildElements: function(element, expressions) {
expressions = Prototype.LegacySelector.split(expressions.join(','));
var results = [], h = Prototype.LegacySelector.handlers;
for (var i = 0, l = expressions.length, selector; i < l; i++) {
selector = new Prototype.LegacySelector(expressions[i].strip());
h.concat(results, selector.findElements(element));
}
return (l > 1) ? h.unique(results) : results;
}
});
if (Prototype.Browser.IE) {
Object.extend(Prototype.LegacySelector.handlers, {
// IE returns comment nodes on getElementsByTagName("*").
// Filter them out.
concat: function(a, b) {
for (var i = 0, node; node = b[i]; i++)
if (node.tagName !== "!") a.push(node);
return a;
}
});
}

View File

@ -0,0 +1,18 @@
//= require "repository/legacy_selector"
Prototype.Selector = (function(engine) {
function select(selector, scope) {
return engine.findChildElements(scope || document, [selector]);
}
function match(element, selector) {
return !!engine.findElement([element], selector);
}
return {
engine: engine,
select: select,
match: match,
filter: engine.matchElements
};
})(Prototype.LegacySelector);

1
vendor/nwmatcher/repository vendored Submodule

@ -0,0 +1 @@
Subproject commit c9f5d5d4fc4ca294477f803bb8d688a8d45de664

18
vendor/nwmatcher/selector_engine.js vendored Normal file
View File

@ -0,0 +1,18 @@
Prototype._original_property = window.NW;
//= require "repository/src/nwmatcher"
Prototype.Selector = (function(engine) {
function select(selector, scope) {
return engine.select(selector, scope || document, null, Element.extend);
}
return {
engine: engine,
select: select,
match: engine.match
};
})(NW.Dom);
// Restore globals.
window.NW = Prototype._original_property;
delete Prototype._original_property;

2
vendor/pdoc vendored

@ -1 +1 @@
Subproject commit 147250bd65eed627e32ca5a70b57fe4f7803ab4b
Subproject commit 472a55dd0019acf034d4f72522915a5e9efd0a1a

1
vendor/sizzle vendored

@ -1 +0,0 @@
Subproject commit e0f5cbc75d12aa78f3ef30930414b2f88da7b2b8

1
vendor/sizzle/repository vendored Submodule

@ -0,0 +1 @@
Subproject commit 415e466f70e5a53f589161b1f2944e5485007409

34
vendor/sizzle/selector_engine.js vendored Normal file
View File

@ -0,0 +1,34 @@
Prototype._original_property = window.Sizzle;
//= require "repository/sizzle"
Prototype.Selector = (function(engine) {
function extend(elements) {
for (var i = 0, length = elements.length; i < length; i++) {
Element.extend(elements[i]);
}
return elements;
}
function select(selector, scope) {
return extend(engine(selector, scope || document));
}
function match(element, selector) {
return engine.matches(selector, [element]).length == 1;
}
function filter(elements, selector) {
return extend(engine.matches(selector, elements));
}
return {
engine: engine,
select: select,
match: match,
filter: filter
};
})(Sizzle);
// Restore globals.
window.Sizzle = Prototype._original_property;
delete Prototype._original_property;