create examples directory with old prototypes
This commit is contained in:
79
www/examples/form/index.html
Normal file
79
www/examples/form/index.html
Normal file
@@ -0,0 +1,79 @@
|
||||
<!DOCTYPE html>
|
||||
<html>
|
||||
<head>
|
||||
<meta content="text/html; charset=utf-8" http-equiv="content-type"/>
|
||||
<meta name="viewport" content="width=device-width, initial-scale=1.0"/>
|
||||
<script data-main="main" src="/bower_components/requirejs/require.js"></script>
|
||||
<style>
|
||||
html, body{
|
||||
padding: 0px;
|
||||
margin: 0px;
|
||||
overflow: hidden;
|
||||
box-sizing: border-box;
|
||||
}
|
||||
|
||||
form {
|
||||
border: 3px solid black;
|
||||
border-radius: 5px;
|
||||
padding: 15px;
|
||||
font-weight: bold !important;
|
||||
font-size: 18px !important;
|
||||
}
|
||||
|
||||
input[type="text"],
|
||||
input[type="password"],
|
||||
input[type="number"],
|
||||
input[type="range"],
|
||||
select
|
||||
{
|
||||
margin-top: 5px;
|
||||
margin-bottom: 5px;
|
||||
width: 80%;
|
||||
}
|
||||
textarea {
|
||||
width: 80%;
|
||||
height: 40vh;
|
||||
font-weight: bold;
|
||||
font-size: 18px;
|
||||
}
|
||||
</style>
|
||||
</head>
|
||||
<body>
|
||||
|
||||
<form>
|
||||
<input type="radio" name="radio" value="one" checked>One
|
||||
<input type="radio" name="radio" value="two">Two
|
||||
<input type="radio" name="radio" value="three">Three<br>
|
||||
|
||||
<input type="checkbox" name="checkbox1" value="1">Checkbox One
|
||||
<input type="checkbox" name="checkbox2" value="2">Checkbox Two<br>
|
||||
|
||||
<input type="text" name="text" placeholder="Text Input"><br>
|
||||
<input type="password" name="password" placeholder="Passwords"><br>
|
||||
|
||||
|
||||
<input type="number" name="number" min="1" max="5" placeholder="Numbers">Number<br>
|
||||
|
||||
<input type="range" name="range" min="0" max="100">Ranges<br>
|
||||
|
||||
<select name="select">
|
||||
<option value="one">One</option>
|
||||
<option value="two">Two</option>
|
||||
<option value="three">Three</option>
|
||||
<option value="four">Four</option>
|
||||
</select> Dropdowns<br>
|
||||
|
||||
<select name="select-multiple" multiple>
|
||||
<option value="pew">Pew</option>
|
||||
<option value="bang">Bang</option>
|
||||
<option value="kapow">Kapow</option>
|
||||
<option value="zing">Zing</option>
|
||||
</select>
|
||||
|
||||
<textarea name="textarea"></textarea><br>
|
||||
|
||||
</form>
|
||||
|
||||
</body>
|
||||
</html>
|
||||
|
||||
226
www/examples/form/main.js
Normal file
226
www/examples/form/main.js
Normal file
@@ -0,0 +1,226 @@
|
||||
require.config({ paths: { 'json.sortify': '/bower_components/json.sortify/dist/JSON.sortify' } });
|
||||
define([
|
||||
'/api/config?cb=' + Math.random().toString(16).substring(2),
|
||||
'/bower_components/chainpad-netflux/chainpad-netflux.js',
|
||||
'/bower_components/chainpad-crypto/crypto.js',
|
||||
'/bower_components/textpatcher/TextPatcher.amd.js',
|
||||
'json.sortify',
|
||||
'ula.js',
|
||||
'/bower_components/chainpad-json-validator/json-ot.js',
|
||||
'/common/cryptpad-common.js',
|
||||
'/bower_components/jquery/dist/jquery.min.js',
|
||||
], function (Config, Realtime, Crypto, TextPatcher, Sortify, Formula, JsonOT, Cryptpad) {
|
||||
var $ = window.jQuery;
|
||||
|
||||
var secret = Cryptpad.getSecrets();
|
||||
|
||||
var module = window.APP = {
|
||||
TextPatcher: TextPatcher,
|
||||
Sortify: Sortify,
|
||||
Formula: Formula,
|
||||
};
|
||||
var initializing = true;
|
||||
|
||||
var uid = module.uid = Formula.uid;
|
||||
|
||||
var getInputType = Formula.getInputType;
|
||||
var $elements = module.elements = $('input, select, textarea');
|
||||
|
||||
var eventsByType = Formula.eventsByType;
|
||||
|
||||
var Map = module.Map = {};
|
||||
|
||||
var UI = module.UI = {
|
||||
ids: [],
|
||||
each: function (f) {
|
||||
UI.ids.forEach(function (id, i, list) {
|
||||
if (!UI[id]) { return; }
|
||||
f(UI[id], i, list);
|
||||
});
|
||||
},
|
||||
add: function (id, ui) {
|
||||
if (UI.ids.indexOf(id) === -1) {
|
||||
UI.ids.push(id);
|
||||
|
||||
UI[id] = ui;
|
||||
return true;
|
||||
} else {
|
||||
// it already exists
|
||||
|
||||
return false;
|
||||
}
|
||||
},
|
||||
remove: function (id) {
|
||||
delete UI[id];
|
||||
var idx = UI.ids.indexOf(id);
|
||||
if (idx > -1) {
|
||||
UI.ids.splice(idx, 1);
|
||||
return true;
|
||||
}
|
||||
}
|
||||
};
|
||||
|
||||
var cursorTypes = ['textarea', 'password', 'text'];
|
||||
|
||||
var canonicalize = function (text) { return text.replace(/\r\n/g, '\n'); };
|
||||
$elements.each(function (index, element) {
|
||||
var $this = $(this);
|
||||
|
||||
var id = uid();
|
||||
var type = getInputType($this);
|
||||
|
||||
// ignore hidden inputs, submit inputs, and buttons
|
||||
if (['button', 'submit', 'hidden'].indexOf(type) !== -1) {
|
||||
return;
|
||||
}
|
||||
|
||||
$this // give each element a uid
|
||||
.data('rtform-uid', id)
|
||||
// get its type
|
||||
.data('rt-ui-type', type);
|
||||
|
||||
var component = {
|
||||
id: id,
|
||||
$: $this,
|
||||
element: element,
|
||||
type: type,
|
||||
preserveCursor: cursorTypes.indexOf(type) !== -1,
|
||||
name: $this.prop('name'),
|
||||
};
|
||||
|
||||
UI.add(id, component);
|
||||
|
||||
component.value = (function () {
|
||||
var checker = ['radio', 'checkbox'].indexOf(type) !== -1;
|
||||
|
||||
if (checker) {
|
||||
return function (content) {
|
||||
return typeof content !== 'undefined'?
|
||||
$this.prop('checked', !!content):
|
||||
$this.prop('checked');
|
||||
};
|
||||
} else {
|
||||
return function (content) {
|
||||
return typeof content !== 'undefined' ?
|
||||
$this.val(content):
|
||||
typeof($this.val()) === 'string'? canonicalize($this.val()): $this.val();
|
||||
};
|
||||
}
|
||||
}());
|
||||
|
||||
var update = component.update = function () { Map[id] = component.value(); };
|
||||
update();
|
||||
});
|
||||
|
||||
var config = module.config = {
|
||||
initialState: Sortify(Map) || '{}',
|
||||
websocketURL: Config.websocketURL,
|
||||
userName: Crypto.rand64(8),
|
||||
channel: secret.channel,
|
||||
crypto: Crypto.createEncryptor(secret.key),
|
||||
transformFunction: JsonOT.validate
|
||||
};
|
||||
|
||||
var setEditable = module.setEditable = function (bool) {
|
||||
/* (dis)allow editing */
|
||||
$elements.each(function () {
|
||||
$(this).attr('disabled', !bool);
|
||||
});
|
||||
};
|
||||
|
||||
setEditable(false);
|
||||
|
||||
var onInit = config.onInit = function (info) {
|
||||
var realtime = module.realtime = info.realtime;
|
||||
window.location.hash = info.channel + secret.key;
|
||||
|
||||
// create your patcher
|
||||
module.patchText = TextPatcher.create({
|
||||
realtime: realtime,
|
||||
logging: true,
|
||||
});
|
||||
};
|
||||
|
||||
var readValues = function () {
|
||||
UI.each(function (ui, i, list) {
|
||||
Map[ui.id] = ui.value();
|
||||
});
|
||||
};
|
||||
|
||||
var onLocal = config.onLocal = function () {
|
||||
if (initializing) { return; }
|
||||
/* serialize local changes */
|
||||
readValues();
|
||||
module.patchText(Sortify(Map));
|
||||
};
|
||||
|
||||
var updateValues = function () {
|
||||
var userDoc = module.realtime.getUserDoc();
|
||||
var parsed = JSON.parse(userDoc);
|
||||
|
||||
console.log(userDoc);
|
||||
|
||||
// flush received values to the map
|
||||
// but only if you don't have them locally
|
||||
// this *shouldn't* break cursors
|
||||
Object.keys(parsed).forEach(function (key) {
|
||||
if (UI.ids.indexOf(key) === -1) { Map[key] = parsed[key]; }
|
||||
});
|
||||
|
||||
UI.each(function (ui, i, list) {
|
||||
var newval = parsed[ui.id];
|
||||
var oldval = ui.value();
|
||||
|
||||
if (typeof(newval) === 'undefined') { return; }
|
||||
if (newval === oldval) { return; }
|
||||
|
||||
var op;
|
||||
var selects;
|
||||
var element = ui.element;
|
||||
if (ui.preserveCursor) {
|
||||
op = TextPatcher.diff(oldval, newval);
|
||||
selects = ['selectionStart', 'selectionEnd'].map(function (attr) {
|
||||
var before = element[attr];
|
||||
var after = TextPatcher.transformCursor(element[attr], op);
|
||||
return after;
|
||||
});
|
||||
}
|
||||
|
||||
ui.value(newval);
|
||||
ui.update();
|
||||
|
||||
if (op && ui.preserveCursor) {
|
||||
//console.log(selects);
|
||||
element.selectionStart = selects[0];
|
||||
element.selectionEnd = selects[1];
|
||||
}
|
||||
});
|
||||
};
|
||||
|
||||
var onRemote = config.onRemote = function (info) {
|
||||
if (initializing) { return; }
|
||||
/* integrate remote changes */
|
||||
updateValues();
|
||||
};
|
||||
|
||||
var onReady = config.onReady = function (info) {
|
||||
updateValues();
|
||||
|
||||
console.log("READY");
|
||||
setEditable(true);
|
||||
initializing = false;
|
||||
};
|
||||
|
||||
var onAbort = config.onAbort = function (info) {
|
||||
window.alert("Network Connection Lost");
|
||||
};
|
||||
|
||||
var rt = Realtime.start(config);
|
||||
|
||||
UI.each(function (ui, i, list) {
|
||||
var type = ui.type;
|
||||
var events = eventsByType[type];
|
||||
ui.$.on(events, onLocal);
|
||||
});
|
||||
|
||||
});
|
||||
14
www/examples/form/types.md
Normal file
14
www/examples/form/types.md
Normal file
@@ -0,0 +1,14 @@
|
||||
|
||||
```Javascript
|
||||
/* elements that we need to listen to */
|
||||
/*
|
||||
* text => $(text).val()
|
||||
* password => $(password).val()
|
||||
* radio => $(radio).prop('checked')
|
||||
* checkbox => $(checkbox).prop('checked')
|
||||
* number => $(number).val() // returns string, no default
|
||||
* range => $(range).val()
|
||||
* select => $(select).val()
|
||||
* textarea => $(textarea).val()
|
||||
*/
|
||||
```
|
||||
25
www/examples/form/ula.js
Normal file
25
www/examples/form/ula.js
Normal file
@@ -0,0 +1,25 @@
|
||||
define([], function () {
|
||||
var ula = {};
|
||||
|
||||
var uid = ula.uid = (function () {
|
||||
var i = 0;
|
||||
var prefix = 'rt_';
|
||||
return function () { return prefix + i++; };
|
||||
}());
|
||||
|
||||
ula.getInputType = function ($el) { return $el[0].type; };
|
||||
|
||||
ula.eventsByType = {
|
||||
text: 'change keyup',
|
||||
password: 'change keyup',
|
||||
radio: 'change click',
|
||||
checkbox: 'change click',
|
||||
number: 'change',
|
||||
range: 'keyup change',
|
||||
'select-one': 'change',
|
||||
'select-multiple': 'change',
|
||||
textarea: 'change keyup',
|
||||
};
|
||||
|
||||
return ula;
|
||||
});
|
||||
Reference in New Issue
Block a user