[Vm-dev] Tangential: A Lisp Interpreter Implemented in Conway's Game of Life
Stéphane Rollandin
lecteur at zogotounga.net
Fri Jan 20 11:34:48 UTC 2023
Attached is a Morph for playing with the #nextGeneration method.
Usage:
(BitBltLifeMorph over: 150 at 120) openInHand
The yellow button menu allows edition (you can hand-paint the cells),
and basic control of the speed and magnification.
Stef
-------------- next part --------------
ImageMorph subclass: #BitBltLifeMorph
instanceVariableNames: 'magnification stepTime'
classVariableNames: ''
poolDictionaries: ''
category: 'MorphicExtras-BitBltLife'!
!BitBltLifeMorph commentStamp: 'spfa 1/20/2023 12:18' prior: 0!
(BitBltLifeMorph over: 150 at 120) openInHand
!
!BitBltLifeMorph methodsFor: 'editing' stamp: 'spfa 1/20/2023 10:49'!
editPattern
self editPattern: image! !
!BitBltLifeMorph methodsFor: 'editing' stamp: 'spfa 1/20/2023 10:57'!
editPattern: anImage
| editor |
self addMorph: (editor := GoLPatternPaint new editForm: (image := anImage);
magnification: self magnification;
brushColor: Color black;
penSize: 1;
bounds: self bounds;
yourself).
^ editor! !
!BitBltLifeMorph methodsFor: 'editing' stamp: 'spfa 1/20/2023 10:50'!
erasePattern
self editPattern: (Form extent: image extent)! !
!BitBltLifeMorph methodsFor: 'editing' stamp: 'spfa 1/20/2023 12:08'!
randomizePattern
| rform |
rform := Form extent: image extent.
(rform width * rform height * 0.5) floor timesRepeat: [
rform colorAt: (rform width -2) atRandom @ (rform height -2) atRandom put: Color black].
(self editPattern: rform) accept! !
!BitBltLifeMorph methodsFor: 'menu' stamp: 'spfa 1/20/2023 11:08'!
beFast
self stepTime: 0! !
!BitBltLifeMorph methodsFor: 'menu' stamp: 'spfa 1/20/2023 11:08'!
beSlow
self stepTime: 200! !
!BitBltLifeMorph methodsFor: 'menu' stamp: 'spfa 1/20/2023 11:31'!
beVerySlow
self stepTime: 1000! !
!BitBltLifeMorph methodsFor: 'menu' stamp: 'spfa 1/20/2023 12:00'!
buildMetaMenu: evt
"Build the morph menu. This menu has two sections. The first section contains commands that are handled by the hand; the second contains commands handled by the argument morph."
| menu |
menu := MenuMorph new defaultTarget: self.
menu addLine.
menu add: 'stop & paint' translated action: #editPattern.
menu addLine.
menu add: 'slow' translated action: #beSlow.
menu add: 'very slow' translated action: #beVerySlow.
menu add: 'fast' translated action: #beFast.
menu addLine.
menu add: 'erase' translated action: #erasePattern.
menu add: 'randomize' translated action: #randomizePattern.
menu addLine.
menu add: 'x2' translated action: #mag2.
menu add: 'x4' translated action: #mag4.
menu add: 'x8' translated action: #mag8.
^ menu! !
!BitBltLifeMorph methodsFor: 'menu' stamp: 'spfa 1/20/2023 10:34'!
buildYellowButtonMenu: aHand
^ self buildMetaMenu: self currentEvent! !
!BitBltLifeMorph methodsFor: 'menu' stamp: 'spfa 1/20/2023 11:26'!
invokeMetaMenu: evt
| menu |
menu := self buildMetaMenu: evt.
menu addTitle: 'Life playground'.
menu popUpEvent: evt in: self world! !
!BitBltLifeMorph methodsFor: 'menu' stamp: 'spfa 1/20/2023 12:00'!
mag2
self magnification: 2! !
!BitBltLifeMorph methodsFor: 'menu' stamp: 'spfa 1/20/2023 12:00'!
mag4
self magnification: 4! !
!BitBltLifeMorph methodsFor: 'menu' stamp: 'spfa 1/20/2023 12:00'!
mag8
self magnification: 8! !
!BitBltLifeMorph methodsFor: 'menu' stamp: 'spfa 1/20/2023 11:28'!
yellowButtonActivity: shiftState
self invokeMetaMenu: self currentEvent! !
!BitBltLifeMorph methodsFor: 'drawing' stamp: 'spfa 1/20/2023 10:17'!
drawOn: aCanvas
self borderStyle ifNotNil:[:style |
style frameRectangle: bounds on: aCanvas.
].
aCanvas drawImage: (image magnifyBy: self magnification) at: self innerBounds origin! !
!BitBltLifeMorph methodsFor: 'accessing' stamp: 'spfa 1/20/2023 12:01'!
magnification
^ magnification ifNil: [4]! !
!BitBltLifeMorph methodsFor: 'accessing' stamp: 'spfa 1/20/2023 12:03'!
magnification: anInteger
magnification := anInteger.
self pattern: image! !
!BitBltLifeMorph methodsFor: 'accessing' stamp: 'spfa 1/20/2023 10:44'!
pattern: anImage
self changed.
image := anImage.
super extent: self preferredExtent! !
!BitBltLifeMorph methodsFor: 'accessing' stamp: 'spfa 1/20/2023 10:16'!
preferredExtent
^ image ifNil: [0 at 0] ifNotNil: [image extent * self magnification]! !
!BitBltLifeMorph methodsFor: 'stepping and presenter' stamp: 'spfa 1/20/2023 12:07'!
step
(self findA: GoLPatternPaint) ifNotNil: [^ self].
image nextGeneration.
self changed! !
!BitBltLifeMorph methodsFor: 'stepping and presenter' stamp: 'spfa 1/20/2023 11:07'!
stepTime
^ stepTime ifNil: [0]! !
!BitBltLifeMorph methodsFor: 'stepping and presenter' stamp: 'spfa 1/20/2023 11:07'!
stepTime: aNumber
stepTime := aNumber! !
"-- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- "!
BitBltLifeMorph class
instanceVariableNames: ''!
!BitBltLifeMorph class methodsFor: 'as yet unclassified' stamp: 'spfa 1/20/2023 11:58'!
over: aPoint
^ self new pattern: (Form extent: aPoint); randomizePattern! !
FatBitsPaint subclass: #GoLPatternPaint
instanceVariableNames: ''
classVariableNames: ''
poolDictionaries: ''
category: 'MorphicExtras-BitBltLife'!
!GoLPatternPaint methodsFor: 'menu' stamp: 'spfa 1/20/2023 10:26'!
accept
super accept.
self delete! !
!GoLPatternPaint methodsFor: 'menu' stamp: 'spfa 1/20/2023 10:39'!
buildYellowButtonMenu: aHand
^ self buildMetaMenu: self currentEvent! !
!GoLPatternPaint methodsFor: 'menu' stamp: 'spfa 1/20/2023 10:28'!
callThisBaseGraphic
self accept! !
!GoLPatternPaint methodsFor: 'meta-actions' stamp: 'spfa 1/20/2023 11:16'!
acceptForOneStep
self owner in: [:o |
self accept.
self delete.
o step.
o editPattern]! !
!GoLPatternPaint methodsFor: 'meta-actions' stamp: 'spfa 1/20/2023 11:29'!
buildMetaMenu: evt
"Build the morph menu. This menu has two sections. The first section contains commands that are handled by the hand; the second contains commands handled by the argument morph."
| menu |
menu := MenuMorph new defaultTarget: self.
menu addLine.
menu add: 'accept & resume' translated action: #accept.
menu add: 'accept & do one step' action: #acceptForOneStep.
menu add: 'dismiss' translated action: #dismiss.
menu add: 'dismiss & resume' translated action: #delete.
menu addLine.
menu add: 'erase' translated action: #erasePattern.
menu add: 'randomize' translated action: #randomizePattern.
^ menu! !
!GoLPatternPaint methodsFor: 'meta-actions' stamp: 'spfa 1/20/2023 11:02'!
dismiss
self owner in: [:o |
self delete.
o editPattern]! !
!GoLPatternPaint methodsFor: 'meta-actions' stamp: 'spfa 1/20/2023 12:27'!
erasePattern
self owner in: [:o |
self delete.
o erasePattern]! !
!GoLPatternPaint methodsFor: 'meta-actions' stamp: 'spfa 1/20/2023 11:20'!
randomizePattern
self owner in: [:o |
self delete.
o randomizePattern.
o editPattern]! !
!GoLPatternPaint methodsFor: 'event handling' stamp: 'spfa 1/20/2023 11:00'!
mouseDown: evt
"Check for option (menu) click"
evt yellowButtonPressed ifTrue: [| menu |
menu := self buildMetaMenu: evt.
menu addTitle: 'Life painter'.
menu popUpInWorld: self currentWorld].
^ super mouseDown: evt
! !
More information about the Vm-dev
mailing list