Flat Message Layout
This commit is contained in:
@@ -23,7 +23,7 @@ class ApiLayoutItemTreeBuilder {
|
|||||||
|
|
||||||
if (nodeMap.has(parseInt(item.parent))) {
|
if (nodeMap.has(parseInt(item.parent))) {
|
||||||
nodeMap.get(parseInt(item.parent)).children.push(item);
|
nodeMap.get(parseInt(item.parent)).children.push(item);
|
||||||
console.log(item.id + ' to ' + item.parent);
|
// console.log(item.id + ' to ' + item.parent);
|
||||||
} else {
|
} else {
|
||||||
console.log('Parent not found: ' + item.parent);
|
console.log('Parent not found: ' + item.parent);
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -161,7 +161,12 @@ class EditableInputController {
|
|||||||
const preCaretRange = range.cloneRange();
|
const preCaretRange = range.cloneRange();
|
||||||
preCaretRange.selectNodeContents(element);
|
preCaretRange.selectNodeContents(element);
|
||||||
preCaretRange.setEnd(range.endContainer, range.endOffset);
|
preCaretRange.setEnd(range.endContainer, range.endOffset);
|
||||||
return preCaretRange.toString().trim().length;
|
const content = preCaretRange.toString().trim();
|
||||||
|
if (content === '\u200B') {
|
||||||
|
return 0; // Return 0 if the content is only the zero-width space character
|
||||||
|
}
|
||||||
|
console.log(content);
|
||||||
|
return content.replace('\u200B', '').length;
|
||||||
}
|
}
|
||||||
|
|
||||||
handleInput(editableDiv) {
|
handleInput(editableDiv) {
|
||||||
@@ -181,15 +186,50 @@ class EditableInputController {
|
|||||||
})
|
})
|
||||||
.join('');
|
.join('');
|
||||||
|
|
||||||
var result = mergedString.replace(/[\u200B-\u200D\uFEFF]/g, '');
|
let result = mergedString.replace(/[\u200B-\u200D\uFEFF]/g, '');
|
||||||
|
|
||||||
let content = this.parseContent(result);
|
let content = this.parseContent(result);
|
||||||
|
|
||||||
this.model.setValue(content.join(''));
|
this.model.setValue(content.join(''));
|
||||||
// Optionally, update the view if needed
|
// Optionally, update the view if needed
|
||||||
this.view.updateUI();
|
this.view.updateUI();
|
||||||
|
|
||||||
this.restoreCursor(editableDiv, cursor);
|
this.restoreCursor(editableDiv, cursor);
|
||||||
|
|
||||||
|
}
|
||||||
|
|
||||||
|
restoreCursor(element, position) {
|
||||||
|
const selection = window.getSelection();
|
||||||
|
const range = document.createRange();
|
||||||
|
range.setStart(element, 0);
|
||||||
|
range.collapse(true);
|
||||||
|
|
||||||
|
const nodeStack = [element];
|
||||||
|
let node, foundStart = false, stop = false;
|
||||||
|
let charIndex = 0;
|
||||||
|
console.log('restoreCursor', position);
|
||||||
|
while (!stop && (node = nodeStack.pop())) {
|
||||||
|
if (node.nodeType === 3) {
|
||||||
|
console.log(node);
|
||||||
|
const nextCharIndex = charIndex + node.length;
|
||||||
|
if (!foundStart && position >= charIndex && position <= nextCharIndex) {
|
||||||
|
range.setStart(node, position - charIndex);
|
||||||
|
foundStart = true;
|
||||||
|
}
|
||||||
|
if (foundStart && position >= charIndex && position <= nextCharIndex) {
|
||||||
|
range.setEnd(node, position - charIndex);
|
||||||
|
stop = true;
|
||||||
|
}
|
||||||
|
charIndex = nextCharIndex;
|
||||||
|
} else {
|
||||||
|
let i = node.childNodes.length;
|
||||||
|
while (i--) {
|
||||||
|
nodeStack.push(node.childNodes[i]);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
selection.removeAllRanges();
|
||||||
|
selection.addRange(range);
|
||||||
}
|
}
|
||||||
|
|
||||||
parseContent(inputString) {
|
parseContent(inputString) {
|
||||||
@@ -218,39 +258,7 @@ class EditableInputController {
|
|||||||
return returnStringArray;
|
return returnStringArray;
|
||||||
}
|
}
|
||||||
|
|
||||||
restoreCursor(element, position) {
|
|
||||||
const selection = window.getSelection();
|
|
||||||
const range = document.createRange();
|
|
||||||
range.setStart(element, 0);
|
|
||||||
range.collapse(true);
|
|
||||||
|
|
||||||
const nodeStack = [element];
|
|
||||||
let node, foundStart = false, stop = false;
|
|
||||||
let charIndex = 0;
|
|
||||||
|
|
||||||
while (!stop && (node = nodeStack.pop())) {
|
|
||||||
if (node.nodeType === 3) {
|
|
||||||
const nextCharIndex = charIndex + node.length;
|
|
||||||
if (!foundStart && position >= charIndex && position <= nextCharIndex) {
|
|
||||||
range.setStart(node, position - charIndex);
|
|
||||||
foundStart = true;
|
|
||||||
}
|
|
||||||
if (foundStart && position >= charIndex && position <= nextCharIndex) {
|
|
||||||
range.setEnd(node, position - charIndex);
|
|
||||||
stop = true;
|
|
||||||
}
|
|
||||||
charIndex = nextCharIndex;
|
|
||||||
} else {
|
|
||||||
let i = node.childNodes.length;
|
|
||||||
while (i--) {
|
|
||||||
nodeStack.push(node.childNodes[i]);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
selection.removeAllRanges();
|
|
||||||
selection.addRange(range);
|
|
||||||
}
|
|
||||||
|
|
||||||
updateUI() {
|
updateUI() {
|
||||||
this.view.updateUI();
|
this.view.updateUI();
|
||||||
|
|||||||
@@ -4,23 +4,31 @@ class LayoutGridModel {
|
|||||||
constructor(items) {
|
constructor(items) {
|
||||||
this.items = items;
|
this.items = items;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
setItems(items) {
|
||||||
|
this.items = items;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
class LayoutGridView {
|
class LayoutGridView {
|
||||||
|
|
||||||
constructor(model, controller) {
|
constructor(selector, model, controller) {
|
||||||
|
this.selector = selector;
|
||||||
this.model = model;
|
this.model = model;
|
||||||
this.controller = controller;
|
this.controller = controller;
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
||||||
render() {
|
render() {
|
||||||
this.renderApiLayout();
|
this.renderApiLayout();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
clear(){
|
||||||
|
this.selector.children().remove();
|
||||||
|
}
|
||||||
|
|
||||||
renderApiLayout() {
|
renderApiLayout() {
|
||||||
const requestContainer = this.targetContent.find('.request_layout');
|
const requestContainer = $(this.selector);
|
||||||
requestContainer.empty();
|
requestContainer.children().remove();;
|
||||||
|
|
||||||
const headerHtml = `
|
const headerHtml = `
|
||||||
<table class="layout_table" style="border-collapse: collapse; border: 1px gray solid;">
|
<table class="layout_table" style="border-collapse: collapse; border: 1px gray solid;">
|
||||||
@@ -72,12 +80,11 @@ class LayoutGridView {
|
|||||||
const editableInput = new EditableInput({
|
const editableInput = new EditableInput({
|
||||||
name: editableElement.dataset.name,
|
name: editableElement.dataset.name,
|
||||||
value: editableElement.dataset.value,
|
value: editableElement.dataset.value,
|
||||||
style : {width : '120px'}
|
style: {width: '120px'}
|
||||||
});
|
});
|
||||||
|
|
||||||
editableInput.init(editableElement, async (value) => {
|
editableInput.init(editableElement, async (value) => {
|
||||||
_.set(this.model, editableElement.dataset.name, value);
|
this.controller.setValue(editableElement.dataset.name, value);
|
||||||
await this.controller.additionalCallback(this.model);
|
|
||||||
});
|
});
|
||||||
});
|
});
|
||||||
|
|
||||||
@@ -86,7 +93,6 @@ class LayoutGridView {
|
|||||||
totalLength += parseInt(item.loutItemLength);
|
totalLength += parseInt(item.loutItemLength);
|
||||||
});
|
});
|
||||||
|
|
||||||
|
|
||||||
this.setupListeners();
|
this.setupListeners();
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -99,13 +105,6 @@ class LayoutGridView {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
recalculateSerno() {
|
|
||||||
// Reassign loutItemSerno sequentially based on the current order
|
|
||||||
this.model.items.forEach((item, index) => {
|
|
||||||
item.loutItemSerno = index + 1; // Assuming you want to start numbering from 1
|
|
||||||
});
|
|
||||||
}
|
|
||||||
|
|
||||||
async handleUIUpdate(event) {
|
async handleUIUpdate(event) {
|
||||||
if (event) {
|
if (event) {
|
||||||
event.preventDefault();
|
event.preventDefault();
|
||||||
@@ -113,8 +112,7 @@ class LayoutGridView {
|
|||||||
const fieldName = $(element).attr('name');
|
const fieldName = $(element).attr('name');
|
||||||
const newValue = this.getFieldValue(element);
|
const newValue = this.getFieldValue(element);
|
||||||
if (fieldName !== '') {
|
if (fieldName !== '') {
|
||||||
_.set(this.model, fieldName, newValue);
|
this.controller.setValue(fieldName, newValue);
|
||||||
await this.controller.additionalCallback(this.model);
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
let totalLength = 0;
|
let totalLength = 0;
|
||||||
@@ -123,82 +121,31 @@ class LayoutGridView {
|
|||||||
});
|
});
|
||||||
}
|
}
|
||||||
|
|
||||||
getLastId (){
|
|
||||||
let lastId = 0;
|
|
||||||
this.model.items.forEach(item => {
|
|
||||||
if (item.id > lastId) {
|
|
||||||
lastId = item.id;
|
|
||||||
}
|
|
||||||
});
|
|
||||||
return lastId + 1;
|
|
||||||
}
|
|
||||||
|
|
||||||
setupListeners() {
|
setupListeners() {
|
||||||
const table = this.targetContent.find('.layout_table');
|
const table = this.selector.find('.layout_table');
|
||||||
table.on('change', 'select.field, input.field', this.handleUIUpdate.bind(this));
|
table.on('change', 'select.field, input.field', this.handleUIUpdate.bind(this));
|
||||||
|
|
||||||
table.on('click', '.add-layout-item', async(event) => {
|
table.on('click', '.add-layout-item', async (event) => {
|
||||||
let item = {
|
await this.controller.addItem();
|
||||||
'id' : this.getLastId(),
|
|
||||||
'parent': 0,
|
|
||||||
'level': 1,
|
|
||||||
'loutName': '',
|
|
||||||
'loutItemName': '',
|
|
||||||
'loutItemDesc': '',
|
|
||||||
'loutItemDepth': 1,
|
|
||||||
'loutItemType': 'Field',
|
|
||||||
'loutItemOccCnt': '',
|
|
||||||
'loutItemOccRef': '',
|
|
||||||
'loutItemDataType': 'String',
|
|
||||||
'loutItemLength': 1,
|
|
||||||
'loutItemDecimal': 0,
|
|
||||||
'loutItemDefault': '',
|
|
||||||
'loutItemMaskYn': 'N',
|
|
||||||
'loutItemMaskOffset': 0,
|
|
||||||
'loutItemMaskLength': 0,
|
|
||||||
'parentLoutItemIndex': 0,
|
|
||||||
'expanded': true,
|
|
||||||
'isLeaf': true,
|
|
||||||
'LOUTITEMPATH': '',
|
|
||||||
'value': '',
|
|
||||||
'loutItemSerno': 0
|
|
||||||
};
|
|
||||||
this.model.items.push(item);
|
|
||||||
this.recalculateSerno();
|
|
||||||
this.renderApiLayout();
|
this.renderApiLayout();
|
||||||
await this.controller.additionalCallback(this.model);
|
|
||||||
});
|
});
|
||||||
|
|
||||||
table.on('click', '.move-up', async (event) => {
|
table.on('click', '.move-up', async (event) => {
|
||||||
const index = $(event.currentTarget).data('index');
|
const index = $(event.currentTarget).data('index');
|
||||||
if (index > 0) {
|
await this.controller.moveUp(index);
|
||||||
const temp = this.model.items[index];
|
this.renderApiLayout();
|
||||||
this.model.items[index] = this.model.items[index - 1];
|
|
||||||
this.model.items[index - 1] = temp;
|
|
||||||
this.recalculateSerno();
|
|
||||||
this.renderApiLayout();
|
|
||||||
await this.controller.additionalCallback(this.model);
|
|
||||||
}
|
|
||||||
});
|
});
|
||||||
|
|
||||||
table.on('click', '.move-down', async (event) => {
|
table.on('click', '.move-down', async (event) => {
|
||||||
const index = $(event.currentTarget).data('index');
|
const index = $(event.currentTarget).data('index');
|
||||||
if (index < this.model.items.length - 1) {
|
await this.controller.moveDown(index);
|
||||||
const temp = this.model.items[index];
|
this.renderApiLayout();
|
||||||
this.model.items[index] = this.model.items[index + 1];
|
|
||||||
this.model.items[index + 1] = temp;
|
|
||||||
this.recalculateSerno();
|
|
||||||
this.renderApiLayout();
|
|
||||||
await this.controller.additionalCallback(this.model);
|
|
||||||
}
|
|
||||||
});
|
});
|
||||||
|
|
||||||
table.on('click', '.delete', async (event) => {
|
table.on('click', '.delete', async (event) => {
|
||||||
const index = $(event.currentTarget).data('index');
|
const index = $(event.currentTarget).data('index');
|
||||||
this.model.items.splice(index, 1);
|
await this.controller.deleteItem(index);
|
||||||
this.recalculateSerno();
|
|
||||||
this.renderApiLayout();
|
this.renderApiLayout();
|
||||||
await this.controller.additionalCallback(this.model);
|
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -244,7 +191,7 @@ class LayoutGridView {
|
|||||||
<input type="number" class="form-control field" style="width: 80px;" name="items[${index}].loutItemLength" min="1" value="${item.loutItemLength}">
|
<input type="number" class="form-control field" style="width: 80px;" name="items[${index}].loutItemLength" min="1" value="${item.loutItemLength}">
|
||||||
</td>
|
</td>
|
||||||
<td class="layout-grid-cell">
|
<td class="layout-grid-cell">
|
||||||
${ item.loutItemType ==='Field'? `<div class="editable" data-name="items[${index}].value" data-value="${item.value}"></div>`:''}
|
${item.loutItemType === 'Field' ? `<div class="editable" data-name="items[${index}].value" data-value="${item.value}"></div>` : ''}
|
||||||
</td>
|
</td>
|
||||||
<td class="layout-grid-cell" style="width: 120px; text-align: center;">
|
<td class="layout-grid-cell" style="width: 120px; text-align: center;">
|
||||||
<div style="width: 120px !important;">
|
<div style="width: 120px !important;">
|
||||||
@@ -260,27 +207,114 @@ class LayoutGridView {
|
|||||||
}
|
}
|
||||||
|
|
||||||
class LayoutGridController {
|
class LayoutGridController {
|
||||||
constructor(model) {
|
constructor(model, view, callback) {
|
||||||
this.model = model;
|
this.model = model;
|
||||||
this.view = new LayoutGridView(this.model, this);
|
this.view = view;
|
||||||
|
this.view.controller = this;
|
||||||
|
this.callback = callback;
|
||||||
|
this.init();
|
||||||
}
|
}
|
||||||
|
|
||||||
init(targetContent, callback) {
|
init() {
|
||||||
this.additionalCallback = callback;
|
|
||||||
this.view.targetContent = targetContent;
|
|
||||||
this.view.render();
|
this.view.render();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
recalculateSerno() {
|
||||||
|
// Reassign loutItemSerno sequentially based on the current order
|
||||||
|
this.model.items.forEach((item, index) => {
|
||||||
|
item.loutItemSerno = index + 1; // Assuming you want to start numbering from 1
|
||||||
|
});
|
||||||
|
}
|
||||||
|
|
||||||
|
async addItem() {
|
||||||
|
let item = {
|
||||||
|
'id': this.getLastId(),
|
||||||
|
'parent': 0,
|
||||||
|
'level': 1,
|
||||||
|
'loutName': '',
|
||||||
|
'loutItemName': '',
|
||||||
|
'loutItemDesc': '',
|
||||||
|
'loutItemDepth': 1,
|
||||||
|
'loutItemType': 'Field',
|
||||||
|
'loutItemOccCnt': '',
|
||||||
|
'loutItemOccRef': '',
|
||||||
|
'loutItemDataType': 'String',
|
||||||
|
'loutItemLength': 1,
|
||||||
|
'loutItemDecimal': 0,
|
||||||
|
'loutItemDefault': '',
|
||||||
|
'loutItemMaskYn': 'N',
|
||||||
|
'loutItemMaskOffset': 0,
|
||||||
|
'loutItemMaskLength': 0,
|
||||||
|
'parentLoutItemIndex': 0,
|
||||||
|
'expanded': true,
|
||||||
|
'isLeaf': true,
|
||||||
|
'LOUTITEMPATH': '',
|
||||||
|
'value': '',
|
||||||
|
'loutItemSerno': 0
|
||||||
|
};
|
||||||
|
this.model.items.push(item);
|
||||||
|
this.recalculateSerno();
|
||||||
|
await this.callback(this.model);
|
||||||
|
}
|
||||||
|
|
||||||
|
async moveUp(index) {
|
||||||
|
if (index > 0) {
|
||||||
|
const temp = this.model.items[index];
|
||||||
|
this.model.items[index] = this.model.items[index - 1];
|
||||||
|
this.model.items[index - 1] = temp;
|
||||||
|
this.recalculateSerno();
|
||||||
|
await this.callback(this.model);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
async moveDown(index) {
|
||||||
|
if (index < this.model.items.length - 1) {
|
||||||
|
const temp = this.model.items[index];
|
||||||
|
this.model.items[index] = this.model.items[index + 1];
|
||||||
|
this.model.items[index + 1] = temp;
|
||||||
|
this.recalculateSerno();
|
||||||
|
await this.callback(this.model);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
async setValue(name, value){
|
||||||
|
_.set(this.model, name, value);
|
||||||
|
await this.callback(this.model);
|
||||||
|
}
|
||||||
|
|
||||||
|
async deleteItem(index) {
|
||||||
|
this.model.items.splice(index, 1);
|
||||||
|
this.recalculateSerno();
|
||||||
|
await this.callback(this.model);
|
||||||
|
}
|
||||||
|
|
||||||
|
getLastId() {
|
||||||
|
let lastId = 0;
|
||||||
|
this.model.items.forEach(item => {
|
||||||
|
if (item.id > lastId) {
|
||||||
|
lastId = item.id;
|
||||||
|
}
|
||||||
|
});
|
||||||
|
return lastId + 1;
|
||||||
|
}
|
||||||
|
|
||||||
|
rebuild(newItems) {
|
||||||
|
this.model.setItems(newItems);
|
||||||
|
this.view.clear();
|
||||||
|
this.init();
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
class LayoutGrid {
|
class LayoutGrid {
|
||||||
constructor(layout) {
|
constructor(selector, layout, callback) {
|
||||||
this.model = new LayoutGridModel(layout.layoutItems);
|
this.model = new LayoutGridModel(layout.layoutItems);
|
||||||
this.controller = new LayoutGridController(this.model);
|
this.view = new LayoutGridView(selector, this.model, this);
|
||||||
|
this.controller = new LayoutGridController(this.model, this.view, callback);
|
||||||
}
|
}
|
||||||
|
|
||||||
init(targetContent, callback) {
|
rebuild(layout) {
|
||||||
this.controller.init(targetContent, callback);
|
this.controller.rebuild(layout.layoutItems);
|
||||||
|
this.controller.callback(this.model);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|||||||
@@ -116,41 +116,8 @@ class LayoutTreeGridController {
|
|||||||
return new Array(depth + 1).join('<span class="treegrid-indent"></span>');
|
return new Array(depth + 1).join('<span class="treegrid-indent"></span>');
|
||||||
}
|
}
|
||||||
|
|
||||||
// addRow(node, depth) {
|
|
||||||
// console.log('================================ addRow: ', node.id);
|
|
||||||
// const tr = $('<tr>').addClass('treegrid-' + node.id).data('nodeId', node.id); // Storing node ID for easy access later
|
|
||||||
//
|
|
||||||
// if (depth === 0) {
|
|
||||||
// tr.css({'display': 'none'});
|
|
||||||
// }
|
|
||||||
//
|
|
||||||
// if (node.parent || (node.parent !== null && parseInt(node.parent) !== this.model.rootId)) {
|
|
||||||
// // if (node.parent !== undefined && node.parent !== null) {
|
|
||||||
// const parentSelector = `.treegrid-${node.parent}`;
|
|
||||||
// const lastChildSelector = `.treegrid-parent-${node.parent}`;
|
|
||||||
// // console.log('lastChild:', $(this.view.table).find(lastChildSelector), 'length: ', $(this.view.table).find(lastChildSelector).length);
|
|
||||||
//
|
|
||||||
// if ($(this.view.table).find(lastChildSelector).length > 0) {
|
|
||||||
// const lastChild = $(this.view.table).find(lastChildSelector).last();
|
|
||||||
// tr.insertAfter(lastChild);
|
|
||||||
// console.log('addRow, node: ', node.id, ' parent: ', node.parent, 'tr: ', tr, 'insertAfterLastChild: ', lastChild);
|
|
||||||
// } else {
|
|
||||||
// console.log('addRow, node: ', node.id, ' parent: ', node.parent, 'tr: ', tr, 'insertAfterParent: ', parentSelector);
|
|
||||||
// tr.insertAfter($(this.view.table).find(parentSelector));
|
|
||||||
// // tr.appendTo(this.view.table);
|
|
||||||
// }
|
|
||||||
// tr.addClass('treegrid-parent-' + node.parent);
|
|
||||||
// } else {
|
|
||||||
// tr.appendTo(this.view.table);
|
|
||||||
// console.log('addRow, node: ', node.id, ' parent: ', node.parent, 'tr: ', tr, 'no parent');
|
|
||||||
// }
|
|
||||||
//
|
|
||||||
// console.log('================================ row Added');
|
|
||||||
// return tr;
|
|
||||||
// }
|
|
||||||
|
|
||||||
addRow(node, depth) {
|
addRow(node, depth) {
|
||||||
console.log('================================ addRow: ', node.id);
|
// console.log('================================ addRow: ', node.id);
|
||||||
const tr = $('<tr>').addClass('treegrid-' + node.id).data('nodeId', node.id);
|
const tr = $('<tr>').addClass('treegrid-' + node.id).data('nodeId', node.id);
|
||||||
|
|
||||||
if (depth === 0) {
|
if (depth === 0) {
|
||||||
@@ -164,18 +131,18 @@ class LayoutTreeGridController {
|
|||||||
if ($(this.view.table).find(lastChildSelector).length > 0) {
|
if ($(this.view.table).find(lastChildSelector).length > 0) {
|
||||||
const lastChild = $(this.view.table).find(lastChildSelector).last();
|
const lastChild = $(this.view.table).find(lastChildSelector).last();
|
||||||
tr.insertAfter(lastChild);
|
tr.insertAfter(lastChild);
|
||||||
console.log('addRow, node: ', node.id, ' parent: ', node.parent, 'tr: ', tr, 'insertAfterLastChild: ', lastChild);
|
// console.log('addRow, node: ', node.id, ' parent: ', node.parent, 'tr: ', tr, 'insertAfterLastChild: ', lastChild);
|
||||||
} else {
|
} else {
|
||||||
console.log('addRow, node: ', node.id, ' parent: ', node.parent, 'tr: ', tr, 'insertAfterParent: ', parentSelector);
|
// console.log('addRow, node: ', node.id, ' parent: ', node.parent, 'tr: ', tr, 'insertAfterParent: ', parentSelector);
|
||||||
tr.insertAfter($(this.view.table).find(parentSelector));
|
tr.insertAfter($(this.view.table).find(parentSelector));
|
||||||
}
|
}
|
||||||
tr.addClass('treegrid-parent-' + node.parent);
|
tr.addClass('treegrid-parent-' + node.parent);
|
||||||
} else {
|
} else {
|
||||||
tr.appendTo(this.view.table);
|
tr.appendTo(this.view.table);
|
||||||
console.log('addRow, node: ', node.id, ' parent: ', node.parent, 'tr: ', tr, 'no parent');
|
// console.log('addRow, node: ', node.id, ' parent: ', node.parent, 'tr: ', tr, 'no parent');
|
||||||
}
|
}
|
||||||
|
|
||||||
console.log('================================ row Added');
|
// console.log('================================ row Added');
|
||||||
return tr;
|
return tr;
|
||||||
}
|
}
|
||||||
addCell(row, node, fieldInfo, depth) {
|
addCell(row, node, fieldInfo, depth) {
|
||||||
|
|||||||
@@ -34,8 +34,8 @@ class TCPClientView {
|
|||||||
|
|
||||||
const layoutDataTreeOptions = [
|
const layoutDataTreeOptions = [
|
||||||
{name: 'loutItemSerno', width: 100, isFirst: true, label: '#'},
|
{name: 'loutItemSerno', width: 100, isFirst: true, label: '#'},
|
||||||
{name: 'loutItemName', width: 100, align: 'center', label: '항목명(영문)'},
|
{name: 'loutItemName', width: 100, align: 'left', label: '항목명(영문)'},
|
||||||
{name: 'loutItemDesc', width: 100, align: 'center', label: '항목설명'},
|
{name: 'loutItemDesc', width: 100, align: 'left', label: '항목설명'},
|
||||||
{name: 'loutItemDepth', width: 60, align: 'center', label: '깊이'},
|
{name: 'loutItemDepth', width: 60, align: 'center', label: '깊이'},
|
||||||
{name: 'loutItemType', width: 100, align: 'center', label: '아이템 유형'},
|
{name: 'loutItemType', width: 100, align: 'center', label: '아이템 유형'},
|
||||||
{name: 'loutItemOccCnt', width: 100, align: 'center', label: '반복 횟수'},
|
{name: 'loutItemOccCnt', width: 100, align: 'center', label: '반복 횟수'},
|
||||||
@@ -48,13 +48,10 @@ class TCPClientView {
|
|||||||
let replicator = new ApiLayoutItemTreeDataBuilder(10000);
|
let replicator = new ApiLayoutItemTreeDataBuilder(10000);
|
||||||
let layoutDataRoot = replicator.createReplicatedTree(layoutRoot);
|
let layoutDataRoot = replicator.createReplicatedTree(layoutRoot);
|
||||||
|
|
||||||
console.log(this.apiRequestTabContent.find(`#api_request_${this.model.id}`).find('.request_layout_data_tree'));
|
|
||||||
console.log(this.apiRequestTabContent.find(`#api_request_${this.model.id}`).find('.request_layout_tree'));
|
|
||||||
console.log(this.apiRequestTabContent.find(`#api_request_${this.model.id}`).find('.total_message_length'));
|
|
||||||
|
|
||||||
let layoutTreeDataGrid = new LayoutTreeDataGrid(this.apiRequestTabContent.find(`#api_request_${this.model.id}`).find('.request_layout_data_tree'), layoutDataRoot, this.model, layoutDataTreeOptions, this.apiRequestTabContent.find(`#api_request_${this.model.id}`).find('.total_message_length'));
|
let layoutTreeDataGrid = new LayoutTreeDataGrid(this.apiRequestTabContent.find(`#api_request_${this.model.id}`).find('.request_layout_data_tree'), layoutDataRoot, this.model, layoutDataTreeOptions, this.apiRequestTabContent.find(`#api_request_${this.model.id}`).find('.total_message_length'));
|
||||||
layoutTreeDataGrid.init( async (finalMessage) => {
|
layoutTreeDataGrid.init( async (finalMessage) => {
|
||||||
const prefix = await this.serverManager.renderServerPrefix(this.server.serverOptions, this.model);
|
const prefix = this.server.serverOptions ? await this.serverManager.renderServerPrefix(this.server.serverOptions, this.model) : '';
|
||||||
|
|
||||||
this.requestBodyEditor.setValue(prefix + finalMessage);
|
this.requestBodyEditor.setValue(prefix + finalMessage);
|
||||||
});
|
});
|
||||||
|
|
||||||
@@ -64,8 +61,7 @@ class TCPClientView {
|
|||||||
layoutTreeDataGrid.rebuild(layoutDataRoot);
|
layoutTreeDataGrid.rebuild(layoutDataRoot);
|
||||||
});
|
});
|
||||||
|
|
||||||
let layoutGrid = new LayoutGrid(this.model.layout);
|
let layoutGrid = new LayoutGrid(this.apiRequestTabContent.find(`#api_request_${this.model.id}`).find('.request_layout'), this.model.layout, (model) => {
|
||||||
layoutGrid.init(this.apiRequestTabContent.find(`#api_request_${this.model.id}`), (model) => {
|
|
||||||
model.items.forEach((item) => {
|
model.items.forEach((item) => {
|
||||||
item.children = [];
|
item.children = [];
|
||||||
});
|
});
|
||||||
@@ -75,6 +71,7 @@ class TCPClientView {
|
|||||||
let layoutDataRoot = replicator.createReplicatedTree(root);
|
let layoutDataRoot = replicator.createReplicatedTree(root);
|
||||||
layoutTreeDataGrid.rebuild(layoutDataRoot);
|
layoutTreeDataGrid.rebuild(layoutDataRoot);
|
||||||
});
|
});
|
||||||
|
this.layoutJsonEditor.setValue(JSON.stringify(this.model.layout, null, 2));
|
||||||
|
|
||||||
$('span.variable').off('mouseover');
|
$('span.variable').off('mouseover');
|
||||||
$('span.variable').off('mouseout');
|
$('span.variable').off('mouseout');
|
||||||
@@ -85,6 +82,22 @@ class TCPClientView {
|
|||||||
});
|
});
|
||||||
});
|
});
|
||||||
|
|
||||||
|
this.apiRequestTabContent.find(`#api_request_${this.model.id}`).find('.load_layout').on('click', () => {
|
||||||
|
try {
|
||||||
|
this.model.layout = JSON.parse(this.layoutJsonEditor.getValue());
|
||||||
|
this.model.layout.layoutItems.forEach((item) => {
|
||||||
|
if (item.value === undefined){
|
||||||
|
item.value = '';
|
||||||
|
}
|
||||||
|
});
|
||||||
|
console.log(this.model);
|
||||||
|
layoutGrid.rebuild(this.model.layout);
|
||||||
|
} catch (e) {
|
||||||
|
console.error(e);
|
||||||
|
alert(e);
|
||||||
|
}
|
||||||
|
});
|
||||||
|
|
||||||
window.addEventListener('resize', this.resizeEditor.bind(this));
|
window.addEventListener('resize', this.resizeEditor.bind(this));
|
||||||
|
|
||||||
}
|
}
|
||||||
@@ -157,15 +170,17 @@ class TCPClientView {
|
|||||||
</ul>
|
</ul>
|
||||||
<div class="tab-content" style="height: 100%;">
|
<div class="tab-content" style="height: 100%;">
|
||||||
<div class="tab-pane fade request_layout_json_tab" role="tabpanel" id="requestLayoutJson_${apiRequest.id}" aria-labelledby="requestLayoutJson-tab">
|
<div class="tab-pane fade request_layout_json_tab" role="tabpanel" id="requestLayoutJson_${apiRequest.id}" aria-labelledby="requestLayoutJson-tab">
|
||||||
<div class="d-flex flex-row">
|
<div class="d-flex flex-column">
|
||||||
<div style="width:calc(100%);">
|
<div style="width:calc(100%);">
|
||||||
<div class="layout-json mt-1" style="height:300px;border:1px solid grey;"></div>
|
<div class="layout-json mt-1" style="height:300px;border:1px solid grey;"></div>
|
||||||
</div>
|
</div>
|
||||||
|
<button class="btn btn-primary mt-1 load_layout">레이아웃 불러오기</button>
|
||||||
</div>
|
</div>
|
||||||
</div>
|
</div>
|
||||||
<div class="tab-pane show fade request_body_tab" role="tabpanel" id="requestBodyTab_${apiRequest.id}" aria-labelledby="requestBody-tab">
|
<div class="tab-pane show fade request_body_tab" role="tabpanel" id="requestBodyTab_${apiRequest.id}" aria-labelledby="requestBody-tab">
|
||||||
<div class="d-flex flex-column">
|
<div class="d-flex flex-column">
|
||||||
<div class="request_layout" style="border:1px solid grey; overflow: scroll"></div>
|
<div class="request_layout" style="border:1px solid grey; overflow: scroll"></div>
|
||||||
|
|
||||||
</div>
|
</div>
|
||||||
</div>
|
</div>
|
||||||
<div class="tab-pane show fade request_layout_tree_tab" role="tabpanel" id="requestLayoutTreeTab_${apiRequest.id}" aria-labelledby="requestLayoutTree-tab">
|
<div class="tab-pane show fade request_layout_tree_tab" role="tabpanel" id="requestLayoutTreeTab_${apiRequest.id}" aria-labelledby="requestLayoutTree-tab">
|
||||||
|
|||||||
@@ -86,6 +86,7 @@ public class ApiRequestMgmtController {
|
|||||||
|
|
||||||
if (dto.getLayout() != null) {
|
if (dto.getLayout() != null) {
|
||||||
dto.getLayout().setApiRequestId(apiId);
|
dto.getLayout().setApiRequestId(apiId);
|
||||||
|
dto.getLayout().setId(apiId);
|
||||||
apiLayoutMgmtService.saveLayout(apiLayoutMapper.map(dto.getLayout()));
|
apiLayoutMgmtService.saveLayout(apiLayoutMapper.map(dto.getLayout()));
|
||||||
}
|
}
|
||||||
return ResponseEntity.ok(apiId);
|
return ResponseEntity.ok(apiId);
|
||||||
|
|||||||
@@ -1,6 +1,7 @@
|
|||||||
package com.eactive.testmaster.client.mapper;
|
package com.eactive.testmaster.client.mapper;
|
||||||
|
|
||||||
import com.eactive.testmaster.client.dto.ApiCollectionDTO;
|
import com.eactive.testmaster.client.dto.ApiCollectionDTO;
|
||||||
|
import com.eactive.testmaster.client.dto.ApiLayoutDTO;
|
||||||
import com.eactive.testmaster.client.dto.ApiRequestDTO;
|
import com.eactive.testmaster.client.dto.ApiRequestDTO;
|
||||||
import com.eactive.testmaster.client.entity.ApiCollection;
|
import com.eactive.testmaster.client.entity.ApiCollection;
|
||||||
import com.eactive.testmaster.client.entity.ApiLayout;
|
import com.eactive.testmaster.client.entity.ApiLayout;
|
||||||
@@ -61,15 +62,17 @@ public abstract class ApiRequestMapper {
|
|||||||
public void handleTypeSpecificMapping(ApiRequestInfo entity, @MappingTarget ApiRequestDTO dto) {
|
public void handleTypeSpecificMapping(ApiRequestInfo entity, @MappingTarget ApiRequestDTO dto) {
|
||||||
if ("TCP".equals(entity.getType())) {
|
if ("TCP".equals(entity.getType())) {
|
||||||
ApiLayout layout = apiLayoutRepository.findFirstByApiRequestInfo(entity);
|
ApiLayout layout = apiLayoutRepository.findFirstByApiRequestInfo(entity);
|
||||||
if (layout!=null) {
|
if (layout != null) {
|
||||||
layout.getLayoutItems().sort(Comparator.comparingInt(ApiLayoutItem::getLoutItemSerno));
|
layout.getLayoutItems().sort(Comparator.comparingInt(ApiLayoutItem::getLoutItemSerno));
|
||||||
dto.setLayout(apiLayoutMapper.map(layout));
|
dto.setLayout(apiLayoutMapper.map(layout));
|
||||||
|
} else {
|
||||||
|
dto.setLayout(new ApiLayoutDTO());
|
||||||
}
|
}
|
||||||
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
public abstract List<ApiRequestInfo> mapApis(List<ApiRequestDTO> apis);
|
public abstract List<ApiRequestInfo> mapApis(List<ApiRequestDTO> apis);
|
||||||
|
|
||||||
public abstract List<ApiCollectionDTO> mapCollections(List<ApiCollection> apis);
|
public abstract List<ApiCollectionDTO> mapCollections(List<ApiCollection> apis);
|
||||||
|
|||||||
@@ -6,6 +6,7 @@ import com.eactive.testmaster.client.entity.ApiRequestInfo;
|
|||||||
import com.eactive.testmaster.client.repository.ApiLayoutRepository;
|
import com.eactive.testmaster.client.repository.ApiLayoutRepository;
|
||||||
import com.eactive.testmaster.client.repository.ApiRequestRepository;
|
import com.eactive.testmaster.client.repository.ApiRequestRepository;
|
||||||
import com.eactive.testmaster.common.exception.NotFoundException;
|
import com.eactive.testmaster.common.exception.NotFoundException;
|
||||||
|
import java.util.Optional;
|
||||||
import java.util.UUID;
|
import java.util.UUID;
|
||||||
import javax.transaction.Transactional;
|
import javax.transaction.Transactional;
|
||||||
import org.springframework.stereotype.Service;
|
import org.springframework.stereotype.Service;
|
||||||
@@ -31,11 +32,9 @@ public class ApiLayoutMgmtService {
|
|||||||
}
|
}
|
||||||
|
|
||||||
public ApiLayout saveLayout(ApiLayout layout) {
|
public ApiLayout saveLayout(ApiLayout layout) {
|
||||||
if (layout.getId() == null) {
|
ApiLayout apiLayout = apiLayoutRepository.findFirstByApiRequestInfo(layout.getApiRequestInfo());
|
||||||
return createLayout(layout);
|
|
||||||
} else {
|
return apiLayout == null ? createLayout(layout) : updateLayout(apiLayout.getId(), layout);
|
||||||
return updateLayout(layout.getId(), layout);
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
|
||||||
public ApiLayout createLayout(ApiLayout layout) {
|
public ApiLayout createLayout(ApiLayout layout) {
|
||||||
|
|||||||
File diff suppressed because one or more lines are too long
Reference in New Issue
Block a user