Revision: 3781
          http://skim-app.svn.sourceforge.net/skim-app/?rev=3781&view=rev
Author:   hofman
Date:     2008-04-21 16:41:33 -0700 (Mon, 21 Apr 2008)

Log Message:
-----------
Move PDFDidplayView overrides to separate file. Add experimental code to make 
annotations accessible for assistive devices. Should probably be disabled for 
the next release.

Modified Paths:
--------------
    trunk/PDFAnnotation_SKExtensions.h
    trunk/PDFAnnotation_SKExtensions.m
    trunk/SKPDFView.h
    trunk/SKPDFView.m
    trunk/Skim.xcodeproj/project.pbxproj

Added Paths:
-----------
    trunk/PDFDisplayView_SKExtensions.h
    trunk/PDFDisplayView_SKExtensions.m

Modified: trunk/PDFAnnotation_SKExtensions.h
===================================================================
--- trunk/PDFAnnotation_SKExtensions.h  2008-04-20 23:54:10 UTC (rev 3780)
+++ trunk/PDFAnnotation_SKExtensions.h  2008-04-21 23:41:33 UTC (rev 3781)
@@ -140,4 +140,13 @@
 - (unsigned long)scriptingEndLineStyle;
 - (id)selectionSpecifier;
 
+- (id)accessibilityRoleAttribute;
+- (id)accessibilityRoleDescriptionAttribute;
+- (id)accessibilityTitleAttribute;
+- (id)accessibilityValueAttribute;
+- (id)accessibilitySelectedTextAttribute;
+- (id)accessibilitySelectedTextRangeAttribute;
+- (id)accessibilityNumberOfCharactersAttribute;
+- (id)accessibilityVisibleCharacterRangeAttribute;
+
 @end

Modified: trunk/PDFAnnotation_SKExtensions.m
===================================================================
--- trunk/PDFAnnotation_SKExtensions.m  2008-04-20 23:54:10 UTC (rev 3780)
+++ trunk/PDFAnnotation_SKExtensions.m  2008-04-21 23:41:33 UTC (rev 3781)
@@ -534,6 +534,40 @@
     return [NSNull null];
 }
 
+#pragma mark Accessibility
+
+- (id)accessibilityRoleAttribute {
+    return NSAccessibilityStaticTextRole;
+}
+
+- (id)accessibilityRoleDescriptionAttribute {
+    return NSAccessibilityRoleDescription([self accessibilityRoleAttribute], 
nil);
+}
+
+- (id)accessibilityTitleAttribute {
+    return [[self type] typeName];
+}
+
+- (id)accessibilityValueAttribute {
+    return [self contents];
+}
+
+- (id)accessibilitySelectedTextAttribute {
+    return @"";
+}
+
+- (id)accessibilitySelectedTextRangeAttribute {
+    return [NSValue valueWithRange:NSMakeRange(0, 0)];
+}
+
+- (id)accessibilityNumberOfCharactersAttribute {
+    return [NSNumber numberWithUnsignedInt:[[self accessibilityValueAttribute] 
length]];
+}
+
+- (id)accessibilityVisibleCharacterRangeAttribute {
+    return [NSValue valueWithRange:NSMakeRange(0, [[self 
accessibilityValueAttribute] length])];
+}
+
 @end
 
 #pragma mark -
@@ -556,4 +590,40 @@
         originalToolTip = OBReplaceMethodImplementationWithSelector(self, 
@selector(toolTip), @selector(replacementToolTip));
 }
 
+- (id)accessibilityRoleAttribute {
+    return NSAccessibilityLinkRole;
+}
+
+- (id)accessibilityRoleDescriptionAttribute {
+    return NSAccessibilityRoleDescription([self accessibilityRoleAttribute], 
nil);
+}
+
+- (id)accessibilityTitleAttribute {
+    NSString *title = nil;
+    if (originalToolTip != NULL)
+        title = originalToolTip(self, _cmd);
+    if (title == nil)
+        title = [self contents];
+    return title;
+}
+
+- (id)accessibilityValueAttribute {
+    return [[[self page] selectionForRect:NSInsetRect([self bounds], -3.0, 
-3.0)] string];
+}
+- (id)accessibilitySelectedTextAttribute {
+    return nil;
+}
+
+- (id)accessibilitySelectedTextRangeAttribute {
+    return nil;
+}
+
+- (id)accessibilityNumberOfCharactersAttribute {
+    return nil;
+}
+
+- (id)accessibilityVisibleCharacterRangeAttribute {
+    return nil;
+}
+
 @end

Added: trunk/PDFDisplayView_SKExtensions.h
===================================================================
--- trunk/PDFDisplayView_SKExtensions.h                         (rev 0)
+++ trunk/PDFDisplayView_SKExtensions.h 2008-04-21 23:41:33 UTC (rev 3781)
@@ -0,0 +1,48 @@
+//
+//  PDFDisplayView_SKExtensions.h
+//  Skim
+//
+//  Created by Christiaan Hofman on 4/22/08.
+/*
+ This software is Copyright (c) 2008
+ Christiaan Hofman. All rights reserved.
+
+ Redistribution and use in source and binary forms, with or without
+ modification, are permitted provided that the following conditions
+ are met:
+
+ - Redistributions of source code must retain the above copyright
+   notice, this list of conditions and the following disclaimer.
+
+ - Redistributions in binary form must reproduce the above copyright
+    notice, this list of conditions and the following disclaimer in
+    the documentation and/or other materials provided with the
+    distribution.
+
+ - Neither the name of Christiaan Hofman nor the names of any
+    contributors may be used to endorse or promote products derived
+    from this software without specific prior written permission.
+
+ THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
+ "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
+ LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
+ A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
+ OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
+ SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
+ LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
+ DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
+ THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
+ OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#import <Cocoa/Cocoa.h>
+#import <Quartz/Quartz.h>
+
+
[EMAIL PROTECTED] PDFDisplayView : NSView
+- (void)passwordEntered:(id)sender;
[EMAIL PROTECTED]
+
[EMAIL PROTECTED] PDFDisplayView (SKExtensions)
[EMAIL PROTECTED]

Added: trunk/PDFDisplayView_SKExtensions.m
===================================================================
--- trunk/PDFDisplayView_SKExtensions.m                         (rev 0)
+++ trunk/PDFDisplayView_SKExtensions.m 2008-04-21 23:41:33 UTC (rev 3781)
@@ -0,0 +1,423 @@
+//
+//  PDFDisplayView_SKExtensions.m
+//  Skim
+//
+//  Created by Christiaan Hofman on 4/22/08.
+/*
+ This software is Copyright (c) 2008
+ Christiaan Hofman. All rights reserved.
+
+ Redistribution and use in source and binary forms, with or without
+ modification, are permitted provided that the following conditions
+ are met:
+
+ - Redistributions of source code must retain the above copyright
+   notice, this list of conditions and the following disclaimer.
+
+ - Redistributions in binary form must reproduce the above copyright
+    notice, this list of conditions and the following disclaimer in
+    the documentation and/or other materials provided with the
+    distribution.
+
+ - Neither the name of Christiaan Hofman nor the names of any
+    contributors may be used to endorse or promote products derived
+    from this software without specific prior written permission.
+
+ THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
+ "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
+ LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
+ A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
+ OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
+ SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
+ LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
+ DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
+ THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
+ OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#import "PDFDisplayView_SKExtensions.h"
+#import "SKPDFView.h"
+#import "PDFAnnotation_SKExtensions.h"
+#import "SKPDFDocument.h"
+#import "SKStringConstants.h"
+#import "OBUtilities.h"
+
+
[EMAIL PROTECTED] SKAccessibilityPDFDisplayViewElement : NSObject {
+    id parent;
+}
+- (id)initWithParent:(id)aParent;
[EMAIL PROTECTED]
+
+#pragma mark -
+
[EMAIL PROTECTED] SKAccessibilityPDFAnnotationElement : NSObject {
+    PDFAnnotation *annotation;
+    SKPDFView *pdfView;
+    id parent;
+}
+- (id)initWithAnnotation:(PDFAnnotation *)anAnnotation pdfView:(SKPDFView 
*)aPdfView parent:(id)aParent;
[EMAIL PROTECTED]
+
+#pragma mark -
+
+static IMP originalAccessibilityAttributeNames = NULL;
+static IMP originalAccessibilityAttributeValue = NULL;
+static IMP originalAccessibilityHitTest = NULL;
+static IMP originalAccessibilityFocusedUIElement = NULL;
+
[EMAIL PROTECTED] PDFDisplayView (SKExtensions)
+
+static IMP originalPasswordEntered = NULL;
+
+- (void)replacementPasswordEntered:(id)sender {
+    SKPDFDocument *document = [[[self window] windowController] document];
+    originalPasswordEntered(self, _cmd, sender);
+    if ([document respondsToSelector:@selector(savePasswordInKeychain:)])
+        [document savePasswordInKeychain:[sender stringValue]];
+}
+
+#pragma mark Accessibility
+
+- (SKPDFView *)skpdfView {
+    id pdfView = nil;
+    @try { pdfView = [self valueForKey:@"pdfView"]; }
+    @catch (id exception) {}
+    return [pdfView isKindOfClass:[SKPDFView class]] ? pdfView : nil;
+}
+
+- (NSArray *)replacementAccessibilityAttributeNames {
+    if ([self skpdfView])
+        return [originalAccessibilityAttributeNames(self, _cmd) 
arrayByAddingObjectsFromArray:[NSArray 
arrayWithObjects:NSAccessibilityChildrenAttribute, 
NSAccessibilityVisibleChildrenAttribute, nil]];
+    else
+        return originalAccessibilityAttributeNames(self, _cmd);
+}
+
+- (id)replacementAccessibilityAttributeValue:(NSString *)attribute {
+    SKPDFView *pdfView = [self skpdfView];
+    if (pdfView == nil) {
+        return originalAccessibilityAttributeValue(self, _cmd, attribute);
+    } else if ([attribute isEqualToString:NSAccessibilityRoleAttribute]) {
+        return NSAccessibilityGroupRole;
+    } else if ([attribute 
isEqualToString:NSAccessibilityRoleDescriptionAttribute]) {
+        return NSAccessibilityRoleDescription(NSAccessibilityGroupRole, nil);
+    } else if ([attribute isEqualToString:NSAccessibilityChildrenAttribute]) {
+        NSMutableArray *children = [NSMutableArray array];
+        [children 
addObjectsFromArray:originalAccessibilityAttributeValue(self, _cmd, attribute)];
+        if (pdfView) {
+            [children addObject:[[[SKAccessibilityPDFDisplayViewElement alloc] 
initWithParent:self] autorelease]];
+            PDFDocument *pdfDoc = [pdfView document];
+            unsigned int i, iMax = [pdfDoc pageCount];
+            for (i = 0; i < iMax; i++) {
+                PDFPage *page = [pdfDoc pageAtIndex:i];
+                NSEnumerator *annotationEnum = [[page annotations] 
objectEnumerator];
+                PDFAnnotation *annotation;
+                while (annotation = [annotationEnum nextObject]) {
+                    if ([[annotation type] isEqualToString:SKLinkString] || 
[annotation isNoteAnnotation])
+                        [children 
addObject:[[[SKAccessibilityPDFAnnotationElement alloc] 
initWithAnnotation:annotation pdfView:pdfView parent:self] autorelease]];
+                }
+            }
+        }
+        return NSAccessibilityUnignoredChildren(children);
+    } else if ([attribute 
isEqualToString:NSAccessibilityVisibleChildrenAttribute]) {
+        NSMutableArray *children = [NSMutableArray array];
+        [children 
addObjectsFromArray:originalAccessibilityAttributeValue(self, _cmd, attribute)];
+        SKPDFView *pdfView = [self skpdfView];
+        if (pdfView) {
+            [children addObject:[[[SKAccessibilityPDFDisplayViewElement alloc] 
initWithParent:self] autorelease]];
+            PDFDocument *pdfDoc = [pdfView document];
+            NSRect visibleRect = [pdfView visibleContentRect];
+            NSRange range = [pdfView visiblePageIndexRange];
+            unsigned int i;
+            for (i = range.location; i < NSMaxRange(range); i++) {
+                PDFPage *page = [pdfDoc pageAtIndex:i];
+                NSEnumerator *annotationEnum = [[page annotations] 
objectEnumerator];
+                PDFAnnotation *annotation;
+                while (annotation = [annotationEnum nextObject]) {
+                    if ([[annotation type] isEqualToString:SKLinkString] || 
[annotation isNoteAnnotation] && 
+                        NSIntersectsRect([pdfView convertRect:[annotation 
bounds] fromPage:[annotation page]], visibleRect))
+                        [children 
addObject:[[[SKAccessibilityPDFAnnotationElement alloc] 
initWithAnnotation:annotation pdfView:pdfView parent:self] autorelease]];
+                }
+            }
+        }
+        return NSAccessibilityUnignoredChildren(children);
+    } else if ([attribute isEqualToString:NSAccessibilityFocusedAttribute]) {
+        NSNumber *focused = originalAccessibilityAttributeValue(self, _cmd, 
attribute);
+        SKPDFView *pdfView = [self skpdfView];
+        if (pdfView)
+            return [NSNumber numberWithBool:[pdfView activeAnnotation] == nil 
&& [focused boolValue]];
+        else
+            return focused;
+    } else {
+        return originalAccessibilityAttributeValue(self, _cmd, attribute);
+    }
+}
+
+- (id)replacementAccessibilityHitTest:(NSPoint)point {
+    SKPDFView *pdfView = [self skpdfView];
+    if (pdfView) {
+        NSPoint localPoint = [pdfView convertPoint:[[pdfView window] 
convertScreenToBase:point] fromView:nil];
+        PDFPage *page = [pdfView pageForPoint:localPoint nearest:NO];
+        if (page) {
+            PDFAnnotation *annotation = [page annotationAtPoint:[pdfView 
convertPoint:localPoint toPage:page]];
+            if ([[annotation type] isEqualToString:SKLinkString] || 
[annotation isNoteAnnotation]) {
+                return [[[[SKAccessibilityPDFAnnotationElement alloc] 
initWithAnnotation:annotation pdfView:pdfView parent:self] autorelease] 
accessibilityHitTest:point];
+            }
+        }
+        return [[[[SKAccessibilityPDFDisplayViewElement alloc] 
initWithParent:self] autorelease] accessibilityHitTest:point];
+    } else {
+        return originalAccessibilityHitTest(self, _cmd, point);
+    }
+}
+
+- (id)replacementAccessibilityFocusedUIElement {
+    SKPDFView *pdfView = [self skpdfView];
+    if (pdfView) {
+        PDFAnnotation *annotation = [pdfView activeAnnotation];
+        if (annotation) {
+            return 
NSAccessibilityUnignoredAncestor([[[SKAccessibilityPDFAnnotationElement alloc] 
initWithAnnotation:annotation pdfView:pdfView parent:self] autorelease]);
+        } else {
+            return 
NSAccessibilityUnignoredAncestor([[[SKAccessibilityPDFDisplayViewElement alloc] 
initWithParent:self] autorelease]);
+        }
+    } else {
+        return originalAccessibilityFocusedUIElement(self, _cmd);
+    }
+}
+
+- (BOOL)accessibilityIsIgnored {
+    return NO;
+}
+
++ (void)load {
+    if ([self instancesRespondToSelector:@selector(passwordEntered:)])
+        originalPasswordEntered = 
OBReplaceMethodImplementationWithSelector(self, @selector(passwordEntered:), 
@selector(replacementPasswordEntered:));
+    if ([self 
instancesRespondToSelector:@selector(accessibilityAttributeNames)])
+        originalAccessibilityAttributeNames = 
OBReplaceMethodImplementationWithSelector(self, 
@selector(accessibilityAttributeNames), 
@selector(replacementAccessibilityAttributeNames));
+    if ([self 
instancesRespondToSelector:@selector(accessibilityAttributeValue:)])
+        originalAccessibilityAttributeValue = 
OBReplaceMethodImplementationWithSelector(self, 
@selector(accessibilityAttributeValue:), 
@selector(replacementAccessibilityAttributeValue:));
+    if ([self instancesRespondToSelector:@selector(accessibilityHitTest:)])
+        originalAccessibilityHitTest = 
OBReplaceMethodImplementationWithSelector(self, 
@selector(accessibilityHitTest:), @selector(replacementAccessibilityHitTest:));
+    if ([self 
instancesRespondToSelector:@selector(accessibilityFocusedUIElement)])
+        originalAccessibilityFocusedUIElement = 
OBReplaceMethodImplementationWithSelector(self, 
@selector(accessibilityFocusedUIElement), 
@selector(replacementAccessibilityFocusedUIElement));
+}
+
[EMAIL PROTECTED]
+
+#pragma mark -
+
[EMAIL PROTECTED] SKAccessibilityPDFDisplayViewElement
+
+- (id)initWithParent:(id)aParent {
+    if (self = [super init]) {
+        parent = aParent;
+    }
+    return self;
+}
+
+- (BOOL)isEqual:(id)object {
+    if ([object isKindOfClass:[SKAccessibilityPDFDisplayViewElement class]]) {
+        SKAccessibilityPDFDisplayViewElement *other = 
(SKAccessibilityPDFDisplayViewElement *)object;
+        return parent == other->parent;
+    } else {
+        return NO;
+    }
+}
+
+- (unsigned int)hash {
+    return [parent hash];
+}
+
+- (NSArray *)accessibilityAttributeNames {
+    return originalAccessibilityAttributeNames(parent, _cmd);
+}
+
+- (id)accessibilityAttributeValue:(NSString *)attribute {
+    if ([attribute isEqualToString:NSAccessibilityParentAttribute]) {
+        return NSAccessibilityUnignoredAncestor(parent);
+    } else if ([attribute isEqualToString:NSAccessibilityWindowAttribute]) {
+        // We're in the same window as our parent.
+        return [NSAccessibilityUnignoredAncestor(parent) 
accessibilityAttributeValue:NSAccessibilityWindowAttribute];
+    } else if ([attribute 
isEqualToString:NSAccessibilityTopLevelUIElementAttribute]) {
+        // We're in the same top level element as our parent.
+        return [NSAccessibilityUnignoredAncestor(parent) 
accessibilityAttributeValue:NSAccessibilityTopLevelUIElementAttribute];
+    } else {
+        return originalAccessibilityAttributeValue(parent, _cmd, attribute);
+    }
+}
+
+- (BOOL)accessibilityIsAttributeSettable:(NSString *)attribute {
+    return [parent respondsToSelector:_cmd] && [parent 
accessibilityIsAttributeSettable:attribute]; 
+}
+
+- (void)accessibilitySetValue:(id)value forAttribute:(NSString *)attribute {
+    if ([parent respondsToSelector:_cmd])
+        [parent accessibilitySetValue:value forAttribute:attribute];
+}
+
+- (NSArray *)accessibilityParameterizedAttributeNames {
+    return [parent respondsToSelector:_cmd] ? [parent 
accessibilityParameterizedAttributeNames] : [NSArray array];
+}
+
+- (id)accessibilityAttributeValue:(NSString *)attribute 
forParameter:(id)parameter {
+    return [parent respondsToSelector:_cmd] ? [parent 
accessibilityAttributeValue:attribute forParameter:parameter] : nil;
+}
+
+- (BOOL)accessibilityIsIgnored {
+    return NO;
+}
+
+- (id)accessibilityHitTest:(NSPoint)point {
+    return NSAccessibilityUnignoredAncestor(self);
+}
+
+- (id)accessibilityFocusedUIElement {
+    return NSAccessibilityUnignoredAncestor(self);
+}
+
+- (NSArray *)accessibilityActionNames {
+    return [parent respondsToSelector:_cmd] ? [parent 
accessibilityActionNames] : [NSArray array];
+}
+
+- (NSString *)accessibilityActionDescription:(NSString *)anAction {
+    return [parent respondsToSelector:_cmd] ? [parent 
accessibilityActionDescription:anAction] : 
NSAccessibilityActionDescription(anAction);
+}
+
+- (void)accessibilityPerformAction:(NSString *)anAction {
+    if ([parent respondsToSelector:_cmd])
+        [parent accessibilityPerformAction:anAction];
+}
+
[EMAIL PROTECTED]
+
+#pragma mark -
+
[EMAIL PROTECTED] SKAccessibilityPDFAnnotationElement
+
+- (id)initWithAnnotation:(PDFAnnotation *)anAnnotation pdfView:(SKPDFView 
*)aPdfView parent:(id)aParent {
+    if (self = [super init]) {
+        annotation = anAnnotation;
+        pdfView = aPdfView;
+        parent = aParent;
+    }
+    return self;
+}
+
+- (BOOL)isEqual:(id)object {
+    if ([object isKindOfClass:[SKAccessibilityPDFAnnotationElement class]]) {
+        SKAccessibilityPDFAnnotationElement *other = 
(SKAccessibilityPDFAnnotationElement *)object;
+        return annotation == other->annotation && pdfView == other->pdfView;
+    } else {
+        return NO;
+    }
+}
+
+- (unsigned int)hash {
+    return [annotation hash] + [pdfView hash];
+}
+
+- (NSArray *)accessibilityAttributeNames {
+    static NSArray *attributes = nil;
+    if (attributes == nil) {
+       attributes = [[NSArray alloc] initWithObjects:
+           NSAccessibilityRoleAttribute,
+           NSAccessibilityRoleDescriptionAttribute,
+        NSAccessibilityTitleAttribute,
+        NSAccessibilityValueAttribute,
+           NSAccessibilityParentAttribute,
+           NSAccessibilityWindowAttribute,
+           NSAccessibilityTopLevelUIElementAttribute,
+           NSAccessibilityFocusedAttribute,
+           NSAccessibilityEnabledAttribute,
+        NSAccessibilityPositionAttribute,
+        NSAccessibilitySizeAttribute,
+           nil];
+    }
+    return attributes;
+}
+
+- (id)accessibilityAttributeValue:(NSString *)attribute {
+    if ([attribute isEqualToString:NSAccessibilityRoleAttribute]) {
+        return [annotation accessibilityRoleAttribute];
+    } else if ([attribute 
isEqualToString:NSAccessibilityRoleDescriptionAttribute]) {
+        return [annotation accessibilityRoleDescriptionAttribute];
+    } else if ([attribute isEqualToString:NSAccessibilityValueAttribute]) {
+        return [annotation accessibilityValueAttribute];
+    } else if ([attribute isEqualToString:NSAccessibilityTitleAttribute]) {
+        return [annotation accessibilityTitleAttribute];
+    } else if ([attribute 
isEqualToString:NSAccessibilitySelectedTextAttribute]) {
+        return [annotation accessibilitySelectedTextAttribute];
+    } else if ([attribute 
isEqualToString:NSAccessibilitySelectedTextRangeAttribute]) {
+        return [annotation accessibilitySelectedTextRangeAttribute];
+    } else if ([attribute 
isEqualToString:NSAccessibilityNumberOfCharactersAttribute]) {
+        return [annotation accessibilityNumberOfCharactersAttribute];
+    } else if ([attribute 
isEqualToString:NSAccessibilityVisibleCharacterRangeAttribute]) {
+        return [annotation accessibilityVisibleCharacterRangeAttribute];
+    } else if ([attribute isEqualToString:NSAccessibilityParentAttribute]) {
+        return NSAccessibilityUnignoredAncestor(parent);
+    } else if ([attribute isEqualToString:NSAccessibilityWindowAttribute]) {
+        // We're in the same window as our parent.
+        return [NSAccessibilityUnignoredAncestor(parent) 
accessibilityAttributeValue:NSAccessibilityWindowAttribute];
+    } else if ([attribute 
isEqualToString:NSAccessibilityTopLevelUIElementAttribute]) {
+        // We're in the same top level element as our parent.
+        return [NSAccessibilityUnignoredAncestor(parent) 
accessibilityAttributeValue:NSAccessibilityTopLevelUIElementAttribute];
+    } else if ([attribute isEqualToString:NSAccessibilityFocusedAttribute]) {
+        return [NSNumber numberWithBool:[pdfView activeAnnotation] == 
annotation];
+    } else if ([attribute isEqualToString:NSAccessibilityEnabledAttribute]) {
+        return [NSNumber numberWithBool:NO];
+    } else if ([attribute isEqualToString:NSAccessibilityPositionAttribute]) {
+        NSRect rect = [pdfView convertRect:[annotation bounds] 
fromPage:[annotation page]];
+        return [NSValue valueWithPoint:[[pdfView window] 
convertBaseToScreen:[pdfView convertPoint:rect.origin toView:nil]]];
+    } else if ([attribute isEqualToString:NSAccessibilitySizeAttribute]) {
+        NSRect rect = [pdfView convertRect:[annotation bounds] 
fromPage:[annotation page]];
+        return [NSValue valueWithSize:[pdfView convertSize:rect.size 
toView:nil]];
+    } else {
+        return nil;
+    }
+}
+
+- (BOOL)accessibilityIsAttributeSettable:(NSString *)attribute {
+    return [attribute isEqualToString:NSAccessibilityFocusedAttribute]; 
+}
+
+- (void)accessibilitySetValue:(id)value forAttribute:(NSString *)attribute {
+    if ([attribute isEqualToString:NSAccessibilityFocusedAttribute]) {
+        if ([value boolValue])
+            [pdfView setActiveAnnotation:annotation];
+        else if ([pdfView activeAnnotation] == annotation)
+            [pdfView setActiveAnnotation:nil];
+    }
+}
+
+- (BOOL)accessibilityIsIgnored {
+    return NO;
+}
+
+- (id)accessibilityHitTest:(NSPoint)point {
+    return NSAccessibilityUnignoredAncestor(self);
+}
+
+- (id)accessibilityFocusedUIElement {
+    return NSAccessibilityUnignoredAncestor(self);
+}
+
+- (NSArray *)accessibilityActionNames {
+    if ([[annotation type] isEqualToString:SKLinkString] || [annotation 
isEditable])
+        return [NSArray arrayWithObject:NSAccessibilityPressAction];
+    else
+        return [NSArray array];
+}
+
+- (NSString *)accessibilityActionDescription:(NSString *)anAction {
+    return NSAccessibilityActionDescription(anAction);
+}
+
+- (void)accessibilityPerformAction:(NSString *)anAction {
+    if ([anAction isEqualToString:NSAccessibilityPressAction]) {
+        if ([pdfView activeAnnotation] != annotation)
+            [pdfView setActiveAnnotation:annotation];
+        [pdfView editActiveAnnotation:self];
+    }
+}
+
[EMAIL PROTECTED]

Modified: trunk/SKPDFView.h
===================================================================
--- trunk/SKPDFView.h   2008-04-20 23:54:10 UTC (rev 3780)
+++ trunk/SKPDFView.h   2008-04-21 23:41:33 UTC (rev 3781)
@@ -187,6 +187,9 @@
 - (void)resetHoverRects;
 - (void)removeHoverRects;
 
+- (NSRange)visiblePageIndexRange;
+- (NSRect)visibleContentRect;
+
 - (NSUndoManager *)undoManager;
 
 @end

Modified: trunk/SKPDFView.m
===================================================================
--- trunk/SKPDFView.m   2008-04-20 23:54:10 UTC (rev 3780)
+++ trunk/SKPDFView.m   2008-04-21 23:41:33 UTC (rev 3781)
@@ -116,9 +116,6 @@
 
 @interface SKPDFView (Private)
 
-- (NSRange)visiblePageIndexRange;
-- (NSRect)visibleContentRect;
-
 - (void)transformCGContext:(CGContextRef)context forPage:(PDFPage *)page;
 
 - (void)autohideTimerFired:(NSTimer *)aTimer;
@@ -527,8 +524,10 @@
                activeAnnotation = nil;
        }
        
-       if (changed)
+       if (changed) {
                [[NSNotificationCenter defaultCenter] 
postNotificationName:SKPDFViewActiveAnnotationDidChangeNotification object:self 
userInfo:nil];
+        NSAccessibilityPostNotification(NSAccessibilityUnignoredAncestor([self 
documentView]), NSAccessibilityFocusedUIElementChangedNotification);
+    }
 }
 
 - (BOOL)isEditing {
@@ -943,6 +942,9 @@
         } else if (([self toolMode] == SKTextToolMode || [self toolMode] == 
SKNoteToolMode) && 
                    (eventChar == NSTabCharacter) && (modifiers == 
NSAlternateKeyMask)) {
             [self selectNextActiveAnnotation:self];
+        } else if (([self toolMode] == SKTextToolMode || [self toolMode] == 
SKNoteToolMode) && 
+                   (eventChar == 0x1B) && (modifiers == NSAlternateKeyMask)) {
+            [self setActiveAnnotation:nil];
         // backtab is a bit inconsistent, it seems Shift+Tab gives a 
Shift-BackTab key event, I would have expected either Shift-Tab (as for the raw 
event) or BackTab (as for most shift-modified keys)
         } else if (([self toolMode] == SKTextToolMode || [self toolMode] == 
SKNoteToolMode) && 
                    (((eventChar == NSBackTabCharacter) && ((modifiers & 
~NSShiftKeyMask) == NSAlternateKeyMask)) || 
@@ -2241,12 +2243,6 @@
     }
 }
 
[EMAIL PROTECTED]
-
-#pragma mark -
-
[EMAIL PROTECTED] SKPDFView (Private)
-
 - (void)transformCGContext:(CGContextRef)context forPage:(PDFPage *)page {
     NSRect boxRect = [page boundsForBox:[self displayBox]];
     
@@ -3931,30 +3927,3 @@
     SKCGContextDrawGrabHandle(context, CGPointMake(CGRectGetMaxX(rect), 
CGRectGetMaxY(rect)), radius, mask == (BDSKMaxXEdgeMask | BDSKMaxYEdgeMask));
     SKCGContextDrawGrabHandle(context, CGPointMake(CGRectGetMaxX(rect), 
CGRectGetMinY(rect)), radius, mask == (BDSKMaxXEdgeMask | BDSKMinYEdgeMask));
 }
-
-#pragma mark -
-
[EMAIL PROTECTED] PDFDisplayView : NSView
-- (void)passwordEntered:(id)sender;
[EMAIL PROTECTED]
-
[EMAIL PROTECTED] PDFDisplayView (SKExtensions)
[EMAIL PROTECTED]
-
[EMAIL PROTECTED] PDFDisplayView (SKExtensions)
-
-static IMP originalPasswordEntered = NULL;
-
-- (void)replacementPasswordEntered:(id)sender {
-    SKPDFDocument *document = [[[self window] windowController] document];
-    originalPasswordEntered(self, _cmd, sender);
-    if ([document respondsToSelector:@selector(savePasswordInKeychain:)])
-        [document savePasswordInKeychain:[sender stringValue]];
-}
-
-+ (void)load {
-    if ([self instancesRespondToSelector:@selector(passwordEntered:)])
-        originalPasswordEntered = 
OBReplaceMethodImplementationWithSelector(self, @selector(passwordEntered:), 
@selector(replacementPasswordEntered:));
-}
-
[EMAIL PROTECTED]

Modified: trunk/Skim.xcodeproj/project.pbxproj
===================================================================
--- trunk/Skim.xcodeproj/project.pbxproj        2008-04-20 23:54:10 UTC (rev 
3780)
+++ trunk/Skim.xcodeproj/project.pbxproj        2008-04-21 23:41:33 UTC (rev 
3781)
@@ -194,6 +194,7 @@
                CECF61FF0DB258D600587D96 /* SKFontWell.m in Sources */ = {isa = 
PBXBuildFile; fileRef = CECF61FE0DB258D600587D96 /* SKFontWell.m */; };
                CEE106150BCBB72C00BF2D3E /* SKNotesDocument.m in Sources */ = 
{isa = PBXBuildFile; fileRef = CEE106140BCBB72C00BF2D3E /* SKNotesDocument.m 
*/; };
                CEE1065E0BCBBE1300BF2D3E /* NotesDocument.nib in Resources */ = 
{isa = PBXBuildFile; fileRef = CEE106580BCBBE1200BF2D3E /* NotesDocument.nib 
*/; };
+               CEE176E40DBD5B0C00E6C317 /* PDFDisplayView_SKExtensions.m in 
Sources */ = {isa = PBXBuildFile; fileRef = CEE176E30DBD5B0C00E6C317 /* 
PDFDisplayView_SKExtensions.m */; };
                CEE229390BFB7CE9002B746B /* ReleaseNotes.rtf in Resources */ = 
{isa = PBXBuildFile; fileRef = CE54AA8E0BBC037400008750 /* ReleaseNotes.rtf */; 
};
                CEE22EA30BFB8672002B746B /* displayline in CopyFiles */ = {isa 
= PBXBuildFile; fileRef = CE1E2F120BDB86A10011D9DD /* displayline */; };
                CEE22EA40BFB8684002B746B /* skimnotes in CopyFiles */ = {isa = 
PBXBuildFile; fileRef = CEF3BF750B99CA2900E12E3D /* skimnotes */; };
@@ -811,6 +812,8 @@
                CEE106590BCBBE1200BF2D3E /* English */ = {isa = 
PBXFileReference; lastKnownFileType = wrapper.nib; name = English; path = 
English.lproj/NotesDocument.nib; sourceTree = "<group>"; };
                CEE107380BCBCA3200BF2D3E /* Dutch */ = {isa = PBXFileReference; 
lastKnownFileType = wrapper.nib; name = Dutch; path = 
Dutch.lproj/NotesDocument.nib; sourceTree = "<group>"; };
                CEE11EF50BCC262800BF2D3E /* Italian */ = {isa = 
PBXFileReference; lastKnownFileType = wrapper.nib; name = Italian; path = 
Italian.lproj/NotesDocument.nib; sourceTree = "<group>"; };
+               CEE176E20DBD5B0C00E6C317 /* PDFDisplayView_SKExtensions.h */ = 
{isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; 
path = PDFDisplayView_SKExtensions.h; sourceTree = "<group>"; };
+               CEE176E30DBD5B0C00E6C317 /* PDFDisplayView_SKExtensions.m */ = 
{isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = 
sourcecode.c.objc; path = PDFDisplayView_SKExtensions.m; sourceTree = 
"<group>"; };
                CEE54D170DA2AA050037169F /* cs */ = {isa = PBXFileReference; 
lastKnownFileType = wrapper.nib; name = cs; path = cs.lproj/InfoWindow.nib; 
sourceTree = "<group>"; };
                CEE54D190DA2AA100037169F /* cs */ = {isa = PBXFileReference; 
lastKnownFileType = wrapper.nib; name = cs; path = cs.lproj/MainMenu.nib; 
sourceTree = "<group>"; };
                CEE54D1A0DA2AA1F0037169F /* cs */ = {isa = PBXFileReference; 
lastKnownFileType = wrapper.nib; name = cs; path = cs.lproj/MainWindow.nib; 
sourceTree = "<group>"; };
@@ -1130,6 +1133,8 @@
                                CEE54D870DA2E37B0037169F /* 
PDFAnnotation_SKExtensions.m */,
                                CEE54DC60DA2EAE00037169F /* 
PDFBorder_SKExtensions.h */,
                                CEE54DC70DA2EAE00037169F /* 
PDFBorder_SKExtensions.m */,
+                               CEE176E20DBD5B0C00E6C317 /* 
PDFDisplayView_SKExtensions.h */,
+                               CEE176E30DBD5B0C00E6C317 /* 
PDFDisplayView_SKExtensions.m */,
                                CE6DC7B90D689138003A072F /* 
PDFDocument_SKExtensions.h */,
                                CE6DC7BA0D689138003A072F /* 
PDFDocument_SKExtensions.m */,
                                CE2DE50B0B85DC4000D0DA12 /* 
PDFPage_SKExtensions.h */,
@@ -2013,6 +2018,7 @@
                                CE0859D20DAE912500760AFC /* 
SKSnapshotPageCell.m in Sources */,
                                CECF61FF0DB258D600587D96 /* SKFontWell.m in 
Sources */,
                                CE80666F0DB910610078D118 /* 
SKSnapshotContentView.m in Sources */,
+                               CEE176E40DBD5B0C00E6C317 /* 
PDFDisplayView_SKExtensions.m in Sources */,
                        );
                        runOnlyForDeploymentPostprocessing = 0;
                };


This was sent by the SourceForge.net collaborative development platform, the 
world's largest Open Source development site.

-------------------------------------------------------------------------
This SF.net email is sponsored by the 2008 JavaOne(SM) Conference 
Don't miss this year's exciting event. There's still time to save $100. 
Use priority code J8TL2D2. 
http://ad.doubleclick.net/clk;198757673;13503038;p?http://java.sun.com/javaone
_______________________________________________
Skim-app-commit mailing list
[email protected]
https://lists.sourceforge.net/lists/listinfo/skim-app-commit

Reply via email to