[Cuis-dev] Morphic-Widget repo (ExamplesBrowser)
Mariano Montone
marianomontone at gmail.com
Sat Dec 11 08:51:09 PST 2021
El 11/12/21 a las 08:49, Mariano Montone escribió:
> What I'd be interested in implementing is a widgets browser, a tool that
> lets you select a widget from a list and opens several examples of how
> the widget is used and how it looks.
I've started an implementation of this :)
Demo:
https://drive.google.com/file/d/1bDs9IH85VNRdYovbMxO4e2XqDCMn8sY-/view?usp=sharing
All system methods that contain examples are collected, so the tool is
useful for any kind of examples, not only for Morphs.
I attach the current implementation in case someone wants to give it a try.
I'm still thinking about the best way of displaying an example; the
class method source is displayed for now, but that may change.
Cheers,
Mariano
-------------- next part --------------
'From Cuis 5.0 [latest update: #4999] on 11 December 2021 at 1:33:29 pm'!
'Description '!
!provides: 'ExamplesBrowser' 1 11!
SystemOrganization addCategory: 'ExamplesBrowser'!
!classDefinition: #ExamplesBrowserWindow category: 'ExamplesBrowser'!
SystemWindow subclass: #ExamplesBrowserWindow
instanceVariableNames: ''
classVariableNames: ''
poolDictionaries: ''
category: 'ExamplesBrowser'!
!classDefinition: 'ExamplesBrowserWindow class' category: 'ExamplesBrowser'!
ExamplesBrowserWindow class
instanceVariableNames: ''!
!classDefinition: #ExamplesBrowser category: 'ExamplesBrowser'!
Object subclass: #ExamplesBrowser
instanceVariableNames: 'examples categoriesIndex subCategoriesIndex examplesListIndex subCategoriesList examplesList categoriesList'
classVariableNames: ''
poolDictionaries: ''
category: 'ExamplesBrowser'!
!classDefinition: 'ExamplesBrowser class' category: 'ExamplesBrowser'!
ExamplesBrowser class
instanceVariableNames: ''!
!ExamplesBrowserWindow methodsFor: 'as yet unclassified' stamp: 'MM 12/11/2021 12:05:09'!
buildMorphicWindow
| navigationLayout categoriesList subCategoriesList examplesList content buttons docsMorph |
navigationLayout _ LayoutMorph newColumn.
categoriesList _ PluggableListMorph model: model
listGetter: #examplesCategories
indexGetter: #examplesCategoriesIndex
indexSetter: #examplesCategoriesIndex:.
subCategoriesList _ PluggableListMorph model: model
listGetter: #examplesSubCategories
indexGetter: #examplesSubCategoriesIndex
indexSetter: #examplesSubCategoriesIndex:.
examplesList _ PluggableListMorph model: model
listGetter: #examplesList
indexGetter: #examplesListIndex
indexSetter: #examplesListIndex:.
navigationLayout
addMorph: categoriesList proportionalHeight: 0.33;
addAdjusterAndMorph: subCategoriesList proportionalHeight: 0.33;
addAdjusterAndMorph: examplesList proportionalHeight: 0.33.
layoutMorph addMorph: navigationLayout proportionalWidth: 0.33.
content _ LayoutMorph newColumn.
docsMorph _ TextModelMorph textProvider: model textGetter: #exampleDocumentation.
content addMorphUseAll: docsMorph.
buttons _ LayoutMorph newRow.
buttons addMorph: (PluggableButtonMorph model: model action: #runExample label: 'Run').
buttons addMorph: (PluggableButtonMorph model: model action: #inspectExample label: 'Inspect').
buttons addMorph: (PluggableButtonMorph model: model action: #exploreExample label: 'Explore').
buttons addMorph: (PluggableButtonMorph model: model action: #browseExample label: 'Browse').
content addMorph: buttons fixedHeight: 30.
layoutMorph addAdjusterAndMorph: content layoutSpec: LayoutSpec useAll.! !
!ExamplesBrowserWindow methodsFor: 'as yet unclassified' stamp: 'MM 12/11/2021 11:12:16'!
initialize
super initialize.
self beRow.! !
!ExamplesBrowserWindow class methodsFor: 'as yet unclassified' stamp: 'MM 12/11/2021 11:51:07'!
open
"self open"
^ self open: ExamplesBrowser new label: 'Examples browser'! !
!ExamplesBrowserWindow class methodsFor: 'as yet unclassified' stamp: 'MM 12/11/2021 13:31:57'!
worldMenuForOpenGroup
^ `{{
#itemGroup -> 10.
#itemOrder -> 50.
#label -> 'Examples Browser'.
#object -> ExamplesBrowserWindow.
#selector -> #open.
#icon -> #morphsIcon.
#balloonText -> 'A browser tool for running examples'.
} asDictionary}`! !
!ExamplesBrowser methodsFor: 'as yet unclassified' stamp: 'MM 12/11/2021 12:11:46'!
browseExample
self currentExample ifNotNil: [:example | example browse]
! !
!ExamplesBrowser methodsFor: 'as yet unclassified' stamp: 'MM 12/11/2021 12:12:46'!
collectExamples
"Collect examples in Smalltalk system"
"Traverse all system classes looking for class methods that start with #example or are annotated with an 'example' pragma."
examples _ Dictionary new.
Smalltalk organization categories do: [:cat |
(Smalltalk organization classesAt: cat) do: [:class | | annotatedMethods namedMethods exampleMethods |
annotatedMethods _ (Pragma allNamed: #example in: class) collect: #method.
namedMethods _ class class methodsSelect: [:method | method selector asString includesSubstring: 'example' caseSensitive: false].
exampleMethods _ (annotatedMethods, namedMethods) asSet asOrderedCollection.
exampleMethods ifNotEmpty: [ | catExamples |
examples at: cat ifAbsent: [examples at: cat put: Dictionary new].
catExamples _ examples at: cat.
catExamples at: class name put: exampleMethods]]].! !
!ExamplesBrowser methodsFor: 'as yet unclassified' stamp: 'MM 12/11/2021 11:49:59'!
currentCategory
^ categoriesIndex ifNotNil: [:index | categoriesList at: index]! !
!ExamplesBrowser methodsFor: 'as yet unclassified' stamp: 'MM 12/11/2021 11:49:41'!
currentExample
^ examplesListIndex ifNotNil: [:index | examplesList at: index]! !
!ExamplesBrowser methodsFor: 'as yet unclassified' stamp: 'MM 12/11/2021 11:49:21'!
currentSubCategory
^ subCategoriesIndex ifNotNil: [:index | subCategoriesList at: index]! !
!ExamplesBrowser methodsFor: 'as yet unclassified' stamp: 'MM 12/11/2021 12:07:19'!
exampleDocumentation
^ self currentExample
ifNotNil: [:example |
String streamContents: [:s |
s nextPutAll: example getSource]]
ifNil: ['']! !
!ExamplesBrowser methodsFor: 'as yet unclassified' stamp: 'MM 12/11/2021 10:23:48'!
examplesCategories
^ examples keys! !
!ExamplesBrowser methodsFor: 'as yet unclassified' stamp: 'MM 12/11/2021 10:40:42'!
examplesCategoriesIndex
^ categoriesIndex ifNil: [0]! !
!ExamplesBrowser methodsFor: 'as yet unclassified' stamp: 'MM 12/11/2021 13:19:36'!
examplesCategoriesIndex: anIndex
anIndex isZero ifTrue: [^ categoriesIndex _ nil].
categoriesIndex _ anIndex.
subCategoriesList _ (examples at: self currentCategory) keys.
self changed: #examplesSubCategories.
self examplesSubCategoriesIndex: 1! !
!ExamplesBrowser methodsFor: 'as yet unclassified' stamp: 'MM 12/11/2021 10:24:11'!
examplesInCategory: aCategory
^ examples at: aCategory! !
!ExamplesBrowser methodsFor: 'as yet unclassified' stamp: 'MM 12/11/2021 13:06:35'!
examplesList
^ examplesList collect: [:example | self formatExampleName: example selector asString]! !
!ExamplesBrowser methodsFor: 'as yet unclassified' stamp: 'MM 12/11/2021 10:43:04'!
examplesListIndex
^ examplesListIndex ifNil: [0]! !
!ExamplesBrowser methodsFor: 'as yet unclassified' stamp: 'MM 12/11/2021 12:09:19'!
examplesListIndex: anIndex
anIndex isZero ifTrue: [^ examplesListIndex _ nil].
examplesListIndex _ anIndex.
self changed: #exampleDocumentation! !
!ExamplesBrowser methodsFor: 'as yet unclassified' stamp: 'MM 12/11/2021 11:53:07'!
examplesSubCategories
^ subCategoriesList ! !
!ExamplesBrowser methodsFor: 'as yet unclassified' stamp: 'MM 12/11/2021 10:42:10'!
examplesSubCategoriesIndex
^ subCategoriesIndex ifNil: [0]! !
!ExamplesBrowser methodsFor: 'as yet unclassified' stamp: 'MM 12/11/2021 13:18:53'!
examplesSubCategoriesIndex: anIndex
anIndex isZero ifTrue: [^ subCategoriesIndex _ nil].
subCategoriesIndex _ anIndex.
examplesList _ (examples at: self currentCategory) at: self currentSubCategory.
self changed: #examplesList.
self examplesListIndex: 1.! !
!ExamplesBrowser methodsFor: 'as yet unclassified' stamp: 'MM 12/11/2021 12:35:32'!
exploreExample
self currentExample ifNotNil: [:example | (example methodClass soleInstance perform: example selector) explore]! !
!ExamplesBrowser methodsFor: 'as yet unclassified' stamp: 'MM 12/11/2021 13:09:46'!
formatExampleName: aString
^ String streamContents: [:s |
s nextPut: aString first asUppercase.
aString allButFirstDo: [:char |
char isDigit ifTrue: [
s nextPut: Character space; nextPut: char]
ifFalse: [
char isUppercase ifTrue: [
s nextPut: Character space; nextPut: char asLowercase]
ifFalse: [s nextPut: char]]]]! !
!ExamplesBrowser methodsFor: 'as yet unclassified' stamp: 'MM 12/11/2021 10:52:26'!
initialize
self collectExamples.
categoriesList _ examples keys.
subCategoriesList _ OrderedCollection new.
examplesList _ OrderedCollection new.! !
!ExamplesBrowser methodsFor: 'as yet unclassified' stamp: 'MM 12/11/2021 12:35:24'!
inspectExample
self currentExample ifNotNil: [:example | (example methodClass soleInstance perform: example selector) inspect]! !
!ExamplesBrowser methodsFor: 'as yet unclassified' stamp: 'MM 12/11/2021 12:37:28'!
runExample
self currentExample ifNotNil: [:example | |result|
result _ example methodClass soleInstance perform: example selector.
(result isKindOf: Morph) ifTrue: [result openInWorld]]! !
!ExamplesBrowser class methodsFor: 'as yet unclassified' stamp: 'MM 12/11/2021 13:22:45'!
windowColor
^ Color lightOrange! !
More information about the Cuis-dev
mailing list