Skip to content

Report comments in MS Word with UIA enabled#9631

Merged
michaelDCurran merged 24 commits into
nvaccess:masterfrom
jakubl7545:i9285
Feb 3, 2021
Merged

Report comments in MS Word with UIA enabled#9631
michaelDCurran merged 24 commits into
nvaccess:masterfrom
jakubl7545:i9285

Conversation

@jakubl7545

Copy link
Copy Markdown
Contributor

Link to issue number:

closes #9285

Summary of the issue:

With UIA enabled it is impossible to read comments. This is because comments ar filtered by its name which appeared to be different across languages.
Also when there are more than 13 comments dates can't be retrieved because don't fit on the screen.

Description of how this pull request fixes the issue:

Instead of name comments are filtered by its role and AnnotationsPattern.
In situations when date is not on the screen only comment itself and author are reported.

Testing performed:

Tested with NVDA running from source with word document which has comments like the attached one.

Known issues with pull request:

None

Change log entry:

Section: Bug fixes
It is now possible to read comments in MS Word with UIA enabled.
test.docx

@zstanecic

zstanecic commented May 28, 2019 via email

Copy link
Copy Markdown
Contributor

@lukaszgo1

Copy link
Copy Markdown
Contributor

@LeonarddeR LeonarddeR left a comment

Copy link
Copy Markdown
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I haven't tested this myself, but here are some comments based on just reading the code.

Comment thread source/NVDAObjects/UIA/wordDocument.py Outdated
UIAElement=UIAElement.buildUpdatedCache(UIAHandler.handler.baseCacheRequest)
obj=UIA(UIAElement=UIAElement)
if not obj.parent or obj.parent.name!='Comment':
if (obj.parent.role !=controlTypes.ROLE_GROUPING and not

Copy link
Copy Markdown
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Why did you remove the ``if not obj.parent` here? This breaks if the object has no parent.

Copy link
Copy Markdown
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I focused on replacing obj.name and missed it. Thanks for pointing this.

Comment thread source/NVDAObjects/UIA/wordDocument.py Outdated
if not obj.parent or obj.parent.name!='Comment':
if (obj.parent.role !=controlTypes.ROLE_GROUPING and not
obj.parent.UIAElement.getCurrentPropertyValue(UIAHandler.UIA_IsAnnotationPatternAvailablePropertyId)):
continue

Copy link
Copy Markdown
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I think it would be good to have some documentation about how you came up with the if clause above.

Copy link
Copy Markdown
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

First I wanted to replace obj.name with something which doesn't change and decided for role which is grouping. In case it would be not enough I checked developer info for that object and discovered that comments have AnnotationPattern which may be significant for them. Then I found UIAElement.getCurrentPropertyValue checks for its presence. It requires one parameter which is propertyId. For AnnotationPattern it is 30118 but I didn't want to use that as itself it means nothing. Thats why as a parameter I used UIAHandler.UIA_IsAnnotationPatternAvailablePropertyId which provides that Id.
Thats how the process of creating looked like but I don't know how much of it should be documented. Maybe you have some ideas.

Copy link
Copy Markdown
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I think it is ok as it is. Thanks for providing the details here. Leaving this treat unresolved until @michaelDCurran or someone else has looked at it.

Comment thread source/NVDAObjects/UIA/wordDocument.py Outdated
comment=obj.makeTextInfo(textInfos.POSITION_ALL).text
dateObj=obj.previous
date=dateObj.name
if not dateObj.previous:

@LeonarddeR LeonarddeR May 28, 2019

Copy link
Copy Markdown
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I think that it is more readable if you check obj.previous.previous first. Now, you are assigning an object to the dateObj variable and then, when it doesn't seem to be a dateObj, you're assigning the same object to authorObj.

For example:

		comment=obj.makeTextInfo(textInfos.POSITION_ALL).text
		tempObj = obj.previous.previous
		authorObj = tempObj or obj.previous
		author =authorObj.name
		if not tempObj:
			return dict(comment=comment,author=author)
		dateObj=obj.previous
		date=dateObj.name
		return dict(comment=comment,author=author,date=date)

Comment thread source/NVDAObjects/UIA/wordDocument.py Outdated
@property
def label(self):
commentInfo=getCommentInfoFromPosition(self.textInfo)
if len(commentInfo) ==2:

Copy link
Copy Markdown
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Suggested change
if len(commentInfo) ==2:
if "date" not in commentInfo:

Comment thread source/NVDAObjects/UIA/wordDocument.py Outdated
# Microsoft Word duplicates the full title of the document on this control, which is redundant as it appears in the title of the app itself.
name=u""

@script(gesture ="kb:NVDA+alt+c")

Copy link
Copy Markdown
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

This lacks the description. Please reuse the description for the script for the object model implementation of Word.

Suggested change
@script(gesture ="kb:NVDA+alt+c")
@script(
gesture="kb:NVDA+alt+c",
# Translators: a description for a script that reports the comment at the caret.
description=_("Reports the text of the comment where the System caret is located.")
)

Comment thread source/NVDAObjects/UIA/wordDocument.py Outdated
@@ -334,17 +345,20 @@ def script_reportCurrentComment(self,gesture):
UIAElement=UIAElementArray.getElement(index)

Copy link
Copy Markdown
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

It really amazes me that this is not calling getCommentInfoFromPosition. Could you please change this in such a way that it uses that function and speaks a message based on what is in the dictionary? I think it is even possible to abstract this further and pas the result of CommentUIATextInfoQuickNavItem.label to ui.message.

If this sounds too complex, I"m happy to take this for you.

Copy link
Copy Markdown
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

It works with getCommentInfoFromPosition but when I tried CommentUIATextInfoQuickNavItem.label I got its adress in a memory or "Property object is not callable" error.

Copy link
Copy Markdown
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I think it would be best to create a new _getPresentableCommentInfoFromPosition function that returns the label. Ten, you can make the label property return what that helper function returns for the particular textInfo, and same for the script.

Does that clear things up for you?

Copy link
Copy Markdown
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I hope I understood you well. If so, should this new function has its doc string?
I also added a message for no comments in script.

@zstanecic

zstanecic commented Jun 4, 2019 via email

Copy link
Copy Markdown
Contributor

@jakubl7545

Copy link
Copy Markdown
Contributor Author

@LeonarddeR Could you have another look on that?

@LeonarddeR

Copy link
Copy Markdown
Collaborator

@jakubl7545: Could you merge current master into this?

@jakubl7545

Copy link
Copy Markdown
Contributor Author

@LeonarddeR: done.

@LeonarddeR

Copy link
Copy Markdown
Collaborator

@jakubl7545 I'm sorry that it took me some time to come back to this. Could you plase merge master again and run scons lint base=origin/master to make sure this doesn't introduce linting errors?

@AppVeyorBot

This comment has been minimized.

@AppVeyorBot

This comment has been minimized.

@jakubl7545

Copy link
Copy Markdown
Contributor Author

@LeonarddeR It's done. Sorry for such a long delay.

LeonarddeR
LeonarddeR previously approved these changes Oct 18, 2019

@LeonarddeR LeonarddeR left a comment

Copy link
Copy Markdown
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Thanks @jakubl7545 , looks good

@jakubl7545

Copy link
Copy Markdown
Contributor Author

@michaelDCurran Would it be possible to merge this PR into 2019.3? It passed a review from @LeonarddeR so I think it's ready.

@codeofdusk

Copy link
Copy Markdown
Contributor

Any updates on this PR? CC @michaelDCurran.

@lukaszgo1

Copy link
Copy Markdown
Contributor

This has been reported several times and it looks like this PR is just awaiting review. @michaelDCurran Do you intent to look at this one?

@michaelDCurran

michaelDCurran commented Nov 16, 2020 via email

Copy link
Copy Markdown
Member

@cary-rowen

Copy link
Copy Markdown
Contributor

What is the latest news of this PR and is it possible to be merged in 2020.4?
Thanks.

@lukaszgo1

Copy link
Copy Markdown
Contributor

@michaelDCurran Ping. This has been asked about again in #11989

@cary-rowen

Copy link
Copy Markdown
Contributor

@michaelDCurran Can you review this

@michaelDCurran

Copy link
Copy Markdown
Member

This is not reporting comments for me in MS Word build 16.0.13707 nor has it been for many months. Can someone else confirm that this code still works in Microsoft Word for them? We need to also work out what MS Word version this broke in, and perhaps try and come up with a solution that works for both.

@michaelDCurran

michaelDCurran commented Jan 15, 2021

Copy link
Copy Markdown
Member

This pr does not work for me with Microsoft Word build 16.0.13707, nor has it worked with builds of MS Word that I have had for some months now. I am right now looking into how we can make this code more robust. At very least, as the annotation pattern is available, we can actually use that pattern to get the needed info directly now.

@michaelDCurran

michaelDCurran commented Jan 15, 2021

Copy link
Copy Markdown
Member

Here is an updated copy of getCommentInfoFromPosition which uses annotation properties directly, and does not need to walk as many objects. This code works on my 16.0.13707 build of MS Word:

def getCommentInfoFromPosition(position):
	"""
	Fetches information about the comment located at the given position in a word document.
	@param position: a TextInfo representing the span of the comment in the word document.
	@type L{TextInfo}
	@return: A dictionary containing keys of comment, author and date
	@rtype: dict
	"""
	val=position._rangeObj.getAttributeValue(UIAHandler.UIA_AnnotationObjectsAttributeId)
	if not val:
		return
	try:
		UIAElementArray=val.QueryInterface(UIAHandler.IUIAutomationElementArray)
	except COMError:
		return
	for index in range(UIAElementArray.length):
		UIAElement=UIAElementArray.getElement(index)
		UIAElement=UIAElement.buildUpdatedCache(UIAHandler.handler.baseCacheRequest)
		typeID = UIAElement.GetCurrentPropertyValue(UIAHandler.UIA_AnnotationAnnotationTypeIdPropertyId)
		if typeID == UIAHandler.AnnotationType_Comment:
			comment = UIAElement.GetCurrentPropertyValue(UIAHandler.UIA_NamePropertyId)
			author = UIAElement.GetCurrentPropertyValue(UIAHandler.UIA_AnnotationAuthorPropertyId)
			date = UIAElement.GetCurrentPropertyValue(UIAHandler.UIA_AnnotationDateTimePropertyId)
			return dict(comment=comment,author=author,date=date)

However, as MS Word now supports comment threads, much of the time, the comment reported will just be "comment thread started by Michael Curran" or similar. Users should really now start viewing comments in the comment thread pain.

@jakubl7545

Copy link
Copy Markdown
Contributor Author

Can someone else confirm that this code still works in Microsoft Word for them

@michaelDCurran Yes, it works for me in MSO (16.0.13530.20368). It reads comment itself, author and date exactly as it should.

@cary-rowen

Copy link
Copy Markdown
Contributor

It works fine for me: Microsoft 365 MSO (16.0.13530.20132) 64 Bit
@michaelDCurran

@AppVeyorBot

Copy link
Copy Markdown

See test results for failed build of commit 52eb987190

@jakubl7545

Copy link
Copy Markdown
Contributor Author

@michaelDCurran I've tried your code but it didn't work. Probably because AnnotationType_Comment is not available. Only AnnotationType_Unknown is returned. So I've combined both approaches to ensure that comments are read in different versions of Office. Could you check if it works for you now?

@michaelDCurran

Copy link
Copy Markdown
Member

@jakubl7545 Yes, this is working for me. Thanks for your work on this.

@michaelDCurran

Copy link
Copy Markdown
Member

@jakubl7545 I think there may be one or more review actions from @feerrenrut before he can also approve?

@feerrenrut feerrenrut left a comment

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

All changes addressed

@michaelDCurran michaelDCurran merged commit 8f31bdc into nvaccess:master Feb 3, 2021
@nvaccessAuto nvaccessAuto added this to the 2021.1 milestone Feb 3, 2021
@cary-rowen

Copy link
Copy Markdown
Contributor

In version Microsoft 365 MSO (16.0.14228.20200) 64-bit the pr reported an incorrect comment:
When I moved the cursor to the position containing the comment and pressed NVDA + Alt + C, NVDA reported the following:
"Comment: Resolved Comment Hint Button by Rowen Cary on 25 minutes ago"
According to the above, the content of the comment is: "Resolved Comment Hint" This is wrong and not the actual comment I wrote.
When I turned off the UIA mode in Word, everything returned to normal.
My language is Simplified Chinese, but I installed the English version of Office and can also reproduce this problem.

@feerrenrut
@michaelDCurran

@lukaszgo1

Copy link
Copy Markdown
Contributor

@cary-rowen Please create a new issue for this and preferably attach a sample document reproducing the problem.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Projects

None yet

Development

Successfully merging this pull request may close these issues.

Word 2016-365 installed with non-English language, with UIA is enabled, comments cannot be read