trace/traceviewer/com.nokia.traceviewer/src/com/nokia/traceviewer/dialog/FilterAdvancedDialog.java
changeset 11 5b9d4d8641ce
equal deleted inserted replaced
10:ed1c9f64298a 11:5b9d4d8641ce
       
     1 /*
       
     2  * Copyright (c) 2007-2010 Nokia Corporation and/or its subsidiary(-ies). 
       
     3  * All rights reserved.
       
     4  * This component and the accompanying materials are made available
       
     5  * under the terms of "Eclipse Public License v1.0"
       
     6  * which accompanies this distribution, and is available
       
     7  * at the URL "http://www.eclipse.org/legal/epl-v10.html".
       
     8  *
       
     9  * Initial Contributors:
       
    10  * Nokia Corporation - initial contribution.
       
    11  *
       
    12  * Contributors:
       
    13  *
       
    14  * Description:
       
    15  *
       
    16  * Advanced filter dialog
       
    17  *
       
    18  */
       
    19 package com.nokia.traceviewer.dialog;
       
    20 
       
    21 import java.net.URL;
       
    22 
       
    23 import org.eclipse.jface.dialogs.IDialogConstants;
       
    24 import org.eclipse.jface.resource.ImageDescriptor;
       
    25 import org.eclipse.jface.viewers.IStructuredSelection;
       
    26 import org.eclipse.jface.viewers.TreeViewer;
       
    27 import org.eclipse.swt.SWT;
       
    28 import org.eclipse.swt.custom.StyledText;
       
    29 import org.eclipse.swt.events.SelectionAdapter;
       
    30 import org.eclipse.swt.events.SelectionEvent;
       
    31 import org.eclipse.swt.graphics.Image;
       
    32 import org.eclipse.swt.graphics.Point;
       
    33 import org.eclipse.swt.layout.GridData;
       
    34 import org.eclipse.swt.layout.GridLayout;
       
    35 import org.eclipse.swt.widgets.Button;
       
    36 import org.eclipse.swt.widgets.Group;
       
    37 import org.eclipse.swt.widgets.Menu;
       
    38 import org.eclipse.swt.widgets.MenuItem;
       
    39 import org.eclipse.swt.widgets.Shell;
       
    40 import org.eclipse.swt.widgets.ToolBar;
       
    41 import org.eclipse.swt.widgets.ToolItem;
       
    42 import org.eclipse.swt.widgets.Tree;
       
    43 
       
    44 import com.nokia.traceviewer.TraceViewerPlugin;
       
    45 import com.nokia.traceviewer.dialog.treeitem.FilterTreeBaseItem;
       
    46 import com.nokia.traceviewer.dialog.treeitem.FilterTreeComponentItem;
       
    47 import com.nokia.traceviewer.dialog.treeitem.FilterTreeTextItem;
       
    48 import com.nokia.traceviewer.dialog.treeitem.TreeItem;
       
    49 import com.nokia.traceviewer.dialog.treeitem.TreeItemContentProvider;
       
    50 import com.nokia.traceviewer.dialog.treeitem.TreeItemLabelProvider;
       
    51 import com.nokia.traceviewer.engine.TraceViewerGlobals;
       
    52 import com.nokia.traceviewer.engine.dataprocessor.FilterRuleObject;
       
    53 import com.nokia.traceviewer.engine.dataprocessor.FilterRuleSet;
       
    54 import com.nokia.traceviewer.engine.dataprocessor.FilterRuleSet.LogicalOperator;
       
    55 
       
    56 /**
       
    57  * Advanced filter dialog
       
    58  * 
       
    59  */
       
    60 public final class FilterAdvancedDialog extends BaseDialog {
       
    61 
       
    62 	/**
       
    63 	 * Indicates how this dialog was exited
       
    64 	 */
       
    65 	public enum ExitStatus {
       
    66 
       
    67 		/**
       
    68 		 * Initial state
       
    69 		 */
       
    70 		NORMAL,
       
    71 
       
    72 		/**
       
    73 		 * Exited through apply button
       
    74 		 */
       
    75 		APPLYBUTTON,
       
    76 
       
    77 		/**
       
    78 		 * Exited through cancel button
       
    79 		 */
       
    80 		CANCELBUTTON,
       
    81 
       
    82 		/**
       
    83 		 * Exited through simple button
       
    84 		 */
       
    85 		SIMPLEBUTTON;
       
    86 	}
       
    87 
       
    88 	/**
       
    89 	 * Error message to show when there is multiple operators inside same set
       
    90 	 */
       
    91 	private static final String MULTIPLE_OPERATORS_ERROR_MSG = Messages
       
    92 			.getString("FilterAdvancedDialog.MultipleOperatorsErrorMsg"); //$NON-NLS-1$
       
    93 
       
    94 	/**
       
    95 	 * Error message to show when there is extra characters inside same set
       
    96 	 */
       
    97 	private static final String EXTRA_CHARS_ERROR_MSG = Messages
       
    98 			.getString("FilterAdvancedDialog.InvalidSyntaxErrorMsg"); //$NON-NLS-1$
       
    99 
       
   100 	/**
       
   101 	 * Tree
       
   102 	 */
       
   103 	private Tree tree;
       
   104 
       
   105 	/**
       
   106 	 * TreeViewer
       
   107 	 */
       
   108 	private TreeViewer treeViewer;
       
   109 
       
   110 	/**
       
   111 	 * Styled Text rule field
       
   112 	 */
       
   113 	private StyledText ruleTextfield;
       
   114 
       
   115 	/**
       
   116 	 * Button
       
   117 	 */
       
   118 	private Button showButton;
       
   119 
       
   120 	/**
       
   121 	 * Content provider
       
   122 	 */
       
   123 	private final TreeItemContentProvider contentProvider;
       
   124 
       
   125 	/**
       
   126 	 * Tree root
       
   127 	 */
       
   128 	private final TreeItem treeRoot;
       
   129 
       
   130 	/**
       
   131 	 * Start set tool item
       
   132 	 */
       
   133 	private ToolItem startSetToolItem;
       
   134 
       
   135 	/**
       
   136 	 * Start set image location
       
   137 	 */
       
   138 	private static final String startSetImageLocation = "/icons/startset.gif"; //$NON-NLS-1$
       
   139 
       
   140 	/**
       
   141 	 * Start set image
       
   142 	 */
       
   143 	private Image startSetImage;
       
   144 
       
   145 	/**
       
   146 	 * End set tool item
       
   147 	 */
       
   148 	private ToolItem endSetToolItem;
       
   149 
       
   150 	/**
       
   151 	 * End set image location
       
   152 	 */
       
   153 	private static final String endSetImageLocation = "/icons/endset.gif"; //$NON-NLS-1$
       
   154 
       
   155 	/**
       
   156 	 * End set image
       
   157 	 */
       
   158 	private Image endSetImage;
       
   159 
       
   160 	/**
       
   161 	 * AND tool item
       
   162 	 */
       
   163 	private ToolItem andToolItem;
       
   164 
       
   165 	/**
       
   166 	 * AND image location
       
   167 	 */
       
   168 	private static final String andImageLocation = "/icons/logicaland.gif"; //$NON-NLS-1$
       
   169 
       
   170 	/**
       
   171 	 * AND image
       
   172 	 */
       
   173 	private Image andImage;
       
   174 
       
   175 	/**
       
   176 	 * OR tool item
       
   177 	 */
       
   178 	private ToolItem orToolItem;
       
   179 
       
   180 	/**
       
   181 	 * OR image location
       
   182 	 */
       
   183 	private static final String orImageLocation = "/icons/logicalor.gif"; //$NON-NLS-1$
       
   184 
       
   185 	/**
       
   186 	 * OR image
       
   187 	 */
       
   188 	private Image orImage;
       
   189 
       
   190 	/**
       
   191 	 * NOT tool item
       
   192 	 */
       
   193 	private ToolItem notToolItem;
       
   194 
       
   195 	/**
       
   196 	 * NOT image location
       
   197 	 */
       
   198 	private static final String notImageLocation = "/icons/logicalnot.gif"; //$NON-NLS-1$
       
   199 
       
   200 	/**
       
   201 	 * NOT image
       
   202 	 */
       
   203 	private Image notImage;
       
   204 
       
   205 	/**
       
   206 	 * Back tool item
       
   207 	 */
       
   208 	private ToolItem backToolItem;
       
   209 
       
   210 	/**
       
   211 	 * Back image location
       
   212 	 */
       
   213 	private static final String backImageLocation = "/icons/backarrow.gif"; //$NON-NLS-1$
       
   214 
       
   215 	/**
       
   216 	 * Clear tool item
       
   217 	 */
       
   218 	private ToolItem clearToolItem;
       
   219 
       
   220 	/**
       
   221 	 * Clear image location
       
   222 	 */
       
   223 	private static final String clearImageLocation = "/icons/clear.gif"; //$NON-NLS-1$
       
   224 
       
   225 	/**
       
   226 	 * Simple tool item
       
   227 	 */
       
   228 	private ToolItem simpleToolItem;
       
   229 
       
   230 	/**
       
   231 	 * Simple image location
       
   232 	 */
       
   233 	private static final String simpleImageLocation = "/icons/simplefilter.gif"; //$NON-NLS-1$
       
   234 
       
   235 	/**
       
   236 	 * Simple image
       
   237 	 */
       
   238 	private Image simpleImage;
       
   239 
       
   240 	/**
       
   241 	 * Indicates to show traces containing the rule. Otherwise they're hidden
       
   242 	 */
       
   243 	private boolean showTracesContainingRule = true;
       
   244 
       
   245 	/**
       
   246 	 * Rule parser
       
   247 	 */
       
   248 	private FilterAdvancedParser ruleParser;
       
   249 
       
   250 	/**
       
   251 	 * Filter rule set to create from the rule text
       
   252 	 */
       
   253 	private FilterRuleObject ruleSet;
       
   254 
       
   255 	/**
       
   256 	 * Indicates that the dialog can be closed
       
   257 	 */
       
   258 	private boolean canBeClosed = true;
       
   259 
       
   260 	/**
       
   261 	 * Selection menu that opens when user clicks a group in the Tree
       
   262 	 */
       
   263 	private Menu menu;
       
   264 
       
   265 	/**
       
   266 	 * Indicates the exit status of this dialog
       
   267 	 */
       
   268 	public ExitStatus exitStatus;
       
   269 
       
   270 	/**
       
   271 	 * Constructor
       
   272 	 * 
       
   273 	 * @param parent
       
   274 	 *            parent shell
       
   275 	 * @param contentProvider
       
   276 	 *            contentprovider for the tree
       
   277 	 * @param treeRoot
       
   278 	 *            tree root
       
   279 	 */
       
   280 	public FilterAdvancedDialog(Shell parent,
       
   281 			TreeItemContentProvider contentProvider, TreeItem treeRoot) {
       
   282 		super(parent, SWT.DIALOG_TRIM | SWT.APPLICATION_MODAL | SWT.RESIZE);
       
   283 		this.contentProvider = contentProvider;
       
   284 		this.treeRoot = treeRoot;
       
   285 	}
       
   286 
       
   287 	/*
       
   288 	 * (non-Javadoc)
       
   289 	 * 
       
   290 	 * @see com.nokia.traceviewer.dialog.BaseDialog#close()
       
   291 	 */
       
   292 	@Override
       
   293 	public boolean close() {
       
   294 		// If closing dialog by clicking X, do as in Cancel button
       
   295 		if (exitStatus == ExitStatus.NORMAL) {
       
   296 			exitStatus = ExitStatus.CANCELBUTTON;
       
   297 			saveSettings();
       
   298 			dispose();
       
   299 		} else if (exitStatus == ExitStatus.SIMPLEBUTTON) {
       
   300 			saveSettings();
       
   301 		}
       
   302 
       
   303 		return super.close();
       
   304 	}
       
   305 
       
   306 	/*
       
   307 	 * (non-Javadoc)
       
   308 	 * 
       
   309 	 * @see com.nokia.traceviewer.dialog.BaseDialog#createShell()
       
   310 	 */
       
   311 	@Override
       
   312 	protected void createDialogContents() {
       
   313 		// Shell
       
   314 		GridLayout shellGridLayout = new GridLayout();
       
   315 		shellGridLayout.numColumns = 3;
       
   316 		shellGridLayout.makeColumnsEqualWidth = false;
       
   317 		getShell().setText("Advanced Filter Rules"); //$NON-NLS-1$
       
   318 		composite.setLayout(shellGridLayout);
       
   319 		getShell().setMinimumSize(new Point(435, 515));
       
   320 
       
   321 		// Tree
       
   322 		GridData treeGridData = new GridData();
       
   323 		treeGridData.horizontalAlignment = GridData.FILL;
       
   324 		treeGridData.grabExcessHorizontalSpace = true;
       
   325 		treeGridData.grabExcessVerticalSpace = true;
       
   326 		treeGridData.horizontalSpan = 2;
       
   327 		treeGridData.verticalAlignment = GridData.FILL;
       
   328 		treeGridData.widthHint = 250;
       
   329 		tree = new Tree(composite, SWT.BORDER | SWT.V_SCROLL | SWT.H_SCROLL);
       
   330 		tree.setLayoutData(treeGridData);
       
   331 
       
   332 		// Tree viewer
       
   333 		treeViewer = new TreeViewer(tree);
       
   334 		treeViewer.setLabelProvider(new TreeItemLabelProvider());
       
   335 		treeViewer.setContentProvider(contentProvider);
       
   336 
       
   337 		// Set root and expand all items
       
   338 		treeViewer.setInput(treeRoot);
       
   339 		treeViewer.expandAll();
       
   340 
       
   341 		// Select the root item
       
   342 		if (tree.getItem(0) != null) {
       
   343 			tree.setSelection(tree.getItem(0));
       
   344 		}
       
   345 
       
   346 		// Create toolbar
       
   347 		createToolBar();
       
   348 
       
   349 		// Rule text field
       
   350 		GridData ruleTextFieldGridData = new GridData();
       
   351 		ruleTextFieldGridData.grabExcessHorizontalSpace = true;
       
   352 		ruleTextFieldGridData.horizontalAlignment = GridData.FILL;
       
   353 		ruleTextFieldGridData.verticalAlignment = GridData.FILL;
       
   354 		ruleTextFieldGridData.heightHint = 70;
       
   355 		ruleTextFieldGridData.horizontalSpan = 2;
       
   356 		ruleTextFieldGridData.grabExcessVerticalSpace = false;
       
   357 		ruleTextFieldGridData.minimumHeight = 100;
       
   358 		ruleTextFieldGridData.horizontalIndent = 5;
       
   359 		ruleTextfield = new StyledText(composite, SWT.BORDER | SWT.WRAP
       
   360 				| SWT.V_SCROLL);
       
   361 		ruleTextfield.setLayoutData(ruleTextFieldGridData);
       
   362 
       
   363 		// Create new rule parser to this rule text field
       
   364 		ruleParser = new FilterAdvancedParser(ruleTextfield, tree.getItems()[0]
       
   365 				.getItems());
       
   366 		// Set parser to be the key, mouse and focus listener
       
   367 		ruleTextfield.addKeyListener(ruleParser);
       
   368 		ruleTextfield.addMouseListener(ruleParser);
       
   369 		ruleTextfield.addFocusListener(ruleParser);
       
   370 
       
   371 		// Set text from previous visit
       
   372 		ruleTextfield.setText(FilterAdvancedParser.SPACE_STR
       
   373 				+ TraceViewerGlobals.getTraceViewer().getDataProcessorAccess()
       
   374 						.getFilterProcessor().getAdvancedFilterString()
       
   375 				+ FilterAdvancedParser.SPACE_STR);
       
   376 		ruleTextfield.setCaretOffset(ruleTextfield.getCharCount());
       
   377 
       
   378 		// Create Group
       
   379 		createGroup();
       
   380 	}
       
   381 
       
   382 	/**
       
   383 	 * Creates the toolbar containing pushable buttons to the right side of the
       
   384 	 * dialog.
       
   385 	 */
       
   386 	private void createToolBar() {
       
   387 		// Create the toolBar
       
   388 		GridData toolBarGridData = new GridData();
       
   389 		toolBarGridData.horizontalAlignment = GridData.FILL;
       
   390 		toolBarGridData.grabExcessVerticalSpace = true;
       
   391 		toolBarGridData.verticalSpan = 2;
       
   392 		toolBarGridData.verticalAlignment = GridData.FILL;
       
   393 		ToolBar toolBar = new ToolBar(composite, SWT.VERTICAL);
       
   394 		toolBar.setLayoutData(toolBarGridData);
       
   395 
       
   396 		// Create "Start set" item
       
   397 		startSetToolItem = new ToolItem(toolBar, SWT.PUSH);
       
   398 		startSetToolItem.setText(Messages
       
   399 				.getString("FilterAdvancedDialog.StartSetButtonText")); //$NON-NLS-1$
       
   400 		startSetToolItem.setToolTipText(Messages
       
   401 				.getString("FilterAdvancedDialog.StartSetToolTip")); //$NON-NLS-1$
       
   402 		// Set image to the "Start set" item
       
   403 		URL url = TraceViewerPlugin.getDefault().getBundle().getEntry(
       
   404 				startSetImageLocation);
       
   405 		startSetImage = ImageDescriptor.createFromURL(url).createImage();
       
   406 		startSetToolItem.setImage(startSetImage);
       
   407 
       
   408 		// Create "End set" item
       
   409 		endSetToolItem = new ToolItem(toolBar, SWT.PUSH);
       
   410 		endSetToolItem.setText(Messages
       
   411 				.getString("FilterAdvancedDialog.EndSetButtonText")); //$NON-NLS-1$
       
   412 		endSetToolItem.setToolTipText(Messages
       
   413 				.getString("FilterAdvancedDialog.EndSetToolTip")); //$NON-NLS-1$
       
   414 		// Set image to the "End set" item
       
   415 		url = TraceViewerPlugin.getDefault().getBundle().getEntry(
       
   416 				endSetImageLocation);
       
   417 		endSetImage = ImageDescriptor.createFromURL(url).createImage();
       
   418 		endSetToolItem.setImage(endSetImage);
       
   419 
       
   420 		// Create "And" item
       
   421 		andToolItem = new ToolItem(toolBar, SWT.PUSH);
       
   422 		andToolItem.setText(FilterAdvancedParser.AND);
       
   423 		andToolItem.setToolTipText(Messages
       
   424 				.getString("FilterAdvancedDialog.ANDToolTip")); //$NON-NLS-1$
       
   425 		// Set image to the "And" item
       
   426 		url = TraceViewerPlugin.getDefault().getBundle().getEntry(
       
   427 				andImageLocation);
       
   428 		andImage = ImageDescriptor.createFromURL(url).createImage();
       
   429 		andToolItem.setImage(andImage);
       
   430 
       
   431 		// Create "Or" item
       
   432 		orToolItem = new ToolItem(toolBar, SWT.PUSH);
       
   433 		orToolItem.setText(FilterAdvancedParser.OR);
       
   434 		orToolItem.setToolTipText(Messages
       
   435 				.getString("FilterAdvancedDialog.ORToolTip")); //$NON-NLS-1$
       
   436 		// Set image to the "Or" item
       
   437 		url = TraceViewerPlugin.getDefault().getBundle().getEntry(
       
   438 				orImageLocation);
       
   439 		orImage = ImageDescriptor.createFromURL(url).createImage();
       
   440 		orToolItem.setImage(orImage);
       
   441 
       
   442 		// Create "Not" item
       
   443 		notToolItem = new ToolItem(toolBar, SWT.PUSH);
       
   444 		notToolItem.setText(FilterAdvancedParser.NOT);
       
   445 		notToolItem.setToolTipText(Messages
       
   446 				.getString("FilterAdvancedDialog.NOTToolTip")); //$NON-NLS-1$
       
   447 		// Set image to the "Not" item
       
   448 		url = TraceViewerPlugin.getDefault().getBundle().getEntry(
       
   449 				notImageLocation);
       
   450 		notImage = ImageDescriptor.createFromURL(url).createImage();
       
   451 		notToolItem.setImage(notImage);
       
   452 
       
   453 		// Create "Back" item
       
   454 		backToolItem = new ToolItem(toolBar, SWT.PUSH);
       
   455 		backToolItem.setText(Messages
       
   456 				.getString("FilterAdvancedDialog.BackButtonText")); //$NON-NLS-1$
       
   457 		backToolItem.setToolTipText(Messages
       
   458 				.getString("FilterAdvancedDialog.BackToolTip")); //$NON-NLS-1$
       
   459 		// Set image to the "Back" item
       
   460 		url = TraceViewerPlugin.getDefault().getBundle().getEntry(
       
   461 				backImageLocation);
       
   462 		Image backImage = ImageDescriptor.createFromURL(url).createImage();
       
   463 		backToolItem.setImage(backImage);
       
   464 
       
   465 		// Create "Clear" item
       
   466 		clearToolItem = new ToolItem(toolBar, SWT.PUSH);
       
   467 		clearToolItem.setText(Messages
       
   468 				.getString("FilterAdvancedDialog.ClearButtonText")); //$NON-NLS-1$
       
   469 		clearToolItem.setToolTipText(Messages
       
   470 				.getString("FilterAdvancedDialog.ClearToolTip")); //$NON-NLS-1$
       
   471 		// Set image to the "Clear" item
       
   472 		url = TraceViewerPlugin.getDefault().getBundle().getEntry(
       
   473 				clearImageLocation);
       
   474 		Image clearImage = ImageDescriptor.createFromURL(url).createImage();
       
   475 		clearToolItem.setImage(clearImage);
       
   476 
       
   477 		// Create "Simple" item
       
   478 		simpleToolItem = new ToolItem(toolBar, SWT.PUSH);
       
   479 		simpleToolItem.setText(Messages
       
   480 				.getString("FilterAdvancedDialog.SimpleButtonText")); //$NON-NLS-1$
       
   481 		simpleToolItem.setToolTipText(Messages
       
   482 				.getString("FilterAdvancedDialog.SimpleViewToolTip")); //$NON-NLS-1$
       
   483 		// Set image to the "Simple" item
       
   484 		url = TraceViewerPlugin.getDefault().getBundle().getEntry(
       
   485 				simpleImageLocation);
       
   486 		simpleImage = ImageDescriptor.createFromURL(url).createImage();
       
   487 		simpleToolItem.setImage(simpleImage);
       
   488 	}
       
   489 
       
   490 	/**
       
   491 	 * This method initializes group
       
   492 	 */
       
   493 	private void createGroup() {
       
   494 		// Settings group
       
   495 		GridData settingsGroupGridData = new GridData();
       
   496 		settingsGroupGridData.horizontalAlignment = GridData.BEGINNING;
       
   497 		settingsGroupGridData.grabExcessHorizontalSpace = false;
       
   498 		settingsGroupGridData.grabExcessVerticalSpace = false;
       
   499 		settingsGroupGridData.verticalAlignment = GridData.FILL;
       
   500 		GridLayout settingsGroupGridLayout = new GridLayout();
       
   501 		settingsGroupGridLayout.verticalSpacing = 5;
       
   502 		settingsGroupGridLayout.marginWidth = 5;
       
   503 		settingsGroupGridLayout.marginHeight = 5;
       
   504 		settingsGroupGridLayout.numColumns = 2;
       
   505 		settingsGroupGridLayout.horizontalSpacing = 5;
       
   506 		Group settingsGroup = new Group(composite, SWT.NONE);
       
   507 		settingsGroup.setLayout(settingsGroupGridLayout);
       
   508 		settingsGroup.setLayoutData(settingsGroupGridData);
       
   509 		settingsGroup.setText(Messages
       
   510 				.getString("FilterAdvancedDialog.SettingsGroupName")); //$NON-NLS-1$
       
   511 
       
   512 		// Show button
       
   513 		showButton = new Button(settingsGroup, SWT.RADIO);
       
   514 		showButton.setText(Messages
       
   515 				.getString("FilterAdvancedDialog.ShowButtonText")); //$NON-NLS-1$
       
   516 		showButton.setToolTipText(Messages
       
   517 				.getString("FilterAdvancedDialog.ShowButtonToolTip")); //$NON-NLS-1$
       
   518 		showButton.setSelection(showTracesContainingRule);
       
   519 
       
   520 		// Hide button
       
   521 		Button hideButton = new Button(settingsGroup, SWT.RADIO);
       
   522 		hideButton.setText(Messages
       
   523 				.getString("FilterAdvancedDialog.HideButtonText")); //$NON-NLS-1$
       
   524 		hideButton.setToolTipText(Messages
       
   525 				.getString("FilterAdvancedDialog.HideButtonToolTip")); //$NON-NLS-1$
       
   526 		hideButton.setSelection(!showTracesContainingRule);
       
   527 	}
       
   528 
       
   529 	/*
       
   530 	 * (non-Javadoc)
       
   531 	 * 
       
   532 	 * @see com.nokia.traceviewer.dialog.BaseDialog#restoreSettings()
       
   533 	 */
       
   534 	@Override
       
   535 	protected void restoreSettings() {
       
   536 		super.restoreSettings();
       
   537 		exitStatus = ExitStatus.NORMAL;
       
   538 	}
       
   539 
       
   540 	/*
       
   541 	 * (non-Javadoc)
       
   542 	 * 
       
   543 	 * @see com.nokia.traceviewer.dialog.BaseDialog#saveSettings()
       
   544 	 */
       
   545 	@Override
       
   546 	protected void saveSettings() {
       
   547 		super.saveSettings();
       
   548 
       
   549 		if (exitStatus == ExitStatus.APPLYBUTTON) {
       
   550 			// Save advanced filter string
       
   551 			TraceViewerGlobals.getTraceViewer().getDataProcessorAccess()
       
   552 					.getFilterProcessor().setAdvancedFilterString(
       
   553 							ruleTextfield.getText());
       
   554 
       
   555 			showTracesContainingRule = showButton.getSelection();
       
   556 
       
   557 			// Create the rule set
       
   558 			String ruleText = ruleTextfield.getText();
       
   559 			ruleSet = null;
       
   560 			if (ruleText.length() > 0
       
   561 					&& ruleParser.containsFilterRule(ruleText, tree.getItems())) {
       
   562 				ruleSet = createRuleSet(ruleText, false);
       
   563 			}
       
   564 		}
       
   565 	}
       
   566 
       
   567 	/*
       
   568 	 * (non-Javadoc)
       
   569 	 * 
       
   570 	 * @see org.eclipse.jface.dialogs.Dialog#okPressed()
       
   571 	 */
       
   572 	@Override
       
   573 	protected void okPressed() {
       
   574 		exitStatus = ExitStatus.APPLYBUTTON;
       
   575 		boolean valid = checkWrittenRules(ruleTextfield.getText());
       
   576 		if (valid) {
       
   577 			saveSettings();
       
   578 		} else {
       
   579 			TraceViewerGlobals.getTraceViewer().getDialogs().showErrorMessage(
       
   580 					EXTRA_CHARS_ERROR_MSG);
       
   581 			canBeClosed = false;
       
   582 		}
       
   583 
       
   584 		if (canBeClosed) {
       
   585 			super.okPressed();
       
   586 			dispose();
       
   587 		} else {
       
   588 			canBeClosed = true;
       
   589 		}
       
   590 	}
       
   591 
       
   592 	/*
       
   593 	 * (non-Javadoc)
       
   594 	 * 
       
   595 	 * @see org.eclipse.jface.dialogs.Dialog#cancelPressed()
       
   596 	 */
       
   597 	@Override
       
   598 	protected void cancelPressed() {
       
   599 		exitStatus = ExitStatus.CANCELBUTTON;
       
   600 		saveSettings();
       
   601 
       
   602 		super.cancelPressed();
       
   603 
       
   604 		dispose();
       
   605 	}
       
   606 
       
   607 	/*
       
   608 	 * (non-Javadoc)
       
   609 	 * 
       
   610 	 * @see com.nokia.traceviewer.dialog.BaseDialog#createActionListeners()
       
   611 	 */
       
   612 	@Override
       
   613 	protected void createActionListeners() {
       
   614 
       
   615 		// Add selection listener to start Set button
       
   616 		startSetToolItem.addSelectionListener(new SelectionAdapter() {
       
   617 			@Override
       
   618 			public void widgetSelected(SelectionEvent event) {
       
   619 				TraceViewerGlobals.postUiEvent("StartSetButton", "1"); //$NON-NLS-1$ //$NON-NLS-2$
       
   620 				updateRuleTextField(FilterAdvancedParser.START_BRACKET_STR);
       
   621 				TraceViewerGlobals.postUiEvent("StartSetButton", "0"); //$NON-NLS-1$ //$NON-NLS-2$
       
   622 			}
       
   623 		});
       
   624 
       
   625 		// Add selection listener to end Set button
       
   626 		endSetToolItem.addSelectionListener(new SelectionAdapter() {
       
   627 			@Override
       
   628 			public void widgetSelected(SelectionEvent event) {
       
   629 				TraceViewerGlobals.postUiEvent("EndSetButton", "1"); //$NON-NLS-1$ //$NON-NLS-2$
       
   630 				updateRuleTextField(FilterAdvancedParser.END_BRACKET_STR);
       
   631 				TraceViewerGlobals.postUiEvent("EndSetButton", "0"); //$NON-NLS-1$ //$NON-NLS-2$
       
   632 			}
       
   633 		});
       
   634 
       
   635 		// Add selection listener to and button
       
   636 		andToolItem.addSelectionListener(new SelectionAdapter() {
       
   637 			@Override
       
   638 			public void widgetSelected(SelectionEvent event) {
       
   639 				TraceViewerGlobals.postUiEvent("AndButton", "1"); //$NON-NLS-1$ //$NON-NLS-2$
       
   640 				updateRuleTextField(FilterAdvancedParser.AND);
       
   641 				TraceViewerGlobals.postUiEvent("AndButton", "0"); //$NON-NLS-1$ //$NON-NLS-2$
       
   642 			}
       
   643 		});
       
   644 
       
   645 		// Add selection listener to or button
       
   646 		orToolItem.addSelectionListener(new SelectionAdapter() {
       
   647 			@Override
       
   648 			public void widgetSelected(SelectionEvent event) {
       
   649 				TraceViewerGlobals.postUiEvent("OrButton", "1"); //$NON-NLS-1$ //$NON-NLS-2$
       
   650 				updateRuleTextField(FilterAdvancedParser.OR);
       
   651 				TraceViewerGlobals.postUiEvent("OrButton", "0"); //$NON-NLS-1$ //$NON-NLS-2$
       
   652 			}
       
   653 		});
       
   654 
       
   655 		// Add selection listener to not button
       
   656 		notToolItem.addSelectionListener(new SelectionAdapter() {
       
   657 			@Override
       
   658 			public void widgetSelected(SelectionEvent event) {
       
   659 				TraceViewerGlobals.postUiEvent("NotButton", "1"); //$NON-NLS-1$ //$NON-NLS-2$
       
   660 				updateRuleTextField(FilterAdvancedParser.NOT);
       
   661 				TraceViewerGlobals.postUiEvent("NotButton", "0"); //$NON-NLS-1$ //$NON-NLS-2$
       
   662 			}
       
   663 		});
       
   664 
       
   665 		// Add selection listener to back button
       
   666 		backToolItem.addSelectionListener(new SelectionAdapter() {
       
   667 			@Override
       
   668 			public void widgetSelected(SelectionEvent event) {
       
   669 				TraceViewerGlobals.postUiEvent("BackButton", "1"); //$NON-NLS-1$ //$NON-NLS-2$
       
   670 				removeLastWord();
       
   671 				TraceViewerGlobals.postUiEvent("BackButton", "0"); //$NON-NLS-1$ //$NON-NLS-2$
       
   672 			}
       
   673 		});
       
   674 
       
   675 		// Add selection listener to clear button
       
   676 		clearToolItem.addSelectionListener(new SelectionAdapter() {
       
   677 			@Override
       
   678 			public void widgetSelected(SelectionEvent event) {
       
   679 				TraceViewerGlobals.postUiEvent("ClearButton", "1"); //$NON-NLS-1$ //$NON-NLS-2$
       
   680 				ruleTextfield.setText(""); //$NON-NLS-1$
       
   681 				setButtonStates();
       
   682 				TraceViewerGlobals.postUiEvent("ClearButton", "0"); //$NON-NLS-1$ //$NON-NLS-2$
       
   683 			}
       
   684 		});
       
   685 
       
   686 		// Add selection listener to simple button
       
   687 		simpleToolItem.addSelectionListener(new SelectionAdapter() {
       
   688 			@Override
       
   689 			public void widgetSelected(SelectionEvent event) {
       
   690 				TraceViewerGlobals.postUiEvent("SimpleButton", "1"); //$NON-NLS-1$ //$NON-NLS-2$
       
   691 
       
   692 				// Save exit status and advanced filter string
       
   693 				exitStatus = ExitStatus.SIMPLEBUTTON;
       
   694 				TraceViewerGlobals.getTraceViewer().getDataProcessorAccess()
       
   695 						.getFilterProcessor().setAdvancedFilterString(
       
   696 								ruleTextfield.getText());
       
   697 				close();
       
   698 				dispose();
       
   699 				TraceViewerGlobals.postUiEvent("SimpleButton", "0"); //$NON-NLS-1$ //$NON-NLS-2$
       
   700 			}
       
   701 		});
       
   702 
       
   703 		// Add selection listener to Tree
       
   704 		tree.addSelectionListener(new SelectionAdapter() {
       
   705 
       
   706 			@Override
       
   707 			public void widgetSelected(SelectionEvent event) {
       
   708 				TraceViewerGlobals.postUiEvent("TreeSelected", "1"); //$NON-NLS-1$ //$NON-NLS-2$
       
   709 				// Get selection
       
   710 				Object selection = ((IStructuredSelection) treeViewer
       
   711 						.getSelection()).getFirstElement();
       
   712 
       
   713 				if (selection != null) {
       
   714 					// If group selected, add all rules to the list
       
   715 					if (((TreeItem) selection).isGroup()) {
       
   716 						processGroupSelection();
       
   717 
       
   718 					} else {
       
   719 						// Dispose menu if it exists
       
   720 						if (menu != null && !menu.isDisposed()) {
       
   721 							menu.dispose();
       
   722 						}
       
   723 						updateRuleTextField(tree.getSelection()[0].getText());
       
   724 					}
       
   725 				}
       
   726 				TraceViewerGlobals.postUiEvent("TreeSelected", "0"); //$NON-NLS-1$ //$NON-NLS-2$
       
   727 			}
       
   728 
       
   729 			/**
       
   730 			 * Processes group item selection
       
   731 			 */
       
   732 			private void processGroupSelection() {
       
   733 				// Add menu to Tree
       
   734 				menu = new Menu(composite);
       
   735 
       
   736 				MenuItem orItem = new MenuItem(menu, SWT.CASCADE);
       
   737 				if (orImage != null && !orImage.isDisposed()) {
       
   738 					orItem.setImage(orImage);
       
   739 				}
       
   740 				orItem.setEnabled(ruleParser.canOrBeInserted()
       
   741 						|| ruleTextfield.getCharCount() < 4);
       
   742 				orItem.setText(FilterAdvancedParser.OR);
       
   743 
       
   744 				// Add selection listener to OR button
       
   745 				orItem.addSelectionListener(new SelectionAdapter() {
       
   746 					@Override
       
   747 					public void widgetSelected(SelectionEvent event) {
       
   748 						processSelection(FilterAdvancedParser.OR);
       
   749 					}
       
   750 				});
       
   751 
       
   752 				// And item
       
   753 				MenuItem andItem = new MenuItem(menu, SWT.CASCADE);
       
   754 				if (andImage != null && !andImage.isDisposed()) {
       
   755 					andItem.setImage(andImage);
       
   756 				}
       
   757 				andItem.setEnabled(ruleParser.canAndBeInserted()
       
   758 						|| ruleTextfield.getCharCount() < 3);
       
   759 				andItem.setText(FilterAdvancedParser.AND);
       
   760 
       
   761 				// Add selection listener to AND button
       
   762 				andItem.addSelectionListener(new SelectionAdapter() {
       
   763 					@Override
       
   764 					public void widgetSelected(SelectionEvent event) {
       
   765 						processSelection(FilterAdvancedParser.AND);
       
   766 					}
       
   767 				});
       
   768 
       
   769 				tree.setMenu(menu);
       
   770 				menu.setVisible(true);
       
   771 			}
       
   772 		});
       
   773 
       
   774 		// Validate and set button states
       
   775 		ruleParser.validate();
       
   776 		setButtonStates();
       
   777 	}
       
   778 
       
   779 	/**
       
   780 	 * Checks written rules from the rule field
       
   781 	 * 
       
   782 	 * @param text
       
   783 	 *            text to check
       
   784 	 * @return true if rules are ok, false otherwise
       
   785 	 */
       
   786 	public boolean checkWrittenRules(String text) {
       
   787 		boolean ok = false;
       
   788 		if (ruleParser != null) {
       
   789 			ok = ruleParser.checkWrittenRules(text);
       
   790 		}
       
   791 		return ok;
       
   792 	}
       
   793 
       
   794 	/**
       
   795 	 * Process selection of AND or OR
       
   796 	 * 
       
   797 	 * @param operator
       
   798 	 *            operator String
       
   799 	 */
       
   800 	private void processSelection(String operator) {
       
   801 		StringBuffer buf = new StringBuffer();
       
   802 
       
   803 		// Get selection
       
   804 		Object selection = ((IStructuredSelection) treeViewer.getSelection())
       
   805 				.getFirstElement();
       
   806 		if (selection != null) {
       
   807 			Object[] children = ((TreeItem) selection).getChildren();
       
   808 
       
   809 			// If previous word is a rule, add the operator
       
   810 			String prevWord = ruleParser.getPreviousWord(ruleTextfield
       
   811 					.getText(), ruleTextfield.getText().length() - 1);
       
   812 			if (ruleParser.containsFilterRule(prevWord, tree.getItems())) {
       
   813 				buf.append(" " + operator + " "); //$NON-NLS-1$ //$NON-NLS-2$
       
   814 			}
       
   815 
       
   816 			// Loop through children and append them to the string buffer
       
   817 			for (int i = 0; i < children.length; i++) {
       
   818 				if (!((TreeItem) children[i]).isGroup()) {
       
   819 
       
   820 					// If previous word is a rule, add the operator
       
   821 					prevWord = ruleParser.getPreviousWord(buf.toString(), buf
       
   822 							.length() - 1);
       
   823 					if (ruleParser
       
   824 							.containsFilterRule(prevWord, tree.getItems())) {
       
   825 						buf.append(" " + operator + " "); //$NON-NLS-1$ //$NON-NLS-2$
       
   826 					}
       
   827 
       
   828 					buf.append(((TreeItem) children[i]).getName());
       
   829 					if (i < children.length - 1
       
   830 							&& !((TreeItem) children[i + 1]).isGroup()) {
       
   831 						buf.append(" " + operator + " "); //$NON-NLS-1$ //$NON-NLS-2$
       
   832 					}
       
   833 				}
       
   834 
       
   835 			}
       
   836 			updateRuleTextField(buf.toString());
       
   837 		}
       
   838 	}
       
   839 
       
   840 	/**
       
   841 	 * Disposes UI resources if they exist. Is called when the shell is closed
       
   842 	 * or user clicks apply, cancel of simple buttons
       
   843 	 */
       
   844 	private void dispose() {
       
   845 		if (startSetImage != null) {
       
   846 			startSetImage.dispose();
       
   847 		}
       
   848 		if (endSetImage != null) {
       
   849 			endSetImage.dispose();
       
   850 		}
       
   851 		if (orImage != null) {
       
   852 			orImage.dispose();
       
   853 		}
       
   854 		if (andImage != null) {
       
   855 			andImage.dispose();
       
   856 		}
       
   857 		if (notImage != null) {
       
   858 			notImage.dispose();
       
   859 		}
       
   860 		if (simpleImage != null) {
       
   861 			simpleImage.dispose();
       
   862 		}
       
   863 	}
       
   864 
       
   865 	/**
       
   866 	 * Updates rule text field
       
   867 	 * 
       
   868 	 * @param text
       
   869 	 *            text to add to text field
       
   870 	 */
       
   871 	private void updateRuleTextField(String text) {
       
   872 		ruleTextfield.insert(FilterAdvancedParser.SPACE_STR + text
       
   873 				+ FilterAdvancedParser.SPACE_STR);
       
   874 		ruleTextfield.setCaretOffset(ruleTextfield.getCaretOffset()
       
   875 				+ text.length() + 2);
       
   876 		ruleParser.validate();
       
   877 		setButtonStates();
       
   878 	}
       
   879 
       
   880 	/**
       
   881 	 * Removes last word from the rule text field
       
   882 	 */
       
   883 	private void removeLastWord() {
       
   884 
       
   885 		// Get caret offset and text from the text field
       
   886 		int caretPos = ruleTextfield.getCaretOffset();
       
   887 		StringBuffer text = new StringBuffer(ruleTextfield.getText());
       
   888 		int startPos = 0;
       
   889 		if (caretPos == ruleTextfield.getCharCount()) {
       
   890 			caretPos--;
       
   891 		}
       
   892 
       
   893 		// Go through characters starting from the last one
       
   894 		for (int i = caretPos; i > 0; i--) {
       
   895 			char c = text.charAt(i);
       
   896 
       
   897 			// When space is found, set start position for deleting
       
   898 			if (c == FilterAdvancedParser.SPACE && i != caretPos) {
       
   899 				startPos = i;
       
   900 				break;
       
   901 			}
       
   902 		}
       
   903 
       
   904 		// Replace the last word from the text field and set button states
       
   905 		if (startPos < caretPos) {
       
   906 			ruleTextfield.replaceTextRange(startPos, caretPos - startPos, ""); //$NON-NLS-1$
       
   907 			setButtonStates();
       
   908 		}
       
   909 	}
       
   910 
       
   911 	/**
       
   912 	 * Sets button states
       
   913 	 */
       
   914 	public void setButtonStates() {
       
   915 
       
   916 		// Get different statuses from rule parser and set button states
       
   917 		// according to those
       
   918 		startSetToolItem.setEnabled(ruleParser.canNewSetBeStarted());
       
   919 		endSetToolItem.setEnabled(ruleParser.canSetBeEnded());
       
   920 		Button okButton = getButton(IDialogConstants.OK_ID);
       
   921 		if (okButton != null) {
       
   922 			getButton(OK).setEnabled(ruleParser.canApplyBeClicked());
       
   923 		}
       
   924 		andToolItem.setEnabled(ruleParser.canAndBeInserted());
       
   925 		orToolItem.setEnabled(ruleParser.canOrBeInserted());
       
   926 		backToolItem.setEnabled(ruleTextfield.getCaretOffset() > 1);
       
   927 		clearToolItem.setEnabled(ruleTextfield.getCharCount() > 1);
       
   928 	}
       
   929 
       
   930 	/**
       
   931 	 * Creates a rule set out of the rule String
       
   932 	 * 
       
   933 	 * @param text
       
   934 	 *            text to create the rule set from
       
   935 	 * @param notRule
       
   936 	 *            indicates if a rule is a NOT rule
       
   937 	 * @return rule object
       
   938 	 */
       
   939 	public FilterRuleObject createRuleSet(String text, boolean notRule) {
       
   940 		// Tells that NOT status has changed
       
   941 		boolean notHasChanged = false;
       
   942 
       
   943 		// New Filter rule object to be created
       
   944 		FilterRuleObject object = null;
       
   945 
       
   946 		// Trim the text
       
   947 		text = text.trim();
       
   948 
       
   949 		// Check if result is a basic rule
       
   950 		boolean isBasicRule = ruleParser.isBasicRule(text);
       
   951 
       
   952 		// Basic rule
       
   953 		if (isBasicRule) {
       
   954 			// Get the rule from the tree
       
   955 			object = getRuleWithName(text, treeRoot.getChildren());
       
   956 
       
   957 			// Rule set
       
   958 		} else {
       
   959 			object = new FilterRuleSet();
       
   960 
       
   961 			// Get and set Logical Operator for this rule set
       
   962 			LogicalOperator op = ruleParser.getLogicalOperator(text);
       
   963 			((FilterRuleSet) object).setOperator(op);
       
   964 
       
   965 			// Both or non operators in the set, show error
       
   966 			if (op == null) {
       
   967 				canBeClosed = false;
       
   968 				TraceViewerGlobals.getTraceViewer().getDialogs()
       
   969 						.showErrorMessage(MULTIPLE_OPERATORS_ERROR_MSG);
       
   970 			}
       
   971 
       
   972 			// Get children and loop through them
       
   973 			String[] children = ruleParser.getChildren(text);
       
   974 			for (int i = 0; canBeClosed && children != null
       
   975 					&& i < children.length; i++) {
       
   976 
       
   977 				// Check if child is NOT. If yes, it means that the next child
       
   978 				// will have modified NOT status
       
   979 				if (children[i].trim().equals(FilterAdvancedParser.NOT)) {
       
   980 					notHasChanged = true;
       
   981 				} else {
       
   982 					FilterRuleObject child;
       
   983 					if (notHasChanged) {
       
   984 						child = createRuleSet(children[i], !notRule);
       
   985 					} else {
       
   986 						child = createRuleSet(children[i], notRule);
       
   987 					}
       
   988 
       
   989 					((FilterRuleSet) object).addObject(child);
       
   990 					notHasChanged = false;
       
   991 				}
       
   992 			}
       
   993 
       
   994 		}
       
   995 
       
   996 		// Set NOT rule status
       
   997 		object.setLogicalNotRule(notRule);
       
   998 		return object;
       
   999 	}
       
  1000 
       
  1001 	/**
       
  1002 	 * Gets rule with a name
       
  1003 	 * 
       
  1004 	 * @param name
       
  1005 	 *            name text
       
  1006 	 * @param items
       
  1007 	 *            items array
       
  1008 	 * @return true if rule is found from the items
       
  1009 	 */
       
  1010 	private FilterRuleObject getRuleWithName(String name, Object[] items) {
       
  1011 		FilterRuleObject ret = null;
       
  1012 		for (int i = 0; i < items.length; i++) {
       
  1013 			FilterTreeBaseItem item = (FilterTreeBaseItem) items[i];
       
  1014 
       
  1015 			// Contains children, recurse
       
  1016 			if ((item.getChildren().length > 0)) {
       
  1017 				ret = getRuleWithName(name, item.getChildren());
       
  1018 
       
  1019 				// Check item
       
  1020 			} else {
       
  1021 				if (name.equals(item.getName())) {
       
  1022 
       
  1023 					// Create new objects from the existing ones
       
  1024 					// Text item
       
  1025 					if (item instanceof FilterTreeTextItem) {
       
  1026 						FilterTreeTextItem item2 = (FilterTreeTextItem) item;
       
  1027 						ret = new FilterTreeTextItem(null, null, name, item2
       
  1028 								.getRule(), item2.getText(), item2
       
  1029 								.isMatchCase());
       
  1030 
       
  1031 						// Component item
       
  1032 					} else if (item instanceof FilterTreeComponentItem) {
       
  1033 						FilterTreeComponentItem item2 = (FilterTreeComponentItem) item;
       
  1034 						ret = new FilterTreeComponentItem(null, null, name,
       
  1035 								item2.getRule(), item2.getComponentId(), item2
       
  1036 										.getGroupId());
       
  1037 					}
       
  1038 					break;
       
  1039 				}
       
  1040 			}
       
  1041 		}
       
  1042 		return ret;
       
  1043 	}
       
  1044 
       
  1045 	/**
       
  1046 	 * Checks if traces hitting filter should be displayed or not.
       
  1047 	 * 
       
  1048 	 * @return true if traces hitting filter should be displayed.
       
  1049 	 */
       
  1050 	public boolean isShowTracesContainingRule() {
       
  1051 		return showTracesContainingRule;
       
  1052 	}
       
  1053 
       
  1054 	/**
       
  1055 	 * Gets the rule set created
       
  1056 	 * 
       
  1057 	 * @return the ruleSet created
       
  1058 	 */
       
  1059 	public FilterRuleObject getRuleSet() {
       
  1060 		return ruleSet;
       
  1061 	}
       
  1062 
       
  1063 }