diff options
| author | Maxime Porhel | 2016-04-28 10:01:43 +0000 |
|---|---|---|
| committer | Maxime Porhel | 2016-05-10 14:34:23 +0000 |
| commit | 6d7e5a887dadb1a3c9a2f72722d08212d2dec9e7 (patch) | |
| tree | d10757e1b0b99f84e95c92c831f343217cad8de8 | |
| parent | a072d2c1484ee82bfb77cdd9ecdb8f92091b125b (diff) | |
| download | org.eclipse.sirius-6d7e5a887dadb1a3c9a2f72722d08212d2dec9e7.tar.gz org.eclipse.sirius-6d7e5a887dadb1a3c9a2f72722d08212d2dec9e7.tar.xz org.eclipse.sirius-6d7e5a887dadb1a3c9a2f72722d08212d2dec9e7.zip | |
[492634] DLine deletion in EditionTable must not lead to dangling
cells
DTableSynchronizer now removes orphan cells. The DCell is detached from
its line during line deletion. The test getLine() == null is sufficient
now, we have to check this in the unit test.
removeUneededCell has also been modified to improve its capacity to
retrieve the current session and be able to do the minimum work if no
session is found.
TableCommandFactory now removes the deleted cells from their
column.getCells() list. So even in manual refresh, when there is a
delete tool, there is no more dangling cells. If there is no delete
tool, the next refresh will clean the table.
Bug: 492634
Change-Id: I72c3aaf51479cc08489dadc723adc2153ba0d3a5
Signed-off-by: Maxime Porhel <maxime.porhel@obeo.fr>
4 files changed, 67 insertions, 6 deletions
diff --git a/plugins/org.eclipse.sirius.table/src/org/eclipse/sirius/table/business/internal/refresh/DTableElementSynchronizerSpec.java b/plugins/org.eclipse.sirius.table/src/org/eclipse/sirius/table/business/internal/refresh/DTableElementSynchronizerSpec.java index 5f0eb6a5dc..f8d2055a44 100644 --- a/plugins/org.eclipse.sirius.table/src/org/eclipse/sirius/table/business/internal/refresh/DTableElementSynchronizerSpec.java +++ b/plugins/org.eclipse.sirius.table/src/org/eclipse/sirius/table/business/internal/refresh/DTableElementSynchronizerSpec.java @@ -328,10 +328,35 @@ public class DTableElementSynchronizerSpec extends DTableElementSynchronizerImpl * The cell to removed */ protected void removeUneededCell(DCell cell) { - final Session session = SessionManager.INSTANCE.getSession(cell.getTarget()); - final ECrossReferenceAdapter xref = session != null ? session.getSemanticCrossReferencer() : null; + Session session = SessionManager.INSTANCE.getSession(cell.getTarget()); + if (session == null) { + // If session is null, the semantic element might have already been + // deleted and/or cell might be partially deleted but still + // referenced from its column for example. + DLine line = cell.getLine(); + DColumn column = cell.getColumn(); + EObject target = null; + if (line != null) { + target = line.getTarget(); + } else if (column instanceof DFeatureColumn && column.getTable() != null) { + target = column.getTable().getTarget(); + } else if (column instanceof DTargetColumn) { + target = column.getTarget(); + } + + if (target != null) { + session = SessionManager.INSTANCE.getSession(target); + } + } + if (accessor.getPermissionAuthority().canDeleteInstance(cell)) { - accessor.eDelete(cell, xref); + if (session != null) { + final ECrossReferenceAdapter xref = session.getSemanticCrossReferencer(); + accessor.eDelete(cell, xref); + } else { + cell.setLine(null); + cell.setColumn(null); + } } } diff --git a/plugins/org.eclipse.sirius.table/src/org/eclipse/sirius/table/business/internal/refresh/DTableSynchronizerImpl.java b/plugins/org.eclipse.sirius.table/src/org/eclipse/sirius/table/business/internal/refresh/DTableSynchronizerImpl.java index 5f6520198a..7acf675ca2 100644 --- a/plugins/org.eclipse.sirius.table/src/org/eclipse/sirius/table/business/internal/refresh/DTableSynchronizerImpl.java +++ b/plugins/org.eclipse.sirius.table/src/org/eclipse/sirius/table/business/internal/refresh/DTableSynchronizerImpl.java @@ -204,6 +204,15 @@ public class DTableSynchronizerImpl implements DTableSynchronizer { */ private void refreshCells(final IProgressMonitor monitor, final Map<TableMapping, Collection<DTableElement>> mappingToElements, ECrossReferenceAdapter xref) { if (description instanceof EditionTableDescription) { + // Clean orphan cells + for (final DColumn column : table.getColumns()) { + for (DCell cell : Lists.newArrayList(column.getCells())) { + if (cell.getLine() == null) { + doDeleteCell(cell, xref); + } + } + } + fillTableDCells(table); } else if (description instanceof CrossTableDescription) { refreshCellsOfCrossTable(monitor, mappingToElements, xref); diff --git a/plugins/org.eclipse.sirius.table/src/org/eclipse/sirius/table/tools/internal/command/TableCommandFactory.java b/plugins/org.eclipse.sirius.table/src/org/eclipse/sirius/table/tools/internal/command/TableCommandFactory.java index 37287738a2..e66b8685a3 100644 --- a/plugins/org.eclipse.sirius.table/src/org/eclipse/sirius/table/tools/internal/command/TableCommandFactory.java +++ b/plugins/org.eclipse.sirius.table/src/org/eclipse/sirius/table/tools/internal/command/TableCommandFactory.java @@ -1,5 +1,5 @@ /******************************************************************************* - * Copyright (c) 2007, 2015 THALES GLOBAL SERVICES and others. + * Copyright (c) 2007, 2016 THALES GLOBAL SERVICES and others. * All rights reserved. This program and the accompanying materials * are made available under the terms of the Eclipse Public License v1.0 * which accompanies this distribution, and is available at @@ -12,6 +12,7 @@ package org.eclipse.sirius.table.tools.internal.command; import java.text.MessageFormat; import java.util.HashMap; +import java.util.List; import java.util.Map; import org.eclipse.core.runtime.IProgressMonitor; @@ -35,6 +36,7 @@ import org.eclipse.sirius.common.tools.api.interpreter.IInterpreterSiriusVariabl import org.eclipse.sirius.common.tools.api.util.StringUtil; import org.eclipse.sirius.ecore.extender.business.api.accessor.ModelAccessor; import org.eclipse.sirius.ecore.extender.business.api.accessor.exception.FeatureNotFoundException; +import org.eclipse.sirius.ecore.extender.business.api.accessor.exception.MetaClassNotFoundException; import org.eclipse.sirius.ecore.extender.business.api.permission.IPermissionAuthority; import org.eclipse.sirius.ecore.extender.business.api.permission.exception.LockedInstanceException; import org.eclipse.sirius.ext.base.Option; @@ -69,8 +71,8 @@ import org.eclipse.sirius.tools.internal.command.builders.ElementsToSelectTask; import org.eclipse.sirius.viewpoint.DRepresentation; import org.eclipse.sirius.viewpoint.DSemanticDecorator; import org.eclipse.sirius.viewpoint.SiriusPlugin; -import org.eclipse.sirius.viewpoint.description.tool.AbstractToolDescription; import org.eclipse.sirius.viewpoint.description.AbstractVariable; +import org.eclipse.sirius.viewpoint.description.tool.AbstractToolDescription; import org.eclipse.sirius.viewpoint.description.tool.RepresentationCreationDescription; import org.eclipse.sirius.viewpoint.description.tool.ToolPackage; @@ -259,7 +261,27 @@ public class TableCommandFactory extends AbstractCommandFactory implements ITabl private void addDeleteTableElementFromTool(final SiriusCommand cmd, final DTableElement element, final DeleteTool deleteTool) { final EObject semanticElement = ((DSemanticDecorator) element).getTarget(); cmd.getTasks().addAll(buildCommandFromModelOfTool(semanticElement, deleteTool, element.eContainer()).getTasks()); - cmd.getTasks().add(new DeleteDRepresentationElementsTask(modelAccessor, cmd, commandTaskHelper, element)); + cmd.getTasks().add(new DeleteDRepresentationElementsTask(modelAccessor, cmd, commandTaskHelper, element) { + @Override + protected void addDialectSpecificAdditionalDeleteSubTasks(DSemanticDecorator semDec, List<ICommandTask> subTasks) { + super.addDialectSpecificAdditionalDeleteSubTasks(semDec, subTasks); + if (semDec instanceof DCell) { + final DCell cell = (DCell) semDec; + subTasks.add(new AbstractCommandTask() { + + @Override + public String getLabel() { + return ""; //$NON-NLS-1$ + } + + @Override + public void execute() throws MetaClassNotFoundException, FeatureNotFoundException { + cell.setColumn(null); + } + }); + } + } + }); } /** diff --git a/plugins/org.eclipse.sirius.tests.swtbot/src/org/eclipse/sirius/tests/swtbot/table/DeleteLineWithDELShortcutTest.java b/plugins/org.eclipse.sirius.tests.swtbot/src/org/eclipse/sirius/tests/swtbot/table/DeleteLineWithDELShortcutTest.java index 20880f4443..4be80ce7d2 100644 --- a/plugins/org.eclipse.sirius.tests.swtbot/src/org/eclipse/sirius/tests/swtbot/table/DeleteLineWithDELShortcutTest.java +++ b/plugins/org.eclipse.sirius.tests.swtbot/src/org/eclipse/sirius/tests/swtbot/table/DeleteLineWithDELShortcutTest.java @@ -72,13 +72,18 @@ public class DeleteLineWithDELShortcutTest extends AbstractTreeSiriusSWTBotGefTe * Test table line deletion with DEL shortcut. */ public void testTableLineDeletionWithDELShortcut() { + assertEquals("Wrong test data, the current test has been written to check the deletion of a line with one cell only.", 1, dTable.getColumns().size()); + int nbLines = dTable.getLines().size(); + int nbCells = dTable.getColumns().get(0).getCells().size(); + int nbSubLines = dTable.getLines().get(0).getLines().size(); tableEditorBot.setFocus(); tableEditorBot.bot().tree().getAllItems()[0].select(); doLineDeletionWithDELShortcut(tableRepresentation.getTree()); assertEquals(nbLines - 1, dTable.getLines().size()); + assertEquals("Cells of the deleted lines and sublines should be removed from cells referenced from the column.", nbCells - 1 - nbSubLines, dTable.getColumns().get(0).getCells().size()); } private void doLineDeletionWithDELShortcut(SWTBotTree swtBotTree) { |
