[Home] [Downloads] [Search] [Help/forum]


Register forum user name Search FAQ

Gammon Forum

Notice: Any messages purporting to come from this site telling you that your password has expired, or that you need to "verify" your details, making threats, or asking for money, are spam. We do not email users with any such messages. If you have lost your password you can obtain a new one by using the password reset link.
 Entire forum ➜ MUSHclient ➜ Plugins ➜ Super Health Bar plugin with external VB program

Super Health Bar plugin with external VB program

It is now over 60 days since the last post. This thread is closed.     Refresh page


Pages: 1 2  3  

Posted by Nick Gammon   Australia  (23,046 posts)  Bio   Forum Administrator
Date Sat 16 Aug 2003 04:06 AM (UTC)

Amended on Sat 16 Aug 2003 04:08 AM (UTC) by Nick Gammon

Message
I have been mucking around trying to do a "super" health bar - one that uses an external program to display a fancier health bar. It is sort-of working, so I will present it here in the hope someone can make it work perfectly.

The general idea - which works on my development PC (Windows NT 4) - is to write a small VB program (not VBscript) which is invoked from MUSHclient and which draws a nice health bar with multiple lines. See the screen shot in the next post for the general idea.

However I am finding that when attempting to run it on other PCs I get strange behaviour, like missing VB DLLs, and other things. However you may be able to make it work, especially if you have VB installed.

First, the plugin which calls the health bar program - this is similar to the earlier health bar plugin, however it has the enhancement of the 1-second timer that will do a match on the last line, even if there is no newline, so it should work even if the prompt does not have a newline on it.

Super_Health_Bar.xml


<?xml version="1.0" encoding="UTF-8"?>
<!DOCTYPE muclient [
  <!ENTITY trigger_match 
   "^\&lt;\-?(\d+)\/(\d+) hp \-?(\d+)\/(\d+) m \-?(\d+)\/(\d+) mv\&gt;(.*?)$" 
  > 
]>
<!-- Saved on Saturday, August 16, 2003, 7:11 AM -->
<!-- MuClient version 3.42 -->

<!-- Plugin "Super_Health_Bar" generated by Plugin Wizard -->
<!--
You will probably need to customise the trigger to match your MUD.

See ENTITY line near top of file. The above trigger will match on:

  <54/1000 hp 90/100 m 600/750 mv>

A simpler trigger would be:

  &lt;*/*hp */*m */*mv&gt;

-->

<muclient>
<plugin
   name="Super_Health_Bar"
   author="Nick Gammon"
   id="4637b3ca32d84f4b5ea6743b"
   language="VBscript"
   purpose="Health, Mana, Movement bar implemented with external VB program"
   date_written="2003-08-16 07:08:12"
   requires="3.42"
   version="1.0"
   save_state="y" 
   >
<description trim="y">
<![CDATA[
Uses a small Visual Basic program to display your current health, 
mana and movement points in a separate window.

You need your prompt line to display the appropriate information,
naturally. I used this in SMAUG:

prompt <%h/%H hp %m/%M m %v/%V mv>
fprompt <%h/%H hp %m/%M m %v/%V mv>

"prompt" sets the normal prompt, "fprompt" sets the fight prompt.

Customise the plugin if you want to match a different sort of prompt line.

]]>
</description>

</plugin>


<!--  Triggers  -->

<triggers>
  <trigger
   enabled="y"
   match="&trigger_match;"
   regexp="y"
   send_to="12"
   sequence="100"
  >
  <send>

On Error Resume Next

if not isempty (barobject) then
  if not (barobject is nothing) then
    barobject.SetMaxHP %2
    barobject.SetHP %1
    barobject.SetMaxMana %4
    barobject.SetMana %3
    barobject.SetMaxMove %6
    barobject.SetMove %5
  end if
end if

</send>
  </trigger>
</triggers>

<!--  Timers -->

<timers>
  <timer 
    script="CheckPrompt" 
    enabled="y" 
    second="1" 
  >
  </timer>
</timers>


<!--  Script  -->


<script>
<![CDATA[
'
' global variable which is the HP bar Visual Basic COM object
'
dim barobject

barobject = empty

'
'  Central spot for showing errors, so we can easily customise colours
'
sub ShowError (sMessage)
  world.ColourNote "white", "red", sMessage 
end sub


'
' This world has been connected (to the MUD)
'
sub OnPluginConnect
dim X, Y, width

if isempty (barobject) then
  set barobject = nothing
end if

if barobject is nothing then
  On Error Resume Next

  set barobject = createobject ("MUSHclient_bar.Bar")

  If Err.Number <> 0 Then
    ShowError Err.Description
    ShowError "Cannot execute bar display program"
    ShowError "Check it is installed."
    Exit Sub
  End If

  On Error GoTo 0

'
'  reposition it (from value saved last time)
'

  X = GetVariable ("X")
  Y = GetVariable ("Y")
  width = GetVariable ("width")

  if not IsEmpty (X) and not IsEmpty (Y) then
    barobject.SetPosition CInt (X), CInt (Y)
  else
    Note "First time used - using default screen position"
  end if

  if not IsEmpty (width) then
    barobject.SetWidth CInt (width)
  end if

  barobject.SetTitle world, world.WorldName
end if

end sub

'
' This world has been disconnected (from the MUD)
'
sub OnPluginDisconnect

On Error Resume Next

'
'  release bar window - remember position
'

if not isempty (barobject) then
  if not barobject is nothing then
    SetVariable "X", barobject.GetX
    SetVariable "Y", barobject.GetY
    SetVariable "width", barobject.GetWidth
    set barobject = nothing
  end if 
end if 

end sub

sub CheckPrompt (sName)
Dim regEx, Matches, Match, sLine, iNumber

'
'  Find line number of last line in buffer
'
  iNumber = world.GetLinesInBufferCount

' ignore lines with a newline at the end

  if world.GetLineInfo (iNumber, 3) then exit sub

' ignore world.note lines

  if world.GetLineInfo (iNumber, 4) then exit sub

' ignore player input lines

  if world.GetLineInfo (iNumber, 5) then exit sub

'
' So far we have a line that is MUD output (not note or command)
'  and it doesn't have a newline, so it is probably a prompt
'

' get text of line

  sLine = world.GetLineInfo (iNumber, 1)

'
' Make a regular expression to match on the line:
'
'  
  Set regEx = New RegExp

'
'  exit CDATA block so we can use the trigger entity
'
]]>

  regEx.Pattern = "&trigger_match;"

<![CDATA[

'
'  Execute regular expression
'

  Set Matches = regEx.Execute (sLine)

'
'  Exit if no match
'
 
  if Matches.Count = 0 then  exit sub


  Set Match = Matches.Item (0)

  Set regEx = Nothing
  Set Matches = Nothing

'
'  Update the bar
'

  On Error Resume Next

  if not isempty (barobject) then
    if not (barobject is nothing) then
      barobject.SetMaxHP CInt (Match.SubMatches (1))
      barobject.SetHP CInt (Match.SubMatches (0))
      barobject.SetMaxMana CInt (Match.SubMatches (3))
      barobject.SetMana CInt (Match.SubMatches (2))
      barobject.SetMaxMove CInt (Match.SubMatches (5))
      barobject.SetMove CInt (Match.SubMatches (4))
    end if
  end if

  Set Match = Nothing

end sub

'
'  Called if the user closes the bar window
'

sub barclosed (arg)
 OnPluginDisconnect
end sub

]]>


</script>


</muclient>



Next, the VB project.

There is a reference in it to the MUSHclient.tlb file (which comes with MUSHclient). You will probably need to change that to be where you actually have that file.

MUSHclient_bar.vbp


Type=OleExe
Reference=*\G{00020430-0000-0000-C000-000000000046}#2.0#0#C:\WINNT\System32\StdOle2.Tlb#OLE Automation
Reference=*\G{00025E01-0000-0000-C000-000000000046}#5.0#0#C:\Program Files\Common Files\Microsoft Shared\DAO\DAO360.DLL#Microsoft DAO 3.6 Object Library
Reference=*\G{11DFC5E7-AD6F-11D0-8EAE-00A0247B3BFD}#1.0#0#C:\Program Files\MUSHclient\scripts\MUSHclient.tlb#MUSHclient
Object={6B7E6392-850A-101B-AFC0-4210102A8DA7}#1.3#0; COMCTL32.OCX
Class=Bar; Bar.cls
Form=Gauge.frm
Module=Globals; Globals.bas
Startup="(None)"
ExeName32="MUSHclient_bar.exe"
Command32=""
Name="MUSHclient_bar"
HelpContextID="0"
CompatibleMode="0"
CompatibleEXE32="MUSHclient_bar.exe"
MajorVer=1
MinorVer=0
RevisionVer=0
AutoIncrementVer=0
ServerSupportFiles=0
VersionCompanyName="Gammon Software Solutions"
CompilationType=0
OptimizationType=0
FavorPentiumPro(tm)=0
CodeViewDebugInfo=0
NoAliasing=0
BoundsCheck=0
OverflowCheck=0
FlPointCheck=0
FDIVCheck=0
UnroundedFP=0
StartMode=1
Unattended=0
Retained=0
ThreadPerObject=0
MaxNumberOfThreads=1



Next, the "bar" class that is called from MUSHclient.

Bar.cls



VERSION 1.0 CLASS
BEGIN
  MultiUse = 0   'False
  Persistable = 0  'NotPersistable
  DataBindingBehavior = 0  'vbNone
  DataSourceBehavior  = 0  'vbNone
  MTSTransactionMode  = 0  'NotAnMTSObject
END
Attribute VB_Name = "Bar"
Attribute VB_GlobalNameSpace = False
Attribute VB_Creatable = True
Attribute VB_PredeclaredId = False
Attribute VB_Exposed = True

Option Explicit

Sub SetHP(value As Integer)
  If value < 0 Then value = 0
  Gauge.HPbar.value = value
End Sub
Sub SetMaxHP(value As Integer)
  Gauge.HPbar.Max = value
End Sub
Sub SetMove(value As Integer)
  If value < 0 Then value = 0
  Gauge.Movebar.value = value
End Sub
Sub SetMaxMove(value As Integer)
  Gauge.Movebar.Max = value
End Sub
Sub SetMana(value As Integer)
  If value < 0 Then value = 0
  Gauge.Manabar.value = value
End Sub
Sub SetMaxMana(value As Integer)
  Gauge.Manabar.Max = value
End Sub
Sub SetPosition(X As Integer, Y As Integer)
  Gauge.Left = X
  Gauge.Top = Y
End Sub
Sub SetWidth(width As Integer)
  Gauge.width = width
End Sub
'
' remember calling world in case they close the bar window
'
Sub SetTitle(callingworld As Object, title As String)
  Gauge.Caption = title
  Set theworld = callingworld
End Sub
Function GetX()
  GetX = Gauge.Left
End Function
Function GetY()
  GetY = Gauge.Top
End Function
Function GetWidth()
  GetWidth = Gauge.width
End Function

Private Sub Class_Initialize()
  Gauge.Show
End Sub

Private Sub Class_Terminate()
  End
End Sub



Next, the form that you actually see with 3 progress bars on it...

Gauge.frm



VERSION 5.00
Object = "{6B7E6392-850A-101B-AFC0-4210102A8DA7}#1.3#0"; "COMCTL32.OCX"
Begin VB.Form Gauge 
   Caption         =   "Health Bar"
   ClientHeight    =   870
   ClientLeft      =   60
   ClientTop       =   345
   ClientWidth     =   9090
   LinkTopic       =   "Form1"
   ScaleHeight     =   870
   ScaleWidth      =   9090
   StartUpPosition =   3  'Windows Default
   Begin ComctlLib.ProgressBar HPbar 
      Height          =   255
      Left            =   720
      TabIndex        =   0
      Top             =   0
      Width           =   8295
      _ExtentX        =   14631
      _ExtentY        =   450
      _Version        =   327682
      Appearance      =   1
   End
   Begin ComctlLib.ProgressBar Movebar 
      Height          =   255
      Left            =   720
      TabIndex        =   2
      Top             =   600
      Width           =   8295
      _ExtentX        =   14631
      _ExtentY        =   450
      _Version        =   327682
      Appearance      =   1
   End
   Begin ComctlLib.ProgressBar Manabar 
      Height          =   255
      Left            =   720
      TabIndex        =   1
      Top             =   300
      Width           =   8295
      _ExtentX        =   14631
      _ExtentY        =   450
      _Version        =   327682
      Appearance      =   1
   End
   Begin VB.Label movement 
      Alignment       =   1  'Right Justify
      Caption         =   "Move"
      Height          =   255
      Left            =   0
      TabIndex        =   5
      Top             =   600
      Width           =   615
   End
   Begin VB.Label mana 
      Alignment       =   1  'Right Justify
      Caption         =   "Mana"
      Height          =   255
      Left            =   0
      TabIndex        =   4
      Top             =   300
      Width           =   615
   End
   Begin VB.Label HP 
      Alignment       =   1  'Right Justify
      Caption         =   "HP"
      Height          =   255
      Left            =   0
      TabIndex        =   3
      Top             =   0
      Width           =   615
   End
End
Attribute VB_Name = "Gauge"
Attribute VB_GlobalNameSpace = False
Attribute VB_Creatable = False
Attribute VB_PredeclaredId = True
Attribute VB_Exposed = False
Option Explicit

Private Sub Form_Resize()
  HPbar.width = width - 900
  Manabar.width = width - 900
  Movebar.width = width - 900
End Sub

Private Sub Form_Unload(Cancel As Integer)
 
  If Not IsEmpty(theworld) Then
    If Not theworld Is Nothing Then
      theworld.ColourNote "white", "red", "Health Bar has been closed"
      theworld.CallPlugin "4637b3ca32d84f4b5ea6743b", "barclosed", ""
    End If
  End If

End Sub





Finally a file with a single global variable in it.

Globals.bas



Attribute VB_Name = "Globals"
Public theworld As world




Save these 4 files to disk under the indicated names, and open the MUSHclient_bar.vbp file in Visual Basic, and then compile.

All of the above files - the plugin, the 4 files, and the compiled executable - are in the file:


http://www.gammon.com.au/mushclient/HealthBar.zip


What you could try to do is:


  • Get the above zip file
  • Put the plugin (Super_Health_Bar.xml) in your plugins directory
  • Execute the program (MUSHclient_bar.exe) - this will hopefully "register" it with Windows
  • Install the plugin into MUSHclient
  • Connect to your world - with luck, the health bar will appear




Features

The health bar displays 3 progress bars - health, mana, movement.

You can resize it and the progress bars will resize accordingly. The plugin will remember the width for next time.

You can move it and the location on the screen will be remembered by the plugin for next time.

You can use a trigger to individually set the HP, Max HP, movement, max movement, mana and max mana.

eg.

SetHP 22
SetMaxHP 100
SetMove 40
SetMaxMove 88
SetMana 1000
SetMaxMana 2000

You can move it and set its width:

SetPosition 500, 8080
SetWidth 1000

You can set the window title and tell it which world is calling it:

SetTitle world, "SMAUG"

You can get the X and Y coordinates, and with:

X = GetX
Y = GetY
width = GetWidth

- Nick Gammon

www.gammon.com.au, www.mushclient.com
Top

Posted by Nick Gammon   Australia  (23,046 posts)  Bio   Forum Administrator
Date Reply #1 on Sat 16 Aug 2003 04:07 AM (UTC)
Message

This is what the health bar looks like:


- Nick Gammon

www.gammon.com.au, www.mushclient.com
Top

Posted by Shadowfyr   USA  (1,787 posts)  Bio
Date Reply #2 on Sat 16 Aug 2003 05:43 AM (UTC)

Amended on Sat 16 Aug 2003 05:47 AM (UTC) by Shadowfyr

Message
Interesting. Too bad the gauges that VB uses are ugly and a predetermined color. To do anything real impressive you have to build your own control, kind of like with the 'fiddly' toolbars. On the other hand.. It would be fairly simple in the next version, once we have GetFrame, to use my docking idea to position this as though it was really part of the client.

It is fairly simple, you would simply use VB to GetWindowRect() from the Frame and set the top, left, right or bottom to the returned position +1 or -1, depending on where you are docking it. It would require periodic checks to make sure it stays docked on the edge, but that is no big deal.
Top

Posted by Nick Gammon   Australia  (23,046 posts)  Bio   Forum Administrator
Date Reply #3 on Sat 16 Aug 2003 05:56 AM (UTC)
Message
If you look at this link, it gives, in a rather complicated way, a more powerful progress bar in VB.

http://msdn.microsoft.com/library/default.asp?url=/library/en-us/dninvb00/html/conserve.asp

However I decided against doing that, at this stage, as I really wanted to illustrate the basic idea, which all the extra stuff about colour drawing would have hidden.

However if you want to incorporate it, and do a more powerful VB program, by all means. :)

- Nick Gammon

www.gammon.com.au, www.mushclient.com
Top

Posted by Poromenos   Greece  (1,037 posts)  Bio
Date Reply #4 on Sat 16 Aug 2003 08:13 PM (UTC)
Message
I hope that Microsoft site is not about subclassing... Anyway, I have code to make progress bars from simple VB picture controls, which are about 30 lines long. It's really simple, and the results are amazing. I will post some when I get back home... This project sounds interesting.

Vidi, Vici, Veni.
http://porocrom.poromenos.org/ Read it!
Top

Posted by Poromenos   Greece  (1,037 posts)  Bio
Date Reply #5 on Sat 23 Aug 2003 10:10 AM (UTC)
Message
Would it be easy to zip everything up and put them in a .zip file? This is too tedious :/

Vidi, Vici, Veni.
http://porocrom.poromenos.org/ Read it!
Top

Posted by Nick Gammon   Australia  (23,046 posts)  Bio   Forum Administrator
Date Reply #6 on Sat 23 Aug 2003 09:13 PM (UTC)
Message
It is there - see near the bottom of my first post here.

- Nick Gammon

www.gammon.com.au, www.mushclient.com
Top

Posted by Ian Kirker   (30 posts)  Bio
Date Reply #7 on Tue 23 Sep 2003 11:26 PM (UTC)
Message
If you've got some version of Nero installed on your computer, you can use the LED control from their Wave editor as a progress bar-like control. Using the RedZone and YellowZone properties on it, you can get it tricolour, at least.
Top

Posted by Ian Kirker   (30 posts)  Bio
Date Reply #8 on Wed 24 Sep 2003 02:28 AM (UTC)
Message
Oh, and you might also want to use SetWindowPos to make it always on top, comme ça:

Add to the/a module:

Public Const HWND_TOPMOST = -1
Public Const HWND_NOTOPMOST = -2
Public Const SWP_NOMOVE = &H2
Public Const SWP_NOSIZE = &H1
Public Const SWP_SHOWWINDOW = &H40

Public Declare Function SetWindowPos Lib "user32" Alias "SetWindowPos" (ByVal hwnd As Long, ByVal hWndInsertAfter As Long, ByVal x As Long, ByVal y As Long, ByVal cx As Long, ByVal cy As Long, ByVal wFlags As Long) As Long


And then have buttons or a menu that sets it to always on top or not using:

SetWindowPos Gauge.hwnd, HWND_TOPMOST, 0, 0, 0, 0, SWP_NOMOVE And SWP_NOSIZE And SWP_SHOWWINDOW


and

SetWindowPos Gauge.hwnd, HWND_NOTOPMOST, 0, 0, 0, 0, SWP_NOMOVE And SWP_NOSIZE And SWP_SHOWWINDOW


to set and unset the Always on Top-ness respectively.

And maybe have it so it toggles the Title Bar on a double click event.

-Ian
Top

Posted by Ian Kirker   (30 posts)  Bio
Date Reply #9 on Wed 24 Sep 2003 03:07 AM (UTC)
Message
PS: If anyone can get the above title bar thing to work, I'd be most grateful to find out how. For some reason, BorderStyle is read-only at runtime... I could just create two seperate forms, but if anyone else knows a better way...

Thanks,

-Ian
Top

Posted by Ked   Russia  (524 posts)  Bio
Date Reply #10 on Wed 24 Sep 2003 03:47 AM (UTC)
Message
Well, I've got it working in wxPython (with colours and all) but that doesn't help much, does it?
Top

Posted by Ian Kirker   (30 posts)  Bio
Date Reply #11 on Wed 24 Sep 2003 03:53 PM (UTC)
Message
On further testing, I think some of the SWP_ flags conflicted, so I took the former SetWindowPos calls out and did this instead:

Public AOTP as Boolean

Public Sub Form_DblClick()
  If AOTP = False Then
    Dump = SetWindowPos(frmBar.hwnd, HWND_TOPMOST, frmBar.Left / Screen.TwipsPerPixelX, frmBar.Top / Screen.TwipsPerPixelY, frmBar.width / Screen.TwipsPerPixelX, frmBar.Height / Screen.TwipsPerPixelY, SWP_SHOWWINDOW)
    frmBar.Caption = "Status Bar - AOTP"
    AOTP = True
  Else
    Dump = SetWindowPos(frmBar.hwnd, HWND_NOTOPMOST, frmBar.Left / Screen.TwipsPerPixelX, frmBar.Top / Screen.TwipsPerPixelY, frmBar.width / Screen.TwipsPerPixelX, frmBar.Height / Screen.TwipsPerPixelY, SWP_SHOWWINDOW)
    frmBar.Caption = "Status Bar"
    AOTP = False
  End If
End Sub


If you want to make the AOTP variable save, and check it when you start the status bar again, you could save it like the X, Y and size properties, and have a similar bit to the above in the Form_Load sub, assuming that the Class Module loads before the Form.

My bar currently looks like this: [img=http://phenix.rootshell.be/~ian/statusbar.jpg]

(No movement points on our MUD, no sirree!)

-Ian
Top

Posted by Johnathan Allen   (49 posts)  Bio
Date Reply #12 on Fri 28 Nov 2003 08:57 AM (UTC)
Message
Any tips on getting this to 'register' with windows? I always get the "Cannot execute..." note.
Top

Posted by Shadowfyr   USA  (1,787 posts)  Bio
Date Reply #13 on Fri 28 Nov 2003 09:43 PM (UTC)
Message
Well Ian, the problem is not conflicts between the setting you are trying to use. You need to "OR" the values not "AND" them. This also avoids the need to specify the 4 coordinates for the position, since 'SWP_NOMOVE OR SWP_NOSIZE' will cause the API to ignore those options.

The reason "And" doesn't work should be obvious:

&H1 = 00000001 'in binary'
&H2 = 00000010
--------------
AND = 00000000

&H1 = 00000001
&H2 = 00000010
--------------
OR = 00000011

As for registering the thing Johnathan.. If you have VB and do a 'Full Compile' it should automatically register. When you merely 'Run' it, the VB IDE creates a temporary registration that only works with the control as it runs in the debugger. I think there should also be an option under the file menu to generate the full DLL or EXE instead.

If you get a pre-compiled version from some one, then an EXE is ironically easier to use, since it apparently self registers when you run it the first time. For DLLs you have to use a RUNDLL32 command, I can't remember what the command line options are though. It is generally better to have the programs creator use the packaging wizard or some similar installer to create setup file that handles all the stuff needed to run it.

NOTE: There is a bug in all versions of VB before .NET.Depending on your system it will either automatically include or tell you it cannot find four automation files it thinks it needs. These are only supposed to be included when designing web based remote access controls, but the packager tries to add them even for basic ActiveX. Just tell it to ignore these files and continue when/if you make a package to distribute to people. ;)
Top

Posted by Johnathan Allen   (49 posts)  Bio
Date Reply #14 on Fri 28 Nov 2003 11:35 PM (UTC)
Message
I don't have VB, I downloaded the zip file and put it in my plugins directory, installed the plugin, double clicked the .exe, and it didn't work. I've tried several variations to no avail.
Top

The dates and times for posts above are shown in Universal Co-ordinated Time (UTC).

To show them in your local time you can join the forum, and then set the 'time correction' field in your profile to the number of hours difference between your location and UTC time.


109,586 views.

This is page 1, subject is 3 pages long: 1 2  3  [Next page]

It is now over 60 days since the last post. This thread is closed.     Refresh page

Go to topic:           Search the forum


[Go to top] top

Quick links: MUSHclient. MUSHclient help. Forum shortcuts. Posting templates. Lua modules. Lua documentation.

Information and images on this site are licensed under the Creative Commons Attribution 3.0 Australia License unless stated otherwise.

[Home]