<commit_before>
function resolveRequest(type, method, settings) {
	if (type == GET_CAPABILITIES_TYPE) {
		return new GetRequest(settings);
	}
	else if (type == DESCRIBE_PROCESS_TYPE) {
		return new GetRequest(settings);
	}
	else if (type == EXECUTE_TYPE && method == METHOD_POST) {
		return new PostRequest(settings);
	}

	return new GetRequest(settings);
}

function resolveGetParameters() {
	var params = $.url();
	var url = params.param(PARAM_WPS_REQUEST_URL);
	var requestType = params.param(PARAM_WPS_REQUEST_TYPE);

	if (url && requestType) {
		return {url: decodeURIComponent((url+'').replace(/\+/g, '%20')), requestType: requestType};
	}

	return null;
}

function assertValidState(settings) {
	var dataValid = true;
	if (settings.method == METHOD_POST) {
		dataValid = $.isXMLDoc(settings.data);
	}
	return settings.url && settings.requestType && settings.method && dataValid;
}

function callbackOnResponseParsed(responseData, domElement, originalRequest) {
	var factory = new ResponseFactory();
	var responseHandler = factory.resolveResponseHandler(responseData, originalRequest);

	if (responseHandler) {
		domElement.html(responseHandler.createMarkup());
	}

	if (originalRequest.updateSwitch) {
		if (!originalRequest.updateSwitch.callback) {
			originalRequest.updateSwitch.callback = callbackOnResponseParsed;
		}
		if (!originalRequest.updateSwitch.element) {
			originalRequest.updateSwitch.element = "wps-execute-autoUpdate";
		}

		$('#'+originalRequest.updateSwitch.element).click(function() {
			originalRequest.execute(originalRequest.updateSwitch.callback, originalRequest.updateSwitch);
		});
		$('#'+originalRequest.updateSwitch.element).css( 'cursor', 'pointer' );
	}
}

function handleResponse(responseData, domElement, originalRequest) {
	var factory = new ResponseFactory();
	var responseHandler = factory.resolveResponseHandler(responseData, originalRequest);

	if (responseHandler) {
		domElement.html(responseHandler.createMarkup());
	}
}

// using OpenLayers.Format.WPSCapabilities to read the capabilities
function getCapabilities() {
    OpenLayers.Request.GET({
        url: wps,
        params: {
            "SERVICE": "WPS",
            "REQUEST": "GetCapabilities"
        },
        success: function(response){
            capabilities = new OpenLayers.Format.WPSCapabilities().read(
                response.responseText
            );
            var dropdown = document.getElementById("processes");
            var offerings = capabilities.processOfferings, option;
            // populate the dropdown
            for (var p in offerings) {
                option = document.createElement("option");
                option.innerHTML = offerings[p].identifier;
                option.value = p;
                dropdown.appendChild(option);
            }
        }
    });
}

// using OpenLayers.Format.WPSDescribeProcess to get information about a
// process
function describeProcess() {
    var selection = this.options[this.selectedIndex].value;
    OpenLayers.Request.GET({
        url: wps,
        params: {
            "SERVICE": "WPS",
            "REQUEST": "DescribeProcess",
            "VERSION": capabilities.version,
            "IDENTIFIER": selection
        },
        success: function(response) {
            process = new OpenLayers.Format.WPSDescribeProcess().read(
                response.responseText
            ).processDescriptions[selection];
            buildForm();
        }
    });
}

// dynamically create a form from the process description
function buildForm() {
    document.getElementById("abstract").innerHTML = process["abstract"];
    document.getElementById("input").innerHTML = "
Input:
";
    document.getElementById("output").innerHTML = "";

    var inputs = process.dataInputs, supported = true,
        sld = "text/xml; subtype=sld/1.0.0",
        input;
    for (var i=0,ii=inputs.length; i<ii; ++i) {
        input = inputs[i];
        if (input.complexData) {
            var formats = input.complexData.supported.formats;
            if (formats["application/wkt"]) {
                addWKTInput(input);
            } else if (formats["text/xml; subtype=wfs-collection/1.0"]) {
                addWFSCollectionInput(input);
            } else if (formats["image/tiff"]) {
                addRasterInput(input);
            } else if (formats[sld]) {
                addXMLInput(input, sld);
            } else {
                supported = false;
            }
        } else if (input.boundingBoxData) {
            addBoundingBoxInput(input);
        } else if (input.literalData) {
            addLiteralInput(input);
        } else {
            supported = false;
        }
        if (input.minOccurs > 0) {
            document.getElementById("input").appendChild(document.createTextNode("* "));
        }
    }

    if (supported) {
        var executeButton = document.createElement("button");
        executeButton.innerHTML = "Execute";
        document.getElementById("input").appendChild(executeButton);
        executeButton.onclick = execute;
    } else {
        document.getElementById("input").innerHTML = '' +
            "Sorry, the WPS builder does not support the selected process." +
            "";
    }
}

// helper function to dynamically create a textarea for geometry (WKT) data
// input
function addWKTInput(input, previousSibling) {
    var name = input.identifier;
    var container = document.getElementById("input");
    var label = document.createElement("label");
    label["for"] = name;
    label.title = input["abstract"];
    label.innerHTML = name + " (select feature, then click field):";
    previousSibling && previousSibling.nextSibling ?
        container.insertBefore(label, previousSibling.nextSibling) :
        container.appendChild(label);
    var field = document.createElement("textarea");
    field.onclick = function () {
        if (layer.selectedFeatures.length) {
            this.innerHTML = new OpenLayers.Format.WKT().write(
                layer.selectedFeatures[0]
            );
        }
        createCopy(input, this, addWKTInput);
    };
    field.onblur = function() {
        input.data = field.value ? {
            complexData: {
                mimeType: "application/wkt",
                value: this.value
            }
        } : undefined;
    };
    field.title = input["abstract"];
    field.id = name;
    previousSibling && previousSibling.nextSibling ?
        container.insertBefore(field, previousSibling.nextSibling.nextSibling) :
        container.appendChild(field);
}

// helper function for xml input
function addXMLInput(input, type) {
    var name = input.identifier;
    var field = document.createElement("input");
    field.title = input["abstract"];
    field.value = name + " (" + type + ")";
    field.onblur = function() {
        input.data = field.value ? {
            complexData: {
                mimeType: type,
                value: this.value
            }
        } : undefined;
    };
    document.getElementById("input").appendChild(field);
}

// helper function to dynamically create a WFS collection reference input
function addWFSCollectionInput(input) {
    var name = input.identifier;
    var field = document.createElement("input");
    field.title = input["abstract"];
    field.value = name + " (layer on demo server)";
    addValueHandlers(field, function() {
        input.reference = field.value ? {
            mimeType: "text/xml; subtype=wfs-collection/1.0",
            href: "http://geoserver/wfs",
            method: "POST",
            body: {
                wfs: {
                    version: "1.0.0",
                    outputFormat: "GML2",
                    featureType: field.value
                }
            }
        } : undefined;
    });
    document.getElementById("input").appendChild(field);
}

// helper function to dynamically create a raster (GeoTIFF) url input
function addRasterInput(input) {
    var name = input.identifier;
    var field = document.createElement("input");
    field.title = input["abstract"];
    var url = window.location.href.split("?")[0];
    field.value = url.substr(0, url.lastIndexOf("/")+1) + "data/tazdem.tiff";
    document.getElementById("input").appendChild(field);
    (field.onblur = function() {
        input.reference = {
            mimeType: "image/tiff",
            href: field.value,
            method: "GET"
        };
    })();
}

// helper function to dynamically create a bounding box input
function addBoundingBoxInput(input) {
    var name = input.identifier;
    var field = document.createElement("input");
    field.title = input["abstract"];
    field.value = "left,bottom,right,top (EPSG:4326)";
    document.getElementById("input").appendChild(field);
    addValueHandlers(field, function() {
        input.boundingBoxData = {
            projection: "EPSG:4326",
            bounds: OpenLayers.Bounds.fromString(field.value)
        };
    });
}

// helper function to create a literal input textfield or dropdown
function addLiteralInput(input, previousSibling) {
    var name = input.identifier;
    var container = document.getElementById("input");
    var anyValue = input.literalData.anyValue;
    // anyValue means textfield, otherwise we create a dropdown
    var field = document.createElement(anyValue ? "input" : "select");
    field.id = name;
    field.title = input["abstract"];
    previousSibling && previousSibling.nextSibling ?
        container.insertBefore(field, previousSibling.nextSibling) :
        container.appendChild(field);
    if (anyValue) {
        var dataType = input.literalData.dataType;
        field.value = name + (dataType ? " (" + dataType + ")" : "");
        addValueHandlers(field, function() {
            input.data = field.value ? {
                literalData: {
                    value: field.value
                }
            } : undefined;
            createCopy(input, field, addLiteralInput);
        });
    } else {
        var option;
        option = document.createElement("option");
        option.innerHTML = name;
        field.appendChild(option);
        for (var v in input.literalData.allowedValues) {
            option = document.createElement("option");
            option.value = v;
            option.innerHTML = v;
            field.appendChild(option);
        }
        field.onchange = function() {
            createCopy(input, field, addLiteralInput);
            input.data = this.selectedIndex ? {
                literalData: {
                    value: this.options[this.selectedIndex].value
                }
            } : undefined;
        };
    }
}

// if maxOccurs is > 1, this will add a copy of the field
function createCopy(input, field, fn) {
    if (input.maxOccurs && input.maxOccurs > 1 && !field.userSelected) {
        // add another copy of the field - we don't check maxOccurs
        field.userSelected = true;
        var newInput = OpenLayers.Util.extend({}, input);
        // we recognize copies by the occurrence property
        newInput.occurrence = (input.occurrence || 0) + 1;
        process.dataInputs.push(newInput);
        fn(newInput, field);
    }
}

// helper function for adding events to form fields
function addValueHandlers(field, onblur) {
    field.onclick = function() {
        if (!this.initialValue) {
            this.initialValue = this.value;
            this.value = "";
        }
    };
    field.onblur = function() {
        if (!this.value) {
            this.value = this.initialValue;
            delete this.initialValue;
        }
        onblur.apply(this, arguments);
    };
}

// execute the process
function execute() {
    var output = process.processOutputs[0];
    var input;
    // remove occurrences that the user has not filled out
    for (var i=process.dataInputs.length-1; i>=0; --i) {
        input = process.dataInputs[i];
        if ((input.minOccurs === 0 || input.occurrence) && !input.data && !input.reference) {
            OpenLayers.Util.removeItem(process.dataInputs, input);
        }
    }
    process.responseForm = {
        responseDocument: {
        	storeExecuteResponse: true,
        	outputs: [{
        		asReference: true,
        		mimeType: "application/PDF",
        		identifier: output.identifier
            }]
        }
    };
    OpenLayers.Request.POST({
        url: wps,
        data: new OpenLayers.Format.WPSExecute().write(process),
        success: showOutput
    });
}

// add the process's output to the page
function showOutput(response) {

	var statusLocation = response.responseXML.documentElement.getAttribute("statusLocation");

	handleResponse(response.responseXML, '#capabilitiesByClick', statusLocation);

    var result = document.getElementById("output");
    result.innerHTML = "
Output:
";
    var features;
    var contentType = response.getResponseHeader("Content-Type");
    if (contentType == "application/wkt") {
        features = new OpenLayers.Format.WKT().read(response.responseText);
    } else if (contentType == "text/xml; subtype=wfs-collection/1.0") {
        features = new OpenLayers.Format.WFST.v1_0_0().read(response.responseText);
    }
    if (features && (features instanceof OpenLayers.Feature.Vector || features.length)) {
        layer.addFeatures(features);
        result.innerHTML += "The result should also be visible on the map.";
    }
    result.innerHTML += "<textarea>" + response.responseText + "</textarea>";
}

/*
 * jQuery plugin definitions
 */
(function($) {

	$.fn.extend({
		wpsCall : function( options ) {
	    	var settings;
	    	if (options && options.viaUrl) {
	    		/*
	    		 * Call via GET parameters
	    		 */
	    		settings = $.extend(resolveGetParameters(), {method: METHOD_GET});
	    	}
	    	else {
	            /*
	             * Custom User Call
	             */
	            settings = $.extend({
	                method: METHOD_GET
	            }, options);
	    	}

	    	if (assertValidState(settings)) {
	    		return this.each( function() {
	            	var requestSettings = $.extend({
	                    domElement: $(this)
	                }, settings);

	            	var request = resolveRequest(requestSettings.requestType, requestSettings.method,
	            			requestSettings);
	            	request.execute(callbackOnResponseParsed, options.updateSwitch);
	            });
	    	}

	    	return this.each();
	    }
	});

	$.extend({
		wpsSetup : function(setup) {
			if (setup.reset) {
				wpsResetSetup();
				return;
			}

	    	if (setup.templates) {
	    		var templates = setup.templates;
	    		if (templates.capabilities) {
	    			if (typeof templates.capabilities == 'string') {
	    				USER_TEMPLATE_CAPABILITIES_MARKUP = templates.capabilities;
	    			}
	        	}
	        	if (templates.processDescription) {
	        		if (typeof templates.processDescription == 'string') {
	        			USER_TEMPLATE_PROCESS_DESCRIPTION_MARKUP = templates.processDescription;
	        		}
	        	}
	        	if (templates.executeResponse) {
	        		if (typeof templates.executeResponse == 'string') {
	        			USER_TEMPLATE_EXECUTE_RESPONSE_MARKUP = templates.executeResponse;
	        		}
	        	}
	    	}

	    	if (setup.proxy) {
	    		USE_PROXY = true;
	    		PROXY_URL = setup.proxy.url;
	    		PROXY_TYPE = setup.proxy.type;
	    	}
	    }
	});

}(jQuery));
<commit_msg>Show execute response in client<commit_after>
function resolveRequest(type, method, settings) {
	if (type == GET_CAPABILITIES_TYPE) {
		return new GetRequest(settings);
	}
	else if (type == DESCRIBE_PROCESS_TYPE) {
		return new GetRequest(settings);
	}
	else if (type == EXECUTE_TYPE && method == METHOD_POST) {
		return new PostRequest(settings);
	}

	return new GetRequest(settings);
}

function resolveGetParameters() {
	var params = $.url();
	var url = params.param(PARAM_WPS_REQUEST_URL);
	var requestType = params.param(PARAM_WPS_REQUEST_TYPE);

	if (url && requestType) {
		return {url: decodeURIComponent((url+'').replace(/\+/g, '%20')), requestType: requestType};
	}

	return null;
}

function assertValidState(settings) {
	var dataValid = true;
	if (settings.method == METHOD_POST) {
		dataValid = $.isXMLDoc(settings.data);
	}
	return settings.url && settings.requestType && settings.method && dataValid;
}

function callbackOnResponseParsed(responseData, domElement, originalRequest) {
	var factory = new ResponseFactory();
	var responseHandler = factory.resolveResponseHandler(responseData, originalRequest);

	if (responseHandler) {
		domElement.html(responseHandler.createMarkup());
	}

	if (originalRequest.updateSwitch) {
		if (!originalRequest.updateSwitch.callback) {
			originalRequest.updateSwitch.callback = callbackOnResponseParsed;
		}
		if (!originalRequest.updateSwitch.element) {
			originalRequest.updateSwitch.element = "wps-execute-autoUpdate";
		}

		$('#'+originalRequest.updateSwitch.element).click(function() {
			originalRequest.execute(originalRequest.updateSwitch.callback, originalRequest.updateSwitch);
		});
		$('#'+originalRequest.updateSwitch.element).css( 'cursor', 'pointer' );
	}
}

function handleResponse(responseData, domElement, originalRequest) {
	var factory = new ResponseFactory();
	var responseHandler = factory.resolveResponseHandler(responseData, originalRequest);

	if (responseHandler) {
		domElement.html(responseHandler.createMarkup());
	}
}

// using OpenLayers.Format.WPSCapabilities to read the capabilities
function getCapabilities() {
    OpenLayers.Request.GET({
        url: wps,
        params: {
            "SERVICE": "WPS",
            "REQUEST": "GetCapabilities"
        },
        success: function(response){
            capabilities = new OpenLayers.Format.WPSCapabilities().read(
                response.responseText
            );
            var dropdown = document.getElementById("processes");
            var offerings = capabilities.processOfferings, option;
            // populate the dropdown
            for (var p in offerings) {
                option = document.createElement("option");
                option.innerHTML = offerings[p].identifier;
                option.value = p;
                dropdown.appendChild(option);
            }
        }
    });
}

// using OpenLayers.Format.WPSDescribeProcess to get information about a
// process
function describeProcess() {
    var selection = this.options[this.selectedIndex].value;
    OpenLayers.Request.GET({
        url: wps,
        params: {
            "SERVICE": "WPS",
            "REQUEST": "DescribeProcess",
            "VERSION": capabilities.version,
            "IDENTIFIER": selection
        },
        success: function(response) {
            process = new OpenLayers.Format.WPSDescribeProcess().read(
                response.responseText
            ).processDescriptions[selection];
            buildForm();
        }
    });
}

// dynamically create a form from the process description
function buildForm() {
    document.getElementById("abstract").innerHTML = process["abstract"];
    document.getElementById("input").innerHTML = "
Input:
";
    document.getElementById("output").innerHTML = "";

    var inputs = process.dataInputs, supported = true,
        sld = "text/xml; subtype=sld/1.0.0",
        input;
    for (var i=0,ii=inputs.length; i<ii; ++i) {
        input = inputs[i];
        if (input.complexData) {
            var formats = input.complexData.supported.formats;
            if (formats["application/wkt"]) {
                addWKTInput(input);
            } else if (formats["text/xml; subtype=wfs-collection/1.0"]) {
                addWFSCollectionInput(input);
            } else if (formats["image/tiff"]) {
                addRasterInput(input);
            } else if (formats[sld]) {
                addXMLInput(input, sld);
            } else {
                supported = false;
            }
        } else if (input.boundingBoxData) {
            addBoundingBoxInput(input);
        } else if (input.literalData) {
            addLiteralInput(input);
        } else {
            supported = false;
        }
        if (input.minOccurs > 0) {
            document.getElementById("input").appendChild(document.createTextNode("* "));
        }
    }

    if (supported) {
        var executeButton = document.createElement("button");
        executeButton.innerHTML = "Execute";
        document.getElementById("input").appendChild(executeButton);
        executeButton.onclick = execute;
    } else {
        document.getElementById("input").innerHTML = '' +
            "Sorry, the WPS builder does not support the selected process." +
            "";
    }
}

// helper function to dynamically create a textarea for geometry (WKT) data
// input
function addWKTInput(input, previousSibling) {
    var name = input.identifier;
    var container = document.getElementById("input");
    var label = document.createElement("label");
    label["for"] = name;
    label.title = input["abstract"];
    label.innerHTML = name + " (select feature, then click field):";
    previousSibling && previousSibling.nextSibling ?
        container.insertBefore(label, previousSibling.nextSibling) :
        container.appendChild(label);
    var field = document.createElement("textarea");
    field.onclick = function () {
        if (layer.selectedFeatures.length) {
            this.innerHTML = new OpenLayers.Format.WKT().write(
                layer.selectedFeatures[0]
            );
        }
        createCopy(input, this, addWKTInput);
    };
    field.onblur = function() {
        input.data = field.value ? {
            complexData: {
                mimeType: "application/wkt",
                value: this.value
            }
        } : undefined;
    };
    field.title = input["abstract"];
    field.id = name;
    previousSibling && previousSibling.nextSibling ?
        container.insertBefore(field, previousSibling.nextSibling.nextSibling) :
        container.appendChild(field);
}

// helper function for xml input
function addXMLInput(input, type) {
    var name = input.identifier;
    var field = document.createElement("input");
    field.title = input["abstract"];
    field.value = name + " (" + type + ")";
    field.onblur = function() {
        input.data = field.value ? {
            complexData: {
                mimeType: type,
                value: this.value
            }
        } : undefined;
    };
    document.getElementById("input").appendChild(field);
}

// helper function to dynamically create a WFS collection reference input
function addWFSCollectionInput(input) {
    var name = input.identifier;
    var field = document.createElement("input");
    field.title = input["abstract"];
    field.value = name + " (layer on demo server)";
    addValueHandlers(field, function() {
        input.reference = field.value ? {
            mimeType: "text/xml; subtype=wfs-collection/1.0",
            href: "http://geoserver/wfs",
            method: "POST",
            body: {
                wfs: {
                    version: "1.0.0",
                    outputFormat: "GML2",
                    featureType: field.value
                }
            }
        } : undefined;
    });
    document.getElementById("input").appendChild(field);
}

// helper function to dynamically create a raster (GeoTIFF) url input
function addRasterInput(input) {
    var name = input.identifier;
    var field = document.createElement("input");
    field.title = input["abstract"];
    var url = window.location.href.split("?")[0];
    field.value = url.substr(0, url.lastIndexOf("/")+1) + "data/tazdem.tiff";
    document.getElementById("input").appendChild(field);
    (field.onblur = function() {
        input.reference = {
            mimeType: "image/tiff",
            href: field.value,
            method: "GET"
        };
    })();
}

// helper function to dynamically create a bounding box input
function addBoundingBoxInput(input) {
    var name = input.identifier;
    var field = document.createElement("input");
    field.title = input["abstract"];
    field.value = "left,bottom,right,top (EPSG:4326)";
    document.getElementById("input").appendChild(field);
    addValueHandlers(field, function() {
        input.boundingBoxData = {
            projection: "EPSG:4326",
            bounds: OpenLayers.Bounds.fromString(field.value)
        };
    });
}

// helper function to create a literal input textfield or dropdown
function addLiteralInput(input, previousSibling) {
    var name = input.identifier;
    var container = document.getElementById("input");
    var anyValue = input.literalData.anyValue;
    // anyValue means textfield, otherwise we create a dropdown
    var field = document.createElement(anyValue ? "input" : "select");
    field.id = name;
    field.title = input["abstract"];
    previousSibling && previousSibling.nextSibling ?
        container.insertBefore(field, previousSibling.nextSibling) :
        container.appendChild(field);
    if (anyValue) {
        var dataType = input.literalData.dataType;
        field.value = name + (dataType ? " (" + dataType + ")" : "");
        addValueHandlers(field, function() {
            input.data = field.value ? {
                literalData: {
                    value: field.value
                }
            } : undefined;
            createCopy(input, field, addLiteralInput);
        });
    } else {
        var option;
        option = document.createElement("option");
        option.innerHTML = name;
        field.appendChild(option);
        for (var v in input.literalData.allowedValues) {
            option = document.createElement("option");
            option.value = v;
            option.innerHTML = v;
            field.appendChild(option);
        }
        field.onchange = function() {
            createCopy(input, field, addLiteralInput);
            input.data = this.selectedIndex ? {
                literalData: {
                    value: this.options[this.selectedIndex].value
                }
            } : undefined;
        };
    }
}

// if maxOccurs is > 1, this will add a copy of the field
function createCopy(input, field, fn) {
    if (input.maxOccurs && input.maxOccurs > 1 && !field.userSelected) {
        // add another copy of the field - we don't check maxOccurs
        field.userSelected = true;
        var newInput = OpenLayers.Util.extend({}, input);
        // we recognize copies by the occurrence property
        newInput.occurrence = (input.occurrence || 0) + 1;
        process.dataInputs.push(newInput);
        fn(newInput, field);
    }
}

// helper function for adding events to form fields
function addValueHandlers(field, onblur) {
    field.onclick = function() {
        if (!this.initialValue) {
            this.initialValue = this.value;
            this.value = "";
        }
    };
    field.onblur = function() {
        if (!this.value) {
            this.value = this.initialValue;
            delete this.initialValue;
        }
        onblur.apply(this, arguments);
    };
}

// execute the process
function execute() {
    var output = process.processOutputs[0];
    var input;
    // remove occurrences that the user has not filled out
    for (var i=process.dataInputs.length-1; i>=0; --i) {
        input = process.dataInputs[i];
        if ((input.minOccurs === 0 || input.occurrence) && !input.data && !input.reference) {
            OpenLayers.Util.removeItem(process.dataInputs, input);
        }
    }
    process.responseForm = {
        responseDocument: {
        	storeExecuteResponse: true,
        	outputs: [{
        		asReference: true,
        		mimeType: "application/PDF",
        		identifier: output.identifier
            }]
        }
    };
    OpenLayers.Request.POST({
        url: wps,
        data: new OpenLayers.Format.WPSExecute().write(process),
        success: showOutput2
    });
}

// add the process's output to the page
function showOutput2(response, url, data) {

	var settings = {
			url: wps,
			method: "POST",
			domElement: $('#capabilitiesByClick'),
			data: new OpenLayers.Format.WPSExecute().write(process),
			requestType: "Execute"
	}

	var originalRequest = new PostRequest(settings);

	//var statusLocation = response.responseXML.documentElement.getAttribute("statusLocation");

	handleResponse(response.responseXML, $('#capabilitiesByClick'), originalRequest);

    var result = document.getElementById("output");
    result.innerHTML = "
Output:
";
    var features;
    var contentType = response.getResponseHeader("Content-Type");
    if (contentType == "application/wkt") {
        features = new OpenLayers.Format.WKT().read(response.responseText);
    } else if (contentType == "text/xml; subtype=wfs-collection/1.0") {
        features = new OpenLayers.Format.WFST.v1_0_0().read(response.responseText);
    }
    if (features && (features instanceof OpenLayers.Feature.Vector || features.length)) {
        layer.addFeatures(features);
        result.innerHTML += "The result should also be visible on the map.";
    }
    result.innerHTML += "<textarea>" + response.responseText + "</textarea>";
}

// add the process's output to the page
function showOutput(response) {

	var statusLocation = response.responseXML.documentElement.getAttribute("statusLocation");

	handleResponse(response.responseXML, '#capabilitiesByClick', statusLocation);

    var result = document.getElementById("output");
    result.innerHTML = "
Output:
";
    var features;
    var contentType = response.getResponseHeader("Content-Type");
    if (contentType == "application/wkt") {
        features = new OpenLayers.Format.WKT().read(response.responseText);
    } else if (contentType == "text/xml; subtype=wfs-collection/1.0") {
        features = new OpenLayers.Format.WFST.v1_0_0().read(response.responseText);
    }
    if (features && (features instanceof OpenLayers.Feature.Vector || features.length)) {
        layer.addFeatures(features);
        result.innerHTML += "The result should also be visible on the map.";
    }
    result.innerHTML += "<textarea>" + response.responseText + "</textarea>";
}

/*
 * jQuery plugin definitions
 */
(function($) {

	$.fn.extend({
		wpsCall : function( options ) {
	    	var settings;
	    	if (options && options.viaUrl) {
	    		/*
	    		 * Call via GET parameters
	    		 */
	    		settings = $.extend(resolveGetParameters(), {method: METHOD_GET});
	    	}
	    	else {
	            /*
	             * Custom User Call
	             */
	            settings = $.extend({
	                method: METHOD_GET
	            }, options);
	    	}

	    	if (assertValidState(settings)) {
	    		return this.each( function() {
	            	var requestSettings = $.extend({
	                    domElement: $(this)
	                }, settings);

	            	var request = resolveRequest(requestSettings.requestType, requestSettings.method,
	            			requestSettings);
	            	request.execute(callbackOnResponseParsed, options.updateSwitch);
	            });
	    	}

	    	return this.each();
	    }
	});

	$.extend({
		wpsSetup : function(setup) {
			if (setup.reset) {
				wpsResetSetup();
				return;
			}

	    	if (setup.templates) {
	    		var templates = setup.templates;
	    		if (templates.capabilities) {
	    			if (typeof templates.capabilities == 'string') {
	    				USER_TEMPLATE_CAPABILITIES_MARKUP = templates.capabilities;
	    			}
	        	}
	        	if (templates.processDescription) {
	        		if (typeof templates.processDescription == 'string') {
	        			USER_TEMPLATE_PROCESS_DESCRIPTION_MARKUP = templates.processDescription;
	        		}
	        	}
	        	if (templates.executeResponse) {
	        		if (typeof templates.executeResponse == 'string') {
	        			USER_TEMPLATE_EXECUTE_RESPONSE_MARKUP = templates.executeResponse;
	        		}
	        	}
	    	}

	    	if (setup.proxy) {
	    		USE_PROXY = true;
	    		PROXY_URL = setup.proxy.url;
	    		PROXY_TYPE = setup.proxy.type;
	    	}
	    }
	});

}(jQuery));
<|endoftext|>


<commit_before>$(document).ready(function() {
  autofillWorkaround();

  var lang = "en";

  // fill fields from URL and remember language
  (new URL(window.location.href)).searchParams.forEach((x, y) => {
    if (y == "lang") {
      lang = x;
    }
    var field = document.getElementById(y);
    if (field) {
      document.getElementById(y).value = x;
    }
  });

  // // set URL to reach UI
  // if ($('#uiUrl')) {
  // var url = window.location;
  // var paths = url.pathname.split('/');
  // var guiUrl = url .protocol + "//" + url.host + "/";
  // paths.slice(0,paths.length -1).forEach((x) => guiUrl += x + "/");
  // $('#uiUrl').val(guiUrl);
  // }

  var preisindikationInCent = 0;

  // $('#birthdate').on('change', function() {
  // console.log($('#birthdate').val());
  // });

  // Removed Auth
  // beforeSend = function(xhr) {
  // xhr.setRequestHeader('Authorization', 'Basic ' +
  // window.btoa(unescape(encodeURIComponent('${camunda.rest.username}' + ':'
  // + '${camunda.rest.password}'))))
  // };

  var pathArray = window.location.pathname.split('/');
  var baseUrl = window.location.protocol + "//" + window.location.host + "/" + pathArray[1] + "/api";

  // Start single Process Instance
  $('#triggerStartApplication').click(function() {
    var neuantrag = {
      "applicant": {
        "name": $('#applicant').val(),
        "gender": $('#selectSex').val(),
        "birthday": $('#birthdate').val() + "T00:00:00",
        "email": $('#email').val()
      },
      "employment": $('#employment').val(),
      "category": $('#category').val(),
      "priceIndicationInCent": getPrice() * 100,
      "corporation": "Camuntelia"
      // ,
      // "uiUrl": $('#uiUrl').val()
    };

    var data = JSON.stringify(neuantrag);

    console.log(data);

    if (neuantrag.applicant.name === '' || neuantrag.applicant.email === '') {
      return undefined;
    }

    $.ajax({
      type: 'POST',
      url: baseUrl + "/new-application/" + lang,
      data: data,
      contentType: 'application/json; charset=utf-8',
      success: function(result) {
        $('#applicationId').text(result);
        $('#applicationReceived').toggle();
        $('#fieldsetForm').toggle();
      },
      crossDomain: true,
    });

  });

  // correlate message for Antrag
  $('#triggerUploadDocuments').click(function() {
    debugger;
    var fileUpload = $('#documentToUpload').get(0);

    var fileVar = {};
    if (typeof FileReader === 'function' && fileUpload.files.length > 0) {
      var reader = new FileReader();
      reader.onloadend = (function(fileUpload) {
        return function(e) {
          var binary = '';
          var bytes = new Uint8Array(e.target.result);
          var len = bytes.byteLength;
          for (var j = 0; j < len; j++) {
            binary += String.fromCharCode(bytes[j]);
          }
          fileVar.value = btoa(binary);

          // set file metadata as value info
          fileVar.type = 'File';
          fileVar.valueInfo = {
            filename: fileUpload.files[0].name,
            mimeType: fileUpload.files[0].type
          };

          callCallback();
        };
      })(fileUpload);
      reader.readAsArrayBuffer(fileUpload.files[0]);
    };

    var callCallback = function() {
      var data = JSON.stringify(fileVar);
      var url = baseUrl + "/document/" + $('#referenceId').val();
      $.ajax({
        type: 'POST',
        url: url,
        data: data,
        contentType: 'application/json; charset=utf-8',
        dataType: 'json',
        success: function(result) {
          $('#documentsReceived').toggle();
          $('#fieldsetForm').toggle();
        },
        crossDomain: true,
      });
    };

  });

  function chooseCategory(categoryDe, categoryEn) {
    var isGerman = lang.endsWith('de');
    $('#category').val(isGerman ? categoryDe : categoryEn);
    calculatePrice(preisindikationInCent);
  }

  function scrollToAnchor() {
    if (this.hash !== "") {

      // Store hash
      var hash = this.hash;

      // Using jQuery's animate() method to add smooth page scroll
      // The optional number (800) specifies the number of milliseconds it takes to scroll to the specified area
      $('html, body').animate({
        scrollTop: $('#fieldsetForm').offset().top - 85
      }, 800, function() {

        // Add hash (#) to URL when done scrolling (default click behavior)
        window.location.hash = hash;
      });
    } // End if
  }

  //choose category on click
  $('#basicButton').click(function() {
    chooseCategory('Basispaket', 'Basic Package');
    scrollToAnchor();
  });

  $('#standardButton').click(function() {
    chooseCategory('Standard Paket', 'Standard Package');
    scrollToAnchor();
  });

  $('#premiumButton').click(function() {
    chooseCategory('Premium Paket', 'Premium Package');
    scrollToAnchor();
  });

  $('#category').on('change, keyup, mouseup', function() {
    calculatePrice(preisindikationInCent);
  });

  $('#employment').on('change, keyup, mouseup', function() {
    calculatePrice(preisindikationInCent);
  });

  function isEqualToOneOf(objectToBeChecked) {
    for (var i = 1; i < arguments.length; i++) {
      if (arguments[i] == objectToBeChecked) {
        return true;
      }
    }
    return false;
  }

  function calculatePrice(preisindikationInCent) {

    var category = $('#category').val();
    var employment = $('#employment').val();

    if (isEqualToOneOf(category, 'Basispaket', 'Basic Package')) {
      preisindikationInCent = 3;
    } else if (isEqualToOneOf(category, 'Standard Paket', 'Standard Package')) {
      preisindikationInCent = 5;
    } else {
      preisindikationInCent = 15;
    }
    preisindikationInCent = Math.round(preisindikationInCent);
    $('#priceIndicationInCent').val(preisindikationInCent + ",00 EUR");
  }

  function getPrice() {
    var preisindikationInCent;

    var category = $('#category').val();
    var employment = $('#employment').val();

    if (isEqualToOneOf(category, 'Basispaket', 'Basic Package')) {
      preisindikationInCent = 3;
    } else if (isEqualToOneOf(category, 'Standard Paket', 'Standard Package')) {
      preisindikationInCent = 5;
    } else {
      preisindikationInCent = 15;
    }

    return preisindikationInCent;
  }
});

function autofillWorkaround() {
  /**
   * Autofill event polyfill ##version:1.0.0##
   * (c) 2014 Google, Inc.
   * License: MIT
   */
  (function(window) {
    var $ = window.jQuery || window.angular.element;
    var rootElement = window.document.documentElement,
      $rootElement = $(rootElement);

    addGlobalEventListener('change', markValue);
    addValueChangeByJsListener(markValue);

    $.prototype.checkAndTriggerAutoFillEvent = jqCheckAndTriggerAutoFillEvent;

    // Need to use blur and not change event
    // as Chrome does not fire change events in all cases an input is changed
    // (e.g. when starting to type and then finish the input by auto filling a username)
    addGlobalEventListener('blur', function(target) {
      // setTimeout needed for Chrome as it fills other
      // form fields a little later...
      window.setTimeout(function() {
        findParentForm(target).find('input').checkAndTriggerAutoFillEvent();
      }, 20);
    });

    window.document.addEventListener('DOMContentLoaded', function() {
      // The timeout is needed for Chrome as it auto fills
      // login forms some time after DOMContentLoaded!
      window.setTimeout(function() {
        $rootElement.find('input').checkAndTriggerAutoFillEvent();
      }, 200);
    }, false);

    return;

    // ----------

    function jqCheckAndTriggerAutoFillEvent() {
      var i, el;
      for (i = 0; i < this.length; i++) {
        el = this[i];
        if (!valueMarked(el)) {
          markValue(el);
          triggerChangeEvent(el);
        }
      }
    }

    function valueMarked(el) {
      var val = el.value,
        $$currentValue = el.$$currentValue;
      if (!val && !$$currentValue) {
        return true;
      }
      return val === $$currentValue;
    }

    function markValue(el) {
      el.$$currentValue = el.value;
    }

    function addValueChangeByJsListener(listener) {
      var jq = window.jQuery || window.angular.element,
        jqProto = jq.prototype;
      var _val = jqProto.val;
      jqProto.val = function(newValue) {
        var res = _val.apply(this, arguments);
        if (arguments.length > 0) {
          forEach(this, function(el) {
            listener(el, newValue);
          });
        }
        return res;
      }
    }

    function addGlobalEventListener(eventName, listener) {
      // Use a capturing event listener so that
      // we also get the event when it's stopped!
      // Also, the blur event does not bubble.
      rootElement.addEventListener(eventName, onEvent, true);

      function onEvent(event) {
        var target = event.target;
        listener(target);
      }
    }

    function findParentForm(el) {
      while (el) {
        if (el.nodeName === 'FORM') {
          return $(el);
        }
        el = el.parentNode;
      }
      return $();
    }

    function forEach(arr, listener) {
      if (arr.forEach) {
        return arr.forEach(listener);
      }
      var i;
      for (i = 0; i < arr.length; i++) {
        listener(arr[i]);
      }
    }

    function triggerChangeEvent(element) {
      var doc = window.document;
      var event = doc.createEvent("HTMLEvents");
      event.initEvent("change", true, true);
      element.dispatchEvent(event);
    }

  })(window);
}<commit_msg>hide unchosen products after sending request and show filename uploaded<commit_after>$(document).ready(function() {
  autofillWorkaround();

  var lang = "en";

  // fill fields from URL and remember language
  (new URL(window.location.href)).searchParams.forEach((x, y) => {
    if (y == "lang") {
      lang = x;
    }
    var field = document.getElementById(y);
    if (field) {
      document.getElementById(y).value = x;
    }
  });

  // // set URL to reach UI
  // if ($('#uiUrl')) {
  // var url = window.location;
  // var paths = url.pathname.split('/');
  // var guiUrl = url .protocol + "//" + url.host + "/";
  // paths.slice(0,paths.length -1).forEach((x) => guiUrl += x + "/");
  // $('#uiUrl').val(guiUrl);
  // }

  var preisindikationInCent = 0;

  // $('#birthdate').on('change', function() {
  // console.log($('#birthdate').val());
  // });

  // Removed Auth
  // beforeSend = function(xhr) {
  // xhr.setRequestHeader('Authorization', 'Basic ' +
  // window.btoa(unescape(encodeURIComponent('${camunda.rest.username}' + ':'
  // + '${camunda.rest.password}'))))
  // };

  var pathArray = window.location.pathname.split('/');
  var baseUrl = window.location.protocol + "//" + window.location.host + "/" + pathArray[1] + "/api";

  // Start single Process Instance
  $('#triggerStartApplication').click(function(evt) {
    var neuantrag = {
      "applicant": {
        "name": $('#applicant').val(),
        "gender": $('#selectSex').val(),
        "birthday": $('#birthdate').val() + "T00:00:00",
        "email": $('#email').val()
      },
      "employment": $('#employment').val(),
      "category": $('#category').val(),
      "priceIndicationInCent": getPrice() * 100,
      "corporation": "Camuntelia"
    };

    var data = JSON.stringify(neuantrag);

    console.log(data);

    if (neuantrag.applicant.name === '' || neuantrag.applicant.email === '') {
      return undefined;
    }

    $.ajax({
      type: 'POST',
      url: baseUrl + "/new-application/" + lang,
      data: data,
      contentType: 'application/json; charset=utf-8',
      success: function(result) {
        $('#applicationId').text(result);
        $('#applicationReceived').height($('#fieldsetForm').css('height'));
        $('#applicationReceived').toggle();
        $('#fieldsetForm').toggle();
      },
      crossDomain: true,
    });

    var remaining = neuantrag.category;

    var divsToHide = ['basic', 'standard', 'premium']

    divsToHide = divsToHide.filter(elem => {
      var categoryIsEqual = remaining.toLowerCase().substring(0, 4) === elem.substring(0, 4);
      if (categoryIsEqual)
        remaining = elem;
      return !categoryIsEqual;
    });

    divsToHide.forEach(name => {
      $('#' + name).remove();
    });

    $('#' + remaining).css('margin', 'auto');
    $('#' + remaining + 'Button').remove();

    scrollToAnchor(200);

    evt.preventDefault();
  });

  // correlate message for Antrag
  $('#triggerUploadDocuments').click(function() {
    debugger;
    var fileUpload = $('#documentToUpload').get(0);

    var fileVar = {};
    if (typeof FileReader === 'function' && fileUpload.files.length > 0) {
      var reader = new FileReader();
      reader.onloadend = (function(fileUpload) {
        return function(e) {
          var binary = '';
          var bytes = new Uint8Array(e.target.result);
          var len = bytes.byteLength;
          for (var j = 0; j < len; j++) {
            binary += String.fromCharCode(bytes[j]);
          }
          fileVar.value = btoa(binary);

          // set file metadata as value info
          fileVar.type = 'File';
          fileVar.valueInfo = {
            filename: fileUpload.files[0].name,
            mimeType: fileUpload.files[0].type
          };

          callCallback();
        };
      })(fileUpload);
      reader.readAsArrayBuffer(fileUpload.files[0]);
    };

    var callCallback = function() {
      var data = JSON.stringify(fileVar);
      var url = baseUrl + "/document/" + $('#referenceId').val();
      $.ajax({
        type: 'POST',
        url: url,
        data: data,
        contentType: 'application/json; charset=utf-8',
        dataType: 'json',
        success: function(result) {
          $('#documentsReceived').toggle();
          $('#fieldsetForm').toggle();
        },
        crossDomain: true,
      });
    };

  });

  function chooseCategory(categoryDe, categoryEn) {
    var isGerman = lang.endsWith('de');
    $('#category').val(isGerman ? categoryDe : categoryEn);
    calculatePrice(preisindikationInCent);
  }

  function scrollToAnchor() {
    if (this.hash !== "") {

      // Store hash
      var hash = this.hash;

      // Using jQuery's animate() method to add smooth page scroll
      // The optional number (800) specifies the number of milliseconds it takes to scroll to the specified area
      $('html, body').animate({
        scrollTop: $('#fieldsetForm').offset().top - 85
      }, arguments[0] !== undefined ? arguments[0] : 800, function() {

        // Add hash (#) to URL when done scrolling (default click behavior)
        window.location.hash = hash;
      });
    } // End if
  }

  //choose category on click
  $('#basicButton').click(function() {
    chooseCategory('Basispaket', 'Basic Package');
    scrollToAnchor();
  });

  $('#standardButton').click(function() {
    chooseCategory('Standard Paket', 'Standard Package');
    scrollToAnchor();
  });

  $('#premiumButton').click(function() {
    chooseCategory('Premium Paket', 'Premium Package');
    scrollToAnchor();
  });

  $('#category').on('change, keyup, mouseup', function() {
    calculatePrice(preisindikationInCent);
  });

  $('#employment').on('change, keyup, mouseup', function() {
    calculatePrice(preisindikationInCent);
  });

  $('#documentToUpload').on('change', function() {
    $('#fileDesc').css('border-bottom', '1px solid blue');
    var text = $('#documentToUpload').val().match(/\\[\w-\s]+\.\w+/g).toString().substring(1);
    if (text.length > 19)
      text = '...' + text.substring(text.length - 16);
    $('#fileDesc').text(text);
  });

  function isEqualToOneOf(objectToBeChecked) {

    for (var i = 1; i < arguments.length; i++) {
      if (arguments[i] == objectToBeChecked) {
        return true;
      }
    }
    return false;
  }

  function calculatePrice(preisindikationInCent) {

    var category = $('#category').val();
    var employment = $('#employment').val();

    if (isEqualToOneOf(category, 'Basispaket', 'Basic Package')) {
      preisindikationInCent = 3;
    } else if (isEqualToOneOf(category, 'Standard Paket', 'Standard Package')) {
      preisindikationInCent = 5;
    } else {
      preisindikationInCent = 15;
    }
    preisindikationInCent = Math.round(preisindikationInCent);
    $('#priceIndicationInCent').val(preisindikationInCent + ",00 EUR");
  }

  function getPrice() {
    var preisindikationInCent;

    var category = $('#category').val();
    var employment = $('#employment').val();

    if (isEqualToOneOf(category, 'Basispaket', 'Basic Package')) {
      preisindikationInCent = 3;
    } else if (isEqualToOneOf(category, 'Standard Paket', 'Standard Package')) {
      preisindikationInCent = 5;
    } else {
      preisindikationInCent = 15;
    }

    return preisindikationInCent;
  }
});

function autofillWorkaround() {
  /**
   * Autofill event polyfill ##version:1.0.0##
   * (c) 2014 Google, Inc.
   * License: MIT
   */
  (function(window) {
    var $ = window.jQuery || window.angular.element;
    var rootElement = window.document.documentElement,
      $rootElement = $(rootElement);

    addGlobalEventListener('change', markValue);
    addValueChangeByJsListener(markValue);

    $.prototype.checkAndTriggerAutoFillEvent = jqCheckAndTriggerAutoFillEvent;

    // Need to use blur and not change event
    // as Chrome does not fire change events in all cases an input is changed
    // (e.g. when starting to type and then finish the input by auto filling a username)
    addGlobalEventListener('blur', function(target) {
      // setTimeout needed for Chrome as it fills other
      // form fields a little later...
      window.setTimeout(function() {
        findParentForm(target).find('input').checkAndTriggerAutoFillEvent();
      }, 20);
    });

    window.document.addEventListener('DOMContentLoaded', function() {
      // The timeout is needed for Chrome as it auto fills
      // login forms some time after DOMContentLoaded!
      window.setTimeout(function() {
        $rootElement.find('input').checkAndTriggerAutoFillEvent();
      }, 200);
    }, false);

    return;

    // ----------

    function jqCheckAndTriggerAutoFillEvent() {
      var i, el;
      for (i = 0; i < this.length; i++) {
        el = this[i];
        if (!valueMarked(el)) {
          markValue(el);
          triggerChangeEvent(el);
        }
      }
    }

    function valueMarked(el) {
      var val = el.value,
        $$currentValue = el.$$currentValue;
      if (!val && !$$currentValue) {
        return true;
      }
      return val === $$currentValue;
    }

    function markValue(el) {
      el.$$currentValue = el.value;
    }

    function addValueChangeByJsListener(listener) {
      var jq = window.jQuery || window.angular.element,
        jqProto = jq.prototype;
      var _val = jqProto.val;
      jqProto.val = function(newValue) {
        var res = _val.apply(this, arguments);
        if (arguments.length > 0) {
          forEach(this, function(el) {
            listener(el, newValue);
          });
        }
        return res;
      }
    }

    function addGlobalEventListener(eventName, listener) {
      // Use a capturing event listener so that
      // we also get the event when it's stopped!
      // Also, the blur event does not bubble.
      rootElement.addEventListener(eventName, onEvent, true);

      function onEvent(event) {
        var target = event.target;
        listener(target);
      }
    }

    function findParentForm(el) {
      while (el) {
        if (el.nodeName === 'FORM') {
          return $(el);
        }
        el = el.parentNode;
      }
      return $();
    }

    function forEach(arr, listener) {
      if (arr.forEach) {
        return arr.forEach(listener);
      }
      var i;
      for (i = 0; i < arr.length; i++) {
        listener(arr[i]);
      }
    }

    function triggerChangeEvent(element) {
      var doc = window.document;
      var event = doc.createEvent("HTMLEvents");
      event.initEvent("change", true, true);
      element.dispatchEvent(event);
    }

  })(window);
}<|endoftext|>


<commit_before>// @flow

import React from 'react'
import cx from 'classnames'
import {connect} from 'react-redux'
import {FlatButton} from '../../components/button'
import {Icon} from '../../components/icon'
import Requirement from './requirement'
import ProgressBar from '../../components/progress-bar'
import {close, chevronUp, chevronDown} from '../../icons/ionicons'
import {pathToOverride, type EvaluationResult} from '@gob/examine-student'
import {Student, type AreaQuery} from '@gob/object-student'
import {checkStudentAgainstArea} from '../../workers/check-student'
import {loadArea} from '../../helpers/load-area'
import {
	changeStudent,
	type ChangeStudentFunc,
} from '../../redux/students/actions/change'

import './area-of-study.scss'

type Props = {
	areaOfStudy: AreaQuery,
	showCloseButton: boolean,
	showEditButton: boolean,
	student: Student,
	changeStudent: ChangeStudentFunc,
}

type State = {|
	isOpen: boolean,
	confirmRemoval: boolean,
	examining: boolean,
	results: ?EvaluationResult,
	error: ?string,
|}

class AreaOfStudy extends React.Component<Props, State> {
	state = {
		isOpen: false,
		confirmRemoval: false,
		examining: false,
		results: null,
		error: null,
	}

	componentDidMount() {
		this.startExamination()
	}

	startExamination = async () => {
		this.setState(() => ({examining: true}))
		let area = await loadArea(this.props.areaOfStudy)

		if (area.error) {
			this.setState(() => ({examining: false, error: area.message}))
			return
		}

		let results = await checkStudentAgainstArea(
			this.props.student,
			area.data,
		)
		this.setState(() => ({examining: false, results}))
	}

	startRemovalConfirmation = (ev: Event) => {
		ev.preventDefault()
		this.setState({confirmRemoval: true})
	}

	endRemovalConfirmation = (ev: Event) => {
		ev.preventDefault()
		this.setState({confirmRemoval: false})
	}

	toggleAreaExpansion = (ev: Event) => {
		ev.preventDefault()
		this.setState({isOpen: !this.state.isOpen})
	}

	addOverride = (path: string[], ev: Event) => {
		ev.preventDefault()
		const codifiedPath = pathToOverride(path)
		let s = this.props.student.setOverride(codifiedPath, true)
		this.props.changeStudent(s)
	}

	removeOverride = (path: string[], ev: Event) => {
		ev.preventDefault()
		const codifiedPath = pathToOverride(path)
		let s = this.props.student.removeOverride(codifiedPath)
		this.props.changeStudent(s)
	}

	toggleOverride = (path: string[], ev: Event) => {
		ev.preventDefault()
		const codifiedPath = pathToOverride(path)

		if (this.props.student.hasOverride(codifiedPath)) {
			let s = this.props.student.removeOverride(codifiedPath)
			this.props.changeStudent(s)
		} else {
			let s = this.props.student.setOverride(codifiedPath, true)
			this.props.changeStudent(s)
		}
	}

	removeArea = (ev: SyntheticEvent<HTMLButtonElement>) => {
		ev.preventDefault()
		let s = this.props.student.removeArea(this.props.areaOfStudy)
		this.props.changeStudent(s)
	}

	render() {
		let props = this.props
		let {isOpen, confirmRemoval: showConfirmRemoval} = this.state

		let {name = 'Unknown Area'} = props.areaOfStudy

		// TODO: fix slugs
		// let slug = ''
		// if (this.state.results) {
		// 	slug = this.state.results.slug
		// }

		let progressAt = 0
		let progressOf = 1

		let error = false

		if (this.state.results && this.state.results.progress) {
			progressAt = this.state.results.progress.at
			progressAt = this.state.results.progress.of
		}

		if (this.state.results && this.state.results.error) {
			error = this.state.results.error
		}

		const summary = (
			<>

						<CatalogLink slug={'' /*slug*/} name={name} />

						{props.showCloseButton && (
							<FlatButton
								className="area--remove-button"
								onClick={this.startRemovalConfirmation}
							>
								<Icon>{close}</Icon>
							</FlatButton>
						)}
						<Icon className="area--open-indicator">
							{isOpen ? chevronUp : chevronDown}
						</Icon>

				<ProgressBar
					className={cx('area--progress', {error: Boolean(error)})}
					colorful={true}
					value={progressAt}
					max={progressOf}
				/>
			</>
		)

		const removalConfirmation = (

					Remove {name}?

					<FlatButton
						className="area--actually-remove-area"
						onClick={this.removeArea}
					>
						Remove
					</FlatButton>
					<FlatButton onClick={this.endRemovalConfirmation}>
						Cancel
					</FlatButton>

		)

		let contents = null
		if (this.state.examining) {
			contents =
Loading…

		} else {
			contents = (
				<AreaDetails
					results={this.state.results}
					area={props.areaOfStudy}
				/>
			)
		}

		return (
			<>

					{showConfirmRemoval ? removalConfirmation : summary}

				{isOpen && !showConfirmRemoval && contents}
			</>
		)
	}
}

const CatalogLink = ({slug, name}: {slug: ?string, name: string}) => {
	if (!slug) {
		return {name}
	}

	return (
		<a
			className="catalog-link"
			href={`http://catalog.stolaf.edu/academic-programs/${slug}/`}
			target="_blank"
			rel="noopener noreferrer"
			title="View in the St. Olaf Catalog"
		>
			{name}

	)
}

function AreaDetails(props: {results: ?EvaluationResult, area: AreaQuery}) {
	if (!props.results) {
		return null
	}

	let {type, name} = props.area
	let {details, error = ''} = props.results

	if (error) {
		return (

				{error} {':('}

		)
	}

	return (
		<Requirement
			info={details}
			topLevel
			onAddOverride={this.addOverride}
			onRemoveOverride={this.removeOverride}
			onToggleOverride={this.toggleOverride}
			path={[type, name]}
		/>
	)
}

const connected = connect(
	undefined,
	{changeStudent},
)(AreaOfStudy)

export {connected as AreaOfStudy}
<commit_msg>fix passing add/remove/toggleOverride to AreaDetails<commit_after>// @flow

import React from 'react'
import cx from 'classnames'
import {connect} from 'react-redux'
import {FlatButton} from '../../components/button'
import {Icon} from '../../components/icon'
import Requirement from './requirement'
import ProgressBar from '../../components/progress-bar'
import {close, chevronUp, chevronDown} from '../../icons/ionicons'
import {pathToOverride, type EvaluationResult} from '@gob/examine-student'
import {Student, type AreaQuery} from '@gob/object-student'
import {checkStudentAgainstArea} from '../../workers/check-student'
import {loadArea} from '../../helpers/load-area'
import {
	changeStudent,
	type ChangeStudentFunc,
} from '../../redux/students/actions/change'

import './area-of-study.scss'

type Props = {
	areaOfStudy: AreaQuery,
	showCloseButton: boolean,
	showEditButton: boolean,
	student: Student,
	changeStudent: ChangeStudentFunc,
}

type State = {|
	isOpen: boolean,
	confirmRemoval: boolean,
	examining: boolean,
	results: ?EvaluationResult,
	error: ?string,
|}

class AreaOfStudy extends React.Component<Props, State> {
	state = {
		isOpen: false,
		confirmRemoval: false,
		examining: false,
		results: null,
		error: null,
	}

	componentDidMount() {
		this.startExamination()
	}

	startExamination = async () => {
		this.setState(() => ({examining: true}))
		let area = await loadArea(this.props.areaOfStudy)

		if (area.error) {
			this.setState(() => ({examining: false, error: area.message}))
			return
		}

		let results = await checkStudentAgainstArea(
			this.props.student,
			area.data,
		)
		this.setState(() => ({examining: false, results}))
	}

	startRemovalConfirmation = (ev: Event) => {
		ev.preventDefault()
		this.setState({confirmRemoval: true})
	}

	endRemovalConfirmation = (ev: Event) => {
		ev.preventDefault()
		this.setState({confirmRemoval: false})
	}

	toggleAreaExpansion = (ev: Event) => {
		ev.preventDefault()
		this.setState({isOpen: !this.state.isOpen})
	}

	addOverride = (path: string[], ev: Event) => {
		ev.preventDefault()
		const codifiedPath = pathToOverride(path)
		let s = this.props.student.setOverride(codifiedPath, true)
		this.props.changeStudent(s)
	}

	removeOverride = (path: string[], ev: Event) => {
		ev.preventDefault()
		const codifiedPath = pathToOverride(path)
		let s = this.props.student.removeOverride(codifiedPath)
		this.props.changeStudent(s)
	}

	toggleOverride = (path: string[], ev: Event) => {
		ev.preventDefault()
		const codifiedPath = pathToOverride(path)

		if (this.props.student.hasOverride(codifiedPath)) {
			let s = this.props.student.removeOverride(codifiedPath)
			this.props.changeStudent(s)
		} else {
			let s = this.props.student.setOverride(codifiedPath, true)
			this.props.changeStudent(s)
		}
	}

	removeArea = (ev: SyntheticEvent<HTMLButtonElement>) => {
		ev.preventDefault()
		let s = this.props.student.removeArea(this.props.areaOfStudy)
		this.props.changeStudent(s)
	}

	render() {
		let props = this.props
		let {isOpen, confirmRemoval: showConfirmRemoval} = this.state

		let {name = 'Unknown Area'} = props.areaOfStudy

		// TODO: fix slugs
		// let slug = ''
		// if (this.state.results) {
		// 	slug = this.state.results.slug
		// }

		let progressAt = 0
		let progressOf = 1

		let error = false

		if (this.state.results && this.state.results.progress) {
			progressAt = this.state.results.progress.at
			progressAt = this.state.results.progress.of
		}

		if (this.state.results && this.state.results.error) {
			error = this.state.results.error
		}

		const summary = (
			<>

						<CatalogLink slug={'' /*slug*/} name={name} />

						{props.showCloseButton && (
							<FlatButton
								className="area--remove-button"
								onClick={this.startRemovalConfirmation}
							>
								<Icon>{close}</Icon>
							</FlatButton>
						)}
						<Icon className="area--open-indicator">
							{isOpen ? chevronUp : chevronDown}
						</Icon>

				<ProgressBar
					className={cx('area--progress', {error: Boolean(error)})}
					colorful={true}
					value={progressAt}
					max={progressOf}
				/>
			</>
		)

		const removalConfirmation = (

					Remove {name}?

					<FlatButton
						className="area--actually-remove-area"
						onClick={this.removeArea}
					>
						Remove
					</FlatButton>
					<FlatButton onClick={this.endRemovalConfirmation}>
						Cancel
					</FlatButton>

		)

		let contents = null
		if (this.state.examining) {
			contents =
Loading…

		} else {
			contents = (
				<AreaDetails
					results={this.state.results}
					area={props.areaOfStudy}
					addOverride={this.addOverride}
					removeOverride={this.removeOverride}
					toggleOverride={this.toggleOverride}
				/>
			)
		}

		return (
			<>

					{showConfirmRemoval ? removalConfirmation : summary}

				{isOpen && !showConfirmRemoval && contents}
			</>
		)
	}
}

const CatalogLink = ({slug, name}: {slug: ?string, name: string}) => {
	if (!slug) {
		return {name}
	}

	return (
		<a
			className="catalog-link"
			href={`http://catalog.stolaf.edu/academic-programs/${slug}/`}
			target="_blank"
			rel="noopener noreferrer"
			title="View in the St. Olaf Catalog"
		>
			{name}

	)
}

function AreaDetails(props: {
	results: ?EvaluationResult,
	area: AreaQuery,
	addOverride: (Array<string>, Event) => mixed,
	removeOverride: (Array<string>, Event) => mixed,
	toggleOverride: (Array<string>, Event) => mixed,
}) {
	if (!props.results) {
		return null
	}

	let {type, name} = props.area
	let {details, error = ''} = props.results

	if (error) {
		return (

				{error} {':('}

		)
	}

	return (
		<Requirement
			info={details}
			topLevel
			onAddOverride={props.addOverride}
			onRemoveOverride={props.removeOverride}
			onToggleOverride={props.toggleOverride}
			path={[type, name]}
		/>
	)
}

const connected = connect(
	undefined,
	{changeStudent},
)(AreaOfStudy)

export {connected as AreaOfStudy}
<|endoftext|>


<commit_before>/*global cordova, nfc */
/*jslint sloppy: false, browser: true */
"use strict";

function handleNfcFromIntentFilter() {

    // This was historically done in cordova.addConstructor but broke with PhoneGap-2.2.0.
    // We need to handle NFC from an Intent that launched the application, but *after*
    // the code in the application's deviceready has run.  After upgrading to 2.2.0,
    // addConstructor was finishing *before* deviceReady was complete and the
    // ndef listeners had not been registered.
    // It seems like there should be a better solution.
    setTimeout(
        function () {
            cordova.exec(
                function () {
                    console.log("Initialized the NfcPlugin");
                },
                function (reason) {
                    console.log("Failed to initialize the NfcPlugin " + reason);
                },
                "NfcPlugin", "init", []
            );
        }, 10
    );
}

document.addEventListener('deviceready', handleNfcFromIntentFilter, false);

var ndef = {
    // see android.nfc.NdefRecord for documentation about constants
    // http://developer.android.com/reference/android/nfc/NdefRecord.html
    TNF_EMPTY: 0x0,
    TNF_WELL_KNOWN: 0x01,
    TNF_MIME_MEDIA: 0x02,
    TNF_ABSOLUTE_URI: 0x03,
    TNF_EXTERNAL_TYPE: 0x04,
    TNF_UNKNOWN: 0x05,
    TNF_UNCHANGED: 0x06,
    TNF_RESERVED: 0x07,

    RTD_TEXT: [0x54], // "T"
    RTD_URI: [0x55], // "U"
    RTD_SMART_POSTER: [0x53, 0x70], // "Sp"
    RTD_ALTERNATIVE_CARRIER: [0x61, 0x63], // "ac"
    RTD_HANDOVER_CARRIER: [0x48, 0x63], // "Hc"
    RTD_HANDOVER_REQUEST: [0x48, 0x72], // "Hr"
    RTD_HANDOVER_SELECT: [0x48, 0x73], // "Hs"

    /**
     * Creates a JSON representation of a NDEF Record.
     *
     * @tnf 3-bit TNF (Type Name Format) - use one of the TNF_* constants
     * @type byte array, containing zero to 255 bytes, must not be null
     * @id byte array, containing zero to 255 bytes, must not be null
     * @payload byte array, containing zero to (2 ** 32 - 1) bytes, must not be null
     *
     * @returns JSON representation of a NDEF record
     *
     * @see Ndef.textRecord, Ndef.uriRecord and Ndef.mimeMediaRecord for examples
     */
    record: function (tnf, type, id, payload) {
        return {
            tnf: tnf,
            type: type,
            id: id,
            payload: payload
        };
    },

    /**
     * Helper that creates a NDEF record containing plain text.
     *
     * @text String
     * @id byte[] (optional)
     */
    textRecord: function (text, id) {
        var languageCode = 'en', // TODO get from browser
            payload = [];

        if (!id) { id = []; }

        payload.push(languageCode.length);
        nfc.concatArray(payload, nfc.stringToBytes(languageCode));
        nfc.concatArray(payload, nfc.stringToBytes(text));

        return ndef.record(ndef.TNF_WELL_KNOWN, ndef.RTD_TEXT, id, payload);
    },

    /**
     * Helper that creates a NDEF record containing an absolute URI.
     *
     * @text String
     * @id byte[] (optional)
     */
    uriRecord: function (text, id) {
        if (!id) { id = []; }
        return ndef.record(ndef.TNF_ABSOLUTE_URI, ndef.RTD_URI, id, nfc.stringToBytes(text));
    },

    /**
     * Helper that creates a NDEF record containing an mimeMediaRecord.
     *
     * @mimeType String
     * @payload byte[]
     * @id byte[] (optional)
     */
    mimeMediaRecord: function (mimeType, payload, id) {
        if (!id) { id = []; }
        return ndef.record(ndef.TNF_MIME_MEDIA, nfc.stringToBytes(mimeType), id, payload);
    },

    /**
     * Helper that creates an empty NDEF record.
     *
     */
    emptyRecord: function() {
        return ndef.record(ndef.TNF_EMPTY, [], [], []);
    }
};

var nfc = {

    addTagDiscoveredListener: function (callback, win, fail) {
        document.addEventListener("tag", callback, false);
        cordova.exec(win, fail, "NfcPlugin", "registerTag", []);
    },

    addMimeTypeListener: function (mimeType, callback, win, fail) {
        document.addEventListener("ndef-mime", callback, false);
        cordova.exec(win, fail, "NfcPlugin", "registerMimeType", [mimeType]);
    },

    addNdefListener: function (callback, win, fail) {
        document.addEventListener("ndef", callback, false);
        cordova.exec(win, fail, "NfcPlugin", "registerNdef", []);
    },

    addNdefFormatableListener: function (callback, win, fail) {
        document.addEventListener("ndef-formatable", callback, false);
        cordova.exec(win, fail, "NfcPlugin", "registerNdefFormatable", []);
    },

    write: function (ndefMessage, win, fail) {
        cordova.exec(win, fail, "NfcPlugin", "writeTag", [ndefMessage]);
    },

    share: function (ndefMessage, win, fail) {
        cordova.exec(win, fail, "NfcPlugin", "shareTag", [ndefMessage]);
    },

    unshare: function (win, fail) {
        cordova.exec(win, fail, "NfcPlugin", "unshareTag", []);
    },

    erase: function (win, fail) {
        cordova.exec(win, fail, "NfcPlugin", "eraseTag", [[]]);
    },

    removeTagDiscoveredListener: function (callback, win, fail) {
        document.removeEventListener("tag", callback, false);
        cordova.exec(win, fail, "NfcPlugin", "removeTag", []);
    },

    removeMimeTypeListener: function(mimeType, callback, win, fail) {
        document.removeEventListener("ndef-mime", callback, false);
        cordova.exec(win, fail, "NfcPlugin", "removeMimeType", [mimeType]);
    },

    removeNdefListener: function (callback, win, fail) {
        document.removeEventListener("ndef", callback, false);
        cordova.exec(win, fail, "NfcPlugin", "removeNdef", []);
    },

    concatArray: function (a1, a2) { // this isn't built in?
        for (var i = 0; i < a2.length; i++) {
            a1.push(a2[i]);
        }
        return a1;
    },

    bytesToString: function (bytes) {
        var bytesAsString = "";
        for (var i = 0; i < bytes.length; i++) {
            bytesAsString += String.fromCharCode(bytes[i]);
        }
        return bytesAsString;
    },

    // http://stackoverflow.com/questions/1240408/reading-bytes-from-a-javascript-string#1242596
    stringToBytes: function (str) {
        var ch, st, re = [];
        for (var i = 0; i < str.length; i++ ) {
            ch = str.charCodeAt(i);  // get char
            st = [];                 // set up "stack"
            do {
                st.push( ch & 0xFF );  // push byte to stack
                ch = ch >> 8;          // shift value down by 1 byte
            } while ( ch );
            // add stack contents to result
            // done because chars have "wrong" endianness
            re = re.concat( st.reverse() );
        }
        // return an array of bytes
        return re;
    },

    bytesToHexString: function (bytes) {
        var dec, hexstring, bytesAsHexString = "";
        for (var i = 0; i < bytes.length; i++) {
            if (bytes[i] >= 0) {
                dec = bytes[i];
            } else {
                dec = 256 + bytes[i];
            }
            hexstring = dec.toString(16);
            // zero padding
            if (hexstring.length == 1) {
                hexstring = "0" + hexstring;
            }
            bytesAsHexString += hexstring;
        }
        return bytesAsHexString;
    }
};
<commit_msg>fix createUri closes #48<commit_after>/*global cordova, nfc */
/*jslint sloppy: false, browser: true */
"use strict";

function handleNfcFromIntentFilter() {

    // This was historically done in cordova.addConstructor but broke with PhoneGap-2.2.0.
    // We need to handle NFC from an Intent that launched the application, but *after*
    // the code in the application's deviceready has run.  After upgrading to 2.2.0,
    // addConstructor was finishing *before* deviceReady was complete and the
    // ndef listeners had not been registered.
    // It seems like there should be a better solution.
    setTimeout(
        function () {
            cordova.exec(
                function () {
                    console.log("Initialized the NfcPlugin");
                },
                function (reason) {
                    console.log("Failed to initialize the NfcPlugin " + reason);
                },
                "NfcPlugin", "init", []
            );
        }, 10
    );
}

document.addEventListener('deviceready', handleNfcFromIntentFilter, false);

var ndef = {
    // see android.nfc.NdefRecord for documentation about constants
    // http://developer.android.com/reference/android/nfc/NdefRecord.html
    TNF_EMPTY: 0x0,
    TNF_WELL_KNOWN: 0x01,
    TNF_MIME_MEDIA: 0x02,
    TNF_ABSOLUTE_URI: 0x03,
    TNF_EXTERNAL_TYPE: 0x04,
    TNF_UNKNOWN: 0x05,
    TNF_UNCHANGED: 0x06,
    TNF_RESERVED: 0x07,

    RTD_TEXT: [0x54], // "T"
    RTD_URI: [0x55], // "U"
    RTD_SMART_POSTER: [0x53, 0x70], // "Sp"
    RTD_ALTERNATIVE_CARRIER: [0x61, 0x63], // "ac"
    RTD_HANDOVER_CARRIER: [0x48, 0x63], // "Hc"
    RTD_HANDOVER_REQUEST: [0x48, 0x72], // "Hr"
    RTD_HANDOVER_SELECT: [0x48, 0x73], // "Hs"

    /**
     * Creates a JSON representation of a NDEF Record.
     *
     * @tnf 3-bit TNF (Type Name Format) - use one of the TNF_* constants
     * @type byte array, containing zero to 255 bytes, must not be null
     * @id byte array, containing zero to 255 bytes, must not be null
     * @payload byte array, containing zero to (2 ** 32 - 1) bytes, must not be null
     *
     * @returns JSON representation of a NDEF record
     *
     * @see Ndef.textRecord, Ndef.uriRecord and Ndef.mimeMediaRecord for examples
     */
    record: function (tnf, type, id, payload) {
        return {
            tnf: tnf,
            type: type,
            id: id,
            payload: payload
        };
    },

    /**
     * Helper that creates a NDEF record containing plain text.
     *
     * @text String
     * @id byte[] (optional)
     */
    textRecord: function (text, id) {
        var languageCode = 'en', // TODO get from browser
            payload = [];

        if (!id) { id = []; }

        payload.push(languageCode.length);
        nfc.concatArray(payload, nfc.stringToBytes(languageCode));
        nfc.concatArray(payload, nfc.stringToBytes(text));

        return ndef.record(ndef.TNF_WELL_KNOWN, ndef.RTD_TEXT, id, payload);
    },

    /**
     * Helper that creates a NDEF record containing an absolute URI.
     *
     * @text String
     * @id byte[] (optional)
     */
    uriRecord: function (text, id) {
        if (!id) { id = []; }
        return ndef.record(ndef.TNF_ABSOLUTE_URI, nfc.stringToBytes(text), id, []);
    },

    /**
     * Helper that creates a NDEF record containing an mimeMediaRecord.
     *
     * @mimeType String
     * @payload byte[]
     * @id byte[] (optional)
     */
    mimeMediaRecord: function (mimeType, payload, id) {
        if (!id) { id = []; }
        return ndef.record(ndef.TNF_MIME_MEDIA, nfc.stringToBytes(mimeType), id, payload);
    },

    /**
     * Helper that creates an empty NDEF record.
     *
     */
    emptyRecord: function() {
        return ndef.record(ndef.TNF_EMPTY, [], [], []);
    }
};

var nfc = {

    addTagDiscoveredListener: function (callback, win, fail) {
        document.addEventListener("tag", callback, false);
        cordova.exec(win, fail, "NfcPlugin", "registerTag", []);
    },

    addMimeTypeListener: function (mimeType, callback, win, fail) {
        document.addEventListener("ndef-mime", callback, false);
        cordova.exec(win, fail, "NfcPlugin", "registerMimeType", [mimeType]);
    },

    addNdefListener: function (callback, win, fail) {
        document.addEventListener("ndef", callback, false);
        cordova.exec(win, fail, "NfcPlugin", "registerNdef", []);
    },

    addNdefFormatableListener: function (callback, win, fail) {
        document.addEventListener("ndef-formatable", callback, false);
        cordova.exec(win, fail, "NfcPlugin", "registerNdefFormatable", []);
    },

    write: function (ndefMessage, win, fail) {
        cordova.exec(win, fail, "NfcPlugin", "writeTag", [ndefMessage]);
    },

    share: function (ndefMessage, win, fail) {
        cordova.exec(win, fail, "NfcPlugin", "shareTag", [ndefMessage]);
    },

    unshare: function (win, fail) {
        cordova.exec(win, fail, "NfcPlugin", "unshareTag", []);
    },

    erase: function (win, fail) {
        cordova.exec(win, fail, "NfcPlugin", "eraseTag", [[]]);
    },

    removeTagDiscoveredListener: function (callback, win, fail) {
        document.removeEventListener("tag", callback, false);
        cordova.exec(win, fail, "NfcPlugin", "removeTag", []);
    },

    removeMimeTypeListener: function(mimeType, callback, win, fail) {
        document.removeEventListener("ndef-mime", callback, false);
        cordova.exec(win, fail, "NfcPlugin", "removeMimeType", [mimeType]);
    },

    removeNdefListener: function (callback, win, fail) {
        document.removeEventListener("ndef", callback, false);
        cordova.exec(win, fail, "NfcPlugin", "removeNdef", []);
    },

    concatArray: function (a1, a2) { // this isn't built in?
        for (var i = 0; i < a2.length; i++) {
            a1.push(a2[i]);
        }
        return a1;
    },

    bytesToString: function (bytes) {
        var bytesAsString = "";
        for (var i = 0; i < bytes.length; i++) {
            bytesAsString += String.fromCharCode(bytes[i]);
        }
        return bytesAsString;
    },

    // http://stackoverflow.com/questions/1240408/reading-bytes-from-a-javascript-string#1242596
    stringToBytes: function (str) {
        var ch, st, re = [];
        for (var i = 0; i < str.length; i++ ) {
            ch = str.charCodeAt(i);  // get char
            st = [];                 // set up "stack"
            do {
                st.push( ch & 0xFF );  // push byte to stack
                ch = ch >> 8;          // shift value down by 1 byte
            } while ( ch );
            // add stack contents to result
            // done because chars have "wrong" endianness
            re = re.concat( st.reverse() );
        }
        // return an array of bytes
        return re;
    },

    bytesToHexString: function (bytes) {
        var dec, hexstring, bytesAsHexString = "";
        for (var i = 0; i < bytes.length; i++) {
            if (bytes[i] >= 0) {
                dec = bytes[i];
            } else {
                dec = 256 + bytes[i];
            }
            hexstring = dec.toString(16);
            // zero padding
            if (hexstring.length == 1) {
                hexstring = "0" + hexstring;
            }
            bytesAsHexString += hexstring;
        }
        return bytesAsHexString;
    }
};
<|endoftext|>


<commit_before>$(document).ready(function() {

  $('#offer1').on('click', function() {
    console.log('Offer 1 sent');
    /*
    $.ajax({
      method: 'GET',
      url: '/sendoffer1'
    });
    */
    io.emit('send offer', 'burgerking');
  });

  $('#offer2').on('click', function() {
    console.log('Offer 2 sent');
    $.ajax({
      method: 'GET',
      url: '/sendoffer2'
    });
  });

  $('#reminder').on('click', function() {
    console.log('Reminder sent');
    $.ajax({
      method: 'GET',
      url: '/reminder'
    });
  });

  $('#emitRegisterUser').on('click', function() {
    console.log('Emit register clicked');
    $.ajax({
      method: 'GET',
      url: '/emitRegisterUser'
    });
  });
});<commit_msg>Remove io.emit<commit_after>$(document).ready(function() {

  $('#offer1').on('click', function() {
    console.log('Offer 1 sent');
    $.ajax({
      method: 'GET',
      url: '/sendoffer1'
    });
  });

  $('#offer2').on('click', function() {
    console.log('Offer 2 sent');
    $.ajax({
      method: 'GET',
      url: '/sendoffer2'
    });
  });

  $('#reminder').on('click', function() {
    console.log('Reminder sent');
    $.ajax({
      method: 'GET',
      url: '/reminder'
    });
  });

  $('#emitRegisterUser').on('click', function() {
    console.log('Emit register clicked');
    $.ajax({
      method: 'GET',
      url: '/emitRegisterUser'
    });
  });
});<|endoftext|>


<commit_before>/* =========================================================
* bootstrap-modal.js v2.2.2
* http://twitter.github.com/bootstrap/javascript.html#modals
* =========================================================
* Copyright 2012 Twitter, Inc.
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
* ========================================================= */
/*

Modified for use with PrototypeJS

http://github.com/jwestbrook/bootstrap-prototype

*/

/* MODAL CLASS DEFINITION
* ====================== */
if(BootStrap === undefined)
{
	var BootStrap = {};
}

	BootStrap.Modal = Class.create({
	initialize : function (element, options) {
		this.$element = $(element);
		this.options = options
		this.options.backdrop = this.options.backdrop != undefined ? options.backdrop : true
		this.options.keyboard = this.options.keyboard != undefined ? options.keyboard : true
		this.options.show = this.options.show != undefined ? options.show : true

		if(this.options.show)
			this.show();
		$$("[data-dismiss='modal']").invoke("observe","click",function(){
			this.hide()
		}.bind(this))

		if(this.options.remote && this.$element.select('.modal-body'))
		{
			var t = new Ajax.Updater(this.$element.select('.modal-body')[0],this.options.remote);
		}
	},
	toggle: function () {
		return this[!this.isShown ? 'show' : 'hide']()
	}
	, show: function (e) {
		var that = this

		this.$element.setStyle({display:'block'})

		if (this.isShown ) return

		this.isShown = true

		this.escape()

		this.backdrop(function () {
			var transition = (BootStrap.handleeffects == 'css' || (BootStrap.handleeffects == 'effect' && typeof Effect !== 'undefined' && typeof Effect.Fade !== 'undefined')) && that.$element.hasClassName('fade')

			if (!that.$element.up().length) {
				$$("body")[0].insert(that.$element);
			}
			that.$element.setStyle({display:'block'})

			if(transition && BootStrap.handleeffects == 'css')
			{
				that.$element.observe(BootStrap.transitionendevent,function(){
					that.$element.fire("bootstrap:shown");
				});
				setTimeout(function(){
					that.$element.addClassName('in').writeAttribute('aria-hidden',false);
				},1);
			}
			else if(transition && BootStrap.handleeffects == 'effect')
			{
				new Effect.Parallel([
					new Effect.Morph(that.$element,{sync:true,style:'top:50%'}),
					new Effect.Opacity(that.$element,{sync:true,from:0,to:1})
					],{duration:0.3,afterFinish:function(){
						that.$element.addClassName('in').writeAttribute('aria-hidden', false)
						that.$element.fire("bootstrap:shown");
					}})
			}
			else
			{
				that.$element.addClassName('in').writeAttribute('aria-hidden', false).fire("bootstrap:shown");
			}

			that.enforceFocus()
		})
	}

	, hide: function (e) {

		var that = this

		if (!this.isShown ) return

		this.isShown = false

		this.escape()

		if(BootStrap.handleeffects == 'css' && this.$element.hasClassName('fade'))
		{
			this.hideWithTransition()
		}
		else if(BootStrap.handleeffects == 'effect' && typeof Effect !== 'undefined' && typeof Effect.Fade !== 'undefined' && this.$element.hasClassName('fade'))
		{
			this.hideWithTransition()
		}
		else
		{
			this.hideModal()
			this.$element.setStyle({display:''});
		}

	}

	, enforceFocus: function () {
		var that = this
		$(document).on('focus', function (e) {
			if (that.$element[0] !== e.target && !that.$element.has(e.target).length) {
				that.$element.focus()
			}
		})
	}

	, escape: function () {
		var that = this
		if (this.isShown && this.options.keyboard) {
			$(document).on('keyup', function ( e ) {
				e.which == Event.KEY_ESC && that.hide()
			})
		} else if (!this.isShown) {
			$(document).stopObserving('keyup')
		}
	}

	, hideWithTransition: function () {
		var that = this

		if(BootStrap.handleeffects == 'css')
		{
			this.$element.observe(BootStrap.transitionendevent,function(){
				this.setStyle({display:''});
				this.setStyle({top:''})
				that.hideModal()
				this.stopObserving(BootStrap.transitionendevent)
			})
			setTimeout(function(){
				this.$element.removeClassName('in').writeAttribute('aria-hidden',true)
			}.bind(this))
		}
		else
		{
			new Effect.Morph(this.$element,{duration:0.30,style:'top:-25%;',afterFinish:function(effect){
				effect.element.removeClassName('in').writeAttribute('aria-hidden', true)
				effect.element.setStyle({display:''});
				effect.element.setStyle({top:''})
				that.hideModal()
			}})
		}
	}

	, hideModal: function () {
		this.$element.fire('bootstrap:hidden')
		this.backdrop()
	}

	, removeBackdrop: function () {
		this.$backdrop.remove()
		this.$backdrop = null
	}

	, backdrop: function (callback) {

		var that = this
		, animate = this.$element.hasClassName('fade') ? 'fade' : ''

		if (this.isShown && this.options.backdrop) {
			var doAnimate = (BootStrap.handleeffects == 'css' || (BootStrap.handleeffects == 'effect' && typeof Effect !== 'undefined' && typeof Effect.Fade !== 'undefined')) && animate

			this.$backdrop = new Element("div",{"class":"modal-backdrop "+animate})
			if(doAnimate && BootStrap.handleeffects == 'css')
			{
				this.$backdrop.observe(BootStrap.transitionendevent,function(){
					callback()
					this.stopObserving(BootStrap.transitionendevent)
				})
			}
			else if(doAnimate && BootStrap.handleeffects == 'effect')
			{
				this.$backdrop.setOpacity(0)
			}

			this.$backdrop.observe("click",function(){
			that.options.backdrop == 'static' ? '' : that.hide()
			})

			$$("body")[0].insert(this.$backdrop)

			if(doAnimate && BootStrap.handleeffects == 'effect')
			{
				new Effect.Appear(this.$backdrop,{from:0,to:0.80,duration:0.3,afterFinish:callback})
			}
			else
			{
				callback();
			}
			setTimeout(function(){
				that.$backdrop.addClassName('in');
			},1);

		} else if (!this.isShown && this.$backdrop) {

			if(animate && BootStrap.handleeffects == 'css')
			{
				that.$backdrop.observe(BootStrap.transitionendevent,function(){
					that.removeBackdrop()
				});
				setTimeout(function(){
					that.$backdrop.removeClassName('in')
				},1);
			}
			else if(animate && BootStrap.handleeffects == 'effect' && typeof Effect !== 'undefined' && typeof Effect.Fade !== 'undefined')
			{
				new Effect.Fade(that.$backdrop,{duration:0.3,from:that.$backdrop.getOpacity()*1,afterFinish:function(){
					that.$backdrop.removeClassName('in')
					that.removeBackdrop()
				}})
			}
			else
			{
				that.$backdrop.removeClassName('in')
				that.removeBackdrop()
			}

		} else if (callback) {
			callback()
		}
	}
});

/* MODAL DATA-API
* ============== */

document.observe("dom:loaded",function(){
	$$("[data-toggle='modal']").invoke("observe","click",function(e){

		var target = this.readAttribute("data-target") || (this.href && this.href.replace(/.*(?=#[^\s]+$)/,'').replace(/#/,''));
		var options = {};
		if($(target) != undefined)
		{
			target = $(target);
			if(!/#/.test(this.href))
			{
				options.remote = this.href;
			}
			new BootStrap.Modal($(target),options);
		}

		e.stop();
	});
})
<commit_msg>update BootStrap.Modal to ver 2.3.0<commit_after>/* =========================================================
* bootstrap-modal.js v2.2.2
* http://twitter.github.com/bootstrap/javascript.html#modals
* =========================================================
* Copyright 2012 Twitter, Inc.
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
* ========================================================= */
/*

Modified for use with PrototypeJS

http://github.com/jwestbrook/bootstrap-prototype

*/

/* MODAL CLASS DEFINITION
* ====================== */
if(BootStrap === undefined)
{
	var BootStrap = {};
}

	BootStrap.Modal = Class.create({
	initialize : function (element, options) {
		this.$element = $(element);
		this.options = options
		this.options.backdrop = this.options.backdrop != undefined ? options.backdrop : true
		this.options.keyboard = this.options.keyboard != undefined ? options.keyboard : true
		this.options.show = this.options.show != undefined ? options.show : true

		if(this.options.show)
			this.show();
		$$("[data-dismiss='modal']").invoke("observe","click",function(){
			this.hide()
		}.bind(this))

		if(this.options.remote && this.$element.select('.modal-body'))
		{
			var t = new Ajax.Updater(this.$element.select('.modal-body')[0],this.options.remote);
		}
	},
	toggle: function () {
		return this[!this.isShown ? 'show' : 'hide']()
	}
	, show: function (e) {
		var that = this

		this.$element.setStyle({display:'block'})

		if (this.isShown ) return

		this.isShown = true

		this.escape()

		this.backdrop(function () {
			var transition = (BootStrap.handleeffects == 'css' || (BootStrap.handleeffects == 'effect' && typeof Effect !== 'undefined' && typeof Effect.Fade !== 'undefined')) && that.$element.hasClassName('fade')

			if (!that.$element.up().length) {
				$$("body")[0].insert(that.$element);
			}
			that.$element.setStyle({display:'block'})

			if(transition && BootStrap.handleeffects == 'css')
			{
				that.$element.observe(BootStrap.transitionendevent,function(){
					that.$element.fire("bootstrap:shown");
				});
				setTimeout(function(){
					that.$element.addClassName('in').writeAttribute('aria-hidden',false);
				},1);
			}
			else if(transition && BootStrap.handleeffects == 'effect')
			{
				new Effect.Parallel([
					new Effect.Morph(that.$element,{sync:true,style:'top:10%'}),
					new Effect.Opacity(that.$element,{sync:true,from:0,to:1})
					],{duration:0.3,afterFinish:function(){
						that.$element.addClassName('in').writeAttribute('aria-hidden', false)
						that.$element.fire("bootstrap:shown");
					}})
			}
			else
			{
				that.$element.addClassName('in').writeAttribute('aria-hidden', false).fire("bootstrap:shown");
			}

			that.enforceFocus()
		})
	}

	, hide: function (e) {

		var that = this

		if (!this.isShown ) return

		this.isShown = false

		this.escape()

		if(BootStrap.handleeffects == 'css' && this.$element.hasClassName('fade'))
		{
			this.hideWithTransition()
		}
		else if(BootStrap.handleeffects == 'effect' && typeof Effect !== 'undefined' && typeof Effect.Fade !== 'undefined' && this.$element.hasClassName('fade'))
		{
			this.hideWithTransition()
		}
		else
		{
			this.hideModal()
			this.$element.setStyle({display:''});
		}

	}

	, enforceFocus: function () {
		var that = this
		$(document).on('focus', function (e) {
			if (that.$element[0] !== e.target && !that.$element.has(e.target).length) {
				that.$element.focus()
			}
		})
	}

	, escape: function () {
		var that = this
		if (this.isShown && this.options.keyboard) {
			$(document).on('keyup', function ( e ) {
				e.which == Event.KEY_ESC && that.hide()
			})
		} else if (!this.isShown) {
			$(document).stopObserving('keyup')
		}
	}

	, hideWithTransition: function () {
		var that = this

		if(BootStrap.handleeffects == 'css')
		{
			this.$element.observe(BootStrap.transitionendevent,function(){
				this.setStyle({display:''});
				this.setStyle({top:''})
				that.hideModal()
				this.stopObserving(BootStrap.transitionendevent)
			})
			setTimeout(function(){
				this.$element.removeClassName('in').writeAttribute('aria-hidden',true)
			}.bind(this))
		}
		else
		{
			new Effect.Morph(this.$element,{duration:0.30,style:'top:-25%;',afterFinish:function(effect){
				effect.element.removeClassName('in').writeAttribute('aria-hidden', true)
				effect.element.setStyle({display:''});
				effect.element.setStyle({top:''})
				that.hideModal()
			}})
		}
	}

	, hideModal: function () {
		this.$element.hide()
		this.backdrop(function(){
			this.removeBackdrop()
			this.$element.fire('bootstrap:hidden')
		}.bind(this))

	}
	, removeBackdrop: function () {
		this.$backdrop.remove()
		this.$backdrop = null
	}

	, backdrop: function (callback) {

		var that = this
		, animate = this.$element.hasClassName('fade') ? 'fade' : ''

		if (this.isShown && this.options.backdrop) {
			var doAnimate = (BootStrap.handleeffects == 'css' || (BootStrap.handleeffects == 'effect' && typeof Effect !== 'undefined' && typeof Effect.Fade !== 'undefined')) && animate

			this.$backdrop = new Element("div",{"class":"modal-backdrop "+animate})
			if(doAnimate && BootStrap.handleeffects == 'css')
			{
				this.$backdrop.observe(BootStrap.transitionendevent,function(){
					callback()
					this.stopObserving(BootStrap.transitionendevent)
				})
			}
			else if(doAnimate && BootStrap.handleeffects == 'effect')
			{
				this.$backdrop.setOpacity(0)
			}

			this.$backdrop.observe("click",function(){
			that.options.backdrop == 'static' ? '' : that.hide()
			})

			$$("body")[0].insert(this.$backdrop)

			if(doAnimate && BootStrap.handleeffects == 'effect')
			{
				new Effect.Appear(this.$backdrop,{from:0,to:0.80,duration:0.3,afterFinish:callback})
			}
			else
			{
				callback();
			}
			setTimeout(function(){
				that.$backdrop.addClassName('in');
			},1);

		} else if (!this.isShown && this.$backdrop) {

			if(animate && BootStrap.handleeffects == 'css')
			{
				that.$backdrop.observe(BootStrap.transitionendevent,function(){
					callback()
				});
				setTimeout(function(){
					that.$backdrop.removeClassName('in')
				},1);
			}
			else if(animate && BootStrap.handleeffects == 'effect' && typeof Effect !== 'undefined' && typeof Effect.Fade !== 'undefined')
			{
				new Effect.Fade(that.$backdrop,{duration:0.3,from:that.$backdrop.getOpacity()*1,afterFinish:function(){
					that.$backdrop.removeClassName('in')
					callback()
				}})
			}
			else
			{
				that.$backdrop.removeClassName('in')
				callback()
			}

		} else if (callback) {
			callback()
		}
	}
});

/* MODAL DATA-API
* ============== */

document.observe("dom:loaded",function(){
	$$("[data-toggle='modal']").invoke("observe","click",function(e){

		var target = this.readAttribute("data-target") || (this.href && this.href.replace(/.*(?=#[^\s]+$)/,'').replace(/#/,''));
		var options = {};
		if($(target) != undefined)
		{
			target = $(target);
			if(!/#/.test(this.href))
			{
				options.remote = this.href;
			}
			new BootStrap.Modal($(target),options);
		}

		e.stop();
	});
})<|endoftext|>