diff --git a/resources/views/configureQCMetric.html b/resources/views/configureQCMetric.html
index 0d65d3017..565e98994 100644
--- a/resources/views/configureQCMetric.html
+++ b/resources/views/configureQCMetric.html
@@ -230,7 +230,7 @@
const windowConfig = {
parent: this,
- traces: tracesPresent ? traces : {} ,
+ traces: tracesPresent ? traces : [] ,
tracesPresent: tracesPresent,
operation: op
}
@@ -239,7 +239,7 @@
windowConfig.metric = clickedMetric;
}
- Ext4.create('Panorama.Window.AddTraceMetricWindow', windowConfig).show();
+ Panorama.Window.AddTraceMetricWindow.show(windowConfig);
}
});
},
diff --git a/resources/web/PanoramaPremium/window/AddNewTraceMetricWindow.js b/resources/web/PanoramaPremium/window/AddNewTraceMetricWindow.js
index 59e10c321..aa46ed4d0 100644
--- a/resources/web/PanoramaPremium/window/AddNewTraceMetricWindow.js
+++ b/resources/web/PanoramaPremium/window/AddNewTraceMetricWindow.js
@@ -4,518 +4,263 @@
* Licensed under the Apache License, Version 2.0: http://www.apache.org/licenses/LICENSE-2.0
*/
-Ext4.define('Panorama.Window.AddTraceMetricWindow', {
- extend: 'Ext.window.Window',
-
- modal: true,
- closeAction: 'destroy',
- bodyStyle: 'padding: 10px;',
- autoScroll: true,
- border: false,
- update: 'update',
- insert: 'insert',
- timeValueOptions: Ext4.create('Ext.data.Store', {
- fields: ['value'],
- data : [
- { "value":"First"},
- { "value":"Last"},
- { "value":"Max"},
- { "value":"Min"}
- ]
- }),
-
- initComponent: function() {
- var title = this.operation === this.insert ? 'Add New Trace Metric' : 'Edit Trace Metric';
- this.setTitle(title);
- this.height = Ext4.max([Ext4.getBody().getHeight() * 0.3, 250]);
- this.width = Ext4.max([Ext4.getBody().getWidth() * 0.3, 600]);
- this.items = this.getItems();
- this.dockedItems= [{
- xtype: 'toolbar',
- dock: 'bottom',
- ui: 'footer',
- items: this.getButtons()
- }]
-
- this.callParent();
-
- this.timeValue = true;
- this.traceValue = false;
-
- },
-
- getItems: function() {
- return [
- this.getMetricNameField(),
- this.getTracesCombo(),
- this.getYAxisLabelField(),
- this.getTraceValueRadioGroup(),
- this.getQueryError()
- ];
- },
-
- getButtons: function () {
- var buttons = [];
-
- buttons.push(this.getCancelButton());
- buttons.push('->'); // to push remaining buttons to the right
- if (this.operation === this.update) {
- buttons.push(this.getDeleteButton());
- }
- buttons.push(this.getSaveButton());
- return buttons;
- },
-
- getMetricNameField: function() {
- if (!this.metricNameField) {
- this.metricNameField = Ext4.create('Ext.form.field.Text', {
- fieldLabel: 'Metric Name',
- labelWidth: 150,
- width: 570,
- name: 'metricName'
- });
+(function($) {
+ window.Panorama = window.Panorama || {};
+ window.Panorama.Window = window.Panorama.Window || {};
- if (this.operation === this.update) {
- this.metricNameField.setValue(this.metric.name);
- }
- }
+ const DIALOG_ID = 'lk-trace-metric-dialog';
+ const TIME_VALUE_OPTIONS = ['First', 'Last', 'Max', 'Min'];
+ let _config = null;
- return this.metricNameField;
- },
-
- getTracesCombo: function () {
- if (!this.tracesCombo) {
- var config = {
- fieldLabel: 'Use Trace',
- name: 'useTrace',
- labelWidth: 150,
- width: 570
- }
- if (!this.tracesPresent) {
- config.emptyText = 'No trace can be found';
- }
- else {
- config.store = this.getTracesComboStore();
- config.valueField = 'TextId';
- config.displayField = 'TextId';
- }
- this.tracesCombo = Ext4.create('Ext.form.field.ComboBox', config);
-
- if (this.operation === this.update) {
- this.tracesCombo.setValue(this.metric.TraceName);
- this.tracesCombo.bindStore(this.getTracesComboStore());
- }
- }
- return this.tracesCombo;
- },
-
- getTracesComboStore: function () {
- return Ext4.create('Ext.data.Store', {
- fields: ['TextId'],
- sorters: [{property: 'TextId'}],
- data: this.traces
- });
- },
-
- getTraceValueRadioGroup: function () {
- if (!this.traceValueRadioGroup) {
- this.traceValueRadioGroup =
- Ext4.create('Ext.form.Panel', {
- renderTo: Ext4.getBody(),
- width: 570,
-
- border:false,
- items: [{
- xtype: 'radiogroup',
- columns: 1, // Stack radio buttons vertically
- vertical: true,
- items: [
- {
- xtype: 'container',
- layout: 'hbox',
- items: [
- {
- xtype: 'radio',
- name: 'metricValue',
- inputValue: 'timeValue',
- boxLabel: 'Use the',
- width: 65,
- checked: this.operation === this.update ? this.metric.MinTimeValue >= 0 : true,
- listeners: {
- change: {fn : function(cmp, newVal, oldVal){
- this.minTimeValueNumberField.setDisabled(oldVal);
- this.maxTimeValueNumberField.setDisabled(oldVal);
- this.timeValueOptionField.setDisabled(oldVal);
- this.traceValueNumberField.setDisabled(newVal);
-
- // restore the value onChange when it is present
- if (this.operation === this.update) {
- if (newVal) {
- this.minTimeValueNumberField.setValue(this.metric.MinTimeValue);
- this.maxTimeValueNumberField.setValue(this.metric.MaxTimeValue);
- }
- else {
- this.traceValueNumberField.setValue(this.metric.TraceValue);
- }
- }
- else {
- this.traceValueNumberField.setValue(undefined);
- this.minTimeValueNumberField.setValue(undefined);
- this.maxTimeValueNumberField.setValue(undefined);
- this.timeValueOptionField.setValue(undefined);
- }
- }},
- scope : this
- }
- },
- this.getTimeValueOptionField(),
- {
- xtype: 'displayfield',
- value: 'trace value when time in minutes is between',
- margin: '0 5'
- },
- this.getMinTimeValueNumberField(),
- {
- xtype: 'displayfield',
- value: 'and',
- margin: '0 5'
- },
- this.getMaxTimeValueNumberField()
- ]
- },
- {
- xtype: 'container',
- layout: 'hbox',
- items: [
- {
- xtype: 'radio',
- name: 'metricValue',
- inputValue: 'traceValue',
- boxLabel: 'Use time in minutes when the trace first reaches a value greater than or equal to',
- width: 450,
- checked: this.operation === this.update ? this.metric.TraceValue > 0 : false
- },
- this.getTraceValueNumberField()
- ]
- }
- ]
- }]
- });
- }
- return this.traceValueRadioGroup;
- },
-
- getTimeValueOptionField: function() {
- if (!this.timeValueOptionField) {
- this.timeValueOptionField = Ext4.create('Ext.form.field.ComboBox', {
- name: 'timeValueOption',
- store: this.timeValueOptions,
- displayField: 'value',
- valueField: 'value',
- width: 50,
- itemId: 'timeValueOption',
- });
-
- if(this.operation === this.update) {
- this.timeValueOptionField.setValue(this.metric.TimeValueOption);
- }
- }
-
- return this.timeValueOptionField
- },
-
- getMinTimeValueNumberField: function () {
- if (!this.minTimeValueNumberField) {
- this.minTimeValueNumberField = Ext4.create('Ext.form.field.Number', {
- name: 'minTimeValue',
- width: 65,
- disabled: this.operation === this.update ? !(this.metric.MinTimeValue >= 0) : false
- });
-
- if (this.operation === this.update) {
- this.minTimeValueNumberField.setValue(this.metric.MinTimeValue);
- }
-
- }
- return this.minTimeValueNumberField;
- },
-
- getMaxTimeValueNumberField: function () {
- if (!this.maxTimeValueNumberField) {
- this.maxTimeValueNumberField = Ext4.create('Ext.form.field.Number', {
- name: 'maxTimeValue',
- width: 65,
- disabled: this.operation === this.update ? !(this.metric.MaxTimeValue >= 0) : false
- });
-
- if (this.operation === this.update) {
- this.maxTimeValueNumberField.setValue(this.metric.MaxTimeValue);
- }
-
- }
- return this.maxTimeValueNumberField;
- },
-
-
- getTraceValueNumberField: function () {
- if (!this.traceValueNumberField) {
- this.traceValueNumberField = Ext4.create('Ext.form.field.Number', {
- name: 'traceValue',
- width: 65,
- disabled: this.operation === this.update ? !(this.metric.TraceValue >= 0) : true
- });
+ function closeDialog() {
+ $('#' + DIALOG_ID).remove();
+ }
- if (this.operation === this.update) {
- this.traceValueNumberField.setValue(this.metric.TraceValue);
- }
- }
- return this.traceValueNumberField;
- },
-
- getYAxisLabelField: function() {
- if (!this.yAxisLabelField) {
- this.yAxisLabelField = Ext4.create('Ext.form.field.Text', {
- fieldLabel: 'Y Axis Label',
- labelWidth: 150,
- width: 570,
- name: 'yAxisLabel'
- });
+ function showError(msg) {
+ $('#lk-trace-metric-error').text(msg).show();
+ }
- if(this.operation === this.update) {
- this.yAxisLabelField.setValue(this.metric.YAxisLabel);
- }
- }
+ function clearErrors() {
+ $('#lk-trace-metric-error').hide().text('');
+ $('#lk-trace-metric-name, #lk-trace-use-trace, #lk-trace-ylabel, #lk-trace-time-option, #lk-trace-min-time, #lk-trace-max-time, #lk-trace-value')
+ .css('border-color', '');
+ }
- return this.yAxisLabelField;
- },
+ function markInvalid($field) {
+ $field.css('border-color', 'red');
+ }
- getQueryError: function() {
- if (!this.queryError) {
- this.queryError = Ext4.create('Ext.form.Label', {
- name: 'errorMsg',
- hidden: true,
- cls: 'labkey-error',
- text:''
- });
- }
+ function getMode() {
+ return $('input[name="metricValue"]:checked').val(); // 'timeValue' or 'traceValue'
+ }
- return this.queryError;
- },
+ // Enable only the fields belonging to the selected mode
+ function refreshMode() {
+ const isTime = getMode() === 'timeValue';
+ $('#lk-trace-time-option, #lk-trace-min-time, #lk-trace-max-time').prop('disabled', !isTime);
+ $('#lk-trace-value').prop('disabled', isTime);
+ }
- getSaveButton: function() {
- if (!this.saveButton) {
- this.saveButton = Ext4.create('Ext.button.Button', {
- text: 'Save',
- scope: this,
- handler: this.saveNewMetric,
- disabled: !this.tracesPresent
- });
- }
- return this.saveButton;
- },
-
- getDeleteButton: function() {
- if (!this.deleteButton) {
- this.deleteButton = Ext4.create('Ext.button.Button', {
- text: 'Delete',
- scope: this,
- handler: this.deleteMetric
- });
- }
- return this.deleteButton;
- },
-
- getCancelButton: function() {
- if (!this.cancelButton) {
- this.cancelButton = Ext4.create('Ext.button.Button', {
- text: 'Cancel',
- scope: this,
- handler: function(btn){
- btn.up('window').close();
- }
- });
- }
- return this.cancelButton;
- },
+ function isNonNegativeNumber(val) {
+ return val !== '' && val !== null && !isNaN(val) && Number(val) >= 0;
+ }
- validateValues: function() {
- var isValid = true;
- var errorText = 'Required';
+ function validate() {
+ clearErrors();
+ let isValid = true;
- if (!(this.metricNameField.getValue().length > 0)) {
- this.metricNameField.setActiveError(errorText);
+ if (!$('#lk-trace-metric-name').val().trim()) {
+ markInvalid($('#lk-trace-metric-name'));
isValid = false;
}
-
- if (!this.tracesCombo.getValue()) {
- this.tracesCombo.setActiveError(errorText);
+ if (!$('#lk-trace-use-trace').val()) {
+ markInvalid($('#lk-trace-use-trace'));
isValid = false;
}
-
- if (!(this.yAxisLabelField.getValue().length > 0)) {
- this.yAxisLabelField.setActiveError(errorText);
+ if (!$('#lk-trace-ylabel').val().trim()) {
+ markInvalid($('#lk-trace-ylabel'));
isValid = false;
}
- if (this.timeValueOptionField.getValue() === null) {
- this.timeValueOptionField.setActiveError(errorText);
- isValid = false;
- }
-
- if (this.traceValueRadioGroup.down().getValue()['metricValue'] === 'timeValue' &&
- (!(this.minTimeValueNumberField.getValue() >= 0))) {
- this.minTimeValueNumberField.setActiveError(errorText);
- isValid = false;
+ if (getMode() === 'timeValue') {
+ if (!$('#lk-trace-time-option').val()) {
+ markInvalid($('#lk-trace-time-option'));
+ isValid = false;
+ }
+ if (!isNonNegativeNumber($('#lk-trace-min-time').val())) {
+ markInvalid($('#lk-trace-min-time'));
+ isValid = false;
+ }
+ if (!isNonNegativeNumber($('#lk-trace-max-time').val())) {
+ markInvalid($('#lk-trace-max-time'));
+ isValid = false;
+ }
}
-
- if (this.traceValueRadioGroup.down().getValue()['metricValue'] === 'timeValue' &&
- (!(this.maxTimeValueNumberField.getValue() >= 0))) {
- this.maxTimeValueNumberField.setActiveError(errorText);
+ else if (!isNonNegativeNumber($('#lk-trace-value').val())) {
+ markInvalid($('#lk-trace-value'));
isValid = false;
}
- if (this.traceValueRadioGroup.down().getValue()['metricValue'] === 'traceValue' && !this.traceValueNumberField.getValue()) {
- this.traceValueNumberField.setActiveError(errorText);
- isValid = false;
+ if (!isValid) {
+ showError('Please fill in all required fields.');
}
-
return isValid;
- },
-
- checkMetricNameExists: function (metricName, callback) {
- let filterArray = [LABKEY.Filter.create('Name', metricName, LABKEY.Filter.Types.EQUAL)];
+ }
- // If updating, exclude the current metric from the check
- if (this.operation === this.update && this.metric) {
- filterArray.push(LABKEY.Filter.create('id', this.metric.id, LABKEY.Filter.Types.NOT_EQUAL));
+ function checkMetricNameExists(metricName, callback) {
+ const filterArray = [LABKEY.Filter.create('Name', metricName, LABKEY.Filter.Types.EQUAL)];
+ if (_config.operation === 'update' && _config.metric) {
+ filterArray.push(LABKEY.Filter.create('id', _config.metric.id, LABKEY.Filter.Types.NOT_EQUAL));
}
-
LABKEY.Query.selectRows({
containerPath: LABKEY.container.id,
schemaName: 'targetedms',
queryName: 'qcmetricconfiguration',
filterArray: filterArray,
- scope: this,
- success: function (data) {
- callback.call(this, data.rows.length > 0);
- },
- failure: function () {
- callback.call(this, false);
- }
+ success: function(data) { callback(data.rows.length > 0); },
+ failure: function() { callback(false); }
});
- },
-
-
-
- saveNewMetric: function () {
- var isValid = this.validateValues();
-
- if (isValid) {
- var metricName = this.metricNameField.getValue();
-
- this.checkMetricNameExists(metricName, function (exists) {
- if (exists) {
- let errorMessage = 'A metric with the name "' + metricName + '" already exists. Please choose a different name.';
- this.queryError.setText(errorMessage);
- this.queryError.setVisible(true);
- this.metricNameField.setActiveError('Metric name already exists');
- return;
- }
+ }
- var records = [];
- var newMetric = {};
- newMetric.Name = metricName;
- newMetric.QueryName = 'QCTraceMetric'; // dummy text to insert and not an actual query
- newMetric.PrecursorScoped = false;
- newMetric.TraceName = this.tracesCombo.getValue();
- newMetric.YAxisLabel = this.yAxisLabelField.getValue();
-
- if (this.traceValueNumberField.getValue()) {
- newMetric.TraceValue = this.traceValueNumberField.getValue();
- } else {
- if (this.timeValueOptionField.getValue()) {
- newMetric.TimeValueOption = this.timeValueOptionField.getValue();
- }
- if (this.minTimeValueNumberField.getValue()) {
- newMetric.MinTimeValue = this.minTimeValueNumberField.getValue();
- }
- if (this.maxTimeValueNumberField.getValue()) {
- newMetric.MaxTimeValue = this.maxTimeValueNumberField.getValue();
- }
- }
+ function save() {
+ if (!validate()) return;
- if (this.operation === this.update) {
- newMetric.id = this.metric.id;
- }
+ const metricName = $('#lk-trace-metric-name').val().trim();
+ checkMetricNameExists(metricName, function(exists) {
+ if (exists) {
+ showError('A metric with the name "' + LABKEY.Utils.encodeHtml(metricName) + '" already exists. Please choose a different name.');
+ markInvalid($('#lk-trace-metric-name'));
+ return;
+ }
+
+ const newMetric = {
+ Name: metricName,
+ QueryName: 'QCTraceMetric', // dummy text to insert and not an actual query
+ PrecursorScoped: false,
+ TraceName: $('#lk-trace-use-trace').val(),
+ YAxisLabel: $('#lk-trace-ylabel').val().trim()
+ };
+
+ if (getMode() === 'traceValue') {
+ newMetric.TraceValue = Number($('#lk-trace-value').val());
+ }
+ else {
+ newMetric.TimeValueOption = $('#lk-trace-time-option').val();
+ newMetric.MinTimeValue = Number($('#lk-trace-min-time').val());
+ newMetric.MaxTimeValue = Number($('#lk-trace-max-time').val());
+ }
+
+ if (_config.operation === 'update') {
+ newMetric.id = _config.metric.id;
+ }
- records.push(newMetric);
-
- LABKEY.Query.saveRows({
- containerPath: LABKEY.container.id,
- commands: [{
- schemaName: 'targetedms',
- queryName: 'qcmetricconfiguration',
- command: this.operation,
- rows: records
- }],
- scope: this,
- method: 'POST',
- success: function () {
- window.location.reload();
- },
- failure: function (response) {
- let errorMessage = 'Error saving metric';
- if (response && response.exception) {
- errorMessage = response.exception;
- } else if (response && response.message) {
- errorMessage = response.message;
- }
- this.queryError.setText(errorMessage);
- this.queryError.setVisible(true);
- }
- });
+ LABKEY.Query.saveRows({
+ containerPath: LABKEY.container.id,
+ commands: [{ schemaName: 'targetedms', queryName: 'qcmetricconfiguration', command: _config.operation, rows: [newMetric] }],
+ method: 'POST',
+ success: function() { window.location.reload(); },
+ failure: function(response) {
+ showError((response && (response.exception || response.message)) || 'Error saving metric');
+ }
});
- }
+ });
+ }
+
+ function deleteMetric() {
+ if (!confirm('This will delete the "' + _config.metric.name + '" metric. Are you sure?')) return;
- },
-
- deleteMetric: function() {
- Ext4.Msg.confirm('Delete Trace Metric', 'This will delete ' + LABKEY.Utils.encodeHtml(this.metric.name) + ' metric. Are you sure you want to do this?', function(val){
- if (val === 'yes'){
- const qcMetricToDelete = {metric: this.metric.id};
- const metricToDelete = {id: this.metric.id};
-
- LABKEY.Query.saveRows({
- containerPath: LABKEY.container.id,
- commands: [{
- schemaName: 'targetedms',
- queryName: 'qcenabledmetrics',
- command: 'delete',
- rows: [qcMetricToDelete]
- },{
- schemaName: 'targetedms',
- queryName: 'qcmetricconfiguration',
- command: 'delete',
- rows: [metricToDelete]
- }],
- scope: this,
- method: 'POST',
- success: function () {
- window.location.reload();
- },
- failure: function (response) {
- let errorMessage = 'Error saving metric';
- if (response && response.exception) {
- errorMessage = response.exception;
- } else if (response && response.message) {
- errorMessage = response.message;
- }
- this.queryError.setText(errorMessage);
- this.queryError.setVisible(true);
- }
- });
- win.close();
+ LABKEY.Query.saveRows({
+ containerPath: LABKEY.container.id,
+ commands: [
+ { schemaName: 'targetedms', queryName: 'qcenabledmetrics', command: 'delete', rows: [{ metric: _config.metric.id }] },
+ { schemaName: 'targetedms', queryName: 'qcmetricconfiguration', command: 'delete', rows: [{ id: _config.metric.id }] }
+ ],
+ method: 'POST',
+ success: function() { window.location.reload(); },
+ failure: function(response) {
+ showError((response && (response.exception || response.message)) || 'Error deleting metric');
}
- }, this);
+ });
+ }
+
+ function buildTraceOptions(selectedTrace) {
+ const traces = (_config.traces || []).slice().sort(function(a, b) {
+ return String(a.TextId).localeCompare(String(b.TextId));
+ });
+ let html = '';
+ traces.forEach(function(row) {
+ const textId = row.TextId;
+ const sel = textId === selectedTrace ? ' selected' : '';
+ html += '';
+ });
+ return html;
+ }
+
+ function buildTimeOptions(selectedOption) {
+ let html = '';
+ TIME_VALUE_OPTIONS.forEach(function(opt) {
+ const sel = opt === selectedOption ? ' selected' : '';
+ html += '';
+ });
+ return html;
+ }
+
+ function buildDialogHtml() {
+ const op = _config.operation;
+ const metric = _config.metric || {};
+ const tracesPresent = !!_config.tracesPresent;
+ const title = op === 'insert' ? 'Add New Trace Metric' : 'Edit Trace Metric';
+
+ // In update mode, pick the mode based on the stored values; default to the time-value mode.
+ const isTraceValueMode = op === 'update' && metric.TraceValue > 0;
+
+ const num = function(v) {
+ return (v !== undefined && v !== null) ? LABKEY.Utils.encodeHtml(v) : '';
+ };
+
+ const traceSelect = tracesPresent
+ ? ''
+ : '';
+
+ return '
'
+ + '
'
+ + ''
+ + '
'
+ + '
'
+ + '
'
+ + '
'
+ + '
'
+ + ''
+ + (op === 'update' ? ' ' : '')
+ + ' '
+ + '
'
+ + '
'
+ + '
'
+ + '
';
}
-});
+
+ window.Panorama.Window.AddTraceMetricWindow = {
+ show: function(config) {
+ _config = config;
+
+ $('#' + DIALOG_ID).remove();
+ $('body').append(buildDialogHtml());
+
+ $('#lk-trace-metric-cancel').on('click', closeDialog);
+ $('#lk-trace-metric-save').on('click', save);
+ if (config.operation === 'update') {
+ $('#lk-trace-metric-delete').on('click', deleteMetric);
+ }
+ $('input[name="metricValue"]').on('change', refreshMode);
+
+ // close on overlay click
+ $('#' + DIALOG_ID).on('click', function(e) {
+ if (e.target === this) closeDialog();
+ });
+
+ refreshMode();
+ }
+ };
+})(jQuery);
diff --git a/src/org/labkey/targetedms/view/calibrationCurve.jsp b/src/org/labkey/targetedms/view/calibrationCurve.jsp
index 1fefd7f5e..18d011ccb 100644
--- a/src/org/labkey/targetedms/view/calibrationCurve.jsp
+++ b/src/org/labkey/targetedms/view/calibrationCurve.jsp
@@ -30,7 +30,7 @@
@Override
public void addClientDependencies(ClientDependencies dependencies)
{
- dependencies.add("Ext4");
+ dependencies.add("Ext4"); // LABKEY.vis (vis/vis) still uses Ext.isArray for log-scale axes
dependencies.add("vis/vis");
dependencies.add("targetedms/js/CalibrationCurve.js");
dependencies.add("targetedms/css/CalibrationCurve.css");
@@ -46,9 +46,9 @@
var calibrationCurvePlot;
- Ext4.onReady(function () {
+ LABKEY.Utils.onReady(function () {
- calibrationCurvePlot = Ext4.create('LABKEY.targetedms.CalibrationCurve', {
+ calibrationCurvePlot = new LABKEY.targetedms.CalibrationCurve({
renderTo: <%=q(elementId)%>,
data: <%=bean%>
});
diff --git a/src/org/labkey/targetedms/view/paretoPlot.jsp b/src/org/labkey/targetedms/view/paretoPlot.jsp
index 6282a42fe..56ab6ad5b 100644
--- a/src/org/labkey/targetedms/view/paretoPlot.jsp
+++ b/src/org/labkey/targetedms/view/paretoPlot.jsp
@@ -27,11 +27,10 @@
@Override
public void addClientDependencies(ClientDependencies dependencies)
{
- dependencies.add("Ext4");
+ dependencies.add("Ext4"); // still needed by QCMetricConfigLoader.js
dependencies.add("vis/vis");
dependencies.add("targetedms/css/SVGExportIcon.css");
dependencies.add("targetedms/css/ParetoPlot.css");
- dependencies.add("targetedms/js/BaseQCPlotPanel.js");
dependencies.add("targetedms/js/ParetoPlotPanel.js");
dependencies.add("targetedms/js/QCMetricConfigLoader.js");
}
@@ -47,22 +46,11 @@
function init() {
var tiledPlotPanelId = <%=q(tiledPlotPanelId)%>;
- if (Ext4.isIE8) {
- Ext4.get(tiledPlotPanelId).update("Unable to render report in Internet Explorer < 9.");
- return;
- }
-
- initializeParetoPlotPanel(tiledPlotPanelId);
- }
-
- function initializeParetoPlotPanel(tiledPlotPanelId) {
-
- // initialize the panel that displays Pareto plot
- Ext4.create('LABKEY.targetedms.ParetoPlotPanel', {
- cls: 'themed-panel',
+ // initialize the panel that displays Pareto plots
+ new LABKEY.targetedms.ParetoPlotPanel({
plotDivId: tiledPlotPanelId
});
}
- Ext4.onReady(init);
+ LABKEY.Utils.onReady(init);
diff --git a/src/org/labkey/targetedms/view/summaryChartsView.jsp b/src/org/labkey/targetedms/view/summaryChartsView.jsp
index 2156b8af7..965e37a89 100644
--- a/src/org/labkey/targetedms/view/summaryChartsView.jsp
+++ b/src/org/labkey/targetedms/view/summaryChartsView.jsp
@@ -30,7 +30,6 @@
@Override
public void addClientDependencies(ClientDependencies dependencies)
{
- dependencies.add("Ext4");
dependencies.add("internal/jQuery");
dependencies.add("TargetedMS/js/svgChart.js");
dependencies.add("TargetedMS/css/svgChart.css");
@@ -62,7 +61,9 @@
long moleculeId = bean.getMoleculeId();
long moleculePrecursorId = bean.getMoleculePrecursorId();
- if ((peptideList != null && !peptideList.isEmpty()) || peptideId != 0 || precursorId != 0)
+ boolean asProteomics = (peptideList != null && !peptideList.isEmpty()) || peptideId != 0 || precursorId != 0;
+
+ if (asProteomics)
{
peakAreaUrl.addParameter("asProteomics", true);
retentionTimesUrl.addParameter("asProteomics", true);
@@ -98,6 +99,17 @@
peakAreaUrl.addParameter("chartHeight", bean.getInitialHeight());
retentionTimesUrl.addParameter("chartWidth", bean.getInitialWidth());
retentionTimesUrl.addParameter("chartHeight", bean.getInitialHeight());
+
+ // The ExtJS stores prepended "All"/"None" entries, so the original visibility checks were
+ // count-based (e.g. store.count() > 2). Translate those to list-size checks here.
+ boolean hasPeptides = peptideList != null && !peptideList.isEmpty();
+ boolean hasMolecules = moleculeList != null && !moleculeList.isEmpty();
+ boolean showReplicate = replicateList.size() > 1;
+ boolean showAnnotName = !replicateAnnotationNameList.isEmpty();
+ boolean showAnnotValue = !replicateAnnotationValueList.isEmpty();
+ boolean showPeptide = hasPeptides && peptideList.size() > 1;
+ boolean showMolecule = hasMolecules && moleculeList.size() > 1;
+ boolean showCv = showReplicate || showAnnotName;
%>
+
-
-
diff --git a/webapp/TargetedMS/js/CalibrationCurve.js b/webapp/TargetedMS/js/CalibrationCurve.js
index 20fb85ef4..479ae906e 100644
--- a/webapp/TargetedMS/js/CalibrationCurve.js
+++ b/webapp/TargetedMS/js/CalibrationCurve.js
@@ -5,27 +5,29 @@
*/
/**
* Created by Marty on 3/16/2017.
+ *
+ * Plain JS/HTML implementation (no ExtJS). Renders the calibration curve plot (LABKEY.vis)
+ * into the element identified by config.renderTo.
*/
-
-Ext4.define('LABKEY.targetedms.CalibrationCurve', {
-
- extend: 'Ext.panel.Panel',
- layout: 'fit',
- border: false,
-
- selectedPointLayer: null,
- plotHeight: 500,
- minWidth: 800,
-
- colors: {
- unknown: 'black',
- standard: 'gray',
- qc: 'green'
- },
-
- initComponent: function () {
- Ext4.tip.QuickTipManager.init();
- this.callParent();
+if (!LABKEY.targetedms) {
+ LABKEY.targetedms = {};
+}
+
+(function() {
+
+ function CalibrationCurve(config) {
+ this.renderTo = config.renderTo;
+ this.data = config.data;
+
+ this.selectedPointLayer = null;
+ this.plotHeight = 500;
+ this.minWidth = 800;
+ this.plot = null;
+ this.colors = {
+ unknown: 'black',
+ standard: 'gray',
+ qc: 'green'
+ };
this.width = this.getPanelSize();
@@ -35,281 +37,288 @@ Ext4.define('LABKEY.targetedms.CalibrationCurve', {
this.maxX = this.data.calibrationCurve.maxX || 0;
// Ensure plot goes to max x axis for selected point calculations
- var calcMaxX = this.getQuadraticIntersect(this, this.maxY);
- if (calcMaxX > this.maxX)
+ const calcMaxX = this.getQuadraticIntersect(this, this.maxY);
+ if (calcMaxX > this.maxX) {
this.maxX = calcMaxX;
+ }
this.addCurvePoints();
this.refreshPlot();
- var me = this;
- window.addEventListener("resize", function () {
+ const me = this;
+ window.addEventListener("resize", function() {
// Issue 43532 - may have been loaded even if we don't have a curve to plot
if (me.plot) {
- me.setWidth(me.getPanelSize());
- me.plot.setWidth(me.getWidth());
+ me.width = me.getPanelSize();
+ me.plot.setWidth(me.width);
me.plot.render();
// Plot re-renders so need to shrink dots to get back to initial state
d3.selectAll('a.point path').transition().attr("stroke-width", 1);
}
}, false);
- },
-
- refreshPlot: function() {
- // Clear out child