1/* 2 * Copyright (c) 2010, 2013, Oracle and/or its affiliates. All rights reserved. 3 * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER. 4 * 5 * This code is free software; you can redistribute it and/or modify it 6 * under the terms of the GNU General Public License version 2 only, as 7 * published by the Free Software Foundation. 8 * 9 * This code is distributed in the hope that it will be useful, but WITHOUT 10 * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or 11 * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License 12 * version 2 for more details (a copy is included in the LICENSE file that 13 * accompanied this code). 14 * 15 * You should have received a copy of the GNU General Public License version 16 * 2 along with this work; if not, write to the Free Software Foundation, 17 * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA. 18 * 19 * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA 20 * or visit www.oracle.com if you need additional information or have any 21 * questions. 22 */ 23 24/** 25 * This script contains non-standard, Mozilla compatibility functionality on 26 * the standard global objects. Please note that it is incomplete. Only the most 27 * often used functionality is supported. 28 */ 29 30// JavaAdapter 31Object.defineProperty(this, "JavaAdapter", { 32 configurable: true, enumerable: false, writable: true, 33 value: function() { 34 if (arguments.length < 2) { 35 throw new TypeError("JavaAdapter requires atleast two arguments"); 36 } 37 38 var types = Array.prototype.slice.call(arguments, 0, arguments.length - 1); 39 var NewType = Java.extend.apply(Java, types); 40 return new NewType(arguments[arguments.length - 1]); 41 } 42}); 43 44 45// importPackage 46// avoid unnecessary chaining of __noSuchProperty__ again 47// in case user loads this script more than once. 48if (typeof importPackage == 'undefined') { 49 50Object.defineProperty(this, "importPackage", { 51 configurable: true, enumerable: false, writable: true, 52 value: (function() { 53 var _packages = []; 54 var global = this; 55 var oldNoSuchProperty = global.__noSuchProperty__; 56 var __noSuchProperty__ = function(name) { 57 'use strict'; 58 for (var i in _packages) { 59 try { 60 var type = Java.type(_packages[i] + "." + name); 61 global[name] = type; 62 return type; 63 } catch (e) {} 64 } 65 66 if (oldNoSuchProperty) { 67 return oldNoSuchProperty.call(this, name); 68 } else { 69 if (this === undefined) { 70 throw new ReferenceError(name + " is not defined"); 71 } else { 72 return undefined; 73 } 74 } 75 } 76 77 Object.defineProperty(global, "__noSuchProperty__", { 78 writable: true, configurable: true, enumerable: false, 79 value: __noSuchProperty__ 80 }); 81 82 var prefix = "[JavaPackage "; 83 return function() { 84 for (var i in arguments) { 85 var pkgName = arguments[i]; 86 if ((typeof pkgName) != 'string') { 87 pkgName = String(pkgName); 88 // extract name from JavaPackage object 89 if (pkgName.startsWith(prefix)) { 90 pkgName = pkgName.substring(prefix.length, pkgName.length - 1); 91 } 92 } 93 _packages.push(pkgName); 94 } 95 } 96 })() 97}); 98 99} 100 101// sync 102Object.defineProperty(this, "sync", { 103 configurable: true, enumerable: false, writable: true, 104 value: function(func, syncobj) { 105 if (arguments.length < 1 || arguments.length > 2 ) { 106 throw "sync(function [,object]) parameter count mismatch"; 107 } 108 return Java.synchronized(func, syncobj); 109 } 110}); 111 112// Object.prototype.__defineGetter__ 113Object.defineProperty(Object.prototype, "__defineGetter__", { 114 configurable: true, enumerable: false, writable: true, 115 value: function(name, func) { 116 Object.defineProperty(this, name, { 117 configurable: true, enumerable: true, get: func }); 118 } 119}); 120 121// Object.prototype.__defineSetter__ 122Object.defineProperty(Object.prototype, "__defineSetter__", { 123 configurable: true, enumerable: false, writable: true, 124 value: function(name, func) { 125 Object.defineProperty(this, name, { 126 configurable: true, enumerable: true, set: func }); 127 } 128}); 129 130// Object.prototype.__lookupGetter__ 131Object.defineProperty(Object.prototype, "__lookupGetter__", { 132 configurable: true, enumerable: false, writable: true, 133 value: function(name) { 134 var obj = this; 135 while (obj) { 136 var desc = Object.getOwnPropertyDescriptor(obj, name); 137 if (desc) return desc.get; 138 obj = Object.getPrototypeOf(obj); 139 } 140 return undefined; 141 } 142}); 143 144// Object.prototype.__lookupSetter__ 145Object.defineProperty(Object.prototype, "__lookupSetter__", { 146 configurable: true, enumerable: false, writable: true, 147 value: function(name) { 148 var obj = this; 149 while (obj) { 150 var desc = Object.getOwnPropertyDescriptor(obj, name); 151 if (desc) return desc.set; 152 obj = Object.getPrototypeOf(obj); 153 } 154 return undefined; 155 } 156}); 157 158// Object.prototype.toSource 159Object.defineProperty(Object.prototype, "toSource", { 160 configurable: true, enumerable: false, writable: true, 161 value: function(state) { 162 if (! state) { 163 state = java.util.Collections.newSetFromMap(new java.util.HashMap()); 164 } 165 if (state.contains(this)) { 166 return "{}"; 167 } 168 state.add(this); 169 var str = new java.lang.StringBuffer('({'); 170 for (i in this) { 171 str.append(i); 172 str.append(':'); 173 if (this[i] instanceof Object && typeof(this[i].toSource) == 'function') { 174 str.append(this[i].toSource(state)); 175 } else { 176 str.append(String(this[i])); 177 } 178 str.append(', '); 179 } 180 // delete last extra command and space 181 str = str.deleteCharAt(str.length() - 1); 182 str = str.deleteCharAt(str.length() - 1); 183 str.append('})'); 184 return str.toString(); 185 } 186}); 187 188// Boolean.prototype.toSource 189Object.defineProperty(Boolean.prototype, "toSource", { 190 configurable: true, enumerable: false, writable: true, 191 value: function() { 192 return '(new Boolean(' + this.toString() + '))'; 193 } 194}); 195 196// Date.prototype.toSource 197Object.defineProperty(Date.prototype, "toSource", { 198 configurable: true, enumerable: false, writable: true, 199 value: function() { 200 return '(new Date(' + this.valueOf() + '))'; 201 } 202}); 203 204// Function.prototype.toSource -- already implemented in nashorn 205 206// Number.prototype.toSource 207Object.defineProperty(Number.prototype, "toSource", { 208 configurable: true, enumerable: false, writable: true, 209 value: function() { 210 return '(new Number(' + this.toString() + '))'; 211 } 212}); 213 214// RegExp.prototype.toSource 215Object.defineProperty(RegExp.prototype, "toSource", { 216 configurable: true, enumerable: false, writable: true, 217 value: function() { 218 return this.toString(); 219 } 220}); 221 222// String.prototype.toSource 223Object.defineProperty(String.prototype, "toSource", { 224 configurable: true, enumerable: false, writable: true, 225 value: function() { 226 return '(new String(' + this.quote() + '))'; 227 } 228}); 229 230// Error.prototype.toSource 231Object.defineProperty(Error.prototype, "toSource", { 232 configurable: true, enumerable: false, writable: true, 233 value: function() { 234 var msg = this.message? String(this.message).quote() : "''"; 235 return '(new ' + this.name + '(' + msg + '))'; 236 } 237}); 238 239// Function.prototype.arity 240Object.defineProperty(Function.prototype, "arity", { 241 configurable: true, enumerable: false, 242 get: function() { return this.length; }, 243 set: function(x) { 244 throw new TypeError("Function arity can not be modified"); 245 } 246}); 247 248// String.prototype.quote 249Object.defineProperty(String.prototype, "quote", { 250 configurable: true, enumerable: false, writable: true, 251 value: function() { 252 return JSON.stringify(this); 253 } 254}); 255 256// HTML generation methods of String.prototype 257 258// String.prototype.anchor 259Object.defineProperty(String.prototype, "anchor", { 260 configurable: true, enumerable: false, writable: true, 261 value: function(name) { 262 return '<a name="' + name + '">' + this + '</a>'; 263 } 264}); 265 266// String.prototype.big 267Object.defineProperty(String.prototype, "big", { 268 configurable: true, enumerable: false, writable: true, 269 value: function() { 270 return '<big>' + this + '</big>'; 271 } 272}); 273 274// String.prototype.blink 275Object.defineProperty(String.prototype, "blink", { 276 configurable: true, enumerable: false, writable: true, 277 value: function() { 278 return '<blink>' + this + '</blink>'; 279 } 280}); 281 282// String.prototype.bold 283Object.defineProperty(String.prototype, "bold", { 284 configurable: true, enumerable: false, writable: true, 285 value: function() { 286 return '<b>' + this + '</b>'; 287 } 288}); 289 290// String.prototype.fixed 291Object.defineProperty(String.prototype, "fixed", { 292 configurable: true, enumerable: false, writable: true, 293 value: function() { 294 return '<tt>' + this + '</tt>'; 295 } 296}); 297 298// String.prototype.fontcolor 299Object.defineProperty(String.prototype, "fontcolor", { 300 configurable: true, enumerable: false, writable: true, 301 value: function(clr) { 302 return '<font color="' + clr + '">' + this + '</font>'; 303 } 304}); 305 306// String.prototype.fontsize 307Object.defineProperty(String.prototype, "fontsize", { 308 configurable: true, enumerable: false, writable: true, 309 value: function(size) { 310 return '<font size="' + size + '">' + this + '</font>'; 311 } 312}); 313 314// String.prototype.italics 315Object.defineProperty(String.prototype, "italics", { 316 configurable: true, enumerable: false, writable: true, 317 value: function() { 318 return '<i>' + this + '</i>'; 319 } 320}); 321 322// String.prototype.link 323Object.defineProperty(String.prototype, "link", { 324 configurable: true, enumerable: false, writable: true, 325 value: function(url) { 326 return '<a href="' + url + '">' + this + '</a>'; 327 } 328}); 329 330// String.prototype.small 331Object.defineProperty(String.prototype, "small", { 332 configurable: true, enumerable: false, writable: true, 333 value: function() { 334 return '<small>' + this + '</small>'; 335 } 336}); 337 338// String.prototype.strike 339Object.defineProperty(String.prototype, "strike", { 340 configurable: true, enumerable: false, writable: true, 341 value: function() { 342 return '<strike>' + this + '</strike>'; 343 } 344}); 345 346// String.prototype.sub 347Object.defineProperty(String.prototype, "sub", { 348 configurable: true, enumerable: false, writable: true, 349 value: function() { 350 return '<sub>' + this + '</sub>'; 351 } 352}); 353 354// String.prototype.sup 355Object.defineProperty(String.prototype, "sup", { 356 configurable: true, enumerable: false, writable: true, 357 value: function() { 358 return '<sup>' + this + '</sup>'; 359 } 360}); 361 362// Rhino: global.importClass 363Object.defineProperty(this, "importClass", { 364 configurable: true, enumerable: false, writable: true, 365 value: function() { 366 for (var arg in arguments) { 367 var clazz = arguments[arg]; 368 if (Java.isType(clazz)) { 369 var className = Java.typeName(clazz); 370 var simpleName = className.substring(className.lastIndexOf('.') + 1); 371 this[simpleName] = clazz; 372 } else { 373 throw new TypeError(clazz + " is not a Java class"); 374 } 375 } 376 } 377}); 378