From 8172ce52961c55ca419782f61281c7a0f3d85c31 Mon Sep 17 00:00:00 2001 From: Nick Freear Date: Fri, 1 Mar 2013 15:17:21 +0000 Subject: [PATCH 1/8] Issue #84, jquery.jeditable.html5 is a Javascript plugin for Jeditable * It adds HTML5 form input types - eg. type="number".. * ..Form validation constraints - eg. required, pattern= .. * And, improves keyboard accessibility using WAI-ARIA roles etc. --- contributed/jquery.jeditable.html5.js | 129 ++++++++++++++++++++++++++ 1 file changed, 129 insertions(+) create mode 100644 contributed/jquery.jeditable.html5.js diff --git a/contributed/jquery.jeditable.html5.js b/contributed/jquery.jeditable.html5.js new file mode 100644 index 0000000..eaa02ca --- /dev/null +++ b/contributed/jquery.jeditable.html5.js @@ -0,0 +1,129 @@ +/* + * HTML5 and accessibility/WAI-ARIA support for Jeditable. + * + * Copyright (c) 2013 Nick Freear, The Open University. + * + * Licensed under the MIT license: + * http://www.opensource.org/licenses/mit-license.php + */ + +/*jslint browser: true, indent: 4 */ + +(function ($) { + + 'use strict'; + + // Keyboard accessibility/WAI-ARIA - allow users to navigate to an editable element using TAB/Shift+TAB. + $.fn.editableAriaShim = function () { + //$.log('WAI-ARIA shim..'); + + $(this).attr({ + role: 'button', + tabindex: 0 + //, title: 'Editable' -- See 'tooltip' below. + //, 'aria-label':'' + }); + return this; //<--jquery object - chaining. + }; + + + // Keyboard accessibility - use mouse click OR press any key to enable editing. + $.fn.editable.defaults.event = 'click.editable keydown.editable'; + + // Accessibility - there should be a default value for the title/ tooltip. + $.fn.editable.defaults.tooltip = 'Click to edit'; //$.fn.editable.defaults.placeholder + + + $.editable.addInputType('html5_text', { + element: function (settings, original) { + var input = $('').attr({ + // required: settings.required ? 'required' : '', -- See below. + // autofocus -- Not relevant for Jeditable. + // disabled -- Not relevant. + // readonly -- Not relevant. + //autocomplete: settings.autocomplete, -- Todo. + inputmode: settings.input.mode, + list: settings.list, + maxlength: settings.maxlength, + pattern: settings.pattern, + placeholder: settings.html5_placeholder, // Parameter name conflict - add 'html5_'. + title: settings.html5_error_text, + type: 'text' + }); + if (settings.required) { input.attr('required', ''); } // Is this relevant to Jeditable? Probably. + + $(this).append(input); + return input; + } + }); + +$.editable.addInputType('unsigned_integer', { + element: function (settings, original) { + var input = $(''); + $(this).append(input); + return input; + } +}); + +$.editable.addInputType('number', { + element: function (settings, original) { + var input = $('').attr({ + maxlength: settings.maxlength, + //pattern: settings.pattern, -- Does not apply to 'number' (but may be useful if 'number' is not supported). + placeholder: settings.html5_placeholder, + min : settings.min, + max : settings.max, + step: settings.step, + title: settings.html5_error_text, + type: 'number' + }); + $(this).append(input); + return input; + } +}); + +/*$.editable.addInputType('range', { + element: function (settings, original) { + var input = $('').attr({ + maxlength: settings.maxlength, + pattern: settings.pattern, + placeholder: settings.html5_placeholder, + min : settings.min, + max : settings.max, + step: settings.step, + type: 'range' + }); + $(this).append(input); + return input; + } +});*/ + +$.editable.addInputType('email', { + element: function (settings, original) { + var input = $('').attr({ + // pattern -- Not useful. + maxlength: settings.maxlength, + placeholder: settings.html5_placeholder, + type: 'email' + }); + $(this).append(input); + return input; + } +}); + +$.editable.addInputType('url', { + element: function (settings, original) { + var input = $('').attr({ + maxlength: settings.maxlength, + pattern: settings.pattern, + placeholder: settings.html5_placeholder, + title: settings.html5_error_text, + type: 'url' + }); + $(this).append(input); + return input; + } +}); + + +})(jQuery); From 45ec18f7dd3b4d773fac8c1e71894f18a92452ab Mon Sep 17 00:00:00 2001 From: Nick Freear Date: Thu, 14 Mar 2013 15:35:28 +0000 Subject: [PATCH 2/8] Bug #84, Improve and fix error handling of PHP scripts. --- php/config.php | 1 + php/echo.php | 2 +- tests/echo.php | 2 +- 3 files changed, 3 insertions(+), 2 deletions(-) diff --git a/php/config.php b/php/config.php index 0c8ae2f..1b537b0 100644 --- a/php/config.php +++ b/php/config.php @@ -6,6 +6,7 @@ $dbh = new PDO('sqlite:/tmp/editable.sqlite'); } catch(PDOException $e) { print $e->getMessage(); + exit(-1); } /* Create table for storing example data. */ diff --git a/php/echo.php b/php/echo.php index efbc043..f3e867f 100644 --- a/php/echo.php +++ b/php/echo.php @@ -2,7 +2,7 @@ /* Does not save anything. Just echoes back for demonstration purposes. */ -$renderer = isset($_GET['renderer']) ? $_GET['renderer'] : $_POST['renderer']; +$renderer = isset($_GET['renderer']) ? $_GET['renderer'] : (isset($_POST['renderer']) ? $_POST['renderer'] : NULL); if ('textile' == $renderer) { require_once './Textile.php'; $t = new Textile(); diff --git a/tests/echo.php b/tests/echo.php index b5c64b0..7b338a5 100644 --- a/tests/echo.php +++ b/tests/echo.php @@ -2,7 +2,7 @@ /* $Id: echo.php 117 2007-03-02 16:16:08Z tuupola $ */ -$renderer = isset($_GET['renderer']) ? $_GET['renderer'] : $_POST['renderer']; +$renderer = isset($_GET['renderer']) ? $_GET['renderer'] : (isset($_POST['renderer']) ? $_POST['renderer'] : NULL); if ('textile' == $renderer) { require_once './Textile.php'; $t = new Textile(); From 28b36799813983e6b30b450f6bb080a6949ea56c Mon Sep 17 00:00:00 2001 From: Nick Freear Date: Thu, 14 Mar 2013 15:36:25 +0000 Subject: [PATCH 3/8] Bug #84, Add jquery.jeditable.html5 Javascript plugin to QUnit tests * Needed to bump the jQuery version from 1.2.6 to 1.4.4 (likely minimum) --- tests/index.html | 73 +++++++++++++++++++++++++++++++++++++++++++-- tests/testsuite.css | 5 +++- 2 files changed, 75 insertions(+), 3 deletions(-) diff --git a/tests/index.html b/tests/index.html index 4e2cba7..e679276 100644 --- a/tests/index.html +++ b/tests/index.html @@ -3,10 +3,13 @@ Jeditable Unit Tests - + + + + @@ -204,5 +268,10 @@

Select B
Here be dragons.
Here be dragons.
+ +
-2.06
+
Joe+TAG1@example
+
user5
+ diff --git a/tests/testsuite.css b/tests/testsuite.css index a10c107..4f3613c 100644 --- a/tests/testsuite.css +++ b/tests/testsuite.css @@ -6,7 +6,10 @@ h2 { padding: 10px; background-color: #eee; color: black; margin: 0; font-size: .pass { color: green; } .fail { color: red; } -p.result { margin-left: 1em; } +.editable :valid { border-color: green; } +:focus:invalid { border-color: red; } + +p.result, div[id] { margin-left: 1em; } #banner { height: 2em; border-bottom: 1px solid white; } h2.pass { background-color: green; } From a47ed3dc8a30adc7d4e665276db067e7b7469079 Mon Sep 17 00:00:00 2001 From: Nick Freear Date: Thu, 14 Mar 2013 15:40:32 +0000 Subject: [PATCH 4/8] Bug #84, Bug fix for jquery.jeditable.html5 Javascript - 'inputmode' --- contributed/jquery.jeditable.html5.js | 3 +-- 1 file changed, 1 insertion(+), 2 deletions(-) diff --git a/contributed/jquery.jeditable.html5.js b/contributed/jquery.jeditable.html5.js index eaa02ca..0bf0a61 100644 --- a/contributed/jquery.jeditable.html5.js +++ b/contributed/jquery.jeditable.html5.js @@ -26,7 +26,6 @@ return this; //<--jquery object - chaining. }; - // Keyboard accessibility - use mouse click OR press any key to enable editing. $.fn.editable.defaults.event = 'click.editable keydown.editable'; @@ -42,7 +41,7 @@ // disabled -- Not relevant. // readonly -- Not relevant. //autocomplete: settings.autocomplete, -- Todo. - inputmode: settings.input.mode, + inputmode: settings.inputmode, list: settings.list, maxlength: settings.maxlength, pattern: settings.pattern, From 327122112b29f8780938e6b99419aed8f7f8895c Mon Sep 17 00:00:00 2001 From: Nick Freear Date: Thu, 14 Mar 2013 16:01:46 +0000 Subject: [PATCH 5/8] Bug #84, Adding a HTML5 demo page, edits to jquery.jeditable.html5 --- contributed/jquery.jeditable.html5.js | 31 ++++++--- html5.html | 97 +++++++++++++++++++++++++++ 2 files changed, 119 insertions(+), 9 deletions(-) create mode 100644 html5.html diff --git a/contributed/jquery.jeditable.html5.js b/contributed/jquery.jeditable.html5.js index 0bf0a61..81763a4 100644 --- a/contributed/jquery.jeditable.html5.js +++ b/contributed/jquery.jeditable.html5.js @@ -17,7 +17,7 @@ $.fn.editableAriaShim = function () { //$.log('WAI-ARIA shim..'); - $(this).attr({ + this.attr({ role: 'button', tabindex: 0 //, title: 'Editable' -- See 'tooltip' below. @@ -32,7 +32,15 @@ // Accessibility - there should be a default value for the title/ tooltip. $.fn.editable.defaults.tooltip = 'Click to edit'; //$.fn.editable.defaults.placeholder + // Shim - $(sel).checkValidity() + if (! $.fn.checkValidity) { + $.fn.checkValidity = function () { + var inp = this[0]; + return inp ? inp.checkValidity() : null; + }; + } + // Type = text : With HTML5 attributes. $.editable.addInputType('html5_text', { element: function (settings, original) { var input = $('').attr({ @@ -56,14 +64,7 @@ } }); -$.editable.addInputType('unsigned_integer', { - element: function (settings, original) { - var input = $(''); - $(this).append(input); - return input; - } -}); - +// Type = number. $.editable.addInputType('number', { element: function (settings, original) { var input = $('').attr({ @@ -81,6 +82,16 @@ $.editable.addInputType('number', { } }); +// Deprecated. +$.editable.addInputType('unsigned_integer', { + element: function (settings, original) { + var input = $(''); + $(this).append(input); + return input; + } +}); + +// Type = range : Not usable. /*$.editable.addInputType('range', { element: function (settings, original) { var input = $('').attr({ @@ -97,6 +108,7 @@ $.editable.addInputType('number', { } });*/ +// Type = email $.editable.addInputType('email', { element: function (settings, original) { var input = $('').attr({ @@ -110,6 +122,7 @@ $.editable.addInputType('email', { } }); +// Type = url $.editable.addInputType('url', { element: function (settings, original) { var input = $('').attr({ diff --git a/html5.html b/html5.html new file mode 100644 index 0000000..a2e973a --- /dev/null +++ b/html5.html @@ -0,0 +1,97 @@ + + +Jeditable HTML5 Input Types Demo + + + + + + + + + + + + + + +
+ +
+ +

You might also want to check default inputs demo.

+ +
+ +

HTML5

+ +

Some useful introductions to HTML5 forms: + Dive into HTML5: Forms and + HTML5: The input element + +

Number type

+

-2.06

+ +

Email type

+ + +

HTML5 text

+

user5

+ + +
+ + + + + + + + + \ No newline at end of file From 29fe935abe1bc21cb5df88f74d332097c4de3f7d Mon Sep 17 00:00:00 2001 From: Nick Freear Date: Mon, 18 Mar 2013 10:52:12 +0000 Subject: [PATCH 6/8] Bug #84, Improve `$.fn.checkValidity` function and QUnit tests * Fix robustness of `.checkValidity()` * Add function `typeof` unit tests to `tests/index.html` --- contributed/jquery.jeditable.html5.js | 2 +- tests/index.html | 31 +++++++++++++++++---------- 2 files changed, 21 insertions(+), 12 deletions(-) diff --git a/contributed/jquery.jeditable.html5.js b/contributed/jquery.jeditable.html5.js index 81763a4..d77139e 100644 --- a/contributed/jquery.jeditable.html5.js +++ b/contributed/jquery.jeditable.html5.js @@ -36,7 +36,7 @@ if (! $.fn.checkValidity) { $.fn.checkValidity = function () { var inp = this[0]; - return inp ? inp.checkValidity() : null; + return inp && typeof inp.checkValidity==="function" ? inp.checkValidity() : null; }; } diff --git a/tests/index.html b/tests/index.html index e679276..3f74d06 100644 --- a/tests/index.html +++ b/tests/index.html @@ -95,6 +95,7 @@ required: true }); + module("CORE"); test("Event triggers", function() { @@ -217,8 +218,10 @@ module("HTML5"); test("Keyboard accessibility", function () { - equals($(".editable").attr("role"), "button", "WAI-ARIA role should be button"); - equals($(".editable").attr("tabindex"), "0", "Tabindex should be 0"); + /*( isObj($.fn.editableAriaShim, function(){}, "Is a function, v1"); )*/ + equals(typeof $.fn.editableAriaShim, "function", "`$.fn.editableAriaShim` is a function()"); + equals($(".editable").attr("role"), "button", "WAI-ARIA `role` should be `button`"); + equals($(".editable").attr("tabindex"), "0", "Attribute `tabindex` should be 0"); $("#h5-number").trigger("click"); ok($("#h5-number form").size() == 1, "Click event should trigger Jeditable."); $("#h5-number form").submit(); @@ -231,25 +234,31 @@ test("HTML5 input types", function () { $("#h5-number").trigger("click"); - equals($("#h5-number input").attr("type"), "number", "Type should be number"); - equals($("#h5-number input").attr("min"), "0", "Min should be 0"); + equals($("#h5-number input").attr("type"), "number", "Type should be `number`"); + equals($("#h5-number input").attr("min"), "0", "Attribute `min` should be 0"); equals($("#h5-number input").val(), "-2.06", "Value should be -2.06"); - equals(document.querySelector("#h5-number input").checkValidity(), false, "checkValidity() should be false"); + equals(typeof document.querySelector("#h5-number input").checkValidity, "function", "`\x3Cinput>.checkValidity` is a function"); + equals(document.querySelector("#h5-number input").checkValidity(), false, "`\x3Cinput>.checkValidity()` should return false"); $("#h5-number form").submit(); $("#h5-email").trigger("click"); - equals($("#h5-email input").attr("type"), "email", "Type should be email"); - equals($("#h5-email input")[0].checkValidity(), true, "checkValidity() should be true"); + equals($("#h5-email input").attr("type"), "email", "Type should be `email`"); + equals($("#h5-email input")[0].checkValidity(), true, "`checkValidity()` should return true"); $("#h5-email form").submit(); $("#h5-text").trigger("click"); - equals($("#h5-text input").attr("type"), "text", "Type should be text"); - equals($("#h5-text input").attr("required"), '', "Required should be '' (empty string)"); - equals($("#h5-text input").checkValidity(), true, "checkValidity() should be true"); + equals($("#h5-text input").attr("type"), "text", "Type should be `text`"); + equals($("#h5-text input").attr("required"), '', "Attribute `required` should be '' (empty)"); + equals(typeof $.fn.checkValidity, "function", "`$.fn.checkValidity` is a function"); + equals($("#h5-text input").checkValidity(), true, "`$(selector).checkValidity()` should return true"); $("#h5-text form").submit(); }); -}); + // Hack: add IDs for easy reference. + $("#tests > li").each(function (i, el) { + el.id = "qt-" + i; + }); +}); From 8fe08d95674b01b24db6d40bd40c39bf7811a273 Mon Sep 17 00:00:00 2001 From: Nick Freear Date: Tue, 19 Mar 2013 14:25:19 +0000 Subject: [PATCH 7/8] Bug #84, Make `jquery.editable.html5' JS plugin work in Internet Explorer * _supportInType private function based on "Dive into HTML5" example, * http://diveintohtml5.info/everything.html * Re-order QUnit tests --- contributed/jquery.jeditable.html5.js | 18 ++++++++++++++---- tests/index.html | 15 +++++++++------ 2 files changed, 23 insertions(+), 10 deletions(-) diff --git a/contributed/jquery.jeditable.html5.js b/contributed/jquery.jeditable.html5.js index d77139e..f6c760f 100644 --- a/contributed/jquery.jeditable.html5.js +++ b/contributed/jquery.jeditable.html5.js @@ -40,6 +40,16 @@ }; } + var _supportInType = function (type) { + var i = document.createElement('input'); + i.setAttribute('type', type); + return i.type !== 'text' ? type : 'text'; + + //return i.type !== 'text'; + //return ! navigator.userAgent.match(/MSIE/); + }; + //$.fn.supportInType = _supportInType; + // Type = text : With HTML5 attributes. $.editable.addInputType('html5_text', { element: function (settings, original) { @@ -75,7 +85,7 @@ $.editable.addInputType('number', { max : settings.max, step: settings.step, title: settings.html5_error_text, - type: 'number' + type: _supportInType('number') //? 'number' : 'text' }); $(this).append(input); return input; @@ -101,7 +111,7 @@ $.editable.addInputType('unsigned_integer', { min : settings.min, max : settings.max, step: settings.step, - type: 'range' + type: _supportInType('range') }); $(this).append(input); return input; @@ -115,7 +125,7 @@ $.editable.addInputType('email', { // pattern -- Not useful. maxlength: settings.maxlength, placeholder: settings.html5_placeholder, - type: 'email' + type: _supportInType('email') //? 'email' : 'text' }); $(this).append(input); return input; @@ -130,7 +140,7 @@ $.editable.addInputType('url', { pattern: settings.pattern, placeholder: settings.html5_placeholder, title: settings.html5_error_text, - type: 'url' + type: _supportInType('url') //? 'url' : 'text' }); $(this).append(input); return input; diff --git a/tests/index.html b/tests/index.html index 3f74d06..eed7b98 100644 --- a/tests/index.html +++ b/tests/index.html @@ -237,20 +237,21 @@ equals($("#h5-number input").attr("type"), "number", "Type should be `number`"); equals($("#h5-number input").attr("min"), "0", "Attribute `min` should be 0"); equals($("#h5-number input").val(), "-2.06", "Value should be -2.06"); - equals(typeof document.querySelector("#h5-number input").checkValidity, "function", "`\x3Cinput>.checkValidity` is a function"); - equals(document.querySelector("#h5-number input").checkValidity(), false, "`\x3Cinput>.checkValidity()` should return false"); + + equals(typeof $.fn.checkValidity, "function", "`$.fn.checkValidity` is a function"); + equals($("#h5-number input").checkValidity(), false, "`$(selector).checkValidity()` should return false"); $("#h5-number form").submit(); $("#h5-email").trigger("click"); equals($("#h5-email input").attr("type"), "email", "Type should be `email`"); - equals($("#h5-email input")[0].checkValidity(), true, "`checkValidity()` should return true"); + equals($("#h5-email input").checkValidity(), true, "`$(selector).checkValidity()` should return true"); $("#h5-email form").submit(); $("#h5-text").trigger("click"); equals($("#h5-text input").attr("type"), "text", "Type should be `text`"); equals($("#h5-text input").attr("required"), '', "Attribute `required` should be '' (empty)"); - equals(typeof $.fn.checkValidity, "function", "`$.fn.checkValidity` is a function"); - equals($("#h5-text input").checkValidity(), true, "`$(selector).checkValidity()` should return true"); + equals(typeof document.querySelector("#h5-text input").checkValidity, "function", "`\x3Cinput>.checkValidity` is a function"); + equals(document.querySelector("#h5-text input").checkValidity(), true, "`\x3Cinput>.checkValidity()` should return true"); $("#h5-text form").submit(); }); @@ -263,11 +264,13 @@ - +

Jeditable unit tests

+ +
    From 838e2ecad45faa54d395abeaca362a7f1c764449 Mon Sep 17 00:00:00 2001 From: Nick Freear Date: Tue, 19 Mar 2013 14:31:31 +0000 Subject: [PATCH 8/8] Bug #84, Tidy up deprecated code/ comments --- contributed/jquery.jeditable.html5.js | 21 +++------------------ 1 file changed, 3 insertions(+), 18 deletions(-) diff --git a/contributed/jquery.jeditable.html5.js b/contributed/jquery.jeditable.html5.js index f6c760f..747305c 100644 --- a/contributed/jquery.jeditable.html5.js +++ b/contributed/jquery.jeditable.html5.js @@ -15,8 +15,6 @@ // Keyboard accessibility/WAI-ARIA - allow users to navigate to an editable element using TAB/Shift+TAB. $.fn.editableAriaShim = function () { - //$.log('WAI-ARIA shim..'); - this.attr({ role: 'button', tabindex: 0 @@ -44,11 +42,7 @@ var i = document.createElement('input'); i.setAttribute('type', type); return i.type !== 'text' ? type : 'text'; - - //return i.type !== 'text'; - //return ! navigator.userAgent.match(/MSIE/); }; - //$.fn.supportInType = _supportInType; // Type = text : With HTML5 attributes. $.editable.addInputType('html5_text', { @@ -85,22 +79,13 @@ $.editable.addInputType('number', { max : settings.max, step: settings.step, title: settings.html5_error_text, - type: _supportInType('number') //? 'number' : 'text' + type: _supportInType('number') }); $(this).append(input); return input; } }); -// Deprecated. -$.editable.addInputType('unsigned_integer', { - element: function (settings, original) { - var input = $(''); - $(this).append(input); - return input; - } -}); - // Type = range : Not usable. /*$.editable.addInputType('range', { element: function (settings, original) { @@ -125,7 +110,7 @@ $.editable.addInputType('email', { // pattern -- Not useful. maxlength: settings.maxlength, placeholder: settings.html5_placeholder, - type: _supportInType('email') //? 'email' : 'text' + type: _supportInType('email') }); $(this).append(input); return input; @@ -140,7 +125,7 @@ $.editable.addInputType('url', { pattern: settings.pattern, placeholder: settings.html5_placeholder, title: settings.html5_error_text, - type: _supportInType('url') //? 'url' : 'text' + type: _supportInType('url') }); $(this).append(input); return input;