'From Squeak3.1alpha of 28 February 2001 [latest update: #4193] on 12 July 2001 at 6:24:17 pm'! "Change Set: masterComment-sw Date: 12 July 2001 Author: Scott Wallace Adds a way to find the supermost implementor of a method that *has* a precode comment and to return that supermost precode comment, and adds a new kind of annotation, called #masterComment, that reports such a comment. This provides a mechanism for standardized protocol documentation. Previous work has fallen back on a *nearby* super-comment, and only as a bail-out; with the approach here, the supermost comment for any given selector is given primacy."! !Behavior methodsFor: 'accessing method dictionary' stamp: 'sw 6/28/2001 12:37'! supermostPrecodeCommentFor: selector "Answer a string representing the precode comment in the most distant superclass's implementation of the selector. Return nil if none found." | aSuper superComment | (self == Behavior or: [superclass == nil or: [(aSuper _ superclass classThatUnderstands: selector) == nil]]) ifFalse: "There is a super implementor" [superComment _ aSuper supermostPrecodeCommentFor: selector]. ^ superComment ifNil: [self firstPrecodeCommentFor: selector] "ActorState supermostPrecodeCommentFor: #printOn:"! ! !CodeHolder methodsFor: 'annotation' stamp: 'sw 7/12/2001 18:18'! annotationForSelector: aSelector ofClass: aClass "Provide a line of content for an annotation pane, representing information about the given selector and class" | stamp sendersCount implementorsCount aCategory separator aString aList aComment aStream requestList | aStream _ ReadWriteStream on: ''. requestList _ self annotationRequests. separator _ requestList size > 1 ifTrue: [self annotationSeparator] ifFalse: ['']. requestList do: [:aRequest | aRequest == #firstComment ifTrue: [aComment _ aClass firstCommentAt: aSelector. aComment isEmptyOrNil ifFalse: [aStream nextPutAll: aComment, separator]]. aRequest == #masterComment ifTrue: [aComment _ aClass supermostPrecodeCommentFor: aSelector. aComment isEmptyOrNil ifFalse: [aStream nextPutAll: aComment, separator]]. aRequest == #documentation ifTrue: [aComment _ aClass precodeCommentOrInheritedCommentFor: aSelector. aComment isEmptyOrNil ifFalse: [aStream nextPutAll: aComment, separator]]. aRequest == #timeStamp ifTrue: [stamp _ self timeStamp. aStream nextPutAll: (stamp size > 0 ifTrue: [stamp, separator] ifFalse: ['no timeStamp', separator])]. aRequest == #messageCategory ifTrue: [aCategory _ aClass organization categoryOfElement: aSelector. aCategory ifNotNil: "woud be nil for a method no longer present, e.g. in a recent-submissions browser" [aStream nextPutAll: aCategory, separator]]. aRequest == #sendersCount ifTrue: [sendersCount _ (Smalltalk allCallsOn: aSelector) size. sendersCount _ sendersCount == 1 ifTrue: ['1 sender'] ifFalse: [sendersCount printString, ' senders']. aStream nextPutAll: sendersCount, separator]. aRequest == #implementorsCount ifTrue: [implementorsCount _ Smalltalk numberOfImplementorsOf: aSelector. implementorsCount _ implementorsCount == 1 ifTrue: ['1 implementor'] ifFalse: [implementorsCount printString, ' implementors']. aStream nextPutAll: implementorsCount, separator]. aRequest == #priorVersionsCount ifTrue: [self addPriorVersionsCountForSelector: aSelector ofClass: aClass to: aStream]. aRequest == #priorTimeStamp ifTrue: [stamp _ VersionsBrowser timeStampFor: aSelector class: aClass reverseOrdinal: 2. stamp ifNotNil: [aStream nextPutAll: 'prior time stamp: ', stamp, separator]]. aRequest == #recentChangeSet ifTrue: [aString _ ChangeSorter mostRecentChangeSetWithChangeForClass: aClass selector: aSelector. aString size > 0 ifTrue: [aStream nextPutAll: aString, separator]]. aRequest == #allChangeSets ifTrue: [aList _ ChangeSorter allChangeSetsWithClass: aClass selector: aSelector. aList size > 0 ifTrue: [aList size = 1 ifTrue: [aStream nextPutAll: 'only in change set '] ifFalse: [aStream nextPutAll: 'in change sets: ']. aList do: [:aChangeSet | aStream nextPutAll: aChangeSet name, ' ']] ifFalse: [aStream nextPutAll: 'in no change set']. aStream nextPutAll: separator]]. ^ aStream contents! ! !Preferences class methodsFor: 'parameters' stamp: 'sw 7/12/2001 18:18'! annotationInfo "Answer a list of pairs characterizing all the available kinds of annotations; in each pair, the first element is a symbol representing the info type, and the second element is a string providing the corresponding balloon help" ^ #( (timeStamp 'The time stamp of the last submission of the method.') (firstComment 'The first comment in the method, if any.') (masterComment 'The comment at the beginning of the supermost implementor of the method if any.') (documentation 'Comment at beginning of the method or, if it has none, comment at the beginning of a superclass''s implementation of the method') (messageCategory 'Which method category the method lies in') (sendersCount 'A report of how many senders there of the message.') (implementorsCount 'A report of how many implementors there are of the message.') (recentChangeSet 'The most recent change set bearing the method.') (allChangeSets 'A list of all change sets bearing the method.') (priorVersionsCount 'A report of how many previous versions there are of the method' ) (priorTimeStamp 'The time stamp of the penultimate submission of the method, if any'))! !