blob: 60fb78762f8761321371c1c321a8c2faf9d80db6 [file] [log] [blame]
/*******************************************************************************
* Copyright (c) 2008-2011 Chair for Applied Software Engineering,
* Technische Universitaet Muenchen.
* 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
* http://www.eclipse.org/legal/epl-v10.html
*
* Contributors:
* wesendon
******************************************************************************/
package org.eclipse.emf.emfstore.internal.client.ui.dialogs.merge;
import java.text.MessageFormat;
import java.util.ArrayList;
import java.util.List;
import org.eclipse.emf.emfstore.internal.client.model.changeTracking.merging.DecisionManager;
import org.eclipse.emf.emfstore.internal.client.model.changeTracking.merging.conflict.ConflictOption;
import org.eclipse.emf.emfstore.internal.client.model.changeTracking.merging.conflict.ConflictOption.OptionType;
import org.eclipse.emf.emfstore.internal.client.model.changeTracking.merging.conflict.VisualConflict;
import org.eclipse.emf.emfstore.internal.client.ui.dialogs.merge.ui.DecisionBox;
import org.eclipse.emf.emfstore.internal.client.ui.dialogs.merge.util.UIDecisionConfig;
import org.eclipse.jface.dialogs.MessageDialog;
import org.eclipse.jface.layout.GridDataFactory;
import org.eclipse.jface.layout.PixelConverter;
import org.eclipse.jface.wizard.WizardPage;
import org.eclipse.swt.SWT;
import org.eclipse.swt.custom.ScrolledComposite;
import org.eclipse.swt.events.SelectionEvent;
import org.eclipse.swt.events.SelectionListener;
import org.eclipse.swt.graphics.Color;
import org.eclipse.swt.graphics.Point;
import org.eclipse.swt.layout.GridData;
import org.eclipse.swt.layout.GridLayout;
import org.eclipse.swt.layout.RowLayout;
import org.eclipse.swt.widgets.Button;
import org.eclipse.swt.widgets.Composite;
import org.eclipse.swt.widgets.Event;
import org.eclipse.swt.widgets.Listener;
/**
* Represents the main page of the merge wizard.
*
* @author wesendon
*/
public class MergeWizardPage extends WizardPage {
/**
* Name of wizard page.
*/
public static final String PAGE_NAME = Messages.MergeWizardPage_PageName;
private ArrayList<DecisionBox> decisionBoxes;
private final DecisionManager decisionManager;
/**
* Default Constructor.
*
* @param decisionManager
* a decisionManager
*/
protected MergeWizardPage(DecisionManager decisionManager) {
super(PAGE_NAME);
this.decisionManager = decisionManager;
setTitle(Messages.MergeWizardPage_Title);
final int countMyOperations = decisionManager.countMyOperations();
final int countTheirOperations = decisionManager.countTheirOperations();
final int countMyLeafOperations = decisionManager.countMyLeafOperations();
final int countTheirLeafOperations = decisionManager.countTheirLeafOperations();
setDescription(MessageFormat.format(
Messages.MergeWizardPage_Description_1
+ Messages.MergeWizardPage_Description_2
+ Messages.MergeWizardPage_Description_3
+ Messages.MergeWizardPage_Description_4,
countMyOperations,
countMyLeafOperations,
countTheirOperations,
countTheirLeafOperations));
}
/**
* {@inheritDoc}
*/
public void createControl(final Composite parent) {
parent.setLayout(new GridLayout());
final PixelConverter converter = new PixelConverter(parent);
final Composite topBar = createTopBar(parent, converter);
GridDataFactory.fillDefaults().grab(true, false).applyTo(topBar);
final ScrolledComposite scrolledComposite = new ScrolledComposite(parent, SWT.H_SCROLL | SWT.V_SCROLL);
scrolledComposite.setExpandHorizontal(true);
scrolledComposite.setExpandVertical(true);
GridDataFactory.fillDefaults().align(SWT.BEGINNING, SWT.BEGINNING).grab(true, true).applyTo(scrolledComposite);
final Composite client = new Composite(scrolledComposite, SWT.NONE);
client.setLayout(new GridLayout());
final GridData gridData = new GridData(SWT.FILL, SWT.FILL, true, true);
client.setLayoutData(gridData);
final ColorSwitcher colorSwitcher = new ColorSwitcher();
decisionBoxes = new ArrayList<DecisionBox>();
// show only unresolved conflicts
final List<VisualConflict> unresolvedConflicts = new ArrayList<VisualConflict>();
for (final VisualConflict conflict : decisionManager.getConflicts()) {
if (!conflict.isResolved()) {
unresolvedConflicts.add(conflict);
}
}
for (final VisualConflict conflict : unresolvedConflicts) {
decisionBoxes.add(new DecisionBox(client, decisionManager, colorSwitcher.getColor(), conflict));
}
// Listener to check for changes in the width of the client. A changed width can influence the height
// of the client. Thus one has to adjust the height of the scrolledComposite accordingly.
client.addListener(SWT.Resize, new Listener() {
private int widthBeforeChange = -1; // initial negative value
public void handleEvent(Event event) {
final int widthAfterChange = client.getSize().x;
if (widthBeforeChange != widthAfterChange) {
scrolledComposite.setMinHeight(client.computeSize(widthAfterChange, SWT.DEFAULT).y);
widthBeforeChange = widthAfterChange;
}
}
});
scrolledComposite.setContent(client);
final Point computeSize = calcParentSize(parent, topBar, converter);
scrolledComposite.setMinSize(computeSize);
setControl(scrolledComposite);
}
private Point calcParentSize(final Composite parent, Composite topBar, PixelConverter converter) {
final Point computeSize = parent.computeSize(SWT.DEFAULT, SWT.DEFAULT);
computeSize.x = parent.getBounds().width;
// Due to resizing issues give a bit of extra space.
computeSize.y = computeSize.y + topBar.getSize().y + converter.convertHorizontalDLUsToPixels(50);
return computeSize;
}
private Composite createTopBar(Composite parent, PixelConverter converter) {
final Composite composite = new Composite(parent, SWT.NONE);
composite.setLayout(new RowLayout(SWT.HORIZONTAL));
composite.setSize(SWT.DEFAULT, converter.convertVerticalDLUsToPixels(200));
final Button acceptMine = new Button(composite, SWT.PUSH);
acceptMine.setText(Messages.MergeWizardPage_KeepMyChanges);
acceptMine.addSelectionListener(new SelectAllSelectionListener(OptionType.MyOperation));
final Button accecptTheirs = new Button(composite, SWT.PUSH);
accecptTheirs.setText(Messages.MergeWizardPage_KeepTheirChanges);
accecptTheirs.addSelectionListener(new SelectAllSelectionListener(OptionType.TheirOperation));
return composite;
}
/**
* Listener for select all mine and all their buttons.
*
* @author wesendon
*/
private final class SelectAllSelectionListener implements SelectionListener {
private final OptionType type;
public SelectAllSelectionListener(OptionType type) {
this.type = type;
}
public void widgetSelected(SelectionEvent e) {
select();
}
public void widgetDefaultSelected(SelectionEvent e) {
select();
}
private void select() {
if (type.equals(OptionType.MyOperation)) {
final boolean confirm = MessageDialog.openConfirm(getShell(),
Messages.MergeWizardPage_Override_Title,
MessageFormat.format(
Messages.MergeWizardPage_Override_Message_1
+ Messages.MergeWizardPage_Override_Message_2
+ Messages.MergeWizardPage_Override_Message_3,
decisionManager.countTheirOperations(),
decisionManager.countTheirLeafOperations()));
if (!confirm) {
return;
}
}
for (final DecisionBox box : decisionBoxes) {
for (final ConflictOption option : box.getConflict().getOptions()) {
if (option.getType().equals(type)) {
box.setSolution(option);
break;
}
}
}
}
}
/**
* Small class which switches colors from row to row.
*
* @author wesendon
*/
private final class ColorSwitcher {
private boolean color;
public ColorSwitcher() {
color = false;
}
public Color getColor() {
color = !color;
return color ? UIDecisionConfig.getFirstDecisionBoxColor() : UIDecisionConfig.getSecondDecisionBoxColor();
}
}
}