Grafoscopio/repository/Grafoscopio/GrafoscopioNotebook.class.st

555 lines
14 KiB
Smalltalk
Raw Normal View History

"
I am a Grafoscopio Notebook.
Example:
| testTree nb |
testTree := GrafoscopioNode new becomeDefaultTestTree.
nb := GrafoscopioNotebook new.
nb notebookContent: testTree.
nb openWithSpec
"
Class {
#name : #GrafoscopioNotebook,
#superclass : #ComposableModel,
#instVars : [
'tree',
'header',
'body',
'windowMainMenu',
'workingFile',
'notebook'
],
#category : #'Grafoscopio-UI'
}
{ #category : #utility }
GrafoscopioNotebook class >> SHA1For: aFile is: aSHA1String [
"I verify that a file has the same signature that the one in a given string,
returning true in that case or false otherwise"
^ (SHA1 new hashMessage: aFile asFileReference binaryReadStream contents) hex = aSHA1String
]
{ #category : #specs }
GrafoscopioNotebook class >> defaultSpec [
"comment stating purpose of message"
^ SpecLayout composed
newColumn: [:tcol|
tcol newRow: [ :wrow | wrow add: #windowMainMenu ] height: (self toolbarHeight);
newRow: [:row |
row newColumn: [ :tc |
tc add: #tree
] width: 300.
row newColumn: [ :bc |
bc newRow: [ :bcr | bcr add: #header ] height: self toolbarHeight.
bc add: #body ]]]
]
{ #category : #operation }
GrafoscopioNotebook >> addNode [
| newSelectedNode |
tree needRebuild: true.
newSelectedNode := tree selectedItem content addNodeAfterMe.
tree roots: tree roots.
self buildWithSpecLayout: self class defaultSpec.
]
{ #category : #accessing }
GrafoscopioNotebook >> body [
^ body
]
{ #category : #accessing }
GrafoscopioNotebook >> body: anObject [
body := anObject
]
{ #category : #operation }
GrafoscopioNotebook >> changeBody: aNode [
self needRebuild: false.
tree needRebuild: false.
body needRebuild: true.
body := self instantiate: aNode specModelClass new.
body content: aNode content.
body body class = TextModel
2016-07-28 15:09:26 +00:00
ifTrue: [body body whenTextChanged: [ :arg | aNode body: arg ]].
body body class = GlamourPresentationModel
ifTrue: [ | playground |
playground := body body glmPres.
playground when: GLMContextChanged
do: [ :ann | ann property = #text
ifTrue: [ | playgroundText |
playgroundText := (playground pane ports at: 2) value.
aNode body: playgroundText]
]
].
header text: aNode header.
body needRebuild: true.
self buildWithSpecLayout: self class defaultSpec.
]
{ #category : #operation }
GrafoscopioNotebook >> demoteNode [
| currentNode |
currentNode := tree selectedItem content.
currentNode demote.
tree needRebuild: true.
tree roots: tree roots.
self buildWithSpecLayout: self class defaultSpec.
]
{ #category : #persistence }
GrafoscopioNotebook >> exportAsSton: aNotebook on: aFileStream [
| stonPrettyString |
aNotebook flatten.
stonPrettyString := String streamContents: [ :stream |
(STON writer on: stream)
newLine: String crlf;
prettyPrint: true;
keepNewLines: true;
nextPut: aNotebook children].
aFileStream nextPutAll: stonPrettyString
]
{ #category : #accessing }
GrafoscopioNotebook >> extent [
^800@500
]
{ #category : #accessing }
GrafoscopioNotebook >> header [
^ header
]
{ #category : #accessing }
GrafoscopioNotebook >> header: anObject [
header := anObject
]
{ #category : #initialization }
GrafoscopioNotebook >> initializePresenter [
tree whenSelectedItemChanged: [ :item |
self updateBodyFor: item.
header whenTextChanged: [ :arg |
(tree selectedItem content header) = arg
ifFalse: [
(tree highlightedItem) content header: arg.
tree roots: tree roots]]]
]
{ #category : #initialization }
GrafoscopioNotebook >> initializeWidgets [
windowMainMenu := self newWindowMainMenu.
tree := TreeModel new.
header := self newTextInput.
body := self newText.
body disable.
body text: '<- Select a node'.
tree
childrenBlock: [:node | node children];
displayBlock: [:node | node title ].
tree whenBuiltDo: [ tree selectedItem: (tree roots first)"; takeHighlight; yourself" ].
self focusOrder
add: tree;
add: header;
add: body.
]
{ #category : #operation }
GrafoscopioNotebook >> moveNodeAfter [
| currentNode |
currentNode := tree selectedItem content.
currentNode moveAfter.
tree needRebuild: true.
tree roots: tree roots.
self buildWithSpecLayout: self class defaultSpec.
]
{ #category : #operation }
GrafoscopioNotebook >> moveNodeBefore [
| currentNode |
currentNode := tree selectedItem content.
currentNode moveBefore.
tree needRebuild: true.
tree roots: tree roots.
self buildWithSpecLayout: self class defaultSpec.
]
{ #category : #initialization }
GrafoscopioNotebook >> newWindowMainMenu [
^MenuModel new
addGroup: [ :group |
group addItem: [ :item |
item
name: 'Notebook';
icon: Smalltalk ui icons smallObjectsIcon;
subMenu: self notebookSubMenu ].
group addItem: [ :item |
item
name: 'Project';
icon: Smalltalk ui icons catalogIcon;
subMenu: self projectSubMenu ] ];
addGroup: [ :group |
group addItem: [ :item |
item
name: nil;
description: 'Save notebook';
icon: Smalltalk ui icons smallSaveIcon;
action: [ self saveWorkingNotebook ] ].
group addItem: [ :item |
item
name: nil;
description: 'Undo';
icon: Smalltalk ui icons smallUndoIcon;
action: [ self inform: 'To be implemented...' ] ].
group addItem: [ :item |
item
name: nil;
description: 'Redo';
icon: Smalltalk ui icons smallRedoIcon;
action: [ self inform: 'To be implemented...' ] ]];
addGroup: [ :group |
group addItem: [ :item |
item
name: nil;
description: 'Add nodo';
icon: MendaIcons new plusIcon;
action: [ self addNode ] ].
group addItem: [ :item |
item
name: nil;
description: 'Delete node';
icon: MendaIcons new minusIcon;
action: [ self removeNode ] ].
group addItem: [ :item |
item
name: nil;
description: 'Move up node';
icon: MendaIcons new arrowUpIcon;
action: [ self moveNodeBefore ] ].
group addItem: [ :item |
item
name: nil;
description: 'Move down node';
icon: MendaIcons new arrowDownIcon;
action: [ self moveNodeAfter ] ].
group addItem: [ :item |
item
name: nil;
description: 'Move node left';
icon: MendaIcons new arrowLeftIcon;
action: [ self promoteNode ] ].
group addItem: [ :item |
item
name: nil;
description: 'Move node right';
icon: MendaIcons new arrowRightIcon;
action: [ self demoteNode ] ]];
addGroup: [ :group |
group addItem: [ :item |
item
name: nil;
description: 'Togle: code <--> text';
icon: MendaIcons new smalltalkCodeIcon;
action: [ self inform: 'To be implemented...' ] ].
group addItem: [ :item |
item
name: nil;
description: 'Tag as...';
icon: MendaIcons new tagAddIcon;
action: [ self inform: 'To be implemented...' ] ].
group addItem: [ :item |
item
name: nil;
description: 'Untag ....';
icon: MendaIcons new tagMinusIcon;
action: [ self inform: 'To be implemented...' ] ].
group addItem: [ :item |
item
name: nil;
description: 'Edit tags...';
icon: FontAwesomeIcons new tagsIcon;
action: [ self inform: 'To be implemented...' ] ]].
]
{ #category : #accessing }
GrafoscopioNotebook >> notebook [
^ notebook
]
{ #category : #accessing }
GrafoscopioNotebook >> notebook: anObject [
notebook := anObject
]
{ #category : #api }
GrafoscopioNotebook >> notebookContent: aTree [
tree roots: aTree children
]
{ #category : #initialization }
GrafoscopioNotebook >> notebookSubMenu [
^ MenuModel new
addGroup: [ :group |
group addItem: [ :item |
item
name: 'Save';
icon: Smalltalk ui icons smallSaveIcon;
shortcut: $s command;
action: [ self saveWorkingNotebook ] ].
group addItem: [ :item |
item
name: 'Save as...';
icon: Smalltalk ui icons smallSaveAsIcon;
2016-06-28 16:22:00 +00:00
action: [ self saveToFileUI ] ].
group addItem: [ :item |
item
name: 'Export as html';
icon: Smalltalk ui icons smallWindowIcon;
action: [ self inform: 'To be implemented...' ] ].
group addItem: [ :item |
item
name: 'Export as pdf';
icon: Smalltalk ui icons smallPrintIcon;
action: [ self inform: 'To be implemented...' ] ].
group addItem: [ :item |
item
name: 'See html';
icon: Smalltalk ui icons smallInspectItIcon;
action: [ self inform: 'To be implemented...' ] ].
group addItem: [ :item |
item
name: 'See pdf';
icon: Smalltalk ui icons smallInspectItIcon;
action: [ self inform: 'To be implemented...' ] ] ]
]
2016-07-19 13:56:25 +00:00
{ #category : #persistence }
GrafoscopioNotebook >> openDefault [
"I open a new default notebook"
| nb |
nb := self class new.
nb
notebook: (GrafoscopioNode new becomeDefaultTree);
title: ' New | Grafoscopio notebook';
notebookContent: nb notebook.
^ nb openWithSpec.
]
{ #category : #persistence }
GrafoscopioNotebook >> openFromFile: aFileName [
"I open a notebook from a file named aFileName containing a grafoscopio tree"
self workingFile: aFileName.
self notebook: ((STON fromString: self workingFile contents) at: 1) parent.
self title: self workingFile basenameWithIndicator, ' | Grafoscopio notebook'.
self notebookContent: self notebook.
^ self openWithSpec.
]
{ #category : #persistence }
GrafoscopioNotebook >> openFromFileSelector [
| fileStream nb |
fileStream := UITheme builder
fileOpen: 'Choose a file'
extensions: #('ston').
fileStream ifNil: [
self inform: 'No file selected'.
^ self ].
self workingFile: fileStream name asFileReference.
nb := self class new.
nb openFromFile: self workingFile.
]
{ #category : #persistence }
GrafoscopioNotebook >> openFromUrl: anUrl [
"Opens a tree from a file named aFileName"
| fileName |
fileName := anUrl splitOn: '/' last.
GrafoscopioGUI
downloadingFrom: anUrl
withMessage: 'Downloading document...'
into: FileLocator temp.
self class new openFromFile: (FileLocator temp fileName)
]
{ #category : #persistence }
GrafoscopioNotebook >> openFromUrlUI [
"This method generates the UI for the openFromUrl: method, it asks for a URL from the user"
| fileUrl |
"GrafoscopioBrowser configureSettings."
fileUrl := UIManager default
textEntry: 'Ingrese la URL'
title: 'Nuevo documento desde URL'.
fileUrl isNil ifTrue: [ ^nil ].
self class new openFromUrl: fileUrl
]
{ #category : #persistence }
GrafoscopioNotebook >> openTutorial [
| tutorial |
tutorial := (FileLocator documents / 'Grafoscopio/Docs/Es/Turiales/tutorial.ston' ) asFileReference.
tutorial exists
ifTrue: [self class new openFromFile: tutorial]
ifFalse: [ GrafoscopioGUI updateDocumentationUI ]
]
{ #category : #initialization }
GrafoscopioNotebook >> projectSubMenu [
^ MenuModel new
addGroup: [ :group |
group addItem: [ :item |
item
name: 'Activate remote repository...';
icon: Smalltalk ui icons smallPushpinIcon;
action: [ self inform: 'To be implemented ...' ] ].
group addItem: [ :item |
item
name: 'Activate local repository...';
icon: Smalltalk ui icons homeIcon;
action: [ self inform: 'To be implemented ...' ] ].
group addItem: [ :item |
item
name: 'Add file...';
icon: Smalltalk ui icons newerPackagesAvailableIcon;
action: [ self inform: 'To be implemented ...' ] ].
group addItem: [ :item |
item
name: 'Delete file...';
icon: Smalltalk ui icons packageDeleteIcon;
action: [ self inform: 'To be implemented ...' ] ].
group addItem: [ :item |
item
name: 'Commit to repository';
icon: Smalltalk ui icons smallScreenshotIcon;
action: [ self inform: 'To be implemented ...' ] ].
group addItem: [ :item |
item
name: 'Credentials';
icon: Smalltalk ui icons userIcon;
action: [ self inform: 'To be implemented ...' ] ] ]
]
{ #category : #operation }
GrafoscopioNotebook >> promoteNode [
| currentNode |
currentNode := tree selectedItem content.
currentNode promote.
tree needRebuild: true.
tree roots: tree roots.
self buildWithSpecLayout: self class defaultSpec.
]
{ #category : #operation }
GrafoscopioNotebook >> removeNode [
| nodeToDelete |
nodeToDelete := tree selectedItem content.
nodeToDelete parent removeNode: nodeToDelete.
"tree selectedItem: tree selectedItem parentNode."
tree selectOnlyLastHighlighted.
tree needRebuild: true.
tree roots: tree roots.
self buildWithSpecLayout: self class defaultSpec.
]
2016-06-28 16:22:00 +00:00
{ #category : #persistence }
GrafoscopioNotebook >> saveToFile: aFileReference [
"I save the current tree/document to a file"
aFileReference ifNil: [ self inform: 'No file selected for saving. Save NOT done'. ^ self ].
workingFile := aFileReference.
2016-07-19 12:41:41 +00:00
self workingFile exists ifTrue: [self workingFile delete].
self workingFile ensureCreateFile.
[ self exportAsSton: self notebook on: (self workingFile writeStream)]
ensure: [ (self workingFile writeStream) ifNotNil: #close ].
2016-07-19 13:56:25 +00:00
self title: self workingFile basenameWithIndicator, ' | Grafoscopio notebook'.
2016-07-19 12:41:41 +00:00
self inform: ('File saved at: ', String cr, self workingFile fullName).
2016-06-28 16:22:00 +00:00
GrafoscopioGUI updateRecentNotebooksWith: aFileReference.
]
{ #category : #persistence }
GrafoscopioNotebook >> saveToFileUI [
| file |
file := UITheme builder
fileSave: 'Export notebook to file as...'
extensions: #('ston')
path: nil.
file
ifNil: [ self inform: 'Export cancelled'. ^ self ]
ifNotNil:[self saveToFile: file].
]
{ #category : #persistence }
GrafoscopioNotebook >> saveWorkingNotebook [
"Saves the current tree to the user predefined file location used when he/she opened it."
2016-07-19 12:41:41 +00:00
self workingFile
ifNil: [ self saveToFileUI ]
ifNotNil: [ self saveToFile: workingFile ]
]
{ #category : #accessing }
GrafoscopioNotebook >> tree [
^ tree
]
{ #category : #accessing }
GrafoscopioNotebook >> tree: anObject [
tree := anObject
]
{ #category : #operation }
GrafoscopioNotebook >> updateBodyFor: item [
item
ifNotNil: [ self changeBody: item ]
ifNil: [ ]
]
{ #category : #operation }
GrafoscopioNotebook >> updateBodyFor: item or: bufferedSelection [
item
ifNotNil: [ self changeBody: item ]
ifNil: [ self changeBody: bufferedSelection ]
]
{ #category : #accessing }
GrafoscopioNotebook >> windowMainMenu [
^ windowMainMenu
]
{ #category : #accessing }
GrafoscopioNotebook >> windowMainMenu: anObject [
windowMainMenu := anObject
]
{ #category : #accessing }
GrafoscopioNotebook >> workingFile [
^ workingFile
]
{ #category : #accessing }
GrafoscopioNotebook >> workingFile: aFile [
workingFile := aFile.
]