Commit bfd2b54f authored by Carsten  Rose's avatar Carsten Rose
Browse files

Merge remote-tracking branch 'origin/raos_work' into crose_work

parents 4a6daf09 597960d8
......@@ -184,7 +184,7 @@ module.exports = function (grunt) {
cwd: 'bower_components/jqwidgets/jqwidgets/styles/',
src: [
'jqx.base.css',
'jqx.darkblue.css'
'jqx.bootstrap.css'
],
expand: true,
dest: typo3_css,
......@@ -215,7 +215,7 @@ module.exports = function (grunt) {
cwd: 'bower_components/jqwidgets/jqwidgets/styles/',
src: [
'jqx.base.css',
'jqx.darkblue.css'
'jqx.bootstrap.css'
],
expand: true,
dest: 'css/',
......
......@@ -20,11 +20,14 @@ var QfqNS = QfqNS || {};
* The first instance displaying a message will append an `alert container` to the body. The last message being
* dismissed will remove the `alert container`. A typical call sequence might look like:
*
* var alert = new QfqNS.Alert("Text being displayed", "info");
* var alert = new QfqNS.Alert({
* message: "Text being displayed",
* type: "info"
* });
* alert.show();
*
* Messages may have different background colors (severity levels), controlled by the second argument
* `messageType` of the constructor. The possible values are
* Messages may have different background colors (severity levels), controlled by the `type` property. Possible
* values are
*
* * `"info"`
* * `"warning"`
......@@ -34,37 +37,71 @@ var QfqNS = QfqNS || {};
*
* If no buttons are configured, a click anywhere on the alert will close it.
*
* Buttons are configured by passing an array of objects to the constructor. The attributes of the object are as
* follows
* Buttons are configured by passing an array of objects in the `buttons` property. The properties of the object
* are as follows
*
* {
* label: <button label>,
* focus: true | false,
* eventName: <eventname>
* }
* {
* label: <button label>,
* focus: true | false,
* eventName: <eventname>
* }
*
* You can connect to the button events by using
*
* var alert = new QfqNS.Alert("Text being displayed", "info", [{ label: "OK", eventName: "ok" }]);
* alert.on('alert.ok', function(...) { ... });
* var alert = new QfqNS.Alert({
* message: "Text being displayed",
* type: "info",
* buttons: [
* { label: "OK", eventName: "ok" }
* ]
* });
* alert.on('alert.ok', function(...) { ... });
*
* Events are named according to `alert.<eventname>`.
*
* @param message {string} message to be displayed
* @param messageType {string} type of message, can either be `"info"`, `"warning"`, or `"error"`.
* @param buttons {list} buttons to be displayed
* When `"none"` is provided, clicking anywhere on the message will dismiss it.
* If the property `modal` is set to `true`, a kind-of modal alert will be displayed, preventing clicks
* anywhere but the alert.
*
* For compatibility reasons, the old constructor signature is still supported but deprecated
*
* var alert = new QfqNS.Alert(message, type, buttons)
*
* @param {object} options option object having following properties
* @param {string} options.message message to be displayed
* @param {string} [options.type] type of message, can be `"info"`, `"warning"`, or `"error"`. Default is `"info"`.
* @param {boolean} [options.modal] whether or not alert is modal, i.e. prevent clicks anywhere but the dialog.
* Default is `false`.
* @param {object[]} options.buttons what buttons to display on alert. If empty array is provided, no buttons are
* displayed and a click anywhere in the alert will dismiss it.
* @param {string} options.buttons.label label of the button
* @param {string} options.buttons.eventName name of the event when button is clicked.
* @param {boolean} [options.buttons.focus] whether or not button has focus by default. Default is `false`.
*
* @constructor
*/
n.Alert = function (message, messageType, buttons) {
this.message = message;
this.messageType = messageType || "info";
this.buttons = buttons || [];
n.Alert = function (options) {
// Emulate old behavior of method signature
// function(message, messageType, buttons)
if (typeof options === "string") {
this.message = arguments[0];
this.messageType = arguments[1] || "info";
this.buttons = arguments[2] || [];
this.modal = false;
// this.timeout < 1 means forever
this.timeout = 0;
} else {
// new style
this.message = options.message || "MESSAGE";
this.messageType = options.type || "info";
this.buttons = options.buttons || [];
this.modal = options.modal || false;
this.timeout = options.timeout || 0;
}
this.$alertDiv = null;
this.$modalDiv = null;
this.shown = false;
// this.timeout < 1 means forever
this.timeout = 0;
this.fadeInDuration = 400;
this.fadeOutDuration = 400;
this.timerId = null;
......@@ -158,6 +195,12 @@ var QfqNS = QfqNS || {};
}
var $alertContainer = this.makeAlertContainerSingleton();
if (this.modal) {
this.$modalDiv = $("<div>");
this.$modalDiv.css('width', Math.max(document.documentElement.clientWidth, window.innerWidth || 0));
this.$modalDiv.css('height', Math.max(document.documentElement.clientHeight, window.innerHeight || 0));
}
this.$alertDiv = $("<div>")
.hide()
.addClass("alert")
......@@ -175,7 +218,13 @@ var QfqNS = QfqNS || {};
this.$alertDiv.click(this.removeAlert.bind(this));
}
$alertContainer.append(this.$alertDiv);
if (this.modal) {
this.$modalDiv.append(this.$alertDiv);
$alertContainer.append(this.$modalDiv);
} else {
$alertContainer.append(this.$alertDiv);
}
this.$alertDiv.slideDown(this.fadeInDuration, this.afterFadeIn.bind(this));
this.$alertDiv.find(".wants-focus").focus();
this.shown = true;
......@@ -208,8 +257,13 @@ var QfqNS = QfqNS || {};
this.$alertDiv.slideUp(this.fadeOutDuration, function () {
that.$alertDiv.remove();
that.$alertDiv = null;
if (that.modal) {
that.$modalDiv.remove();
that.$modalDiv = null;
}
that.shown = false;
// TODO: removeAlert should not have knowledge on how to handle alert container
if (that.countAlertsInAlertContainer() === 0) {
that.removeAlertContainer();
}
......
......@@ -27,9 +27,15 @@ var QfqNS = QfqNS || {};
n.FileDelete.prototype.buttonClicked = function (event) {
event.preventDefault();
var alert = new n.Alert("Do you want to delete the file?",
"warning",
[{label: "OK", eventName: "ok"}, {label: "Cancel", eventName: "cancel", focus: true}]);
var alert = new n.Alert({
message: "Do you want to delete the file?",
type: "warning",
modal: true,
buttons: [
{label: "OK", eventName: "ok"},
{label: "Cancel", eventName: "cancel", focus: true}
]
});
alert.on('alert.ok', function () {
this.performFileDelete(event);
}.bind(this));
......
/**
* @author Rafael Ostertag <rafael.ostertag@math.uzh.ch>
*/
/* global $ */
/**
* Qfq Namespace
*
* @namespace QfqNS
*/
var QfqNS = QfqNS || {};
/**
* Qfq Helper Namespace
*
* @namespace QfqNS.Helper
*/
QfqNS.Helper = QfqNS.Helper || {};
(function (n) {
'use strict';
var jqxComboBox = function () {
var index;
var $containers = $("div.jqw-combobox");
$containers.each(function (index, object) {
(function ($container) {
var controlName = $container.data('control-name');
if (!controlName) {
QfqNS.Log.error("jqwComboBox container does not have a 'data-control-name' attribute.");
return;
}
var sourceId = controlName + "_source";
var $sourceScript = $('#' + sourceId);
if ($sourceScript.length !== 1) {
QfqNS.Log.error("Unable to find data for jqwComboBox using id '" + sourceId + "'");
return;
}
var source = JSON.parse($sourceScript.text());
$container.jqxComboBox({source: source});
var $hiddenInput = $("<input>")
.attr('type', 'hidden')
.attr('name', controlName);
$container.after($hiddenInput);
$hiddenInput.val($container.jqxComboBox('val'));
$container.on('change', function (event) {
$hiddenInput.val(event.args.item.value);
});
})($(object));
});
};
n.jqxComboBox = jqxComboBox;
})(QfqNS.Helper);
\ No newline at end of file
/**
* @author Rafael Ostertag <rafael.ostertag@math.uzh.ch>
*/
/* global $ */
/**
* Qfq Namespace
*
* @namespace QfqNS
*/
var QfqNS = QfqNS || {};
/**
* Qfq Helper Namespace
*
* @namespace QfqNS.Helper
*/
QfqNS.Helper = QfqNS.Helper || {};
(function (n) {
'use strict';
/**
* Initializes jqxDateTimeInput widgets.
*
* It configures all `<div>`s having a class `jqw-datetimepicker` as jqxDateTimeInput.
*
* Given the HTML snippet
*
* ...
* <div class="jqw-datetimepicker" data-control-name="datetimepicker" ></div>
* ...
*
* it will create a hidden input sibling element of the `<div>` where the selected date is stored for plain old
* form submission, thus rendering the above snippet effectively to
*
* ...
* <div class="jqw-datetimepicker" data-control-name="datetimepicker" ></div>
* <input type="hidden" name="datetimepicker">
* ...
*
* The jqxDateTimeInput can be configured using following `data` attributes
*
* * `data-control-name`: Mandatory attribute. Hold the name of the input element.
* * `data-format-string': Optional Format string as required by jqxDateTimeInput. See also
* {@link http://www.jqwidgets.com/jquery-widgets-documentation/documentation/jqxdatetimeinput/jquery-datetimeinput-api.htm}.
* Default: "F".
* * `data-show-time-button`: Boolean value `true` or `false`, indicating whether or not a time picker will be
* displayed.
*
* @function
* @name QfqNS.Helper.jqxDateTimeInput
*/
var jqxDateTimeInput = function () {
var index;
var $containers = $("div.jqw-datetimepicker");
$containers.each(function (index, object) {
(function ($container) {
var controlName = $container.data('control-name');
if (!controlName) {
QfqNS.Log.error("jqwDateTimePicker does not have a 'data-control-name' attribute.");
return;
}
var formatString = $container.data('format-string');
if (!formatString) {
formatString = "F";
}
var showTimeButton = $container.data('show-time-button');
if (showTimeButton === undefined) {
showTimeButton = false;
}
var jqxDateTimeInputConfig = {
formatString: formatString,
showTimeButton: showTimeButton,
width: '300px',
height: '25px'
};
$container.jqxDateTimeInput(jqxDateTimeInputConfig);
var $hiddenInput = $("<input>")
.attr('type', 'hidden')
.attr('name', controlName);
$container.after($hiddenInput);
$hiddenInput.val($container.jqxDateTimeInput('value').toISOString());
$container.on('valueChanged', function (event) {
$hiddenInput.val(event.args.date.toISOString());
});
})($(object));
});
};
n.jqxDateTimeInput = jqxDateTimeInput;
})(QfqNS.Helper);
\ No newline at end of file
......@@ -74,6 +74,11 @@ var QfqNS = QfqNS || {};
var configurationData = this.readElementConfigurationData();
this.applyElementConfiguration(configurationData);
// Initialize jqxDateTimeInput elements.
n.Helper.jqxDateTimeInput();
// Initialize jqxComboBox elements.
n.Helper.jqxComboBox();
};
n.QfqForm.prototype.on = n.EventEmitter.onMixin;
......@@ -291,13 +296,16 @@ var QfqNS = QfqNS || {};
n.QfqForm.prototype.handleCloseClick = function () {
this.lastButtonPress = "close";
if (this.form.getFormChanged()) {
var alert = new n.Alert("You have unsaved changes. Do you want to save first?", "warning",
[
var alert = new n.Alert({
message: "You have unsaved changes. Do you want to save first?",
type: "warning",
modal: true,
buttons: [
{label: "Yes", eventName: "yes"},
{label: "No", eventName: "no", focus: true},
{
label: "Cancel", eventName: "cancel"
}]);
{label: "Cancel", eventName: "cancel"}
]
});
var that = this;
alert.on('alert.yes', function () {
that.submit();
......@@ -344,12 +352,17 @@ var QfqNS = QfqNS || {};
this.lastButtonPress = "new";
if (this.form.getFormChanged()) {
var alert = new n.Alert("You have unsaved changes. Do you want to save first?", "warning",
var alert = new n.Alert({
message: "You have unsaved changes. Do you want to save first?",
type: "warning",
modal: true,
buttons:
[
{label: "Yes", eventName: "yes", focus: true},
{label: "No", eventName: "no"},
{label: "Cancel", eventName: "cancel"}
]);
]
});
var that = this;
alert.on('alert.no', function () {
that.eventEmitter.emitEvent('qfqform.close-intentional', n.EventEmitter.makePayload(that, null));
......@@ -374,11 +387,15 @@ var QfqNS = QfqNS || {};
n.QfqForm.prototype.handleDeleteClick = function () {
this.lastButtonPress = "delete";
n.Log.debug("delete click");
var alert = new n.Alert("Do you really want to delete the record?", "warning",
[
var alert = new n.Alert({
message: "Do you really want to delete the record?",
type: "warning",
modal: true,
buttons: [
{label: "Yes", eventName: "ok"},
{label: "No", eventName: "cancel", focus: true}
]);
]
});
var that = this;
alert.on('alert.ok', function () {
$.post(that.deleteUrl)
......
......@@ -40,11 +40,15 @@ var QfqNS = QfqNS || {};
}
var alert = new n.Alert("Do you really want to delete the record?", "warning",
[
var alert = new n.Alert({
message: "Do you really want to delete the record?",
type: "warning",
modal: true,
buttons: [
{label: "Yes", eventName: "ok"},
{label: "No", eventName: "cancel", focus: true}
]);
]
});
var that = this;
alert.on('alert.ok', function () {
$.post(that.deleteUrl + "?s=" + sip)
......
......@@ -13,7 +13,24 @@
<button id="showalert2">Show Alert 2</button>
<button id="showalert3">Show Alert 3 primed</button>
<button id="showmanyalert1">Show Many Alert 1</button>
<button id="showmodalalert1">Show Modal Alert 1</button>
<a id="alertinlink" onclick="
var alert = new QfqNS.Alert('Text being displayed', 'info', [
{ label: 'OK', eventName: 'ok' },
{ label: 'Cancel', eventName: 'cancel'}
]);
alert.on('alert.ok', function() {
window.location = $('#alertinlink').attr('href');
});
alert.show();
return false;
" href="http://www.google.ch">Link alert</a>
<div style="margin-top: 20ex">
<button onclick="alert('Button clicked')">Modal test button</button>
</div>
<script src="../js/jquery.min.js"></script>
<script src="../js/bootstrap.min.js"></script>
......@@ -40,8 +57,10 @@
});
$('#showalert3').click(function () {
var alert = new QfqNS.Alert("This is alert 3. Disappears after 3 secs.");
alert.timeout = 3000;
var alert = new QfqNS.Alert({
message: "This is alert 3. Disappears after 3 secs.",
timeout: 3000
});
alert.show();
});
......@@ -55,6 +74,27 @@
alert = new QfqNS.Alert("This is alert 3", "error");
alert.show();
});
$('#showmodalalert1').click(function () {
var alert = new QfqNS.Alert(
{
message: "This is modal alert 1",
type: 'error',
buttons: [
{label: "OK", eventName: "ok", focus: true},
{label: "Cancel", eventName: "cancel"}
],
modal: true
}
);
alert.on('alert.ok', function () {
console.log("OK button modal alert 1");
});
alert.on('alert.cancel', function () {
console.log("Cancel button modal alert 1");
});
alert.show();
});
});
</script>
</body>
......
......@@ -7,6 +7,6 @@ header("Content-Type: text/json");
echo json_encode([
'status' => "error",
'message'
'message' => "error uploading file"
]);
......@@ -8,7 +8,7 @@
<link rel="stylesheet" href="../css/bootstrap.min.css">
<link rel="stylesheet" href="../css/bootstrap-theme.min.css">
<link rel="stylesheet" href="../css/jqx.base.css">
<link rel="stylesheet" href="../css/jqx.darkblue.css">
<link rel="stylesheet" href="../css/jqx.bootstrap.css">
<link rel="stylesheet" href="../css/qfq-bs.css">
<title>Person Form Mockup</title>
......@@ -224,7 +224,34 @@
<label for="personGeburtstag" class="control-label">Geburtstag</label>
</div>
<div class="col-md-6">
<input id="personGeburtstag" type="text" class="form-control" name="geburtstag">
<div id="personGeburtstag" class="jqw-datetimepicker"
data-control-name="personGeburtstag" data-format-string="dd.MM.yyyy HH:mm"
data-show-time-button="true"></div>
</div>
</div>
<div class="form-group">
<div class="col-md-2">
<label for="anotherDate" class="control-label">Another Date</label>
</div>
<div class="col-md-6">
<div id="anotherDate" class="jqw-datetimepicker"
data-control-name="anotherDate" data-format-string="dd.MM.yyyy"
data-show-time-button="false"></div>
</div>
</div>
<div class="form-group">
<div class="col-md-2">
<label for="combobox1" class="control-label">Combobox 1</label>
</div>
<div class="col-md-6">
<div id="combobox1" class="jqw-combobox"
data-control-name="combobox1"></div>
</div>
</div>
......@@ -796,6 +823,15 @@
<a href="www.google.ch">away</a>
</div>
<script type="application/jqw-combobox-source" id="combobox1_source">
[
"item 1",
"item 2",
"item 3"
]
</script>
<script src="../js/jquery.min.js"></script>
<script src="../js/bootstrap.min.js"></script>
<script src="../js/validator.min.js"></script>
......
Supports Markdown
0% or .
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment