Skip to content

How to extend Mirage

Julien Delplanque edited this page Jul 17, 2016 · 1 revision

This page provides documentation about how to extends Mirage.

Creating you own view

Listening to MIModel announcements

WindowsPreviewer graphical elements are all listening to the announcements of a MIModel object to update their state. The following list contains the announcements that can be announced by a MIModel:

Announcement Purpose
MIOpenRequest Announced when the previewer is opened.
MIWindowSelected Announced when the user selected a window in the previewer.
MICloseRequest Announced when the previewer is closed.

Each graphical element must uses MIModelListener trait and override the following methods (defined in the trait):

Method Purpose
#handleOpenRequest: Defines what it should do when the previewer is opened.
#handleWindowSelected: Defines what it should do when the previewer's current window change.
#handleCloseRequest: Defines what if should do when the previewer is closed.

These methods receive the corresponding announcement when they are called.

Making the view appear in the Setting browser

To let the user enable/disable the view you created and let MIModel know it can use your view, you have to make it use MIViewSetting trait. This trait adds methods on the class side and some of them need to be overrided:

Method Purpose
#activate: Enable/disable the view according to a Boolean given as parameter.
#isActivated Returns true if the view is enabled, else returns false.
#wpSettingOn: Create the setting node in the setting browser using #buildSettingNamed:with:.

Example: MITaskbarTasksHighlighter

As an example we will explain how MITaskbarTasksHighlighter is implemented. This view highlight the taskbar task's button associated with the window currently selected.

MIButtonHighlighterMorph

First of all we create an object that inherits from Morph and have the duty to highlight a button given as parameter:

Morph subclass: #MIButtonHighlighterMorph
    instanceVariableNames: ''
    classVariableNames: ''
    package: 'Mirage-Highlighter'

We override the #initialize method:

initialize
    super initialize.
    self
        height: Smalltalk ui theme wpTaskbarTasksHighlighterHeight;
        color: Smalltalk ui theme wpTaskbarTasksHighlighterColor

Then, we create a method that make the morph "highlight" a button given as parameter:

highlightButton: aButton
    self
        position: aButton position - (0@self height);
        width: aButton width

Now we are ready to implement our view.

MITaskbarTasksHighlighter

Let's create our object that uses MIModelListener and MIViewSetting traits:

Object subclass: #MITaskbarTasksHighlighter
    uses: MIModelListener + MIViewSetting
    instanceVariableNames: 'buttonHighlighter'
    classVariableNames: ''
    package: 'Mirage-Highlighter'

with its #initialize method:

initialize
    super initialize.
    buttonHighlighter := MIButtonHighlighterMorph new
Reacting to announcements

Now, we define the behavior of the object when the previewer open (it adds the buttonHighlighter as submorph of the background):

handleOpenRequest: aMIOpenRequest
    aWPOpenRequest background addMorph: buttonHighlighter

Then, we define the behavior of the object when the previewer close (it unsubscribes from the MIModel announcements):

handleCloseRequest: aMICloseRequest
    aMICloseRequest model announcer unsubscribe: self

And finally, we define the behavior of the object when the selected window of the previewer change (it highlights the taskbar button corresponding):

handleWindowSelected: aMIThumbnailSelected
    buttonHighlighter
        highlightButton: (aWPThumbnailSelected window worldTaskbar buttonForMorph: aMIThumbnailSelected window)
Appearing in the Settings browser

To do that, we go the class side of WPTaskbarTasksHighlighter and override the following methods:

  • #activate: and #isActivated to let know if the view is activated or not.
activate: aBoolean
    isActivated := aBoolean
isActivated
    ^ isActivated
  • #wpSettingOn: To actually build the setting node in the System browser.
wpSettingOn: aBuilder
    <systemsettings>
    (self buildSettingNamed: #wpTaskbarTasksHighlighterSetting with: aBuilder)
        label: 'Taskbar tasks highlighter';
        description: 'Activate the taskbar tasks highlighter' translated

Finished

The example is now complete. It is already implemented in the 'Mirage-Highlighter' package, have a look!

Add a windows ordering method

It is possible to change the order used by the windows previewer to sort windows in World at opening.

To do that, just add a method (as an extension) to MIModel that will be called at the previewer opening (to collect windows to use). This method must holds the pragma #wpWindowsManagementNamed: with as argument the name of the method.

For example, look at the default windows ordering methods implemented in MIModel:

  • #useWindowsOrderedByTaskbar
useWindowsOrderedByTaskbar
    <wpWindowsManagementNamed: 'Taskbar order'>
    self windowsManaged: self windowsOrderedByTaskbar
  • #useWindowsOrderedByWorld
useWindowsOrderedByWorld
    <wpWindowsManagementNamed: 'World order'>
    self windowsManaged: self windowsOrderedByWorld

A (stupid) example: no order ordering method

A simple (but stupid) example would be to extend MIModel by adding an ordering method that shuffle the windows order at opening. This example should not be implemented in real life, this is just to show how to create an ordering method.

The code would be as simple as this:

useWindowsShuffled
    <wpWindowsManagementNamed: 'No order (shuffle)'>
    self windowsManaged: self windowsOrderedByWorld shuffled

Once this method is saved, the 'No order (shuffle)' choice appears in the setting's list.