Source Code Cross Referenced for NavigationHistory.java in  » IDE-Eclipse » ui-workbench » org » eclipse » ui » internal » Java Source Code / Java DocumentationJava Source Code and Java Documentation

Java Source Code / Java Documentation
1. 6.0 JDK Core
2. 6.0 JDK Modules
3. 6.0 JDK Modules com.sun
4. 6.0 JDK Modules com.sun.java
5. 6.0 JDK Modules sun
6. 6.0 JDK Platform
7. Ajax
8. Apache Harmony Java SE
9. Aspect oriented
10. Authentication Authorization
11. Blogger System
12. Build
13. Byte Code
14. Cache
15. Chart
16. Chat
17. Code Analyzer
18. Collaboration
19. Content Management System
20. Database Client
21. Database DBMS
22. Database JDBC Connection Pool
23. Database ORM
24. Development
25. EJB Server geronimo
26. EJB Server GlassFish
27. EJB Server JBoss 4.2.1
28. EJB Server resin 3.1.5
29. ERP CRM Financial
30. ESB
31. Forum
32. GIS
33. Graphic Library
34. Groupware
35. HTML Parser
36. IDE
37. IDE Eclipse
38. IDE Netbeans
39. Installer
40. Internationalization Localization
41. Inversion of Control
42. Issue Tracking
43. J2EE
44. JBoss
45. JMS
46. JMX
47. Library
48. Mail Clients
49. Net
50. Parser
51. PDF
52. Portal
53. Profiler
54. Project Management
55. Report
56. RSS RDF
57. Rule Engine
58. Science
59. Scripting
60. Search Engine
61. Security
62. Sevlet Container
63. Source Control
64. Swing Library
65. Template Engine
66. Test Coverage
67. Testing
68. UML
69. Web Crawler
70. Web Framework
71. Web Mail
72. Web Server
73. Web Services
74. Web Services apache cxf 2.0.1
75. Web Services AXIS2
76. Wiki Engine
77. Workflow Engines
78. XML
79. XML UI
Java
Java Tutorial
Java Open Source
Jar File Download
Java Articles
Java Products
Java by API
Photoshop Tutorials
Maya Tutorials
Flash Tutorials
3ds-Max Tutorials
Illustrator Tutorials
GIMP Tutorials
C# / C Sharp
C# / CSharp Tutorial
C# / CSharp Open Source
ASP.Net
ASP.NET Tutorial
JavaScript DHTML
JavaScript Tutorial
JavaScript Reference
HTML / CSS
HTML CSS Reference
C / ANSI-C
C Tutorial
C++
C++ Tutorial
Ruby
PHP
Python
Python Tutorial
Python Open Source
SQL Server / T-SQL
SQL Server / T-SQL Tutorial
Oracle PL / SQL
Oracle PL/SQL Tutorial
PostgreSQL
SQL / MySQL
MySQL Tutorial
VB.Net
VB.Net Tutorial
Flash / Flex / ActionScript
VBA / Excel / Access / Word
XML
XML Tutorial
Microsoft Office PowerPoint 2007 Tutorial
Microsoft Office Excel 2007 Tutorial
Microsoft Office Word 2007 Tutorial
Java Source Code / Java Documentation » IDE Eclipse » ui workbench » org.eclipse.ui.internal 
Source Cross Referenced  Class Diagram Java Document (Java Doc) 


001:        /*******************************************************************************
002:         * Copyright (c) 2000, 2007 IBM Corporation and others.
003:         * All rights reserved. This program and the accompanying materials
004:         * are made available under the terms of the Eclipse Public License v1.0
005:         * which accompanies this distribution, and is available at
006:         * http://www.eclipse.org/legal/epl-v10.html
007:         *
008:         * Contributors:
009:         *     IBM Corporation - initial API and implementation
010:         *******************************************************************************/package org.eclipse.ui.internal;
011:
012:        import java.util.ArrayList;
013:        import java.util.HashMap;
014:        import java.util.Iterator;
015:        import java.util.LinkedList;
016:        import java.util.Map;
017:
018:        import org.eclipse.core.runtime.Assert;
019:        import org.eclipse.swt.widgets.Control;
020:        import org.eclipse.swt.widgets.Display;
021:        import org.eclipse.ui.IEditorInput;
022:        import org.eclipse.ui.IEditorPart;
023:        import org.eclipse.ui.IMemento;
024:        import org.eclipse.ui.INavigationHistory;
025:        import org.eclipse.ui.INavigationLocation;
026:        import org.eclipse.ui.INavigationLocationProvider;
027:        import org.eclipse.ui.IPartListener2;
028:        import org.eclipse.ui.IWorkbenchPage;
029:        import org.eclipse.ui.IWorkbenchPartReference;
030:        import org.eclipse.ui.IWorkbenchPartSite;
031:        import org.eclipse.ui.internal.StartupThreading.StartupRunnable;
032:        import org.eclipse.ui.internal.tweaklets.TabBehaviour;
033:        import org.eclipse.ui.internal.tweaklets.Tweaklets;
034:
035:        /**
036:         * Implementation of the back and forward actions.
037:         */
038:        public class NavigationHistory implements  INavigationHistory {
039:
040:            private static final int CAPACITY = 50;
041:
042:            private NavigationHistoryAction backwardAction;
043:
044:            private NavigationHistoryAction forwardAction;
045:
046:            private int ignoreEntries;
047:
048:            private ArrayList history = new ArrayList(CAPACITY);
049:
050:            Map perTabHistoryMap = new HashMap();
051:
052:            private ArrayList editors = new ArrayList(CAPACITY);
053:
054:            private WorkbenchPage page;
055:
056:            private int activeEntry = 0;
057:
058:            /**
059:             * Creates a new NavigationHistory to keep the NavigationLocation
060:             * entries of the specified page.
061:             */
062:            public NavigationHistory(final WorkbenchPage page) {
063:                this .page = page;
064:                page.addPartListener(new IPartListener2() {
065:                    public void partActivated(IWorkbenchPartReference partRef) {
066:                    }
067:
068:                    public void partBroughtToTop(IWorkbenchPartReference partRef) {
069:                    }
070:
071:                    public void partDeactivated(IWorkbenchPartReference partRef) {
072:                    }
073:
074:                    public void partOpened(IWorkbenchPartReference partRef) {
075:                    }
076:
077:                    public void partHidden(IWorkbenchPartReference partRef) {
078:                    }
079:
080:                    public void partVisible(IWorkbenchPartReference partRef) {
081:                    }
082:
083:                    public void partClosed(IWorkbenchPartReference partRef) {
084:                        if (isPerTabHistoryEnabled()
085:                                && partRef instanceof  EditorReference) {
086:                            if (!((EditorReference) partRef).isDisposed()) {
087:                                Object editorTabCookie = ((EditorReference) partRef)
088:                                        .getPane();
089:                                disposeHistoryForTab(editorTabCookie);
090:                                updateActions();
091:                            }
092:                        }
093:                        updateNavigationHistory(partRef, true);
094:                    }
095:
096:                    public void partInputChanged(IWorkbenchPartReference partRef) {
097:                        updateNavigationHistory(partRef, false);
098:                    }
099:
100:                    private void updateNavigationHistory(
101:                            IWorkbenchPartReference partRef, boolean partClosed) {
102:                        if (partRef != null
103:                                && partRef.getPart(false) instanceof  IEditorPart) {
104:                            IEditorPart editor = (IEditorPart) partRef
105:                                    .getPart(false);
106:                            IEditorInput input = editor.getEditorInput();
107:                            String id = editor.getSite().getId();
108:                            Iterator e = editors.iterator();
109:                            NavigationHistoryEditorInfo info = null;
110:                            NavigationHistoryEditorInfo currentInfo = null;
111:                            NavigationHistoryEntry current = getEntry(activeEntry);
112:                            if (current != null) {
113:                                currentInfo = current.editorInfo;
114:                            }
115:                            while (e.hasNext()) {
116:                                info = (NavigationHistoryEditorInfo) e.next();
117:                                if (id.equals(info.editorID)
118:                                        && input.equals(info.editorInput)) {
119:                                    if (partClosed && info != currentInfo) {
120:                                        info.handlePartClosed();
121:                                    }
122:                                    break;
123:                                }
124:                                info = null;
125:                            }
126:                            if (info == null) {
127:                                return;
128:                            }
129:                            boolean isEntryDisposed = false;
130:                            e = history.iterator();
131:                            int i = 0;
132:                            while (e.hasNext()) {
133:                                NavigationHistoryEntry entry = (NavigationHistoryEntry) e
134:                                        .next();
135:                                if (entry.editorInfo == info) {
136:                                    if (!entry.handlePartClosed()) {
137:                                        // update the active entry since we are removing an item
138:                                        if (i < activeEntry) {
139:                                            activeEntry--;
140:                                        } else if (i == activeEntry) {
141:                                            if (i != 0) {
142:                                                activeEntry--;
143:                                            }
144:                                        } else {
145:                                            // activeEntry is before item we deleted
146:                                            i++;
147:                                        }
148:                                        isEntryDisposed = true;
149:                                        e.remove();
150:                                        disposeEntry(entry);
151:                                    } else {
152:                                        i++;
153:                                    }
154:                                }
155:                            }
156:
157:                            /*
158:                             * Promote the entry of the last closed editor to be the active
159:                             * one, see: https://bugs.eclipse.org/bugs/show_bug.cgi?id=154431 
160:                             */
161:                            if (!isEntryDisposed
162:                                    && page.getActiveEditor() == null
163:                                    && activeEntry < history.size())
164:                                activeEntry++;
165:
166:                            updateActions();
167:                        }
168:                    }
169:                });
170:            }
171:
172:            private Display getDisplay() {
173:                return page.getWorkbenchWindow().getShell().getDisplay();
174:            }
175:
176:            private boolean isPerTabHistoryEnabled() {
177:                return ((TabBehaviour) Tweaklets.get(TabBehaviour.KEY))
178:                        .isPerTabHistoryEnabled();
179:            }
180:
181:            /*
182:             * Adds an editor to the editor history without getting its location.
183:             */
184:            public void markEditor(final IEditorPart part) {
185:                if (ignoreEntries > 0 || part == null) {
186:                    return;
187:                }
188:                /* Ignore all entries until the async exec runs. Workaround to avoid 
189:                 * extra entry when using Open Declaration (F3) that opens another editor. */
190:                ignoreEntries++;
191:                getDisplay().asyncExec(new Runnable() {
192:                    public void run() {
193:                        if (--ignoreEntries == 0) {
194:                            if (part.getEditorSite() instanceof  EditorSite) {
195:                                EditorSite site = (EditorSite) part
196:                                        .getEditorSite();
197:                                Control c = site.getPane().getControl();
198:                                if (c == null || c.isDisposed()) {
199:                                    return;
200:                                }
201:                                NavigationHistoryEntry e = getEntry(activeEntry);
202:                                if (e != null
203:                                        && part.getEditorInput() != e.editorInfo.editorInput) {
204:                                    updateEntry(e);
205:                                }
206:                                addEntry(part);
207:                            }
208:                        }
209:                    }
210:                });
211:            }
212:
213:            /*
214:             * (non-Javadoc)
215:             * Method declared on INavigationHistory.
216:             */
217:            public void markLocation(IEditorPart part) {
218:                addEntry(part);
219:            }
220:
221:            /*
222:             * Return the backward history entries.  Return in restore order (i.e., the
223:             * first entry is the entry that would become active if the "Backward" action 
224:             * was executed).
225:             * <p>
226:             * (Called by NavigationHistoryAction)
227:             * </p>
228:             */
229:            NavigationHistoryEntry[] getBackwardEntries() {
230:                if (isPerTabHistoryEnabled()) {
231:                    return getEntriesForTab(false);
232:                }
233:                int length = activeEntry;
234:                NavigationHistoryEntry[] entries = new NavigationHistoryEntry[length];
235:                for (int i = 0; i < activeEntry; i++) {
236:                    entries[activeEntry - 1 - i] = getEntry(i);
237:                }
238:                return entries;
239:            }
240:
241:            /*
242:             * Return the forward history entries.  Return in restore order (i.e., the first
243:             * entry is the entry that would become active if the "Forward" action was
244:             * executed).
245:             * <p>
246:             * (Called by NavigationHistoryAction)
247:             * </p>
248:             */
249:            NavigationHistoryEntry[] getForwardEntries() {
250:                if (isPerTabHistoryEnabled()) {
251:                    return getEntriesForTab(true);
252:                }
253:                int length = history.size() - activeEntry - 1;
254:                length = Math.max(0, length);
255:                NavigationHistoryEntry[] entries = new NavigationHistoryEntry[length];
256:                for (int i = activeEntry + 1; i < history.size(); i++) {
257:                    entries[i - activeEntry - 1] = getEntry(i);
258:                }
259:                return entries;
260:            }
261:
262:            /*
263:             * (non-Javadoc)
264:             * Method declared on INavigationHistory.
265:             */
266:            public INavigationLocation[] getLocations() {
267:                INavigationLocation result[] = new INavigationLocation[history
268:                        .size()];
269:                for (int i = 0; i < result.length; i++) {
270:                    NavigationHistoryEntry e = (NavigationHistoryEntry) history
271:                            .get(i);
272:                    result[i] = e.location;
273:                }
274:                return result;
275:            }
276:
277:            /*
278:             * (non-Javadoc)
279:             * Method declared on INavigationHistory.
280:             */
281:            public INavigationLocation getCurrentLocation() {
282:                NavigationHistoryEntry entry = getEntry(activeEntry);
283:                return entry == null ? null : entry.location;
284:            }
285:
286:            /**
287:             * Disposes this NavigationHistory and all entries.
288:             */
289:            public void dispose() {
290:                disposeHistoryForTabs();
291:                Iterator e = history.iterator();
292:                while (e.hasNext()) {
293:                    NavigationHistoryEntry entry = (NavigationHistoryEntry) e
294:                            .next();
295:                    disposeEntry(entry);
296:                }
297:            }
298:
299:            /**
300:             * Keeps a reference to the forward action to update its state
301:             * whenever needed.
302:             * <p>
303:             * (Called by NavigationHistoryAction)
304:             * </p>
305:             */
306:            void setForwardAction(NavigationHistoryAction action) {
307:                forwardAction = action;
308:                updateActions();
309:            }
310:
311:            /**
312:             * Keeps a reference to the backward action to update its state
313:             * whenever needed.
314:             * <p>
315:             * (Called by NavigationHistoryAction)
316:             * </p>
317:             */
318:            void setBackwardAction(NavigationHistoryAction action) {
319:                backwardAction = action;
320:                updateActions();
321:            }
322:
323:            /*
324:             * Returns the history entry indexed by <code>index</code>
325:             */
326:            private NavigationHistoryEntry getEntry(int index) {
327:                if (0 <= index && index < history.size()) {
328:                    return (NavigationHistoryEntry) history.get(index);
329:                }
330:                return null;
331:            }
332:
333:            /*
334:             * Adds the specified entry to the history.
335:             */
336:            private void add(NavigationHistoryEntry entry) {
337:                removeForwardEntries();
338:                if (history.size() == CAPACITY) {
339:                    NavigationHistoryEntry e = (NavigationHistoryEntry) history
340:                            .remove(0);
341:                    disposeEntry(e);
342:                }
343:                history.add(entry);
344:                activeEntry = history.size() - 1;
345:            }
346:
347:            /*
348:             * Remove all entries after the active entry.
349:             */
350:            private void removeForwardEntries() {
351:                int length = history.size();
352:                for (int i = activeEntry + 1; i < length; i++) {
353:                    NavigationHistoryEntry e = (NavigationHistoryEntry) history
354:                            .remove(activeEntry + 1);
355:                    disposeEntry(e);
356:                }
357:            }
358:
359:            /*
360:             * Adds a location to the history.
361:             */
362:            private void addEntry(IEditorPart part) {
363:                if (ignoreEntries > 0 || part == null) {
364:                    return;
365:                }
366:
367:                if (isPerTabHistoryEnabled()) {
368:                    markLocationForTab(part);
369:                }
370:                INavigationLocation location = null;
371:                if (part instanceof  INavigationLocationProvider) {
372:                    location = ((INavigationLocationProvider) part)
373:                            .createNavigationLocation();
374:                }
375:
376:                NavigationHistoryEntry current = getEntry(activeEntry);
377:                if (current != null && current.editorInfo.memento != null) {
378:                    current.editorInfo.restoreEditor();
379:                    checkDuplicates(current.editorInfo);
380:                }
381:                NavigationHistoryEntry e = createEntry(page, part, location);
382:                if (current == null) {
383:                    add(e);
384:                } else {
385:                    if (e.mergeInto(current)) {
386:                        disposeEntry(e);
387:                        removeForwardEntries();
388:                    } else {
389:                        add(e);
390:                    }
391:                }
392:                printEntries("added entry"); //$NON-NLS-1$
393:                updateActions();
394:            }
395:
396:            /*
397:             * Prints all the entries in the console. For debug only.
398:             */
399:            private void printEntries(String label) {
400:                if (false) {
401:                    System.out.println("+++++ " + label + "+++++ "); //$NON-NLS-1$ //$NON-NLS-2$
402:                    int size = history.size();
403:                    for (int i = 0; i < size; i++) {
404:                        String append = activeEntry == i ? ">>" : ""; //$NON-NLS-1$ //$NON-NLS-2$
405:                        System.out.println(append
406:                                + "Index: " + i + " " + history.get(i)); //$NON-NLS-1$ //$NON-NLS-2$
407:                    }
408:                }
409:            }
410:
411:            /*
412:             * Returns true if the forward action can be performed otherwise returns false.
413:             * <p>
414:             * (Called by NavigationHistoryAction)
415:             * </p>
416:             */
417:            /* package */boolean canForward() {
418:                if (isPerTabHistoryEnabled()) {
419:                    return hasEntriesForTab(true);
420:                }
421:                return (0 <= activeEntry + 1)
422:                        && (activeEntry + 1 < history.size());
423:            }
424:
425:            /*
426:             * Returns true if the backward action can be performed otherwise returns false.
427:             * <p>
428:             * (Called by NavigationHistoryAction)
429:             * </p>
430:             */
431:            /* package */boolean canBackward() {
432:                if (isPerTabHistoryEnabled()) {
433:                    return hasEntriesForTab(false);
434:                }
435:                return (0 <= activeEntry - 1)
436:                        && (activeEntry - 1 < history.size());
437:            }
438:
439:            /*
440:             * Update the actions enable/disable and tooltip state.
441:             */
442:            private void updateActions() {
443:                if (backwardAction != null) {
444:                    backwardAction.update();
445:                }
446:                if (forwardAction != null) {
447:                    forwardAction.update();
448:                }
449:            }
450:
451:            /*
452:             * Restore the specified entry
453:             */
454:            private void gotoEntry(NavigationHistoryEntry entry) {
455:                if (entry == null) {
456:                    return;
457:                }
458:                try {
459:                    ignoreEntries++;
460:                    if (entry.editorInfo.memento != null) {
461:                        entry.editorInfo.restoreEditor();
462:                        checkDuplicates(entry.editorInfo);
463:                    }
464:                    entry.restoreLocation();
465:                    updateActions();
466:                    printEntries("goto entry"); //$NON-NLS-1$
467:                } finally {
468:                    ignoreEntries--;
469:                }
470:            }
471:
472:            /*
473:             * update the active entry
474:             */
475:            private void updateEntry(NavigationHistoryEntry activeEntry) {
476:                if (activeEntry == null || activeEntry.location == null) {
477:                    return;
478:                }
479:                activeEntry.location.update();
480:                printEntries("updateEntry"); //$NON-NLS-1$
481:            }
482:
483:            /*
484:             * Perform the forward action by getting the next location and restoring
485:             * its context.
486:             * <p>
487:             * (Called by NavigationHistoryAction)
488:             * </p>
489:             */
490:            void forward() {
491:                if (isPerTabHistoryEnabled()) {
492:                    forwardForTab();
493:                    return;
494:                }
495:                if (canForward()) {
496:                    shiftEntry(true);
497:                }
498:            }
499:
500:            /*
501:             * Perform the backward action by getting the previous location and restoring
502:             * its context.
503:             * <p>
504:             * (Called by NavigationHistoryAction)
505:             * </p>
506:             */
507:            void backward() {
508:                if (isPerTabHistoryEnabled()) {
509:                    backwardForTab();
510:                    return;
511:                }
512:                if (canBackward()) {
513:                    shiftEntry(false);
514:                }
515:            }
516:
517:            /*
518:             * Shift the history back or forward
519:             */
520:            private void shiftEntry(boolean forward) {
521:                updateEntry(getEntry(activeEntry));
522:                if (forward) {
523:                    activeEntry++;
524:                } else {
525:                    activeEntry--;
526:                }
527:                NavigationHistoryEntry entry = getEntry(activeEntry);
528:                if (entry != null) {
529:                    gotoEntry(entry);
530:                }
531:            }
532:
533:            /*
534:             * Shift the history to the given entry.
535:             * <p>
536:             * (Called by NavigationHistoryAction)
537:             * </p>
538:             */
539:            void shiftCurrentEntry(NavigationHistoryEntry entry, boolean forward) {
540:                if (isPerTabHistoryEnabled()) {
541:                    gotoEntryForTab(entry, forward);
542:                    return;
543:                }
544:                updateEntry(getEntry(activeEntry));
545:                activeEntry = history.indexOf(entry);
546:                gotoEntry(entry);
547:            }
548:
549:            /**
550:             * Save the state of this history into the memento.
551:             */
552:            void saveState(IMemento memento) {
553:                NavigationHistoryEntry cEntry = getEntry(activeEntry);
554:                if (cEntry == null || !cEntry.editorInfo.isPersistable()) {
555:                    return;
556:                }
557:
558:                ArrayList editors = (ArrayList) this .editors.clone();
559:                for (Iterator iter = editors.iterator(); iter.hasNext();) {
560:                    NavigationHistoryEditorInfo info = (NavigationHistoryEditorInfo) iter
561:                            .next();
562:                    if (!info.isPersistable()) {
563:                        iter.remove();
564:                    }
565:                }
566:                IMemento editorsMem = memento
567:                        .createChild(IWorkbenchConstants.TAG_EDITORS);
568:                for (Iterator iter = editors.iterator(); iter.hasNext();) {
569:                    NavigationHistoryEditorInfo info = (NavigationHistoryEditorInfo) iter
570:                            .next();
571:                    info.saveState(editorsMem
572:                            .createChild(IWorkbenchConstants.TAG_EDITOR));
573:                }
574:
575:                ArrayList list = new ArrayList(history.size());
576:                int size = history.size();
577:                for (int i = 0; i < size; i++) {
578:                    NavigationHistoryEntry entry = (NavigationHistoryEntry) history
579:                            .get(i);
580:                    if (entry.editorInfo.isPersistable()) {
581:                        list.add(entry);
582:                    }
583:                }
584:                size = list.size();
585:                for (int i = 0; i < size; i++) {
586:                    NavigationHistoryEntry entry = (NavigationHistoryEntry) list
587:                            .get(i);
588:                    IMemento childMem = memento
589:                            .createChild(IWorkbenchConstants.TAG_ITEM);
590:                    if (entry == cEntry) {
591:                        childMem.putString(IWorkbenchConstants.TAG_ACTIVE,
592:                                "true"); //$NON-NLS-1$
593:                    }
594:                    entry.saveState(childMem, list);
595:                    childMem.putInteger(IWorkbenchConstants.TAG_INDEX, editors
596:                            .indexOf(entry.editorInfo));
597:                }
598:            }
599:
600:            /**
601:             * Restore the state of this history from the memento.
602:             */
603:            void restoreState(IMemento memento) {
604:                IMemento editorsMem = memento
605:                        .getChild(IWorkbenchConstants.TAG_EDITORS);
606:                IMemento items[] = memento
607:                        .getChildren(IWorkbenchConstants.TAG_ITEM);
608:                if (items.length == 0 || editorsMem == null) {
609:                    if (page.getActiveEditor() != null) {
610:                        markLocation(page.getActiveEditor());
611:                    }
612:                    return;
613:                }
614:
615:                IMemento children[] = editorsMem
616:                        .getChildren(IWorkbenchConstants.TAG_EDITOR);
617:                NavigationHistoryEditorInfo editorsInfo[] = new NavigationHistoryEditorInfo[children.length];
618:                for (int i = 0; i < editorsInfo.length; i++) {
619:                    editorsInfo[i] = new NavigationHistoryEditorInfo(
620:                            children[i]);
621:                    editors.add(editorsInfo[i]);
622:                }
623:
624:                for (int i = 0; i < items.length; i++) {
625:                    IMemento item = items[i];
626:                    int index = item.getInteger(IWorkbenchConstants.TAG_INDEX)
627:                            .intValue();
628:                    NavigationHistoryEditorInfo info = editorsInfo[index];
629:                    info.refCount++;
630:                    NavigationHistoryEntry entry = new NavigationHistoryEntry(
631:                            info, page, null, null);
632:                    history.add(entry);
633:                    entry.restoreState(item);
634:                    if (item.getString(IWorkbenchConstants.TAG_ACTIVE) != null) {
635:                        activeEntry = i;
636:                    }
637:                }
638:
639:                final NavigationHistoryEntry entry = getEntry(activeEntry);
640:                if (entry != null && entry.editorInfo.editorInput != null) {
641:                    if (page.getActiveEditor() == page
642:                            .findEditor(entry.editorInfo.editorInput)) {
643:                        StartupThreading
644:                                .runWithoutExceptions(new StartupRunnable() {
645:
646:                                    public void runWithException()
647:                                            throws Throwable {
648:                                        gotoEntry(entry);
649:                                    }
650:                                });
651:                    }
652:                }
653:            }
654:
655:            public NavigationHistoryEntry createEntry(IWorkbenchPage page,
656:                    IEditorPart part, INavigationLocation location) {
657:                String editorID = part.getSite().getId();
658:                IEditorInput editorInput = part.getEditorInput();
659:                NavigationHistoryEditorInfo info = null;
660:                for (Iterator iter = editors.iterator(); iter.hasNext();) {
661:                    info = (NavigationHistoryEditorInfo) iter.next();
662:                    if (editorID.equals(info.editorID)
663:                            && editorInput.equals(info.editorInput)) {
664:                        info.refCount++;
665:                        break;
666:                    } else {
667:                        info = null;
668:                    }
669:                }
670:                if (info == null) {
671:                    info = new NavigationHistoryEditorInfo(part);
672:                    info.refCount++;
673:                    editors.add(info);
674:                }
675:                return new NavigationHistoryEntry(info, page, part, location);
676:            }
677:
678:            public void disposeEntry(NavigationHistoryEntry entry) {
679:                if (entry.editorInfo == null) {
680:                    return;
681:                }
682:                entry.editorInfo.refCount--;
683:                if (entry.editorInfo.refCount == 0) {
684:                    editors.remove(entry.editorInfo);
685:                }
686:                entry.dispose();
687:            }
688:
689:            void checkDuplicates(NavigationHistoryEditorInfo info) {
690:                NavigationHistoryEditorInfo dup = null;
691:                if (info.editorInput == null) {
692:                    return;
693:                }
694:                for (Iterator iter = editors.iterator(); iter.hasNext();) {
695:                    dup = (NavigationHistoryEditorInfo) iter.next();
696:                    if (info != dup && info.editorID.equals(dup.editorID)
697:                            && info.editorInput.equals(dup.editorInput)) {
698:                        break;
699:                    } else {
700:                        dup = null;
701:                    }
702:                }
703:                if (dup == null) {
704:                    return;
705:                }
706:                for (Iterator iter = history.iterator(); iter.hasNext();) {
707:                    NavigationHistoryEntry entry = (NavigationHistoryEntry) iter
708:                            .next();
709:                    if (entry.editorInfo == dup) {
710:                        entry.editorInfo = info;
711:                        info.refCount++;
712:                    }
713:                }
714:                editors.remove(dup);
715:            }
716:
717:            /*********************************************************/
718:            /*** new per-tab history code                          ***/
719:            /*********************************************************/
720:
721:            private static class PerTabHistory {
722:                LinkedList backwardEntries = new LinkedList();
723:                NavigationHistoryEntry currentEntry = null;
724:                LinkedList forwardEntries = new LinkedList();
725:            }
726:
727:            private void setNewCurrentEntryForTab(PerTabHistory perTabHistory,
728:                    NavigationHistoryEntry entry) {
729:                if (perTabHistory.currentEntry != null) {
730:                    perTabHistory.backwardEntries
731:                            .addFirst(perTabHistory.currentEntry);
732:                }
733:                perTabHistory.currentEntry = entry;
734:                removeEntriesForTab(perTabHistory.forwardEntries);
735:            }
736:
737:            private Object getCookieForTab(IEditorPart part) {
738:                if (part != null) {
739:                    IWorkbenchPartSite site = part.getSite();
740:                    if (site instanceof  PartSite) {
741:                        PartSite partSite = (PartSite) site;
742:                        WorkbenchPartReference ref = (WorkbenchPartReference) partSite
743:                                .getPartReference();
744:                        if (!ref.isDisposed()) {
745:                            return partSite.getPane();
746:                        }
747:                    }
748:                }
749:                return null;
750:            }
751:
752:            private void markLocationForTab(IEditorPart part) {
753:                if (part instanceof  ErrorEditorPart) {
754:                    updateActions();
755:                    return;
756:                }
757:                Object tabCookie = getCookieForTab(part);
758:                if (tabCookie != null) {
759:                    INavigationLocation location = null;
760:                    if (part instanceof  INavigationLocationProvider) {
761:                        location = ((INavigationLocationProvider) part)
762:                                .createNavigationLocation();
763:                    }
764:                    PerTabHistory perTabHistory = (PerTabHistory) perTabHistoryMap
765:                            .get(tabCookie);
766:                    if (perTabHistory == null) {
767:                        perTabHistory = new PerTabHistory();
768:                        perTabHistoryMap.put(tabCookie, perTabHistory);
769:                    }
770:                    NavigationHistoryEntry current = perTabHistory.currentEntry;
771:                    if (current != null && current.editorInfo.memento != null) {
772:                        current.editorInfo.restoreEditor();
773:                        checkDuplicates(current.editorInfo);
774:                    }
775:                    NavigationHistoryEntry entry = createEntry(page, part,
776:                            location);
777:                    if (current != null && entry.mergeInto(current)) {
778:                        disposeEntry(entry);
779:                        removeEntriesForTab(perTabHistory.forwardEntries);
780:                    } else {
781:                        setNewCurrentEntryForTab(perTabHistory, entry);
782:                    }
783:                }
784:                updateActions();
785:            }
786:
787:            public void updateCookieForTab(Object oldCookie, Object newCookie) {
788:                if (newCookie.equals(oldCookie)) {
789:                    return;
790:                }
791:                PerTabHistory perTabHistory = (PerTabHistory) perTabHistoryMap
792:                        .remove(oldCookie);
793:                if (perTabHistory != null) {
794:                    perTabHistoryMap.put(newCookie, perTabHistory);
795:                }
796:            }
797:
798:            private void gotoEntryForTab(NavigationHistoryEntry target,
799:                    boolean forward) {
800:                Object editorTabCookie = getCookieForTab(page.getActiveEditor());
801:                if (editorTabCookie != null) {
802:                    PerTabHistory perTabHistory = (PerTabHistory) perTabHistoryMap
803:                            .get(editorTabCookie);
804:                    if (perTabHistory != null) {
805:                        LinkedList source = forward ? perTabHistory.forwardEntries
806:                                : perTabHistory.backwardEntries;
807:                        LinkedList destination = forward ? perTabHistory.backwardEntries
808:                                : perTabHistory.forwardEntries;
809:                        if (perTabHistory.currentEntry != null) {
810:                            if (perTabHistory.currentEntry.location != null) {
811:                                perTabHistory.currentEntry.location.update();
812:                            }
813:                            destination.addFirst(perTabHistory.currentEntry);
814:                        }
815:                        NavigationHistoryEntry newCurrent = null;
816:                        while (!source.isEmpty() && newCurrent == null) {
817:                            NavigationHistoryEntry entry = (NavigationHistoryEntry) source
818:                                    .removeFirst();
819:                            if (entry.equals(target)) {
820:                                newCurrent = entry;
821:                            } else {
822:                                destination.addFirst(entry);
823:                            }
824:                        }
825:                        Assert.isTrue(newCurrent != null);
826:                        perTabHistory.currentEntry = newCurrent;
827:                        try {
828:                            ignoreEntries++;
829:                            if (newCurrent.editorInfo.memento != null) {
830:                                newCurrent.editorInfo.restoreEditor();
831:                                checkDuplicates(newCurrent.editorInfo);
832:                            }
833:                            newCurrent.restoreLocation();
834:                            updateActions();
835:                        } finally {
836:                            ignoreEntries--;
837:                        }
838:                    }
839:                }
840:            }
841:
842:            private void forwardForTab() {
843:                Object editorTabCookie = getCookieForTab(page.getActiveEditor());
844:                if (editorTabCookie != null) {
845:                    PerTabHistory perTabHistory = (PerTabHistory) perTabHistoryMap
846:                            .get(editorTabCookie);
847:                    if (perTabHistory != null
848:                            && !perTabHistory.forwardEntries.isEmpty()) {
849:                        NavigationHistoryEntry newCurrent = (NavigationHistoryEntry) perTabHistory.forwardEntries
850:                                .removeFirst();
851:                        if (perTabHistory.currentEntry != null) {
852:                            final INavigationLocation location = perTabHistory.currentEntry.location;
853:                            if (location != null) {
854:                                location.update();
855:                            }
856:                            perTabHistory.backwardEntries
857:                                    .addFirst(perTabHistory.currentEntry);
858:                        }
859:                        perTabHistory.currentEntry = newCurrent;
860:                        try {
861:                            ignoreEntries++;
862:                            if (newCurrent.editorInfo.memento != null) {
863:                                newCurrent.editorInfo.restoreEditor();
864:                                checkDuplicates(newCurrent.editorInfo);
865:                            }
866:                            newCurrent.restoreLocation();
867:                            updateActions();
868:                        } finally {
869:                            ignoreEntries--;
870:                        }
871:                    }
872:                }
873:            }
874:
875:            private void backwardForTab() {
876:                Object editorTabCookie = getCookieForTab(page.getActiveEditor());
877:                if (editorTabCookie != null) {
878:                    PerTabHistory perTabHistory = (PerTabHistory) perTabHistoryMap
879:                            .get(editorTabCookie);
880:                    if (perTabHistory != null
881:                            && !perTabHistory.backwardEntries.isEmpty()) {
882:                        NavigationHistoryEntry newCurrent = (NavigationHistoryEntry) perTabHistory.backwardEntries
883:                                .removeFirst();
884:                        if (perTabHistory.currentEntry != null) {
885:                            perTabHistory.currentEntry.location.update();
886:                            perTabHistory.forwardEntries
887:                                    .addFirst(perTabHistory.currentEntry);
888:                        }
889:                        perTabHistory.currentEntry = newCurrent;
890:                        try {
891:                            ignoreEntries++;
892:                            if (newCurrent.editorInfo.memento != null) {
893:                                newCurrent.editorInfo.restoreEditor();
894:                                checkDuplicates(newCurrent.editorInfo);
895:                            }
896:                            newCurrent.restoreLocation();
897:                            updateActions();
898:                        } finally {
899:                            ignoreEntries--;
900:                        }
901:                    }
902:                }
903:            }
904:
905:            private boolean hasEntriesForTab(boolean forward) {
906:                Object editorTabCookie = getCookieForTab(page.getActiveEditor());
907:                if (editorTabCookie != null) {
908:                    PerTabHistory perTabHistory = (PerTabHistory) perTabHistoryMap
909:                            .get(editorTabCookie);
910:                    if (perTabHistory != null) {
911:                        LinkedList entries = forward ? perTabHistory.forwardEntries
912:                                : perTabHistory.backwardEntries;
913:                        return !entries.isEmpty();
914:                    }
915:                }
916:                return false;
917:            }
918:
919:            /**
920:             * Returns entries in restore order.
921:             * @param editorTabCookie
922:             * @param forward
923:             * @return
924:             */
925:            private NavigationHistoryEntry[] getEntriesForTab(boolean forward) {
926:                Object editorTabCookie = getCookieForTab(page.getActiveEditor());
927:                if (editorTabCookie != null) {
928:                    PerTabHistory perTabHistory = (PerTabHistory) perTabHistoryMap
929:                            .get(editorTabCookie);
930:                    if (perTabHistory != null) {
931:                        LinkedList entries = forward ? perTabHistory.forwardEntries
932:                                : perTabHistory.backwardEntries;
933:                        return (NavigationHistoryEntry[]) entries
934:                                .toArray(new NavigationHistoryEntry[entries
935:                                        .size()]);
936:                    }
937:                }
938:                return new NavigationHistoryEntry[0];
939:            }
940:
941:            private void disposeHistoryForTabs() {
942:                Object[] keys = perTabHistoryMap.keySet().toArray();
943:                for (int i = 0; i < keys.length; i++) {
944:                    disposeHistoryForTab(keys[i]);
945:                }
946:            }
947:
948:            void disposeHistoryForTab(Object editorTabCookie) {
949:                PerTabHistory perTabHistory = (PerTabHistory) perTabHistoryMap
950:                        .remove(editorTabCookie);
951:                if (perTabHistory != null) {
952:                    if (perTabHistory.currentEntry != null) {
953:                        disposeEntry(perTabHistory.currentEntry);
954:                        perTabHistory.currentEntry = null;
955:                    }
956:                    removeEntriesForTab(perTabHistory.backwardEntries);
957:                    removeEntriesForTab(perTabHistory.forwardEntries);
958:                }
959:            }
960:
961:            private void removeEntriesForTab(LinkedList entries) {
962:                for (Iterator it = entries.iterator(); it.hasNext();) {
963:                    NavigationHistoryEntry entry = (NavigationHistoryEntry) it
964:                            .next();
965:                    disposeEntry(entry);
966:                    it.remove();
967:                }
968:            }
969:        }
www.java2java.com | Contact Us
Copyright 2009 - 12 Demo Source and Support. All rights reserved.
All other trademarks are property of their respective owners.