include("lib.prototype");
include("lib.tristate");
include("fitbank.proc.clases");
include("fitbank.formulario");
include("fitbank.util");
include("fitbank.logger");
include("fitbank.ui.estatus");
include("fitbank.ui.tabs");
include("fitbank.ui.teclas");
include("lib.fastclick");
/**
* Espacio horizontal que se debe guardar para poner barras de scroll
*/
var WIDTH_SPACE_NORMAL = 20;
/**
* Espacio vertical que se debe guardar para poner barras de scroll
* (contando tambien barras de herramientas, de teclas, etc).
*/
var HEIGHT_SPACE_NORMAL = 200;
/**
* Espacio vertical que se debe guardar para poner barras de scroll
* (contando tambien barras de herramientas, etc) menos las teclas.
* Para mostrar aplicaciones remotas unicamente
*/
var HEIGHT_SPACE_NO_KEYS = 80;
/**
* Espacio vertical que se debe guardar para poner barras de scroll
* (contando tambien barras de herramientas, etc) menos las teclas.
* Para mostrar aplicaciones remotas unicamente
*/
var HEIGHT_SPACE_REMOTE = 30;
/**
* Class Contexto - Contiene información sobre el contexto en que se ejecuta un
* formulario.
*/
var Contexto = Class.create( {
widthSpace: WIDTH_SPACE_NORMAL,
heightSpace: HEIGHT_SPACE_NORMAL,
/**
* Id del contexto.
*/
id: null,
/**
* Indica si el contexto actual, es para un entorno remoto.
*/
isRemoteContext: window.location.pathname.endsWith("entornolimpio.html"),
/**
* Formulario.
*/
formulario: null,
/**
* Elemento FORM que contiene los campos.
*/
form: null,
/**
* Elemento donde se carga el contexto.
*/
elemento: null,
/**
* Lista Valores actualmente visibles.
*/
listaValores: null,
/**
* Es un contexto secundario.
*/
secundario: false,
/**
* Subcontextos.
*/
subContextos: $A(),
/**
* Si el contexto es remoto, contiene el iframe del formulario.
*/
remoto: null,
/**
* Variables del contexto.
*/
vars: {},
/**
* Elementos en su estado original (al cargar o despues de una peticion).
*/
originalElements: {},
/**
* Guarda la navegación para cuando se utiliza ReturnLink.
*/
navegacion: $A(),
/**
* Variable que indica si se deben guardar los webpages en cache para esta
* sesion web.
*/
saveWebpagesInCache: Parametros['fitbank.cacheWebpages.ENABLED'] == "true",
/**
* Guarda un registro de formularios previamente cargados (carga en cache)
* Valido unicamente para la sesion web actual.
*
* Se reinicia en cada nueva sesion.
*/
webpagesCache: $H(),
//Constructor, llamado automáticamente por Prototype.
initialize: function(elemento, secundario) {
this.elemento = $(elemento);
this.secundario = secundario;
this.reset();
},
reset: function(keepContent) {
this.id = Math.round(Math.random() * 10000);
this.formulario = new Formulario();
this.subContextos = $A();
this.consultar = this._consultar;
this.mantener = this._mantener;
this.limpiar = this._limpiar;
this.ayudar = this._ayudar;
this.menuRapido = this._menuRapido;
this.mostrarVersion = this._mostrarVersion;
this.recargar = this._recargar;
this.calcular = this._calcular;
if (!keepContent) {
this.elemento.update("");
}
this.elemento.removeClassName("remote");
this.remoto = null;
ListaFormularios.cargar();
this.widthSpace = WIDTH_SPACE_NORMAL;
this.heightSpace = this.isRemoteContext ? HEIGHT_SPACE_REMOTE : HEIGHT_SPACE_NORMAL;
},
resize: function(contenedor) {
var resizeElement = document.onresize ? document : window;
if (!contenedor.visible()) {
contenedor.resize.stop();
return;
}
if(!Mobile) {
contenedor.setStyle({
maxWidth: ($(document.body).getWidth() - this.widthSpace) + "px",
maxHeight: ($(document.body).getHeight() - this.heightSpace) + "px"
});
}
if (!contenedor.resize) {
contenedor.resize = Event.on(resizeElement, "resize",
this.resize.bind(this, contenedor));
}
},
/**
* Revisa si existen cambios pendientes en el formulario y pregunta si se
* quiere continuar. Devuelve true si se cancela la acción. False en caso
* de que no existan cambios.
*/
revisarCambios: function() {
return Parametros['fitbank.revisarCambios.ENABLED'] == "true"
&& Util.checkForChanges(this.originalElements)
&& !confirm(Util.getMensaje(Mensajes, "fitbank.contexto.CAMBIOS"));
},
/**
* Devuelve las opciones indicadas con los defaults para los campos no
* especificados.
*
* @private
*/
_default: function(opciones) {
return Object.extend({
subsistema: null,
transaccion: null,
campos: null,
nameMap: null,
objetoJS: null,
action: null,
fields: null,
consulta: true,
reset: true,
registro: 0,
fullQuery: false
}, opciones);
},
/**
* Carga un formulario. Las opciones que acepta son las siguientes:
*
*
* - subsistema
- (String) Subsistema
* - transaccion
- (String) Transaccion
* - campos
- (Objeto) Indica los campos que se van a cargar en el próximo
* formulario, en la forma { "nameOtroFormulario": valor, ... }
* - nameMap
- (Objeto) Es el mapa de nombres de campos en la forma
* { "nameFormularioDestino": "nameFormularioActual", ... }
* para poder tener links de regreso
* - objetoJS
- En Caso de que el link quiera mandar un objeto JS
* - action
- (String) Acción extra a ser ejecutada: "NEXT", "PREV", "END"
* - fields
- (Objeto) Es el mapa de nombres de campos en la forma
* { "nameFormularioActual": "id", ... }
* - consulta
- (boolean) Indica si se consulta despues de cargar el
* formulario, solo sirve si se paso la opcion campos
* - registro
- (int) Registro destino de la carga de campos
*
*
* @param opciones (Object) objeto con las opciones
*/
cargar: function(opciones) {
if (this._revisarBloqueo() || this.revisarCambios()) {
return;
}
// Soportar llamada con muchos parámetros
if (Object.isString(opciones)) {
Logger.warning("Se está llamando a Contexto#cargar incorrectamente");
var n = Object.isString(arguments[1]) ? 2 : 1;
opciones = {
subsistema: arguments[0],
transaccion: arguments[1],
campos: arguments[n++],
nameMap: arguments[n++],
objetoJS: arguments[n++]
}
if (n == 1) {
opciones.st = opciones.subsistema;
}
}
var pt = $("entorno-pt");
if (opciones.st) {
opciones.st = opciones.st.replace(/[^\d]/g, "");
if (opciones.st.length <= 2) {
Estatus.mensaje("Ingrese por lo menos 3 digitos.", null, "error");
pt && Form.Element.activate("entorno-pt");
return;
}
opciones.subsistema = opciones.st.substring(0, 2);
opciones.transaccion = opciones.st.substring(2, 6);
opciones.st = null;
}
opciones = this._default(opciones);
while (opciones.transaccion.length < 4) {
opciones.transaccion = 0 + opciones.transaccion;
}
// Información necesaria para los links de regreso
if (opciones.nameMap) {
this.navegacion.push({
subsistema: this.formulario.subsistema,
transaccion: this.formulario.transaccion,
nameMap: opciones.nameMap,
objetoJS: opciones.objetoJS
});
} else if (opciones.nameMap == null
|| typeof opciones.nameMap == "undefined") {
this.navegacion.clear();
}
if (!this.secundario && pt) {
pt.value = opciones.subsistema + "-" + opciones.transaccion;
}
this._obtener(opciones);
},
_revisarBloqueo: function() {
if (Entorno.bloqueado()) {
Estatus.mensaje("Por favor espere a que el proceso actual termine.",
null, "warning");
return true;
} else {
return false;
}
},
/**
* @private
*/
_obtener: function(opciones) {
if (opciones.reset) {
this.reset(true);
}
var cargandoTexto = Mobile ? "Cargando..." : "Cargando formulario...";
this.idProceso = Estatus.iniciarProceso(cargandoTexto);
//Obtener informacion del formulario desde cache
var cache = this.webpagesCache.get(opciones.subsistema + opciones.transaccion);
var request;
if (cache) {
this.id = cache.contexto;
this.mostrarForm(opciones, cache.respuesta);
request = null;
} else {
request = new Ajax.Request('proc/' + (opciones.tipo || GeneralRequestTypes.FORM), {
parameters: {
_contexto: this.id,
_subs: opciones.subsistema,
_tran: opciones.transaccion,
_values: Object.toJSON(opciones.values),
_fields: Object.toJSON(opciones.fields),
_action: opciones.action
},
onSuccess: this.mostrarForm.bind(this, opciones),
onFailure: this.onError.bind(this),
onException: rethrow
});
}
Estatus.getProceso(this.idProceso).setRequest(request);
},
/**
* @private
*/
mostrarFormSimple: function(opciones, respuesta) {
var json = respuesta.responseJSON;
this.formulario = new Formulario(Object.extend({
subsistema: this.subsystem,
transaccion: this.transaction
}, json));
this.elemento.update(this._crearTitulo(json));
document.title = json.titulo + " - FitBank";
var contenedor = new Element("div", {
className: "entorno-html"
}).update(json.html);
this.resize(contenedor);
this.elemento.insert(contenedor);
this._initFormularioSimple.bind(this).defer(respuesta, opciones);
},
/**
* @private
*/
mostrarForm: function(opciones, respuesta) {
var json = respuesta.responseJSON;
opciones = this._default(opciones);
// Cargar variables del contexto que vienen del transporte db
$H(json && json.db).keys().each(function(key) {
this[key] = json.db[key];
}, this);
this.accountingDate = new Date(this.accountingDate);
var original = this.formulario;
this.formulario = new Formulario(Object.extend({
subsistema: this.subsystem,
transaccion: this.transaction
}, json));
// Copiar estados originales
if (!opciones.reset) {
this.formulario.consultado = original.consultado;
}
ListaFormularios.cargar(json.navigation);
var contenedor;
if (this.secundario) {
contenedor = this.elemento;
} else {
contenedor = new Element("div", {
className: "entorno-html"
});
this.resize(contenedor);
this.elemento.update(this._crearTitulo(json));
document.title = json.titulo + " - FitBank";
}
if(Mobile) {
FastClick.attach(contenedor);
FastClick.attach($('entorno-teclas'));
}
contenedor.insert(json.html);
//Limpiar datepickers del formulario anterior
if(!Mobile) {
datePickerController && datePickerController.cleanUp();
//En este punto ya está disponible la información de idioma.
//Configurar a todos los datepickers con el idioma del formulario.
datePickerController && datePickerController.setGlobalOptions({
lang: (this.language || "es").toLowerCase()
});
}
if (!this.secundario) {
this.elemento.insert(contenedor);
}
//Guardar la respuesta del formulario en cache
if (this.saveWebpagesInCache) {
this.webpagesCache.set(this.subsystem + this.transaction, {
contexto: this.id,
respuesta: respuesta
});
}
this._initFormulario.bind(this).defer(respuesta, opciones);
},
/**
* @private
*/
_crearTitulo: function(json) {
var div = new Element("div", {
className: "entorno-formulario-titulo"
});
div.update(json.titulo);
return div;
},
/**
* Inicializa un formulario remoto
*
* @param src dirección de la página a la que se hace el post
* @param id Id del elemento
* @param consultar si es true hace una consulta previa.
* @param post usar POST o GET.
* @param hideKeys Muestra o no las teclas de F1...F12
* @param initRemoto Especifica si se debe iniciar un proceso y mostrar la
* animación en la barra de estado.
* @param expand Indica si se va a expandir el iFrame en todo el entorno
*/
initRemoto: function(src, id, consultar, post, hideKeys, initRemoto, expand) {
this.remoto = $(id);
this.remoto.on("load", c._registrarRemoto.bind(c));
var callback = (function() {
var params = $H({
_subs: this.formulario.subsistema,
_tran: this.formulario.transaccion,
_contexto: this.id
});
if (initRemoto) {
var cargandoTextoExterno = Mobile ? "Carga externa..." : "Cargando formulario externo...";
this.idInicial = Estatus.iniciarProceso(cargandoTextoExterno);
} else {
Estatus.mensaje("Formulario externo activo", null, false);
}
var files = Form.getInputs(this.form, "file");
var action = this.form.action;
var separador = src.indexOf("?") > 0 ? "&" : "?";
this.form.onsubmit = "return true;";
this.form.method = post ? "POST" : "GET";
this.form.enctype = post && files.length ? "multipart/form-data" : "";
this.form.action = src + separador + params.toQueryString();
this.form.target = id;
this.form.submit();
this.form.action = action;
this.form.onsubmit = "return false;";
}).bind(this);
if (consultar) {
this.consultar.bind(this).defer(null, Function.defer.bind(callback));
} else {
callback.defer();
}
if (hideKeys) {
Teclas.esconder();
this.heightSpace = this.HEIGHT_SPACE_NO_KEYS;
}
if (expand) {
var interval = setInterval(function() {
if (!c.remoto) {
clearInterval(interval);
return;
}
c.remoto.setStyle({
width: ($(document.body).getWidth() - c.widthSpace - 10) + "px",
height: ($(document.body).getHeight() - c.heightSpace - 10) + "px"
});
}, 1000);
this.resize(this.form.up());
}
},
/**
* Registra un formulario remoto.
*
* @private
*/
_registrarRemoto: function() {
this.elemento.addClassName("remote");
var cw = Util.getContentWindow(this.remoto);
this.consultar = cw.consultar;
this.mantener = cw.mantener;
this.limpiar = cw.limpiar;
this.recargar = cw.recargar;
this.ayudar = cw.ayudar;
this.menuRapido = cw.menuRapido;
this.calcular = cw.calcular;
var proceso = c.idInicial;
cw.addStatusListener && cw.addStatusListener(function(mensaje, iniciar, cod) {
if (iniciar) {
proceso = Estatus.iniciarProceso(mensaje);
} else {
Estatus.finalizarProceso(mensaje, proceso, cod != 0 ? "error" : "");
}
});
cw.addTransactionListener && cw.addTransactionListener(function(st, t) {
st = Object.isString(t) ? st + ":" + t : st;
st = st.replace(/[^\d]/g, "");
var subs = st.substring(0, 2);
var tran = st.substring(2, 6);
var pt = $("entorno-pt");
if (pt) {
pt.value = subs + "-" + tran;
}
});
},
/**
* Inicializa el formulario
*
* @private
*/
_initFormularioSimple: function(respuesta, opciones) {
this.form = this.elemento.select("form")[0];
Tabs.reset();
this.loadValues(respuesta);
this.$$("*[registro]").each(function(elemento) {
elemento.removeAttribute("id");
elemento.removeAttribute("name");
});
var tables = c.$$("table");
document.on("scroll", function() {
tables.each(function(elemento) {
if (elemento.viewportOffset().top < 0) {
elemento.addClassName("fixed");
} else {
elemento.removeClassName("fixed");
}
});
});
},
/**
* Inicializa el formulario
*
* @private
*/
_initFormulario: function(respuesta, opciones) {
var json = respuesta.responseJSON;
this.form = this.elemento.select("form")[0];
Tabs.reset(opciones === true || opciones && opciones.mantenerTab);
this.$$("input, select, textarea, button").each(function(elemento) {
elemento.on("focus", (function(e) {
elemento.focused = true;
this.formulario.controlConFoco = elemento.name;
this.formulario.registroActivo = elemento.registro;
}).bind(this));
elemento.on("blur", (function(e) {
elemento.focused = false;
}).bind(this));
elemento.focused = false;
// Para llamar formateadores con valores completos
var change = (function(e) {
e.options = e.options || {};
if (e.options.load) {
return;
}
// Solo llamar una vez este onchange por evento
if (elemento._disparando) {
return;
}
elemento._disparando = true;
(function() {
elemento._disparando = false;
elemento._processValue(e.options);
this.calcular();
}).bind(this).defer();
}).bind(this);
var blur = (function(e) {
e.options = e.options || {};
if (e.options.load) {
return;
}
(function() {
elemento._processValue(e.options);
this.calcular();
}).bind(this).defer();
}).bind(this);
elemento.on("blur", blur);
elemento.on("change", change);
// Para llamar formateadores con valores parciales y asegurarse que
// se dispare onchange si se cambio el valor. Bug de Chrome: 92492
elemento.on("keyup", (function(e) {
if (elemento._processValue({
partial: true
}) && !elemento.onblurchange) {
elemento.onblurchange = elemento.on("blur", function() {
elemento.fireDOMEvent("change", {
generated: false
});
elemento.onblurchange.stop();
elemento.onblurchange = null;
});
}
}).bind(this));
if (elemento.type == "checkbox") {
Util.initCheckBox(elemento);
}
if (elemento.tagName.toLowerCase() == "select") {
Util.initComboBox(elemento);
}
elemento.originalTabIndex = elemento.getAttribute("tabindex-original");
}, this);
this.$$("*[registro]").each(function(elemento) {
elemento.registro = parseInt(elemento.getAttribute("registro")) || 0;
});
this.$$("tr.clonada input").each(function(input) {
var tr = input.up("tr");
input.on("blur", function() {
tr.removeClassName("selected");
});
input.on("focus", function() {
tr.addClassName("selected");
});
});
$H(json.values).each(function(pair) {
var name = pair.key;
var obj = pair.value;
this.$N(name).each(function(element, n) {
if (element.widget) {
element = element.widget;
}
element.setDisabled(obj.disabled[n]);
}, this);
}, this);
if (!this.isRemoteContext) {
Teclas.mostrar();
}
this.formulario.jsInicial();
this.loadValues(respuesta);
this.formulario.evalFormulas();
this.calcular();
(function () {
this.formulario.jsInicialWebPage();
var firstFocus = this.$N(this.formulario.firstFocus, 0);
if (firstFocus) {
Form.Element.activate(firstFocus);
}
if (opciones.campos) {
opciones.campos = $H(opciones.campos);
opciones.campos.keys().each(function(campo) {
c.$N(campo, opciones.registro).changeValue(opciones.campos.get(campo));
}, this);
if (opciones.consulta) {
this.consultar.bind(this).defer();
}
}
if (opciones.posLink) {
this._checkError(opciones.posLink.curry(opciones),
Util.getMensaje(Mensajes, 'fitbank.contexto.ERROR_POSLINK'));
}
//Registrar los campos y sus valores originales en la carga del formulario
this.originalElements = Util.getOriginalElements();
this._checkError.defer(this.formulario.posCargar.bind(this.formulario),
Util.getMensaje(Mensajes, 'fitbank.contexto.ERROR_POSCARGAR'));
}).bind(this).defer();
this._mostrarControlesTablaDinamica();
this._mostrarMensajeTablaDinamica(Util.getMensaje(Mensajes, 'fitbank.contexto.dynamictable.PERFORM_QUERY'),
this.consultar.bind(this));
//Si el container es oculto, ocultar su titulo tambien.
$$("fieldset .oculto").each(function (elemento) {
elemento.up("fieldset").addClassName("oculto");
});
Mobile && Mobile.initForm();
},
_checkError: function(funcion, mensaje) {
var res;
var stacktrace = null;
if (!funcion) {
return false;
}
try {
res = funcion();
} catch(e) {
res = false;
stacktrace = e && e.stack;
}
if (res === false) {
Estatus.mensaje(mensaje, stacktrace, "error");
return true;
} else if (res && res.length > 1) {
Estatus.mensaje(res, stacktrace, "error");
return true;
}
return false;
},
/**
* Revisa que no existan campos sin validarse.
**/
_validar: function() {
var errorElements = [];
this.$$('tr.delete-record').each(function(row) {
row.getElementsBySelector('.error').each(function(element) {
element.removeClassName('error');
errorElements.push(element);
});
});
this.$$(".error-required").each(function(e) {
Validar.ok(e, "required");
}, this);
var errors = this.$$(".error");
if (errors && errors.length) {
Estatus.mensaje(Validar.getMessage(errors[0])
|| Util.getMensaje(Mensajes, "fitbank.contexto.ERROR_VALIDACION"), null, "error");
errorElements.each(function(element) {
element && element.addClassName('error');
});
return true;
}
errorElements.each(function(element) {
element && element.addClassName('error');
});
return false;
},
/**
* Quita el foco del elemento y lo regresa al terminar de procesar el thread.
*/
refrescarFoco: function() {
var controlConFoco = this.formulario.controlConFoco;
var registroActivo = this.formulario.registroActivo;
var elemento = this.$(controlConFoco, registroActivo);
if (elemento && elemento.blur) {
elemento.blur();
Form.Element.activate.defer(elemento);
}
},
/**
* Hace un mantenimiento con el formulario del contexto actual.
*/
setupAutoScroll: function() {
document.on("scroll", (function() {
var el = document.body;
var scrollPos = el.scrollHeight - el.clientHeight - el.scrollTop;
if (scrollPos < 500 && !Entorno.bloqueado()) {
this.consultar.bind(this).defer(1, null, true);
}
}).bind(this));
},
/**
* Obtiene una lista de contextos y subcontextos en orden.
*/
_getContextos: function(behaviorType) {
var contextos = [];
this.subContextos.each(function(contexto) {
if (contexto.adjunto[behaviorType] == AttachedBehavior.BEFORE) {
contextos.push(contexto);
}
});
contextos.push(this);
this.subContextos.each(function(contexto) {
if (contexto.adjunto[behaviorType] == AttachedBehavior.AFTER) {
contextos.push(contexto);
}
});
contextos.reverse();
return contextos;
},
/**
* Hace una consulta con el formulario del contexto actual.
*/
_consultar: function(paginacion, callback, fullQuery) {
if (paginacion && this.formulario.paginacion != Paginacion.HABILITADA) {
Estatus.mensaje(Util.getMensaje(Mensajes, "fitbank.contexto.PAGINACION_NO_HABILITADA"), null, "error");
return;
}
if (this._revisarBloqueo() || this._checkError(this.formulario.preConsultar,
Util.getMensaje(Mensajes, "fitbank.contexto.ERROR_PRE_CONSULTA")) || this._validar()) {
return;
}
if (!this.formulario.query) {
Estatus.mensaje(Util.getMensaje(Mensajes, "fitbank.contexto.ERROR_NO_APLICA_CONSULTA"),
null, "error");
return;
}
if (!this.formulario.fullQuery && fullQuery) {
Estatus.mensaje(Util.getMensaje(Mensajes, "fitbank.contexto.ERROR_NO_APLICA_FULLQUERY"),
null, "error");
return;
}
this.formulario.consultando = true;
var contextos = this._getContextos("queryBehavior");
var submit = (function() {
if (!contextos.length) {
this.formulario.consultando = false;
//Registrar los campos y sus valores luego de la consulta
this.originalElements = Util.getOriginalElements();
this._resetearTablaDinamica();
if (this._checkError(this.formulario.posConsultar,
Util.getMensaje(Mensajes, "fitbank.contexto.ERROR_POS_CONSULTA"))) {
return;
}
this.formulario.consultado = true;
if (!fullQuery) {
this.formulario.evalFormulasWithElements();
callback && callback();
this.calcular();
var queryFocus = this.$N(this.formulario.queryFocus, 0);
if (queryFocus) {
queryFocus.focus();
}
this._mostrarMensajeTablaDinamica(Util.getMensaje(Mensajes, "fitbank.contexto.dynamictable.NO_RECORDS"));
}
} else {
Enlace.submit(contextos.pop(), {
tipo: GeneralRequestTypes.CONSULTA,
paginacion: paginacion,
callback: submit,
fullQuery: fullQuery
});
}
}).bind(this);
submit();
},
/**
* Hace un mantenimiento con el formulario del contexto actual.
*/
_mantener: function(callback) {
if (this.formulario.requiresQuery && !this.formulario.consultado) {
Estatus.mensaje(Util.getMensaje(Mensajes, "fitbank.contexto.ERROR_REQUIERE_CONSULTA"),
null, "error");
return;
}
if (!this.formulario.store) {
Estatus.mensaje(Util.getMensaje(Mensajes, "fitbank.contexto.ERROR_NO_APLICA_MANTENIMIENTO"),
null, "error");
return;
}
if (this._revisarBloqueo() || this._checkError(this.formulario.preMantener,
Util.getMensaje(Mensajes, "fitbank.contexto.ERROR_PRE_MANTENIMIENTO")) || this._validar()) {
return;
}
this.formulario.manteniendo = true;
var contextos = this._getContextos("storeBehavior");
var submit = (function() {
if (!contextos.length) {
this.formulario.manteniendo = false;
//Registrar los campos y sus valores luego del mantenimiento
this.originalElements = Util.getOriginalElements();
if (this._checkError(this.formulario.posMantener,
Util.getMensaje(Mensajes, "fitbank.contexto.ERROR_POS_MANTENIMIENTO"))) {
return;
}
this.formulario.evalFormulasWithElements();
callback && callback();
this.calcular();
if (this.formulario.postQuery) {
this.consultar.bind(this).defer(0);
}
this._resetearTablaDinamica();
} else {
Enlace.submit(contextos.pop(), {
tipo: GeneralRequestTypes.MANTENIMIENTO,
callback: submit
});
}
}).bind(this);
submit();
},
/**
* Limpia el formulario en el contexto actual
*/
_limpiar: function() {
if (c.formulario.clean) {
if (!this._revisarBloqueo()) {
this._obtener(this._default({
tipo: GeneralRequestTypes.LIMPIAR,
subsistema: c.subsystem,
transaccion: c.transaction,
reset: false
}));
}
} else {
Estatus.mensaje(Util.getMensaje(Mensajes, "fitbank.contexto.ERROR_NO_APLICA_LIMPIEZA"), null, "error");
}
},
/**
* Recarga el formulario
*/
_recargar: function() {
if (!this._revisarBloqueo()) {
this._obtener({
subsistema: this.subsystem,
transaccion: this.transaction,
tipo: GeneralRequestTypes.RECARGAR
});
}
},
/**
* Llama al proceso BorrarCache, que recarga el formulario actual sin
* traerlo desde la cache de formularios.
*/
borrarCache: function() {
if (this.revisarCambios() || this._revisarBloqueo() || !this.subsystem
|| !this.form) {
return;
}
//Borrar cache de webpages en el explorador.
this.webpagesCache = $H();
//Borrar cache de webpages en el servidor.
this._obtener({
subsistema: this.subsystem,
transaccion: this.transaction,
tipo: GeneralRequestTypes.BORRAR_CACHE
});
},
/**
* Carga los values del response simplemente.
*
* @private
*/
loadValues: function(response, error, opciones) {
if (!response.responseJSON) {
var msj = Util.getMensaje(Mensajes, "fitbank.contexto.RESPUESTA_VACIA");
Estatus.mensaje(msj, null, 'error');
return;
}
this.cargando = true;
if (opciones && opciones.fullQuery) {
var newHtml = new Element("div").update(response.responseJSON.html);
var newTbodies = newHtml.select("tbody");
var curTbodies = this.$$("tbody");
for (var i = 0; i < newTbodies.length; i++) {
curTbodies[i].insert({ bottom: newTbodies[i].innerHTML });
}
}
$H(response.responseJSON.values).each((function(pair) {
var name = pair.key;
var obj = pair.value;
this.$N(name).each(function(element, n) {
element.changeValue(obj.values[n], {
load: true
});
if (element.widget) {
element = element.widget;
}
!error && element.setDisabled(obj.disabled[n]);
if (obj.error[n] && obj.error[n].id) {
Validar.error(element, obj.error[n].mensaje, obj.error[n].id);
if (obj.error[n].id == "required") {
Logger.debug("Requerido: " + element.name);
}
}
if (obj.classNames && obj.classNames[n]) {
obj.classNames[n].split(" ").each(function(className) {
element.addClassName(className);
});
}
element.fire("widget:init");
}, this);
}).bindTryCatch(this));
if (opciones && opciones.drawHtml) {
this.mostrarForm(opciones, response);
}
this.cargando = false;
this._ready(response, error);
},
/**
* Maneja mensajes de error.
*/
onError: function(response) {
var json = response.responseJSON;
if (!json) {
Estatus.finalizarProceso(Util.getMensaje(Mensajes, "fitbank.contexto.SIN_RESPUESTA", null, "error"),
this.idProceso, "error");
this.elemento.update("");
} else {
this.loadValues(response, "error");
}
},
/**
* Función llamada al terminar de cargar un formulario.
*
* @param response La respuesta
* @param error Boolean que indica si hubo error
*/
_ready: function(response, error) {
var json = response.responseJSON;
if (error) {
Estatus.finalizarProceso(json.mensajeUsuario
|| Util.getMensaje(Mensajes, "fitbank.contexto.ERROR_CARGANDO", null, "error"),
this.idProceso, error && "error", json.stack);
} else {
Estatus.finalizarProceso(json.mensajeUsuario
|| Util.getMensaje(Mensajes, "fitbank.contexto.CARGADO"), this.idProceso, (Mobile?"processing":"ok"));
}
Estatus.registrar(response);
},
/**
* Función que ejecuta calculos.
*/
_calcular: function() {
this.formulario.calcular();
},
/**
* Función que muestra ventana emergente de ayuda
*/
_ayudar: function() {
var ventana = new Ventana({
titulo: "Ayuda",
contenido: "Cargando...",
w: 500,
h: 300,
verFondo: false
});
new Ajax.Updater(ventana.contenido, "../MANUAL/manuales/"
+ c.subsystem + c.transaction + ".html");
ventana.ver();
},
/**
* Función que muestra ventana emergente del menu
*/
_menuRapido: function() {
Menu.menuRapido.alternar();
},
/**
* Función que muestra ventana emergente de version del sistema
*/
_mostrarVersion: function() {
var divVersion = $('entorno-barra-version');
if (divVersion) {
var versionContent = new Element("div", {
id: 'barra-botones-version'
});
if (divVersion.textContent) {
var libraries = divVersion.textContent.split(',');
//Para casos donde solo viene el esquema (versiones anteriores)
if (libraries.length == 1) {
var libraryDiv = new Element("div", {
'class': 'barra-botones-library'
}).update("Esquema: " + libraries[0]);
versionContent.insert(libraryDiv);
} else {
libraries.each(function(library) {
var libraryName = library.split("=")[0];
var libraryVersion = library.split("=")[1];
var libraryNameDiv = new Element("div").update(libraryName);
var libraryVersionDiv = new Element("div").update(libraryVersion);
var libraryDiv = new Element("div", {
'class': 'barra-botones-library'
});
libraryDiv.insert(libraryNameDiv);
libraryDiv.insert(libraryVersionDiv);
versionContent.insert(libraryDiv)
});
}
} else {
var libraryDiv = new Element("div", {
'class': 'barra-botones-library'
}).update(Util.getMensaje(Mensajes, "fitbank.contexto.NO_EXISTE_VERSION"));
versionContent.insert(libraryDiv);
}
var ventana = new Ventana({
titulo: "Versión",
contenido: versionContent
});
ventana.ver();
}
},
/**
* Muestra un mensaje bajo tablas dinamicas
*
* @param mensaje Mensaje a mostrar
* @param funcion Funcion JS a ejecutarse al hacer click en el mensaje
* @param dynamicTable Elemento de la tabla dinamica a ocupar (opcional)
*/
_mostrarMensajeTablaDinamica: function(mensaje, funcion, dynamicTable) {
if (!dynamicTable) {
$$("div.dynamic-table-container > table").each((function (tableElement) {
this._mostrarMensajeTablaDinamica(mensaje, funcion, tableElement);
}).bind(this));
return;
}
var bodyElement = dynamicTable.down("tbody");
if (bodyElement && bodyElement.select("tr.show").length == 0) {
var labelElement = new Element("label").update(mensaje);
if (funcion) {
labelElement.observe("click", funcion);
}
var td = new Element("td", {
colspan: "100%",
align: "center"
});
td.insert(labelElement);
var tr = new Element("tr", {
'class': "message"
});
tr.insert(td);
bodyElement.insert({
bottom: tr
});
}
},
/**
* Agrega botones de control sobre tablas dinamicas
*/
_mostrarControlesTablaDinamica: function() {
$$("div.dynamic-table-container > table.showControls > thead").each((function(element) {
var tr = element.select("tr");
//Agregar los controles unicamente a tablas con cabeceras
if (tr && tr.length > 0) {
var addRowButton = new Element("button", {
'class':'addRow',
onmouseover: "window.status=title='" + Util.getMensaje(Mensajes, "fitbank.contexto.controls.ADD_ROW") + "';"
}).observe("click", (function(e) {
var element = Event.element(e);
var dynamicTable = element.up('table');
var messageElement = dynamicTable.down('tbody tr.message');
if (messageElement) {
element = dynamicTable.down('tbody tr');
this._resetearTablaDinamica(dynamicTable);
} else {
element = dynamicTable.down('tbody tr[class^=\'clonada show\'] + tr[class=\'clonada par\'], tr[class^=\'clonada par show\'] + tr[class=\'clonada\']');
}
if (element) {
element.addClassName('show new-record');
//Buscar el primer elemento visible modificable y asignarle el foco
var focusElement = element.select("input[type!=hidden][readonly!=\'\']")[0];
if (focusElement) {
this.$$(' .current-focus').invoke('removeClassName','current-focus');
focusElement.addClassName('current-focus');
focusElement.activate();
}
}
}).bind(this));
var cloneRowButton = new Element("button", {
'class':'cloneRow',
onmouseover: "window.status=title='" + Util.getMensaje(Mensajes, "fitbank.contexto.controls.CLONE_ROW") + "';"
}).observe("click", (function(e) {
var element = Event.element(e);
var dynamicTable = element.up('table');
var messageElement = dynamicTable.down('tbody tr.message');
if (!messageElement) {
element = dynamicTable.down('tbody tr[class^=\'clonada show\'] + tr[class=\'clonada par\'], tr[class^=\'clonada par show\'] + tr[class=\'clonada\']');
if (element) {
var cloneRow = this.$$(' .current-focus')[0].up('tr.clonada');
if (cloneRow) {
var index = 0;
var copyCount = 0;
cloneRow.select('input').each(function (cloneElement) {
var targetElement = element.select('input')[index];
if (cloneElement.name == targetElement.name) {
targetElement.changeValue(cloneElement.value);
copyCount++;
}
index++;
});
if (copyCount == index) {
element.addClassName("show new-record");
//Buscar el primer elemento visible modificable y asignarle el foco
var focusElement = element.select("input[type!=hidden][readonly!=\'\']")[0];
if (focusElement) {
this.$$(' .current-focus').invoke('removeClassName','current-focus');
focusElement.addClassName('current-focus');
focusElement.activate();
}
} else {
element.select("input[type!=hidden]").each(function(el) {
el.changeValue('');
});
}
}
}
}
}).bind(this));
var removeRowButton = new Element("button", {
'class':'removeRow',
onmouseover: "window.status=title='" + Util.getMensaje(Mensajes, "fitbank.contexto.controls.REMOVE_ROW") + "';"
}).observe("click", (function(e) {
var element = Event.element(e);
var dynamicTable = element.up('table');
var clearElement = dynamicTable.down('input.current-focus');
if (clearElement) {
clearElement = clearElement.up('tr.clonada');
}
if (clearElement) {
//Borrar la fila unicamente si es nueva
if (!clearElement.hasClassName('new-record')) {
//Si no es nueva pero tiene un delete-record, activarlo
if (clearElement.select('td.delete-record').length > 0) {
var deleteRecord = clearElement.select('td.delete-record input[type=checkbox]')[0];
if (deleteRecord) {
deleteRecord.setChecked(true);
}
}
return;
}
clearElement.removeClassName('show');
clearElement.removeClassName('new-record');
clearElement.select("input[type!=hidden]").each(function(element) {
if (element.hasClassName('pk-disabled')) {
element.readOnly = false;
}
if (element.hasClassName('delete-record')) {
element.setDisabled(true);
}
element.changeValue('');
});
//Buscar la siguiente fila visible para ubicar el foco
var nextRow = clearElement.next("tr.show");
var previousRow = clearElement.previous("tr.show");
var focusElement = null;
//Buscar el primer elemento visible modificable del registro anterior y asignarle el foco
if (nextRow) {
focusElement = nextRow.select("input[type!=hidden][readonly!=\'\']")[0];
} else if (previousRow) {
focusElement = previousRow.select("input[type!=hidden][readonly!=\'\']")[0];
}
if (focusElement) {
this.$$(' .current-focus').invoke('removeClassName','current-focus');
focusElement.addClassName('current-focus');
focusElement.activate();
}
}
var nexElement = dynamicTable.down('tbody tr.show');
if (!nexElement) {
this._resetearTablaDinamica(dynamicTable);
this._mostrarMensajeTablaDinamica(Util.getMensaje(Mensajes, "fitbank.contexto.dynamictable.PERFORM_QUERY"),
this.consultar.bind(this), dynamicTable);
}
}).bind(this));
var td = new Element("td", {
colspan: "100%",
align: "right",
'class': "table-controls"
});
td.insert(addRowButton);
td.insert(cloneRowButton);
td.insert(removeRowButton);
tr = tr.reverse()[0];
tr.insert(td)
}
}).bind(this));
},
/**
* Controla los estilos para elementos de tablas dinamicas
*/
_resetearTablaDinamica: function(dynamicTable) {
if (!dynamicTable) {
$$("div.dynamic-table-container > table").each((function (tableElement) {
this._resetearTablaDinamica(tableElement);
}).bind(this));
return;
}
var tableBody = dynamicTable.down("tbody");
if (!tableBody) {
return;
}
var bodyRows = tableBody.select("tr");
bodyRows.each(function (element) {
if (element.hasClassName("show")) {
element.removeClassName("show");
}
if (element.hasClassName("message")) {
element.remove();
}
var tdElements = element.select("td .show");
var showRow = tdElements.length > 0;
if (showRow) {
tdElements.invoke("removeClassName", "show");
element.addClassName("show");
element.removeClassName('new-record');
dynamicTable.removeClassName("oculto");
dynamicTable.up("fieldset") && dynamicTable.up("fieldset").removeClassName("oculto");
}
});
},
/**
* Borra todos los campos indicados.
*
* @param a
* Primer parámetro (se pueden pasar más parametros tambien)
*/
borrar: function(a) {
a.split(",").each(function(e) {
this.$(e).value = '';
}, this);
},
/**
* Obtiene el elemento (o elementos) referenciados por el name y el
* registro. Si hay un solo elemento no devuelve un array si no el elemento
* en sí.
*
* @param name
* Nombre del elemento.
* @param registro
* Opcional, el numero de registro que se quiere obtener.
*
* @return Un elemento o un array de elementos
*/
$: function(name, registro) {
var e = this.$W(name, registro);
return Object.isArray(e) && e.length == 1 ? e[0] : e;
},
/**
* Obtiene un array de los elementos referenciados por el name y el
* registro.
*
* @param name
* Nombre del elemento.
* @param registro
* Opcional, el numero de registro que se quiere obtener.
*
* @return Un array de elementos incluso si hay un solo elemento
*/
$N: function(name, registro) {
return $N(this.form, name, registro);
},
/**
* Obtiene un array de los valores de los elementos referenciados por el
* name y el registro.
*
* @param name
* Nombre del elemento.
* @param registro
* Opcional, el numero de registro que se quiere obtener.
*
* @return Un array de valores incluso si hay un solo valor
*/
$V: function(name, registro) {
return $V(this.form, name, registro);
},
/**
* Obtiene un array de los widgets visible de los elementos referenciados por el
* name y el registro.
*
* @param name
* Nombre del elemento.
* @param registro
* Opcional, el numero de registro que se quiere obtener.
*
* @return Un array de valores incluso si hay un solo valor
*/
$W: function(name, registro) {
return $W(this.form, name, registro);
},
/**
* Obtiene un array de los elementos que cumplen con el selector.
*
* @param selector
* Un selector CSS
*
* @return Un array de elementos
*/
$$: function(selector) {
return this.form.select(selector);
}
});