bootbox.js 23 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469470471472473474475476477478479480481482483484485486487488489490491492493494495496497498499500501502503504505506507508509510511512513514515516517518519520521522523524525526527528529530531532533534535536537538539540541542543544545546547548549550551552553554555556557558559560561562563564565566567568569570571572573574575576577578579580581582583584585586587588589590591592593594595596597598599600601602603604605606607608609610611612613614615616617618619620621622623624625626627628629630631632633634635636637638639640641642643644645646647648649650651652653654655656657658659660661662663664665666667668669670671672673674675676677678679680681682683684685686687688689690691692693694695696697698699700701702703704705706707708709710711712713714715716717718719720721722723724725726727728729730731732733734735736737738739740741742743744745746747748749750751752753754755756757758759760761762763764765766767768769770771772773774775776777778779780781782783784785786787788789790791792793794795796797798799800801802803804805806807808809810811812813814815816817818819820821822823824825826827828829830831832833834835836837838839840841842843844845846847848849850851852853854855856857858859860861862863864865866867868869870871872873874875876877878879880881882883884885886887888889890891892893894
  1. /**
  2. * bootbox.js [v4.3.0]
  3. *
  4. * http://bootboxjs.com/license.txt
  5. */
  6. // @see https://github.com/makeusabrew/bootbox/issues/180
  7. // @see https://github.com/makeusabrew/bootbox/issues/186
  8. (function (root, factory) {
  9. "use strict";
  10. if (typeof define === "function" && define.amd) {
  11. // AMD. Register as an anonymous module.
  12. define(["jquery"], factory);
  13. } else if (typeof exports === "object") {
  14. // Node. Does not work with strict CommonJS, but
  15. // only CommonJS-like environments that support module.exports,
  16. // like Node.
  17. module.exports = factory(require("jquery"));
  18. } else {
  19. // Browser globals (root is window)
  20. root.bootbox = factory(root.jQuery);
  21. }
  22. }(this, function init($, undefined) {
  23. "use strict";
  24. // the base DOM structure needed to create a modal
  25. var templates = {
  26. dialog:
  27. "<div class='bootbox modal' tabindex='-1' role='dialog'>" +
  28. "<div class='modal-dialog'>" +
  29. "<div class='modal-content'>" +
  30. "<div class='modal-body'><div class='bootbox-body'></div></div>" +
  31. "</div>" +
  32. "</div>" +
  33. "</div>",
  34. header:
  35. "<div class='modal-header'>" +
  36. "<h4 class='modal-title'></h4>" +
  37. "</div>",
  38. footer:
  39. "<div class='modal-footer'></div>",
  40. closeButton:
  41. "<button type='button' class='bootbox-close-button close' data-dismiss='modal' aria-hidden='true'>&times;</button>",
  42. form:
  43. "<form class='bootbox-form'></form>",
  44. inputs: {
  45. text:
  46. "<input class='bootbox-input bootbox-input-text form-control' autocomplete=off type=text />",
  47. textarea:
  48. "<textarea class='bootbox-input bootbox-input-textarea form-control'></textarea>",
  49. email:
  50. "<input class='bootbox-input bootbox-input-email form-control' autocomplete='off' type='email' />",
  51. select:
  52. "<select class='bootbox-input bootbox-input-select form-control'></select>",
  53. checkbox:
  54. "<div class='checkbox'><label><input class='bootbox-input bootbox-input-checkbox' type='checkbox' /></label></div>",
  55. date:
  56. "<input class='bootbox-input bootbox-input-date form-control' autocomplete=off type='date' />",
  57. time:
  58. "<input class='bootbox-input bootbox-input-time form-control' autocomplete=off type='time' />",
  59. number:
  60. "<input class='bootbox-input bootbox-input-number form-control' autocomplete=off type='number' />",
  61. password:
  62. "<input class='bootbox-input bootbox-input-password form-control' autocomplete='off' type='password' />"
  63. }
  64. };
  65. var defaults = {
  66. // default language
  67. locale: "zh_CN",
  68. // show backdrop or not
  69. backdrop: true,
  70. // animate the modal in/out
  71. animate: true,
  72. // additional class string applied to the top level dialog
  73. className: null,
  74. // whether or not to include a close button
  75. closeButton: true,
  76. // show the dialog immediately by default
  77. show: true,
  78. // dialog container
  79. container: "body"
  80. };
  81. // our public object; augmented after our private API
  82. var exports = {};
  83. /**
  84. * @private
  85. */
  86. function _t(key) {
  87. var locale = locales[defaults.locale];
  88. return locale ? locale[key] : locales.en[key];
  89. }
  90. function processCallback(e, dialog, callback) {
  91. e.stopPropagation();
  92. e.preventDefault();
  93. // by default we assume a callback will get rid of the dialog,
  94. // although it is given the opportunity to override this
  95. // so, if the callback can be invoked and it *explicitly returns false*
  96. // then we'll set a flag to keep the dialog active...
  97. var preserveDialog = $.isFunction(callback) && callback(e) === false;
  98. // ... otherwise we'll bin it
  99. if (!preserveDialog) {
  100. dialog.modal("hide");
  101. }
  102. }
  103. function getKeyLength(obj) {
  104. // @TODO defer to Object.keys(x).length if available?
  105. var k, t = 0;
  106. for (k in obj) {
  107. t ++;
  108. }
  109. return t;
  110. }
  111. function each(collection, iterator) {
  112. var index = 0;
  113. $.each(collection, function(key, value) {
  114. iterator(key, value, index++);
  115. });
  116. }
  117. function sanitize(options) {
  118. var buttons;
  119. var total;
  120. if (typeof options !== "object") {
  121. throw new Error("Please supply an object of options");
  122. }
  123. if (!options.message) {
  124. throw new Error("Please specify a message");
  125. }
  126. // make sure any supplied options take precedence over defaults
  127. options = $.extend({}, defaults, options);
  128. if (!options.buttons) {
  129. options.buttons = {};
  130. }
  131. // we only support Bootstrap's "static" and false backdrop args
  132. // supporting true would mean you could dismiss the dialog without
  133. // explicitly interacting with it
  134. options.backdrop = options.backdrop ? "static" : false;
  135. buttons = options.buttons;
  136. total = getKeyLength(buttons);
  137. each(buttons, function(key, button, index) {
  138. if ($.isFunction(button)) {
  139. // short form, assume value is our callback. Since button
  140. // isn't an object it isn't a reference either so re-assign it
  141. button = buttons[key] = {
  142. callback: button
  143. };
  144. }
  145. // before any further checks make sure by now button is the correct type
  146. if ($.type(button) !== "object") {
  147. throw new Error("button with key " + key + " must be an object");
  148. }
  149. if (!button.label) {
  150. // the lack of an explicit label means we'll assume the key is good enough
  151. button.label = key;
  152. }
  153. if (!button.className) {
  154. if (total <= 2 && index === total-1) {
  155. // always add a primary to the main option in a two-button dialog
  156. button.className = "btn-primary";
  157. } else {
  158. button.className = "btn-default";
  159. }
  160. }
  161. });
  162. return options;
  163. }
  164. /**
  165. * map a flexible set of arguments into a single returned object
  166. * if args.length is already one just return it, otherwise
  167. * use the properties argument to map the unnamed args to
  168. * object properties
  169. * so in the latter case:
  170. * mapArguments(["foo", $.noop], ["message", "callback"])
  171. * -> { message: "foo", callback: $.noop }
  172. */
  173. function mapArguments(args, properties) {
  174. var argn = args.length;
  175. var options = {};
  176. if (argn < 1 || argn > 2) {
  177. throw new Error("Invalid argument length");
  178. }
  179. if (argn === 2 || typeof args[0] === "string") {
  180. options[properties[0]] = args[0];
  181. options[properties[1]] = args[1];
  182. } else {
  183. options = args[0];
  184. }
  185. return options;
  186. }
  187. /**
  188. * merge a set of default dialog options with user supplied arguments
  189. */
  190. function mergeArguments(defaults, args, properties) {
  191. return $.extend(
  192. // deep merge
  193. true,
  194. // ensure the target is an empty, unreferenced object
  195. {},
  196. // the base options object for this type of dialog (often just buttons)
  197. defaults,
  198. // args could be an object or array; if it's an array properties will
  199. // map it to a proper options object
  200. mapArguments(
  201. args,
  202. properties
  203. )
  204. );
  205. }
  206. /**
  207. * this entry-level method makes heavy use of composition to take a simple
  208. * range of inputs and return valid options suitable for passing to bootbox.dialog
  209. */
  210. function mergeDialogOptions(className, labels, properties, args) {
  211. // build up a base set of dialog properties
  212. var baseOptions = {
  213. className: "bootbox-" + className,
  214. buttons: createLabels.apply(null, labels)
  215. };
  216. // ensure the buttons properties generated, *after* merging
  217. // with user args are still valid against the supplied labels
  218. return validateButtons(
  219. // merge the generated base properties with user supplied arguments
  220. mergeArguments(
  221. baseOptions,
  222. args,
  223. // if args.length > 1, properties specify how each arg maps to an object key
  224. properties
  225. ),
  226. labels
  227. );
  228. }
  229. /**
  230. * from a given list of arguments return a suitable object of button labels
  231. * all this does is normalise the given labels and translate them where possible
  232. * e.g. "ok", "confirm" -> { ok: "OK, cancel: "Annuleren" }
  233. */
  234. function createLabels() {
  235. var buttons = {};
  236. for (var i = 0, j = arguments.length; i < j; i++) {
  237. var argument = arguments[i];
  238. var key = argument.toLowerCase();
  239. var value = argument.toUpperCase();
  240. buttons[key] = {
  241. label: _t(value)
  242. };
  243. }
  244. return buttons;
  245. }
  246. function validateButtons(options, buttons) {
  247. var allowedButtons = {};
  248. each(buttons, function(key, value) {
  249. allowedButtons[value] = true;
  250. });
  251. each(options.buttons, function(key) {
  252. if (allowedButtons[key] === undefined) {
  253. throw new Error("button key " + key + " is not allowed (options are " + buttons.join("\n") + ")");
  254. }
  255. });
  256. return options;
  257. }
  258. exports.alert = function() {
  259. var options;
  260. options = mergeDialogOptions("alert", ["ok"], ["message", "callback"], arguments);
  261. if (options.callback && !$.isFunction(options.callback)) {
  262. throw new Error("alert requires callback property to be a function when provided");
  263. }
  264. /**
  265. * overrides
  266. */
  267. options.buttons.ok.callback = options.onEscape = function() {
  268. if ($.isFunction(options.callback)) {
  269. return options.callback();
  270. }
  271. return true;
  272. };
  273. return exports.dialog(options);
  274. };
  275. exports.confirm = function() {
  276. var options;
  277. options = mergeDialogOptions("confirm", ["cancel", "confirm"], ["message", "callback"], arguments);
  278. /**
  279. * overrides; undo anything the user tried to set they shouldn't have
  280. */
  281. options.buttons.cancel.callback = options.onEscape = function() {
  282. return options.callback(false);
  283. };
  284. options.buttons.confirm.callback = function() {
  285. return options.callback(true);
  286. };
  287. // confirm specific validation
  288. if (!$.isFunction(options.callback)) {
  289. throw new Error("confirm requires a callback");
  290. }
  291. return exports.dialog(options);
  292. };
  293. exports.prompt = function() {
  294. var options;
  295. var defaults;
  296. var dialog;
  297. var form;
  298. var input;
  299. var shouldShow;
  300. var inputOptions;
  301. // we have to create our form first otherwise
  302. // its value is undefined when gearing up our options
  303. // @TODO this could be solved by allowing message to
  304. // be a function instead...
  305. form = $(templates.form);
  306. // prompt defaults are more complex than others in that
  307. // users can override more defaults
  308. // @TODO I don't like that prompt has to do a lot of heavy
  309. // lifting which mergeDialogOptions can *almost* support already
  310. // just because of 'value' and 'inputType' - can we refactor?
  311. defaults = {
  312. className: "bootbox-prompt",
  313. buttons: createLabels("cancel", "confirm"),
  314. value: "",
  315. inputType: "text"
  316. };
  317. options = validateButtons(
  318. mergeArguments(defaults, arguments, ["title", "callback"]),
  319. ["cancel", "confirm"]
  320. );
  321. // capture the user's show value; we always set this to false before
  322. // spawning the dialog to give us a chance to attach some handlers to
  323. // it, but we need to make sure we respect a preference not to show it
  324. shouldShow = (options.show === undefined) ? true : options.show;
  325. /**
  326. * overrides; undo anything the user tried to set they shouldn't have
  327. */
  328. options.message = form;
  329. options.buttons.cancel.callback = options.onEscape = function() {
  330. return options.callback(null);
  331. };
  332. options.buttons.confirm.callback = function() {
  333. var value;
  334. switch (options.inputType) {
  335. case "text":
  336. case "textarea":
  337. case "email":
  338. case "select":
  339. case "date":
  340. case "time":
  341. case "number":
  342. case "password":
  343. value = input.val();
  344. break;
  345. case "checkbox":
  346. var checkedItems = input.find("input:checked");
  347. // we assume that checkboxes are always multiple,
  348. // hence we default to an empty array
  349. value = [];
  350. each(checkedItems, function(_, item) {
  351. value.push($(item).val());
  352. });
  353. break;
  354. }
  355. return options.callback(value);
  356. };
  357. options.show = false;
  358. // prompt specific validation
  359. if (!options.title) {
  360. throw new Error("prompt requires a title");
  361. }
  362. if (!$.isFunction(options.callback)) {
  363. throw new Error("prompt requires a callback");
  364. }
  365. if (!templates.inputs[options.inputType]) {
  366. throw new Error("invalid prompt type");
  367. }
  368. // create the input based on the supplied type
  369. input = $(templates.inputs[options.inputType]);
  370. switch (options.inputType) {
  371. case "text":
  372. case "textarea":
  373. case "email":
  374. case "date":
  375. case "time":
  376. case "number":
  377. case "password":
  378. input.val(options.value);
  379. break;
  380. case "select":
  381. var groups = {};
  382. inputOptions = options.inputOptions || [];
  383. if (!inputOptions.length) {
  384. throw new Error("prompt with select requires options");
  385. }
  386. each(inputOptions, function(_, option) {
  387. // assume the element to attach to is the input...
  388. var elem = input;
  389. if (option.value === undefined || option.text === undefined) {
  390. throw new Error("given options in wrong format");
  391. }
  392. // ... but override that element if this option sits in a group
  393. if (option.group) {
  394. // initialise group if necessary
  395. if (!groups[option.group]) {
  396. groups[option.group] = $("<optgroup/>").attr("label", option.group);
  397. }
  398. elem = groups[option.group];
  399. }
  400. elem.append("<option value='" + option.value + "'>" + option.text + "</option>");
  401. });
  402. each(groups, function(_, group) {
  403. input.append(group);
  404. });
  405. // safe to set a select's value as per a normal input
  406. input.val(options.value);
  407. break;
  408. case "checkbox":
  409. var values = $.isArray(options.value) ? options.value : [options.value];
  410. inputOptions = options.inputOptions || [];
  411. if (!inputOptions.length) {
  412. throw new Error("prompt with checkbox requires options");
  413. }
  414. if (!inputOptions[0].value || !inputOptions[0].text) {
  415. throw new Error("given options in wrong format");
  416. }
  417. // checkboxes have to nest within a containing element, so
  418. // they break the rules a bit and we end up re-assigning
  419. // our 'input' element to this container instead
  420. input = $("<div/>");
  421. each(inputOptions, function(_, option) {
  422. var checkbox = $(templates.inputs[options.inputType]);
  423. checkbox.find("input").attr("value", option.value);
  424. checkbox.find("label").append(option.text);
  425. // we've ensured values is an array so we can always iterate over it
  426. each(values, function(_, value) {
  427. if (value === option.value) {
  428. checkbox.find("input").prop("checked", true);
  429. }
  430. });
  431. input.append(checkbox);
  432. });
  433. break;
  434. }
  435. if (options.placeholder) {
  436. input.attr("placeholder", options.placeholder);
  437. }
  438. if(options.pattern){
  439. input.attr("pattern", options.pattern);
  440. }
  441. // now place it in our form
  442. form.append(input);
  443. form.on("submit", function(e) {
  444. e.preventDefault();
  445. // Fix for SammyJS (or similar JS routing library) hijacking the form post.
  446. e.stopPropagation();
  447. // @TODO can we actually click *the* button object instead?
  448. // e.g. buttons.confirm.click() or similar
  449. dialog.find(".btn-primary").click();
  450. });
  451. dialog = exports.dialog(options);
  452. // clear the existing handler focusing the submit button...
  453. dialog.off("shown.bs.modal");
  454. // ...and replace it with one focusing our input, if possible
  455. dialog.on("shown.bs.modal", function() {
  456. input.focus();
  457. });
  458. if (shouldShow === true) {
  459. dialog.modal("show");
  460. }
  461. return dialog;
  462. };
  463. exports.dialog = function(options) {
  464. options = sanitize(options);
  465. var dialog = $(templates.dialog);
  466. var innerDialog = dialog.find(".modal-dialog");
  467. var body = dialog.find(".modal-body");
  468. var buttons = options.buttons;
  469. var buttonStr = "";
  470. var callbacks = {
  471. onEscape: options.onEscape
  472. };
  473. each(buttons, function(key, button) {
  474. // @TODO I don't like this string appending to itself; bit dirty. Needs reworking
  475. // can we just build up button elements instead? slower but neater. Then button
  476. // can just become a template too
  477. buttonStr += "<button data-bb-handler='" + key + "' type='button' class='btn " + button.className + "'>" + button.label + "</button>";
  478. callbacks[key] = button.callback;
  479. });
  480. body.find(".bootbox-body").html(options.message);
  481. if (options.animate === true) {
  482. dialog.addClass("fade");
  483. }
  484. if (options.className) {
  485. dialog.addClass(options.className);
  486. }
  487. if (options.size === "large") {
  488. innerDialog.addClass("modal-lg");
  489. }
  490. if (options.size === "small") {
  491. innerDialog.addClass("modal-sm");
  492. }
  493. if (options.title) {
  494. body.before(templates.header);
  495. }
  496. if (options.closeButton) {
  497. var closeButton = $(templates.closeButton);
  498. if (options.title) {
  499. dialog.find(".modal-header").prepend(closeButton);
  500. } else {
  501. closeButton.css("margin-top", "-10px").prependTo(body);
  502. }
  503. }
  504. if (options.title) {
  505. dialog.find(".modal-title").html(options.title);
  506. }
  507. if (buttonStr.length) {
  508. body.after(templates.footer);
  509. dialog.find(".modal-footer").html(buttonStr);
  510. }
  511. /**
  512. * Bootstrap event listeners; used handle extra
  513. * setup & teardown required after the underlying
  514. * modal has performed certain actions
  515. */
  516. dialog.on("hidden.bs.modal", function(e) {
  517. // ensure we don't accidentally intercept hidden events triggered
  518. // by children of the current dialog. We shouldn't anymore now BS
  519. // namespaces its events; but still worth doing
  520. if (e.target === this) {
  521. dialog.remove();
  522. }
  523. });
  524. /*
  525. dialog.on("show.bs.modal", function() {
  526. // sadly this doesn't work; show is called *just* before
  527. // the backdrop is added so we'd need a setTimeout hack or
  528. // otherwise... leaving in as would be nice
  529. if (options.backdrop) {
  530. dialog.next(".modal-backdrop").addClass("bootbox-backdrop");
  531. }
  532. });
  533. */
  534. dialog.on("shown.bs.modal", function() {
  535. dialog.find(".btn-primary:first").focus();
  536. });
  537. /**
  538. * Bootbox event listeners; experimental and may not last
  539. * just an attempt to decouple some behaviours from their
  540. * respective triggers
  541. */
  542. dialog.on("escape.close.bb", function(e) {
  543. if (callbacks.onEscape) {
  544. processCallback(e, dialog, callbacks.onEscape);
  545. }
  546. });
  547. /**
  548. * Standard jQuery event listeners; used to handle user
  549. * interaction with our dialog
  550. */
  551. dialog.on("click", ".modal-footer button", function(e) {
  552. var callbackKey = $(this).data("bb-handler");
  553. processCallback(e, dialog, callbacks[callbackKey]);
  554. });
  555. dialog.on("click", ".bootbox-close-button", function(e) {
  556. // onEscape might be falsy but that's fine; the fact is
  557. // if the user has managed to click the close button we
  558. // have to close the dialog, callback or not
  559. processCallback(e, dialog, callbacks.onEscape);
  560. });
  561. dialog.on("keyup", function(e) {
  562. if (e.which === 27) {
  563. dialog.trigger("escape.close.bb");
  564. }
  565. });
  566. // the remainder of this method simply deals with adding our
  567. // dialogent to the DOM, augmenting it with Bootstrap's modal
  568. // functionality and then giving the resulting object back
  569. // to our caller
  570. $(options.container).append(dialog);
  571. dialog.modal({
  572. backdrop: options.backdrop,
  573. keyboard: false,
  574. show: false
  575. });
  576. if (options.show) {
  577. dialog.modal("show");
  578. }
  579. // @TODO should we return the raw element here or should
  580. // we wrap it in an object on which we can expose some neater
  581. // methods, e.g. var d = bootbox.alert(); d.hide(); instead
  582. // of d.modal("hide");
  583. /*
  584. function BBDialog(elem) {
  585. this.elem = elem;
  586. }
  587. BBDialog.prototype = {
  588. hide: function() {
  589. return this.elem.modal("hide");
  590. },
  591. show: function() {
  592. return this.elem.modal("show");
  593. }
  594. };
  595. */
  596. return dialog;
  597. };
  598. exports.setDefaults = function() {
  599. var values = {};
  600. if (arguments.length === 2) {
  601. // allow passing of single key/value...
  602. values[arguments[0]] = arguments[1];
  603. } else {
  604. // ... and as an object too
  605. values = arguments[0];
  606. }
  607. $.extend(defaults, values);
  608. };
  609. exports.hideAll = function() {
  610. $(".bootbox").modal("hide");
  611. return exports;
  612. };
  613. /**
  614. * standard locales. Please add more according to ISO 639-1 standard. Multiple language variants are
  615. * unlikely to be required. If this gets too large it can be split out into separate JS files.
  616. */
  617. var locales = {
  618. br : {
  619. OK : "OK",
  620. CANCEL : "Cancelar",
  621. CONFIRM : "Sim"
  622. },
  623. cs : {
  624. OK : "OK",
  625. CANCEL : "Zrušit",
  626. CONFIRM : "Potvrdit"
  627. },
  628. da : {
  629. OK : "OK",
  630. CANCEL : "Annuller",
  631. CONFIRM : "Accepter"
  632. },
  633. de : {
  634. OK : "OK",
  635. CANCEL : "Abbrechen",
  636. CONFIRM : "Akzeptieren"
  637. },
  638. el : {
  639. OK : "Εντάξει",
  640. CANCEL : "Ακύρωση",
  641. CONFIRM : "Επιβεβαίωση"
  642. },
  643. en : {
  644. OK : "OK",
  645. CANCEL : "Cancel",
  646. CONFIRM : "OK"
  647. },
  648. es : {
  649. OK : "OK",
  650. CANCEL : "Cancelar",
  651. CONFIRM : "Aceptar"
  652. },
  653. et : {
  654. OK : "OK",
  655. CANCEL : "Katkesta",
  656. CONFIRM : "OK"
  657. },
  658. fi : {
  659. OK : "OK",
  660. CANCEL : "Peruuta",
  661. CONFIRM : "OK"
  662. },
  663. fr : {
  664. OK : "OK",
  665. CANCEL : "Annuler",
  666. CONFIRM : "D'accord"
  667. },
  668. he : {
  669. OK : "אישור",
  670. CANCEL : "ביטול",
  671. CONFIRM : "אישור"
  672. },
  673. id : {
  674. OK : "OK",
  675. CANCEL : "Batal",
  676. CONFIRM : "OK"
  677. },
  678. it : {
  679. OK : "OK",
  680. CANCEL : "Annulla",
  681. CONFIRM : "Conferma"
  682. },
  683. ja : {
  684. OK : "OK",
  685. CANCEL : "キャンセル",
  686. CONFIRM : "確認"
  687. },
  688. lt : {
  689. OK : "Gerai",
  690. CANCEL : "Atšaukti",
  691. CONFIRM : "Patvirtinti"
  692. },
  693. lv : {
  694. OK : "Labi",
  695. CANCEL : "Atcelt",
  696. CONFIRM : "Apstiprināt"
  697. },
  698. nl : {
  699. OK : "OK",
  700. CANCEL : "Annuleren",
  701. CONFIRM : "Accepteren"
  702. },
  703. no : {
  704. OK : "OK",
  705. CANCEL : "Avbryt",
  706. CONFIRM : "OK"
  707. },
  708. pl : {
  709. OK : "OK",
  710. CANCEL : "Anuluj",
  711. CONFIRM : "Potwierdź"
  712. },
  713. pt : {
  714. OK : "OK",
  715. CANCEL : "Cancelar",
  716. CONFIRM : "Confirmar"
  717. },
  718. ru : {
  719. OK : "OK",
  720. CANCEL : "Отмена",
  721. CONFIRM : "Применить"
  722. },
  723. sv : {
  724. OK : "OK",
  725. CANCEL : "Avbryt",
  726. CONFIRM : "OK"
  727. },
  728. tr : {
  729. OK : "Tamam",
  730. CANCEL : "İptal",
  731. CONFIRM : "Onayla"
  732. },
  733. zh_CN : {
  734. OK : "OK",
  735. CANCEL : "取消",
  736. CONFIRM : "确认"
  737. },
  738. zh_TW : {
  739. OK : "OK",
  740. CANCEL : "取消",
  741. CONFIRM : "確認"
  742. }
  743. };
  744. exports.init = function(_$) {
  745. return init(_$ || $);
  746. };
  747. return exports;
  748. }));