ElectronWorkstation.st
author Claus Gittinger <cg@exept.de>
Tue, 15 Oct 2019 11:10:05 +0200
changeset 8833 5044eaa4cce2
parent 8832 f94a3aaa37ac
child 8834 d6c5483bf5c0
permissions -rw-r--r--
#FEATURE by exept class: ElectronWorkstation changed: #createWindowFor:type:origin:extent:minExtent:maxExtent:borderWidth:subViewOf:style:inputOnly:label:owner:icon:iconMask:iconView: class: ElectronWorkstation class added: #example2 #example3 changed: #example1

"{ Encoding: utf8 }"

"{ Package: 'stx:libview' }"

"{ NameSpace: Smalltalk }"

DeviceWorkstation subclass:#ElectronWorkstation
	instanceVariableNames:'bridge eventQueue'
	classVariableNames:'ExposureMask StructureNotifyMask KeyPressMask KeyReleaseMask
		PointerMotionMask EnterWindowMask LeaveWindowMask ButtonPressMask
		ButtonMotionMask ButtonReleaseMask PropertyChangeMask'
	poolDictionaries:''
	category:'Interface-Graphics'
!

DeviceGraphicsContext subclass:#ElectronGraphicsContext
	instanceVariableNames:''
	classVariableNames:''
	poolDictionaries:''
	privateIn:ElectronWorkstation
!

!ElectronWorkstation class methodsFor:'documentation'!

documentation
"
    experimental work in progress: a Display which draws in an electron application.
"
!

example1
    |dpy result|

    Smalltalk at:#Display2 put:(dpy := ElectronWorkstation newFor:'localhost:8888').
    result := dpy bridge 
                callFunction:'helloE'
                withArguments:#().
    Transcript showCR:result.
    self assert:result == 123.
    dpy close.

    "
     Display2 close
    "
!

example2
    |dpy result|

    Smalltalk at:#Display2 put:(dpy := ElectronWorkstation newFor:'localhost:8888').
    result := dpy bridge 
                eval:'return 10+20'
                withArguments:#().
    Transcript showCR:result.
    self assert:result == 30.

    result := dpy bridge 
                eval:'return arguments[0]+arguments[1]+1'
                withArguments:#(10 20).
    Transcript showCR:result.
    self assert:result == 31.

    dpy close.

    "
     Display2 close
    "
!

example3
    |v dpy|

    Smalltalk at:#Display2 put:(dpy := ElectronWorkstation newFor:'localhost:8888').

    v := (TopView onDevice:dpy) 
            label:'Hello';
            open.
    v waitUntilVisible.
    v close.
    dpy close.

    "
     Display2 close
    "
! !

!ElectronWorkstation class methodsFor:'class initialization'!

initialize
    ExposureMask        := 1 bitShift:0.
    StructureNotifyMask := 1 bitShift:1.
    KeyPressMask        := 1 bitShift:2.
    KeyReleaseMask      := 1 bitShift:3.
    PointerMotionMask   := 1 bitShift:4.
    EnterWindowMask     := 1 bitShift:5.
    LeaveWindowMask     := 1 bitShift:6.
    ButtonPressMask     := 1 bitShift:7.
    ButtonMotionMask    := 1 bitShift:8.
    ButtonReleaseMask   := 1 bitShift:9.
    PropertyChangeMask  := 1 bitShift:10.
! !

!ElectronWorkstation class methodsFor:'logging'!

logFacility
    "the 'log facility';
     this is used by the Logger both as a prefix to the log message, 
     and maybe (later) used to filter and/or control per-facility log thresholds."

    ^ self nameWithoutPrefix
! !

!ElectronWorkstation methodsFor:'accessing'!

bridge
    ^ bridge
! !

!ElectronWorkstation methodsFor:'accessing & queries'!

defaultEventMask
    "return a mask to enable some events by default."

    ^ ExposureMask | StructureNotifyMask |
      KeyPressMask | KeyReleaseMask |
      PointerMotionMask |
      EnterWindowMask | LeaveWindowMask |
      ButtonPressMask | ButtonMotionMask | ButtonReleaseMask |
      PropertyChangeMask

!

isOpen
    "return true, if there is a valid connection to the display"

    ^ bridge notNil
! !

!ElectronWorkstation methodsFor:'event handling'!

eventPending 
    ^ eventQueue notNil and:[eventQueue notEmpty]

! !

!ElectronWorkstation methodsFor:'font stuff'!

ascentOf:aFontId
    "/ the font name is its ID
    Logger info:'unimplemented: ascentOf'.
    ^ 17
!

descentOf:aFontId
    "/ the font name is its ID
    Logger info:'unimplemented: descentOf'.
    ^ 17
!

getFontWithFamily:familyString face:faceString style:styleString size:sizeArg sizeUnit:sizeUnit encoding:encodingSym
    "try to get the specified font, return id.
     If not available, try next smaller font.
     If no font fits, return nil"

    "/ return the font name as ID
    ^ '%1-%2-%3-%4-%5-%6' 
        bindWith:familyString 
        with:faceString 
        with:styleString 
        with:sizeArg 
        with:sizeUnit 
        with:encodingSym
!

maxAscentOf:aFontId
    "/ the font name is its ID
    Logger info:'unimplemented: maxAscentOf'.
    ^ 17
!

maxDescentOf:aFontId
    "/ the font name is its ID
    Logger info:'unimplemented: maxDescentOf'.
    ^ 17
!

maxWidthOfFont:aFontId
    "/ the font name is its ID
    Logger info:'unimplemented: maxWidthOfFont'.
    ^ 20
!

minWidthOfFont:aFontId
    "/ the font name is its ID
    Logger info:'unimplemented: minWidthOfFont'.
    ^ 20
!

widthOf:aString from:index1 to:index2 inFont:aFontId
    "/ the font name is its ID
    Logger info:'unimplemented: widthOf'.
    ^ (index2-index1+1) * 20
! !

!ElectronWorkstation methodsFor:'initialization & release'!

closeConnection
    "close down connection to Display - usually never done"

    |b|

    (b := bridge) notNil ifTrue:[
        bridge := nil.
        b close
    ].

    "Created: 13.1.1997 / 22:10:07 / cg"
!

initializeFor:aHostAndPortStringOrNil
    |nodeBridge _ElectronBridge|

    nodeBridge := Smalltalk requirePackage:'exept:bridgeFramework/nodeJSBridge'.
    _ElectronBridge := nodeBridge classNamed:'NodeJSBridge::ElectronBridge'.
    bridge := _ElectronBridge newBridgeForHostAndPort:aHostAndPortStringOrNil.
    bridge startBridgeIn:'.' debug:true.
    bridge connectWithTimeoutMS:5000.

    self initializeScreenProperties.
    self initializeDefaultValues.
    self initializeKeyboardMap.
    self initializeDeviceSignals.
    self initializeDeviceResourceTables.

    Screen default isNil ifTrue:[
        "not initialized yet?"
        self initializeViewStyle.
    ].

    "
     ElectronWorkstation newFor:'localhost:8098'
    "
!

initializeScreenProperties
    super initializeScreenProperties.

    monitorType := #unknown.
    visualType := #TrueColor.
    depth := 24.
    redShift := 16.
    greenShift := 8.
    blueShift := 0.

    Display notNil ifTrue:[
        width := Display width.
        height := Display height.
    ] ifFalse:[
        width := 1280.
        height := 1024.
    ].
! !

!ElectronWorkstation methodsFor:'keyboard stuff'!

ungrabKeyboard
    Logger info:'unimplemented: ungrabKeyboard'.
! !

!ElectronWorkstation methodsFor:'pointer stuff'!

pointerPosition
    Logger info:'unimplemented: pointerPosition'.
    ^ 0@0
!

ungrabPointer
    Logger info:'unimplemented: ungrabPointer'.
! !

!ElectronWorkstation methodsFor:'window stuff'!

createWindowFor:aView type:typeSymbol origin:org extent:ext
        minExtent:minE maxExtent:maxE borderWidth:bw subViewOf:sv
        style:styleSymbol inputOnly:inp
        label:label owner:owner
        icon:icn iconMask:icnM iconView:icnV

    |result|

    result := bridge callFunction:'createWindow' withArguments:#().
    ^ result
!

destroyView:aView withId:aWindowId

    Logger info:'unimplemented: destroyView:'.
!

mapWindow:aWindowId
    "map a window"

    Logger info:'unimplemented: mapWindow:'.
!

setWindowBackground:aColorIndex in:aWindowId
    "set a windows background color"

    Logger info:'unimplemented: setWindowBackground:'.
!

setWindowName:aString in:aWindowId
    "define a windows name (i.e. windowTitle)"

    Logger info:'unimplemented: setWindowName:'.
!

unmapWindow:aWindowId
    "unmap a window"

    Logger info:'unimplemented: unmapWindow:'.
! !

!ElectronWorkstation::ElectronGraphicsContext class methodsFor:'documentation'!

documentation
"
    documentation to be added.

    class:
        <a short class summary here, describing what instances represent>

    responsibilities:    
        <describing what my main role is>

    collaborators:    
        <describing with whom and how I talk to>

    API:
        <public api and main messages>
        
    example:
        <a one-line examples on how to use - can also be in a separate example method>

    implementation:
        <implementation points>

    [author:]
        exept MBP

    [instance variables:]

    [class variables:]

    [see also:]

"
! !

!ElectronWorkstation class methodsFor:'documentation'!

version_CVS
    ^ '$Header$'
! !


ElectronWorkstation initialize!