Advertisement
C0deMaver1ck

unlock-your-device-b.js

Sep 20th, 2012
628
0
Never
Not a member of Pastebin yet? Sign Up, it unlocks many cool features!
  1. RightNow.Widget.UPDTextInput = function (data, instanceID) {
  2.     this.data = data;
  3.     this.instanceID = instanceID;
  4.     this._formErrorLocation = null;
  5.     this._validated = false;
  6.     this._inputField = document.getElementById("rn_" + this.instanceID + "_" + this.data.js.name);
  7.     if (this.data.js.hint) this._initializeHint();
  8.     if (this.data.attrs.initial_focus && this._inputField.focus) this._inputField.focus();
  9.     if (this.data.js.mask) this._initializeMask();
  10.     RightNow.Event.subscribe("evt_formFieldValidateRequest", this._onValidate, this);
  11.     this._fieldName = this.data.js.name;
  12.     if (this.data.attrs.validate_on_blur) YAHOO.util.Event.addListener(this._inputField, "blur", this._blurValidate, null, this);
  13. };
  14. RightNow.Widget.UPDTextInput.prototype = {
  15.     _onValidate: function (type, args) {
  16.         this._validated = true;
  17.         this._formErrorLocation = args[0].data.error_location;
  18.         this._trimField();
  19.         if (this._compareInputToMask(true) && this._checkRequired() && this._checkData() && this._checkValue() && this._checkUrl() && this._checkProd) {
  20.             YAHOO.util.Dom.removeClass(this._inputField, "rn_ErrorField");
  21.             YAHOO.util.Dom.removeClass("rn_" + this.instanceID + "_Label", "rn_ErrorLabel");
  22.             var eo = new RightNow.Event.EventObject();
  23.             eo.data = {
  24.                 "name": this.data.js.name,
  25.                 "value": this._getValue(),
  26.                 "table": this.data.js.table,
  27.                 "required": (this.data.attrs.required ? true : false),
  28.                 "prev": this.data.js.prev,
  29.                 "form": RightNow.UI.findParentForm("rn_" + this.instanceID)
  30.             };
  31.             if (this.data.js.profile) eo.data.profile = true;
  32.             if (this.data.js.customID) {
  33.                 eo.data.custom = true;
  34.                 eo.data.customID = this.data.js.customID;
  35.                 eo.data.customType = this.data.js.type;
  36.             } else {
  37.                 eo.data.custom = false;
  38.             }
  39.             if (this.data.js.channelID) {
  40.                 eo.data.channelID = this.data.js.channelID;
  41.             }
  42.             eo.w_id = this.data.info.w_id;
  43.             RightNow.Event.fire("evt_formFieldValidateResponse", eo);
  44.         } else {
  45.             RightNow.UI.Form.formError = true;
  46.         }
  47.         RightNow.Event.fire("evt_formFieldCountRequest");
  48.     },
  49.     _blurValidate: function () {
  50.         this._formErrorLocation = null;
  51.         if (this._onAccountExistsResponse._dialogShowing) return;
  52.         if (this._fieldName == "incoming_esn_or_csn") {
  53.             this._getWarrantyData();
  54.         }
  55.         this._trimField();
  56.     },
  57.     _checkValue: function () {
  58.         if (this.data.js.type === RightNow.Interface.Constants.EUF_DT_INT) {
  59.             if (this._inputField.value !== "" && (isNaN(Number(this._inputField.value)) || parseInt(this._inputField.value) !== parseFloat(this._inputField.value))) {
  60.                 this._displayError(RightNow.Interface.getMessage('VALUE_MUST_BE_AN_INTEGER_MSG'));
  61.                 return false;
  62.             }
  63.             if (this.data.js.maxVal || this.data.js.minVal) {
  64.                 var value = parseInt(this._inputField.value);
  65.                 if (this.data.js.maxVal && value > parseInt(this.data.js.maxVal)) {
  66.                     this._displayError(RightNow.Interface.getMessage('VALUE_IS_TOO_LARGE_MAX_VALUE_MSG') + this.data.js.maxVal + ")");
  67.                     return false;
  68.                 }
  69.                 if (this.data.js.minVal && value < parseInt(this.data.js.minVal)) {
  70.                     this._displayError(RightNow.Interface.getMessage('VALUE_IS_TOO_SMALL_MIN_VALUE_MSG') + this.data.js.minVal + ")");
  71.                     return false;
  72.                 }
  73.             }
  74.         } else if (this.data.js.type === RightNow.Interface.Constants.EUF_DT_PASSWORD && this.data.js.name !== "password" && this.data.js.passwordLength) {
  75.             var length = RightNow.Text.Encoding.utf8Length(this._inputField.value),
  76.                 minLength = this.data.js.passwordLength;
  77.             if (length < minLength) {
  78.                 this._displayError(RightNow.Text.sprintf(RightNow.Interface.getMessage("PCT_D_CHARACTERS_MSG"), minLength));
  79.                 return false;
  80.             }
  81.         }
  82.         if (this.data.js.fieldSize) {
  83.             var length = RightNow.Text.Encoding.utf8Length(this._inputField.value),
  84.                 maxLength = this.data.js.field_size;
  85.             if (maxLength < length) {
  86.                 var extra, errorString, roughMBCS = parseInt(length / (this._inputField.value.length)),
  87.                     numtokExp = new RegExp("%d");
  88.                 if (length % (this._inputField.value.length) !== 0) roughMBCS++;
  89.                 extra = parseInt((length - maxLength) / roughMBCS);
  90.                 errorString = RightNow.Text.sprintf(RightNow.Interface.getMessage("EXCEEDS_SZ_LIMIT_PCT_D_CHARS_PCT_D_LBL"), numtokExp, parseInt(maxLength / roughMBCS));
  91.                 if ((length - maxLength) % (roughMBCS) !== 0) extra++;
  92.                 errorString = errorString.replace(numtokExp, extra);
  93.                 this._displayError(errorString);
  94.                 return false;
  95.             }
  96.         }
  97.         return true;
  98.     },
  99.     _checkData: function (silent) {
  100.         return true;
  101.     },
  102.     _checkUrl: function (silent) {
  103.         if ((this.data.js.customID) && (this.data.js.url) && !(this._inputField.value === "")) {
  104.             if (!RightNow.Text.isValidUrl(this._inputField.value)) {
  105.                 if (!silent) this._displayError(RightNow.Interface.getMessage("IS_NOT_A_VALID_URL_MSG"));
  106.                 return false;
  107.             }
  108.         }
  109.         return true;
  110.     },
  111.     _checkRequired: function () {
  112.         if (this.data.attrs.required) {
  113.             if (this._inputField.value === "") {
  114.                 this._displayError(this.data.attrs.label_required);
  115.                 return false;
  116.             }
  117.         }
  118.         return true;
  119.     },
  120.     _getValue: function () {
  121.         if (this.data.js.type === RightNow.Interface.Constants.EUF_DT_INT) {
  122.             if (this._inputField.value !== "") return parseInt(this._inputField.value);
  123.         }
  124.         if (this.data.js.mask) return this._stripMaskFromFieldValue();
  125.         return this._inputField.value;
  126.     },
  127.     _trimField: function () {
  128.         if (this._inputField.value !== "" && this.data.js.type !== RightNow.Interface.Constants.EUF_DT_PASSWORD) this._inputField.value = YAHOO.lang.trim(this._inputField.value);
  129.         return true;
  130.     },
  131.     _initializeHint: function () {
  132.         if (YAHOO.widget.Overlay) {
  133.             var overlay = document.createElement("span");
  134.             overlay.id = "rn_" + this.instanceID + "_Hint";
  135.             YAHOO.util.Dom.addClass(overlay, "rn_HintBox");
  136.             YAHOO.util.Dom.insertAfter(overlay, this._inputField);
  137.             overlay = new YAHOO.widget.Overlay(overlay, {
  138.                 visible: false
  139.             });
  140.             overlay.setBody(this.data.js.hint);
  141.             overlay.render();
  142.             YAHOO.util.Event.addListener(this._inputField, "focus", function () {
  143.                 overlay.show();
  144.             });
  145.             YAHOO.util.Event.addListener(this._inputField, "blur", function () {
  146.                 overlay.hide();
  147.             });
  148.         } else {
  149.             var hint = document.createElement("span");
  150.             hint.className = "rn_HintText";
  151.             hint.innerHTML = this.data.js.hint;
  152.             YAHOO.util.Dom.insertAfter(hint, this._inputField);
  153.         }
  154.     },
  155.     _displayError: function (errorMessage) {
  156.         var commonErrorDiv = document.getElementById(this._formErrorLocation);
  157.         if (commonErrorDiv) {
  158.             RightNow.UI.Form.errorCount++;
  159.             if (RightNow.UI.Form.chatSubmit && RightNow.UI.Form.errorCount === 1) commonErrorDiv.innerHTML = "";
  160.             var errorLink = "<div><b><a href='javascript:void(0);' onclick='document.getElementById(\"" + this._inputField.id + "\").focus(); return false;'>" + this.data.attrs.label_input + " ";
  161.             if (errorMessage.indexOf("%s") > -1) errorLink = RightNow.Text.sprintf(errorMessage, errorLink);
  162.             else errorLink = errorLink + errorMessage;
  163.             errorLink += "</a></b></div> ";
  164.             commonErrorDiv.innerHTML += errorLink;
  165.         }
  166.         YAHOO.util.Dom.addClass(this._inputField, "rn_ErrorField");
  167.         YAHOO.util.Dom.addClass("rn_" + this.instanceID + "_Label", "rn_ErrorLabel");
  168.     },
  169.     _getWarrantyData: function () {
  170.         $('#processingContainer').removeClass('noShow');
  171.         var serialNumber = this._inputField.value;
  172.         $.ajax({
  173.             type: "POST",
  174.             url: "/cc/MotorolaService/GetWarrantyInfo/SN/" + serialNumber,
  175.             dataType: "json",
  176.             success: function (data) {
  177.                 var eo = new RightNow.Event.EventObject();
  178.                 if (data != null) {
  179.                     $('#processingContainer').addClass('noShow');
  180.                     for (var dataIndex = 0; dataIndex < data.length; dataIndex++) {
  181.                         if (dataIndex == 0) {
  182.                             if ((data[dataIndex].val.toUpperCase() == "E09003") || (data[dataIndex].val.toUpperCase() == "E05002")) {
  183.                                 alert("Your serial number was not found in our product database, please re-enter it");
  184.                             }
  185.                         }
  186.                         var localUpdObj = data[dataIndex];
  187.                         if (localUpdObj.key == "WarrantyStatus") {
  188.                             var warrStatus = localUpdObj.val;
  189.                             eo.data.warrStatus = warrStatus;
  190.                             if (warrStatus == "Out Of Warranty") {
  191.                                 $("#warrValid").addClass('noShow');
  192.                                 $("#warrInvalid").removeClass('noShow');
  193.                             } else if (warrStatus == "Out Of Warranty(POP date considered)") {
  194.                                 $("#warrValid").addClass('noShow');
  195.                                 $("#warrInvalid").removeClass('noShow');
  196.                             } else {
  197.                                 $("#warrValid").removeClass('noShow');
  198.                                 $("#warrInvalid").addClass('noShow');
  199.                             }
  200.                         }
  201.                         if (localUpdObj.key == "DeviceAuthentication") {
  202.                             var bootloaderCheck = localUpdObj.val;
  203.                             if (bootloaderCheck == 'BTL') {
  204.                                 alert('Your device is out of warranty because you have performed a bootloader unlock on this device.');
  205.                             }
  206.                         }
  207.                         if (localUpdObj.key == "WarrantyCountry") {
  208.                             var warrCountry = localUpdObj.val;
  209.                             eo.data.warrCountry = warrCountry;
  210.                             RightNow.Event.fire("evt_UPDCountry", warrCountry);
  211.                         }
  212.                         if (localUpdObj.key == "WarrantyFlag") {
  213.                             var warrBool = localUpdObj.val;
  214.                             eo.data.warrBool = warrBool;
  215.                         }
  216.                         if (localUpdObj.key == "POPDateFromUPD") {
  217.                             var purchDate = localUpdObj.val;
  218.                             eo.data.purchDate = purchDate;
  219.                         }
  220.                         if (localUpdObj.key == "SoftwareUpdateEligibleFlag") {
  221.                             var updateBool = localUpdObj.val;
  222.                             eo.data.updateBool = updateBool;
  223.                         }
  224.                         if (localUpdObj.key == "SoftwareUpdateWarrantyExpirationDate") {
  225.                             var updateExpire = localUpdObj.val;
  226.                             eo.data.updateExpire = updateExpire;
  227.                         }
  228.                         if (localUpdObj.key == "CustomerModelNumber") {
  229.                             var custModel = localUpdObj.val;
  230.                             eo.data.custModel = custModel;
  231.                         }
  232.                         if (localUpdObj.key == "TransceiverModelNumber") {
  233.                             var transModel = localUpdObj.val;
  234.                             eo.data.transModel = transModel;
  235.                         }
  236.                         if (localUpdObj.key == "APC") {
  237.                             var apc = localUpdObj.val;
  238.                             eo.data.apc = apc;
  239.                         }
  240.                         if (localUpdObj.key == "CustomerSerialNumberType") {
  241.                             var serialType = localUpdObj.val;
  242.                             eo.data.serialType = serialType;
  243.                         }
  244.                         if (localUpdObj.key == "CustomerModelNumberFromUPD") {
  245.                             var custModelUPD = localUpdObj.val;
  246.                             eo.data.custModelUPD = custModelUPD;
  247.                         }
  248.                     }
  249.                     RightNow.Event.fire("evt_formUPDResponse", eo);
  250.                 }
  251.             },
  252.             error: function (xhr) {
  253.                 alert("failed");
  254.                 alert(xhr.responseText);
  255.             }
  256.         });
  257.     },
  258.     _onAccountExistsResponse: function (type, args) {
  259.         RightNow.Event.unsubscribe("evt_formFieldAccountExistsResponse", this._onAccountExistsResponse);
  260.         var results = args[0];
  261.         if (results !== false && this._validated === false) {
  262.             YAHOO.util.Dom.addClass("rn_" + this.instanceID + "_Label", "rn_ErrorLabel");
  263.             YAHOO.util.Dom.addClass(this._inputField, "rn_ErrorField");
  264.             var handleOK = function () {
  265.                 warnDialog.hide();
  266.                 this._onAccountExistsResponse._dialogShowing = false;
  267.                 this._inputField.focus();
  268.             };
  269.             var buttons = [{
  270.                 text: RightNow.Interface.getMessage("OK_LBL"),
  271.                 handler: {
  272.                     fn: handleOK,
  273.                     scope: this
  274.                 },
  275.                 isDefault: true
  276.             }];
  277.             var dialogBody = document.createElement("div");
  278.             dialogBody.innerHTML = results.message;
  279.             var warnDialog = RightNow.UI.Dialog.actionDialog(RightNow.Interface.getMessage("WARNING_LBL"), dialogBody, {
  280.                 "buttons": buttons,
  281.                 "width": "250px"
  282.             });
  283.             this._onAccountExistsResponse._dialogShowing = true;
  284.             warnDialog.show();
  285.         } else {
  286.             YAHOO.util.Dom.removeClass("rn_" + this.instanceID + "_Label", "rn_ErrorLabel");
  287.             YAHOO.util.Dom.removeClass(this._inputField, "rn_ErrorField");
  288.             this._validated = false;
  289.         }
  290.         return false;
  291.     },
  292.     _onUPDChange: function (type, args) {
  293.         var eventObj = args[0];
  294.         if ((this._fieldName == "incoming_esn_or_csn") && (eventObj.data.apc == undefined)) {
  295.             this._inputField.value = '';
  296.         }
  297.         if ((this._fieldName == "purch_store_type") && ("apc" in eventObj.data)) {
  298.             this._inputField.value = eventObj.data.apc;
  299.         }
  300.         if ((this._fieldName == "upd_std_warr_date") && ("warrExpire" in eventObj.data)) {
  301.             this._inputField.value = eventObj.data.warrExpire;
  302.         }
  303.         if ((this._fieldName == "upd_cust_model_num") && ("warrModel" in eventObj.data)) {
  304.             this._inputField.value = eventObj.data.warrModel;
  305.         }
  306.         if ((this._fieldName == "ts_primary_issue") && ("warrCountry" in eventObj.data)) {
  307.             this._inputField.value = eventObj.data.warrCountry;
  308.         }
  309.         if ((this._fieldName == "upd_status_name") && ("warrBool" in eventObj.data)) {
  310.             this._inputField.value = eventObj.data.warrBool;
  311.         }
  312.     },
  313.     _onProvinceChange: function (type, args) {
  314.         var eventObj = args[0],
  315.             resetMask = false;
  316.         if (!eventObj.states.length) this.data.js.mask = "";
  317.         if ((this._fieldName === "postal_code") && ("postal_mask" in eventObj)) {
  318.             resetMask = true;
  319.             this.data.js.mask = eventObj.postal_mask;
  320.         } else if ("phone_mask" in eventObj) {
  321.             resetMask = true;
  322.             this.data.js.mask = eventObj.phone_mask;
  323.         }
  324.         if (resetMask && this.data.js.mask) this._initializeMask();
  325.         else if (this._maskNodeOnPage) this._maskNodeOnPage.parentNode.removeChild(this._maskNodeOnPage);
  326.     },
  327.     _initializeMask: function () {
  328.         YAHOO.util.Event.addListener(this._inputField, "keyup", this._compareInputToMask, null, this);
  329.         YAHOO.util.Event.addListener(this._inputField, "blur", this._hideMaskMessage, null, this);
  330.         YAHOO.util.Event.addListener(this._inputField, "focus", this._compareInputToMask, null, this);
  331.         this.data.js.mask = this._createMaskArray(this.data.js.mask);
  332.         var overlay = document.createElement("div");
  333.         YAHOO.util.Dom.addClass(overlay, "rn_MaskOverlay");
  334.         if (YAHOO.widget.Overlay) {
  335.             this._maskNode = YAHOO.util.Dom.insertAfter(overlay, this._inputField);
  336.             this._maskNode = new YAHOO.widget.Overlay(this._maskNode, {
  337.                 visible: false
  338.             });
  339.             this._maskNode.cfg.setProperty("context", [this._inputField, "tl", "bl", ["windowScroll"]]);
  340.             this._maskNode.setBody("");
  341.             this._maskNode.render();
  342.         } else {
  343.             YAHOO.util.Dom.addClass(overlay, "rn_Hidden");
  344.             this._maskNode = overlay;
  345.             YAHOO.util.Dom.insertAfter(this._maskNode, this._inputField);
  346.         }
  347.         if (this.data.attrs.always_show_mask) {
  348.             var maskMessageOnPage = this._getSimpleMaskString(),
  349.                 widgetContainer = document.getElementById("rn_" + this.instanceID);
  350.             if (maskMessageOnPage && widgetContainer) {
  351.                 var messageNode = document.createElement("div");
  352.                 messageNode.innerHTML = RightNow.Interface.getMessage("EXPECTED_INPUT_LBL") + ": " + maskMessageOnPage;
  353.                 YAHOO.util.Dom.addClass(messageNode, 'rn_Mask' + (YAHOO.util.Dom.hasClass(widgetContainer.lastChild, 'rn_HintText') ? ' rn_MaskBuffer' : ''));
  354.                 this._maskNodeOnPage = widgetContainer.appendChild(messageNode);
  355.             }
  356.         }
  357.     },
  358.     _createMaskArray: function (mask) {
  359.         if (!mask) return;
  360.         var maskArray = [];
  361.         for (var i = 0, j = 0, size = mask.length / 2; i < size; i++) {
  362.             maskArray[i] = mask.substring(j, j + 2);
  363.             j += 2;
  364.         }
  365.         return maskArray;
  366.     },
  367.     _stripMaskFromFieldValue: function () {
  368.         if (!this.data.js.mask || this._inputField.value === "") return this._inputField.value;
  369.         var result = "";
  370.         for (var i = 0; i < this._inputField.value.length; i++) {
  371.             if (i < this.data.js.mask.length && this.data.js.mask[i].charAt(0) !== 'F') result += this._inputField.value.charAt(i);
  372.         }
  373.         return result;
  374.     },
  375.     _getSimpleMaskString: function () {
  376.         if (!this.data.js.mask) return "";
  377.         var maskString = "";
  378.         for (var i = 0; i < this.data.js.mask.length; i++) {
  379.             switch (this.data.js.mask[i].charAt(0)) {
  380.             case "F":
  381.                 maskString += this.data.js.mask[i].charAt(1);
  382.                 break;
  383.             case "U":
  384.                 switch (this.data.js.mask[i].charAt(1)) {
  385.                 case "#":
  386.                     maskString += "#";
  387.                     break;
  388.                 case "A":
  389.                 case "C":
  390.                     maskString += "@";
  391.                     break;
  392.                 case "L":
  393.                     maskString += "A";
  394.                     break;
  395.                 }
  396.                 break;
  397.             case "L":
  398.                 switch (this.data.js.mask[i].charAt(1)) {
  399.                 case "#":
  400.                     maskString += "#";
  401.                     break;
  402.                 case "A":
  403.                 case "C":
  404.                     maskString += "@";
  405.                     break;
  406.                 case "L":
  407.                     maskString += "a";
  408.                     break;
  409.                 }
  410.                 break;
  411.             case "M":
  412.                 switch (this.data.js.mask[i].charAt(1)) {
  413.                 case "#":
  414.                     maskString += "#";
  415.                     break;
  416.                 case "A":
  417.                 case "C":
  418.                 case "L":
  419.                     maskString += "@";
  420.                     break;
  421.                 }
  422.                 break;
  423.             }
  424.         }
  425.         return maskString;
  426.     },
  427.     _compareInputToMask: function (submitting) {
  428.         if (!this.data.js.mask) return true;
  429.         var error = [];
  430.         if (this._inputField.value.length > 0) {
  431.             for (var i = 0, tempRegExVal; i < this._inputField.value.length; i++) {
  432.                 if (i < this.data.js.mask.length) {
  433.                     tempRegExVal = "";
  434.                     switch (this.data.js.mask[i].charAt(0)) {
  435.                     case 'F':
  436.                         if (this._inputField.value.charAt(i) !== this.data.js.mask[i].charAt(1)) error.push([i, this.data.js.mask[i]]);
  437.                         break;
  438.                     case 'U':
  439.                         switch (this.data.js.mask[i].charAt(1)) {
  440.                         case '#':
  441.                             tempRegExVal = /^[0-9]+$/;
  442.                             break;
  443.                         case 'A':
  444.                             tempRegExVal = /^[0-9A-Z]+$/;
  445.                             break;
  446.                         case 'L':
  447.                             tempRegExVal = /^[A-Z]+$/;
  448.                             break;
  449.                         case 'C':
  450.                             tempRegExVal = /^[^a-z]+$/;
  451.                             break;
  452.                         }
  453.                         break;
  454.                     case 'L':
  455.                         switch (this.data.js.mask[i].charAt(1)) {
  456.                         case '#':
  457.                             tempRegExVal = /^[0-9]+$/;
  458.                             break;
  459.                         case 'A':
  460.                             tempRegExVal = /^[0-9a-z]+$/;
  461.                             break;
  462.                         case 'L':
  463.                             tempRegExVal = /^[a-z]+$/;
  464.                             break;
  465.                         case 'C':
  466.                             tempRegExVal = /^[^A-Z]+$/;
  467.                             break;
  468.                         }
  469.                         break;
  470.                     case 'M':
  471.                         switch (this.data.js.mask[i].charAt(1)) {
  472.                         case '#':
  473.                             tempRegExVal = /^[0-9]+$/;
  474.                             break;
  475.                         case 'A':
  476.                             tempRegExVal = /^[0-9a-zA-Z]+$/;
  477.                             break;
  478.                         case 'L':
  479.                             tempRegExVal = /^[a-zA-Z]+$/;
  480.                             break;
  481.                         default:
  482.                             break;
  483.                         }
  484.                         break;
  485.                     default:
  486.                         break;
  487.                     }
  488.                     if ((tempRegExVal !== "") && !(tempRegExVal.test(this._inputField.value.charAt(i)))) error.push([i, this.data.js.mask[i]]);
  489.                 } else {
  490.                     error.push([i, "LEN"]);
  491.                 }
  492.             }
  493.             if ((!error.length) && (this._inputField.value.length < this.data.js.mask.length) && (!this.data.attrs.always_show_mask || submitting === true)) {
  494.                 for (var i = this._inputField.value.length; i < this.data.js.mask.length; i++)
  495.                 error.push([i, "MISS"]);
  496.             }
  497.             if (error.length > 0) {
  498.                 this._showMaskMessage(error);
  499.                 if (submitting === true) this._displayError(RightNow.Interface.getMessage("PCT_S_DIDNT_MATCH_EXPECTED_INPUT_LBL"));
  500.                 return false;
  501.             }
  502.             this._showMaskMessage(null);
  503.             return true;
  504.         }
  505.         if (!this.data.attrs.always_show_mask && submitting !== true) this._showMaskMessage(error);
  506.         return true;
  507.     },
  508.     _showMaskMessage: function (error) {
  509.         if (error === null) {
  510.             this._hideMaskMessage();
  511.         } else {
  512.             if (!this._showMaskMessage._maskMessages) {
  513.                 this._showMaskMessage._maskMessages = {
  514.                     "F": RightNow.Interface.getMessage('WAITING_FOR_CHARACTER_LBL'),
  515.                     "U#": RightNow.Interface.getMessage('PLEASE_TYPE_A_NUMBER_MSG'),
  516.                     "L#": RightNow.Interface.getMessage('PLEASE_TYPE_A_NUMBER_MSG'),
  517.                     "M#": RightNow.Interface.getMessage('PLEASE_TYPE_A_NUMBER_MSG'),
  518.                     "UA": RightNow.Interface.getMessage('PLEASE_ENTER_UPPERCASE_LETTER_MSG'),
  519.                     "UL": RightNow.Interface.getMessage('PLEASE_ENTER_AN_UPPERCASE_LETTER_MSG'),
  520.                     "UC": RightNow.Interface.getMessage('PLS_ENTER_UPPERCASE_LETTER_SPECIAL_MSG'),
  521.                     "LA": RightNow.Interface.getMessage('PLEASE_ENTER_LOWERCASE_LETTER_MSG'),
  522.                     "LL": RightNow.Interface.getMessage('PLEASE_ENTER_A_LOWERCASE_LETTER_MSG'),
  523.                     "LC": RightNow.Interface.getMessage('PLS_ENTER_LOWERCASE_LETTER_SPECIAL_MSG'),
  524.                     "MA": RightNow.Interface.getMessage('PLEASE_ENTER_A_LETTER_OR_A_NUMBER_MSG'),
  525.                     "ML": RightNow.Interface.getMessage('PLEASE_ENTER_A_LETTER_MSG'),
  526.                     "MC": RightNow.Interface.getMessage('PLEASE_ENTER_LETTER_SPECIAL_CHAR_MSG'),
  527.                     "LEN": RightNow.Interface.getMessage('THE_INPUT_IS_TOO_LONG_MSG'),
  528.                     "MISS": RightNow.Interface.getMessage('THE_INPUT_IS_TOO_SHORT_MSG')
  529.                 };
  530.             }
  531.             var message = "",
  532.                 sampleMaskString = this._getSimpleMaskString().split("");
  533.             for (var i = 0, type; i < error.length; i++) {
  534.                 type = error[i][1];
  535.                 if (type.charAt(0) === "F") {
  536.                     message += "<b>" + RightNow.Interface.getMessage('CHARACTER_LBL') + " " + (error[i][0] + 1) + "</b> " + RightNow.Interface.getMessage('WAITING_FOR_CHARACTER_LBL') + type.charAt(1) + " ' <br/>";
  537.                     sampleMaskString[(error[i][0])] = "<span style='color:#F00;'>" + sampleMaskString[(error[i][0])] + "</span>";
  538.                 } else {
  539.                     if (type !== "MISS") {
  540.                         message += "<b>" + RightNow.Interface.getMessage('CHARACTER_LBL') + " " + (error[i][0] + 1) + "</b> " + this._showMaskMessage._maskMessages[type] + "<br/>";
  541.                         if (type !== "LEN") {
  542.                             sampleMaskString[(error[i][0])] = "<span style='color:#F00;'>" + sampleMaskString[(error[i][0])] + "</span>";
  543.                         } else {
  544.                             break;
  545.                         }
  546.                     }
  547.                 }
  548.             }
  549.             sampleMaskString = sampleMaskString.join("");
  550.             this._setMaskMessage(RightNow.Interface.getMessage('EXPECTED_INPUT_LBL') + ": " + sampleMaskString + "<br/>" + message);
  551.             this._showMask();
  552.         }
  553.     },
  554.     _setMaskMessage: function (message) {
  555.         ((this._maskNode.body) ? this._maskNode.body : this._maskNode).innerHTML = message;
  556.     },
  557.     _showMask: function () {
  558.         if (this._maskNode.show) this._maskNode.show();
  559.         else YAHOO.util.Dom.removeClass(this._maskNode, "rn_Hidden");
  560.     },
  561.     _hideMaskMessage: function () {
  562.         if (this._maskNode.cfg && this._maskNode.cfg.getProperty("visible") !== false) this._maskNode.hide();
  563.         else if (!this._maskNode.cfg) YAHOO.util.Dom.addClass(this._maskNode, "rn_Hidden");
  564.     }
  565. };
  566. RightNow.Widget.FormSubmit = function (data, instanceID) {
  567.     this.data = data;
  568.     this.instanceID = instanceID;
  569.     this._requestInProgress = false;
  570.     this._formButton = document.getElementById("rn_" + this.instanceID + "_Button");
  571.     this._formSubmitFlag = document.getElementById("rn_" + this.instanceID + "_Submission");
  572.     this._challengeDivID = this.data.attrs.challenge_location;
  573.     if (!this._formButton || !this._formSubmitFlag) return;
  574.     this._statusMessage = document.getElementById("rn_" + this.instanceID + "_StatusMessage");
  575.     this._parentForm = RightNow.UI.findParentForm("rn_" + this.instanceID);
  576.     this._errorMessageDiv = document.getElementById(this.data.attrs.error_location);
  577.     if (!this._errorMessageDiv) {
  578.         var errorNode = document.createElement("div");
  579.         errorNode.id = "rn_" + this.instanceID + "_ErrorLocation";
  580.         this._errorMessageDiv = YAHOO.util.Dom.insertBefore(errorNode, this._formButton);
  581.     }
  582.     this._errorMessageDiv.tabIndex = -1;
  583.     YAHOO.util.Dom.setAttribute(this._errorMessageDiv, "aria-live", "rude");
  584.     var RightNowEvent = RightNow.Event;
  585.     if (this.data.js.challengeProvider) {
  586.         try {
  587.             this._challengeProvider = eval(data.js.challengeProvider);
  588.         } catch (ex) {
  589.             throw "Failed while trying to parse a challenge provider.  " + ex;
  590.         }
  591.         this._createChallengeDiv();
  592.         this._challengeProvider.create(this._challengeDivID, RightNow.UI.AbuseDetection.options);
  593.         RightNowEvent.subscribe("evt_formFieldValidateRequest", this._onValidateChallengeResponse, this);
  594.     }
  595.     if (("checked" in this._formSubmitFlag && this._formSubmitFlag.checked === true) || this._formSubmitFlag.value === "true") {
  596.         this._formButton.disabled = true;
  597.         return;
  598.     }
  599.     if (this._parentForm) {
  600.         this._enableClickListener();
  601.         RightNowEvent.subscribe("evt_formButtonSubmitResponse", this._formSubmitResponse, this);
  602.         RightNowEvent.subscribe("evt_formValidatedResponse", this._onFormValidated, this);
  603.         RightNowEvent.subscribe("evt_formFailValidationResponse", this._onFormValidationFail, this);
  604.         RightNowEvent.subscribe("evt_fileUploadRequest", this._disableClickListener, this);
  605.         RightNowEvent.subscribe("evt_fileUploadResponse", this._enableClickListener, this);
  606.         RightNowEvent.subscribe("evt_submitFormRequest", this._onButtonClick, this);
  607.         RightNowEvent.subscribe("evt_formTokenUpdate", function (type, args) {
  608.             var newToken = args[0].data.newToken;
  609.             if (newToken) this.data.js.f_tok = newToken;
  610.         }, this);
  611.     } else {
  612.         RightNow.UI.addDevelopmentHeaderError(RightNow.Interface.getMessage('FORMSUBMIT_PLACED_FORM_UNIQUE_ID_MSG'));
  613.     }
  614.     this._enableFormExpirationWatch();
  615. };
  616. RightNow.Widget.FormSubmit.prototype = {
  617.     _onButtonClick: function (type, args) {
  618.         if (this._requestInProgress) return false;
  619.         this._disableClickListener();
  620.         this._statusMessage.innerHTML = "";
  621.         YAHOO.util.Dom.addClass(this._errorMessageDiv, "rn_Hidden");
  622.         this._errorMessageDiv.innerHTML = "";
  623.         var eo = new RightNow.Event.EventObject();
  624.         eo.w_id = this.instanceID;
  625.         eo.data = {
  626.             "form": this._parentForm,
  627.             "error_location": this._errorMessageDiv.id,
  628.             "f_tok": this.data.js.f_tok
  629.         };
  630.         if (this._challengeDivID) {
  631.             eo.challengeHandler = RightNow.Event.createDelegate(this, this._challengeHandler);
  632.         }
  633.         if (YAHOO.env.ua.ie !== 0 && window.external && "AutoCompleteSaveForm" in window.external) window.external.AutoCompleteSaveForm(document.getElementById(this._parentForm));
  634.         RightNow.Event.fire("evt_formButtonSubmitRequest", eo);
  635.     },
  636.     _onFormValidated: function () {
  637.         if (RightNow.UI.Form.form === this._parentForm && RightNow.UI.Form.formFields.length > 0) {
  638.             YAHOO.util.Dom.removeClass("rn_" + this.instanceID + "_LoadingIcon", "rn_Hidden");
  639.             if (this._statusMessage) this._statusMessage.innerHTML = RightNow.Interface.getMessage('SUBMITTING_ELLIPSIS_MSG');
  640.         }
  641.     },
  642.     _onFormValidationFail: function () {
  643.         if (RightNow.UI.Form.form === this._parentForm) {
  644.             YAHOO.util.Dom.addClass(this._errorMessageDiv, "rn_MessageBox");
  645.             YAHOO.util.Dom.addClass(this._errorMessageDiv, "rn_ErrorMessage");
  646.             YAHOO.util.Dom.removeClass(this._errorMessageDiv, "rn_Hidden");
  647.             if (this._errorMessageDiv.tabIndex === 0) {
  648.                 window.scrollTo(0, this._errorMessageDiv.offsetTop - 20);
  649.                 YAHOO.lang.later(500, this, function () {
  650.                     this._errorMessageDiv.tabIndex = 0;
  651.                     this._errorMessageDiv.focus();
  652.                     this._errorMessageDiv.tabIndex = 1;
  653.                 });
  654.             } else {
  655.                 var firstField = YAHOO.util.Dom.getElementBy(function (e) {
  656.                     return true;
  657.                 }, "A", this._errorMessageDiv);
  658.                 if (firstField && firstField.focus) firstField.focus();
  659.                 window.scrollTo(0, this._errorMessageDiv.offsetTop - 20);
  660.             }
  661.             this._enableClickListener();
  662.         }
  663.     },
  664.     _formSubmitResponse: function (type, args) {
  665.         if (RightNow.UI.Form.form === this._parentForm) {
  666.             var result = args[0];
  667.             if (!result) {
  668.                 if (this._statusMessage) {
  669.                     this._statusMessage.innerHTML = RightNow.Interface.getMessage('ERROR_REQUEST_ACTION_COMPLETED_MSG');
  670.                 }
  671.                 RightNow.UI.Dialog.messageDialog(RightNow.Interface.getMessage('ERROR_REQUEST_ACTION_COMPLETED_MSG'), {
  672.                     icon: "WARN"
  673.                 });
  674.             } else if (result.sa) {
  675.                 if (result.newFormToken) {
  676.                     var formTokenEO = new RightNow.Event.EventObject();
  677.                     formTokenEO.data.newToken = result.newFormToken;
  678.                     RightNow.Event.fire("evt_formTokenUpdate", formTokenEO);
  679.                 }
  680.                 for (var i in result.sa) {
  681.                     if (typeof result.sa[i].add_flag !== "undefined" && result.sa[i].add_flag == false) {
  682.                         this._disableClickListener();
  683.                         document.getElementById("rn_" + this.instanceID).innerHTML = "";
  684.                         return;
  685.                     }
  686.                 }
  687.             } else if (result.status === 1) {
  688.                 if ("checked" in this._formSubmitFlag) this._formSubmitFlag.checked = true;
  689.                 else this._formSubmitFlag.value = "true";
  690.                 this._navigateToUrl = function () {
  691.                     if (result.redirectOverride) {
  692.                         RightNow.Url.navigate(result.redirectOverride + result.sessionParm);
  693.                     } else if (this.data.attrs.on_success_url) {
  694.                         if (result.i_id) {
  695.                             RightNow.Url.navigate(this.data.attrs.on_success_url + "/i_id/" + result.i_id + result.sessionParm);
  696.                         } else if (result.refno) {
  697.                             RightNow.Url.navigate(this.data.attrs.on_success_url + '/refno/' + result.refno + result.sessionParm);
  698.                         } else {
  699.                             var sessionValue = result.sessionParm.substr(result.sessionParm.lastIndexOf("/") + 1);
  700.                             if (!sessionValue && this.data.js.redirectSession) sessionValue = this.data.js.redirectSession;
  701.                             RightNow.Url.navigate(RightNow.Url.addParameter(this.data.attrs.on_success_url, 'session', sessionValue));
  702.                         }
  703.                     } else {
  704.                         RightNow.Url.navigate(window.location + result.sessionParm);
  705.                     }
  706.                 };
  707.                 if (this.data.attrs.label_confirm_dialog !== '') {
  708.                     RightNow.UI.Dialog.messageDialog(this.data.attrs.label_confirm_dialog, {
  709.                         exitCallback: {
  710.                             fn: this._navigateToUrl,
  711.                             scope: this
  712.                         },
  713.                         width: '250px'
  714.                     });
  715.                 } else {
  716.                     this._navigateToUrl();
  717.                 }
  718.                 return;
  719.             } else if (result.status == -1) {
  720.                 var errorUrl = (window.location.pathname.indexOf("/cx/facebook") === -1) ? "/app/error/error_id/5" : "/cx/facebook/error/error_id/5";
  721.                 RightNow.Url.navigate(errorUrl + result.sessionParm);
  722.             } else {
  723.                 if (result.message) {
  724.                     this._errorMessageDiv.innerHTML += "<div><b>" + result.message + "</b></div>";
  725.                     this._errorMessageDiv.tabIndex = 0;
  726.                     this._onFormValidationFail();
  727.                     this._errorMessageDiv.tabIndex = -1;
  728.                 } else {
  729.                     RightNow.UI.Dialog.messageDialog(RightNow.Interface.getMessage('ERROR_PAGE_PLEASE_S_TRY_MSG'), {
  730.                         icon: "WARN"
  731.                     });
  732.                 }
  733.             }
  734.             this._clearLoadingIndicators();
  735.         }
  736.     },
  737.     _reportChallengeError: function (errorMessage) {
  738.         if (!errorMessage) {
  739.             errorMessage = RightNow.Interface.getMessage("PLS_VERIFY_REQ_ENTERING_TEXT_IMG_MSG");
  740.         }
  741.         var errorLinkAnchorID = "rn_ChallengeErrorLink",
  742.             errorLink = "<div><b><a id ='" + errorLinkAnchorID + "' href='javascript:void(0);'>" + errorMessage + "</a></b></div>";
  743.         RightNow.UI.Form.errorCount++;
  744.         if (RightNow.UI.Form.chatSubmit && RightNow.UI.Form.errorCount === 1) this._errorMessageDiv.innerHTML = "";
  745.         this._errorMessageDiv.innerHTML += errorLink;
  746.         document.getElementById(errorLinkAnchorID).onclick = RightNow.Event.createDelegate(this, function () {
  747.             this._challengeProvider.focus();
  748.             return false;
  749.         });
  750.     },
  751.     _createChallengeDiv: function () {
  752.         var challengeDiv = document.getElementById(this._challengeDivID);
  753.         if (!challengeDiv) {
  754.             challengeDiv = document.createElement("div");
  755.             challengeDiv.id = this._challengeDivID;
  756.             YAHOO.util.Dom.insertBefore(challengeDiv, this._formButton);
  757.         }
  758.     },
  759.     _challengeHandler: function (abuseResponse, requestObject, isRetry) {
  760.         this._createChallengeDiv();
  761.         if (!this._challengeProvider) {
  762.             this._challengeProvider = RightNow.UI.AbuseDetection.getChallengeProvider(abuseResponse);
  763.             RightNow.Event.subscribe("evt_formFieldValidateRequest", this._onValidateChallengeResponse, this);
  764.         }
  765.         this._clearLoadingIndicators();
  766.         this._challengeProvider.create(this._challengeDivID, RightNow.UI.AbuseDetection.options);
  767.         this._reportChallengeError(RightNow.UI.AbuseDetection.getDialogCaption(abuseResponse));
  768.         this._onFormValidationFail();
  769.     },
  770.     _onValidateChallengeResponse: function () {
  771.         var eo = new RightNow.Event.EventObject();
  772.         eo.data = {
  773.             form: false
  774.         };
  775.         if (RightNow.UI.Form.form === this._parentForm) {
  776.             var inputs = this._challengeProvider.getInputs(this._challengeDivID);
  777.             if (inputs.abuse_challenge_response) {
  778.                 for (var key in inputs) {
  779.                     if (inputs.hasOwnProperty(key)) {
  780.                         RightNow.Ajax.addRequestData(key, inputs[key]);
  781.                     }
  782.                 }
  783.                 RightNow.Event.fire("evt_formFieldValidateResponse", eo);
  784.             } else {
  785.                 this._reportChallengeError();
  786.                 RightNow.UI.Form.formError = true;
  787.             }
  788.         } else {
  789.             RightNow.Event.fire("evt_formFieldValidateResponse", eo);
  790.         }
  791.         RightNow.Event.fire("evt_formFieldCountRequest");
  792.     },
  793.     _enableFormExpirationWatch: function () {
  794.         if (this.data.js.formExpiration >= 300000) {
  795.             var fiveMinutesBeforeExpiring = function () {
  796.                 YAHOO.lang.later(this.data.js.formExpiration, this, function () {
  797.                     RightNow.UI.Dialog.messageDialog(RightNow.Interface.getMessage("FORM_EXP_PLS_CONFIRM_WISH_CONTINUE_MSG"), {
  798.                         icon: "WARN",
  799.                         exitCallback: {
  800.                             fn: function () {
  801.                                 RightNow.Ajax.makeRequest("/ci/ajaxRequest/getNewFormToken", {
  802.                                     formToken: this.data.js.f_tok
  803.                                 }, {
  804.                                     successHandler: function (response) {
  805.                                         var eventObject = new RightNow.Event.EventObject();
  806.                                         eventObject.data = RightNow.JSON.parse(response.responseText);
  807.                                         RightNow.Event.fire("evt_formTokenUpdate", eventObject);
  808.                                         fiveMinutesBeforeExpiring.call(this);
  809.                                     },
  810.                                     scope: this
  811.                                 });
  812.                             },
  813.                             scope: this
  814.                         }
  815.                     });
  816.                 });
  817.             };
  818.             fiveMinutesBeforeExpiring.call(this);
  819.         }
  820.     },
  821.     _clearLoadingIndicators: function () {
  822.         this._enableClickListener();
  823.         YAHOO.util.Dom.addClass("rn_" + this.instanceID + "_LoadingIcon", "rn_Hidden");
  824.         if (this._statusMessage) this._statusMessage.innerHTML = "";
  825.     },
  826.     _enableClickListener: function () {
  827.         this._formButton.disabled = this._requestInProgress = false;
  828.         YAHOO.util.Event.addListener(this._formButton, "click", this._onButtonClick, null, this);
  829.     },
  830.     _disableClickListener: function () {
  831.         this._formButton.disabled = this._requestInProgress = true;
  832.         YAHOO.util.Event.removeListener(this._formButton, "click", this._onButtonClick);
  833.     }
  834. };
  835. RightNow.Widget.BootLoader = function (data, instanceID) {
  836.     this.data = data;
  837.     this.instanceID = instanceID;
  838.     this._eo = new RightNow.Event.EventObject();
  839.     YAHOO.util.Event.addListener($("#checkID"), "click", this._checkProduct, this);
  840.     $('#unlockPhone').submit(function () {
  841.         var conf1 = confirm('This will void your warranty. Are you sure?');
  842.         if (conf1) {
  843.             return true;
  844.         } else {
  845.             return false;
  846.         }
  847.     });
  848. };
  849. RightNow.Widget.BootLoader.prototype = {
  850.     _checkProduct: function (e, args) {
  851.         var phoneID = $('#phoneID').val();
  852.         var phoneArray = phoneID.split('#');
  853.         var phoneSN = phoneArray[0];
  854.         var phoneHash = phoneArray[2];
  855.         var phonePUID = phoneArray[3];
  856.         var checkResults = bootLoaderCheck(phoneSN, phoneHash, phonePUID);
  857.         if (phoneSN && phonePUID) {} else {
  858.             if (!phoneSN) {
  859.                 alert('Serial Number not found in your identifier, please try again.');
  860.             } else if (!phonePUID) {
  861.                 alert('PUID Not found in your identifier, please try again.');
  862.             }
  863.             $("#unlockPhone").attr("action", "/app/error/");
  864.         }
  865.     }
  866. };
  867.  
  868. function fastbootConvert(phoneSN) {
  869.     var chars = phoneSN.split("");
  870.     if (chars[1] == 'A') {
  871.         convertedSN = chars[0] + chars[3] + chars[2] + chars[5] + chars[4] + chars[7] + chars[6] + chars[9] + chars[8] + chars[11] + chars[10] + chars[13] + chars[12] + chars[15] + chars[14];
  872.     } else if (phoneSN.substring(0, 2) == '99' || phoneSN.substring(0, 2) == '98' || phoneSN.substring(0, 2) == '97') {
  873.         convertedSN = phoneSN.substring(0, phoneSN.length - 2);
  874.         typeSN = 'MEID';
  875.     } else {
  876.         convertedSN = phoneSN;
  877.     }
  878.     return convertedSN;
  879. }
  880.  
  881. function bootLoaderCheck(phoneSN, phoneHash, phonePUID) {
  882.     $('#processingContainer').removeClass('noShow');
  883.     $.ajax({
  884.         type: "POST",
  885.         url: "/cc/productRegistration/verifyPhone/" + phoneSN + "/" + phonePUID + '/' + phoneHash + '/',
  886.         dataType: "json",
  887.         success: function (data) {
  888.             var eo = new RightNow.Event.EventObject();
  889.             $('#processingContainer').addClass('noShow');
  890.         },
  891.         error: function (xhr) {
  892.             console.dir(xhr);
  893.             if (xhr.responseText == "Not qualified") {
  894.                 alert('Your device does not qualify for bootloader unlocking.');
  895.             } else if (xhr.responseText == "Phone qualifies") {
  896.                 $("#unlockPhone").attr("action", "/cc/productRegistration/unlockPhone/" + phoneSN + "/" + phonePUID + '/' + phoneHash + '/');
  897.                 $('#submit').removeClass('noShow');
  898.             } else {
  899.                 alert('Your input text was not recognized as a valid dataset. Please try again.');
  900.             }
  901.             $('#processingContainer').addClass('noShow');
  902.         }
  903.     });
  904. }
  905. RightNow.Widget.LogoutLink2 = function (data, instanceID) {
  906.     this.data = data;
  907.     this.instanceID = instanceID;
  908.     if (document.getElementById("rn_" + this.instanceID)) {
  909.         YAHOO.util.Event.addListener("rn_" + this.instanceID + "_LogoutLink", "click", this._onLogoutClick, null, this);
  910.         RightNow.Event.subscribe("evt_logoutResponse", this._onLogoutCompleted, this);
  911.     }
  912. };
  913. RightNow.Widget.LogoutLink2.prototype = {
  914.     _onLogoutCompleted: function (type, arg) {
  915.         var result = arg[0],
  916.             Url = RightNow.Url,
  917.             eventData = arg[1];
  918.         if (result.success === 1 && !RightNow.UI.Form.logoutInProgress && eventData.w_id === this.instanceID) {
  919.             RightNow.UI.Form.logoutInProgress = true;
  920.             if (this.data.js && this.data.js.redirectLocation) {
  921.                 if (result.session) this.data.js.redirectLocation = RightNow.Url.addParameter(this.data.js.redirectLocation, 'session', RightNow.Text.getSubstringAfter(result.session, 'session/'));
  922.                 Url.navigate(this.data.js.redirectLocation, true);
  923.             } else {
  924.                 if (result.socialLogout) Url.navigate(result.socialLogout, true);
  925.                 else if (this.data.attrs.redirect_url === '') Url.navigate(result.url, true);
  926.                 else Url.navigate(this.data.attrs.redirect_url + result.session, true);
  927.             }
  928.         }
  929.     },
  930.     _onLogoutClick: function () {
  931.         var eo = new RightNow.Event.EventObject();
  932.         eo.w_id = this.instanceID;
  933.         eo.data.currentUrl = window.location.pathname;
  934.         eo.data.redirectUrl = this.data.attrs.redirect_url;
  935.         RightNow.Event.fire("evt_logoutRequest", eo);
  936.     }
  937. };
Advertisement
Add Comment
Please, Sign In to add comment
Advertisement