BSA – Modbus Demo

This took me < 2 min to set up and is just a simple Modbus demo.

  1. ComLink1 is a serial port connected to com3 in this case. The component has an auto option that allows it to always be connected that I use in this case.
  2. ModbusTable1 define parts of a Modbus map – in this case a single float value located at register 30000. Ths setting also specify base 0 and that 30000 is 0.
  3. MyForm is an app as simple as you get with my new Circular Gauge on it. The only detail I am not happy with here is that the name “MyGauge” is a bit hidden.
  4. The diagram at bottom start with a timer triggering once per sec calling a Select that read ModbusTable1 using ComLink1. If that works I call an Assign that update the value of MyGauge.

That’s it. If you pay attention you will see that every detail I need to code this application is on the screen.

BSA – Circular Gauge

This shows the Standard Circular Gauge. Starting from left I only show the needle and add component by component – in this case by enabling a checkbox. Background is made half transparent, something all colors support. This is a standard Draw, Drop & Use gauge in case yoiu don’t want the extra fuzz of creating your own custom one. Colors and Needle types, Slider button type as well as range and angles can be adjusted in the designer. The standard gauge is quite capable. This one ends up with a lot of properties, but it is designed to be a srtaight forward, easy to use Gauge.

This is also the standard gauge – just different angle setting and background removed on 4 of the gaugses.

This is just another example – still the standard gauge – three of them.

 

BSA – Circular Gauges – Part 10 . Circular Slider

The last circular component I want to write about is the Slider – a circular slider. I will build Linear Gauge later and after that I want to do the Real Time Plot – all build component by component.

A Circuar Slider is basically only a needle with a larger Inner-/Outer- Radius formed as a small button rather than a needle + it takes user interface to move the button in a circle. This example show an pointer (Orange triangle) that can be used to set values – threshold values or limits etc. You click on the button and drag it. Me in person I am not that big fan of these sliders because I preffer setting values using edit fields. Doing the same with a visual component can be a bit fiddly to get the value you want – but, they have their usage and is easy to make.

BSA – Circular Gauges – Part 9 – Common Coordinates

One of the challenges I have is that it is a big difference from making a library component and making a BSA supported component. Take Width/Hight/Center/Radius of a circular gauge as an example – this is straight forward in your own code, but doing the same on a visual designer is challenging because the visual designer snap to grids and it can be difficult/impossible to align circular components with diferent radius correctly. The example above is a bit made up, but it illustrate the problem and this is a designer only problem.

The easy solution is to implement a “UseParameters” property forcing the controls to use fixed property values for a reference design. This works – the difference is that you then use a common fixed coordinate reference and ignore size markers in the designer. Dealing with circular designs I find this to be a must.

To make this scalable I need to track design width/height and compute the difference to actual width/height as we draw the components. It is important that we scale by drawing with re-computed coordinates and don’t attempt a zoom that will give a similar, but fuzzy result.

To make it easy to align coordinates I also show reference coordinates for parameterized designs. This challenge was very obvious with circular components that needs to fit together, but I also wonder if I should implement this all over – parameterized design that can override the visual click&drag designer? To switch off the grid will only make things worse as it becomes very difficult to align anything. I already have two grid sizes to assist on this, but parameterized design seems as a savior for those situations where we will struggle with the grid.

 

BSA – Circular Gauges – Part 8 – Custom Gauges

As I now have some components that I can use to create a Gauge I also need a way to design the final API for that Gauge. Each component have a set of properties I want to access as a group, so I need an easee way to combine properties and add logic if needed.

In the example above I have (1) a circular label, (2) a circular tick, (3 ) a pie and (4) a needle. They all have Start-/End-Angle, radius settings, range setting etc that needs to be coordinated in the final gauge. And this is an easy one since all common parameters will be the same except for radius and colors.

This new gauge(above) adds two more Pie’s to show value areas in Green, Yellow and Red. Green start at 45 degrees and last 180 degrees, yellow start where Green end and last 60 degrees while Red occupy the rest. Start- and End- Angle on these are calculations depending on separate threshold values that only exist in the final gauge. I have ways of doing logic in BSA so that is not the challenge – the same goes to curstom properties, methods and events. A possible solution is drafted below. In this example I add a table called “Properties” to the diagram and define the Gauge properties here. I then process “Changed” for Start- and End-Angle by computing in a Assign box.

I need to think on this a little to see if this achieves what I want – to be able to design complex gauges fast. Now lets use our new Gauge:

In this example I assume that I have a Modbus device with a double value located in register 30000 to 30003, so I map this and set up a timer to read using a Select Statement. If we receive data we send a “NewValue” event that we can use to change value of the Needle component. I did not show the later, but you get the idea.

This last example is the same as the previous – I just added “Gauge4” as the diagram is called directly to illustrate how a gauge (or any UI component) can be linked directly into other diagrams and used. This example assume we have a Form named “Form3” that contains our gauge named “Gauge4”. The sub-diagram above reference that object allowing me to use it in logic and I have hidden all the methods/events I don’t want to see as part of this diagram.

I will need to actually use this a bit myself to see if it came together with the result I wanted to, so bear with me if I miss details because this is still work in progress.

BSA – Circular Gauges – Part 7 – The Needle

In a classic circular gauge we often use a needle to indicate current value. To draw this you have two options – (1) you can compute cartesian coordinates or (2) you can just draw the needle and rotate it – I used the later trick in this example. I have no idea what is the most efficient way and I don’t really care because rotation is done by the GPU. This example is drawen horisontally to the right before it is rotated -45 degrees.

The next issue is animation. QML is very good at animations, but they exist in WPF as well. Animating a needle is easy – you give the next position to a background thread that move the needle to make it look analogue. And the best thing is that done right the only thing you change is the needle. The rest of the gauge is not even redrawn as you only alter the Needle layer.

Next we will compose some fancy gauges to demonstrate how powerfully this system is.

BSA – Circular Gauges – Part 6 – A bad idea got right

Some of you will remember my idea to use a grid to enter components one by one and then showing the result at top. Having tested that option a bit I decided against it. I found that just using the normal designer stacking the components on top of eachother was easier. At the end you just select

The Gauge below is actually not a gauge but composed of an Ellispe, a circular Label, a circular Tick and a Pie. It is very easy to assemble in the designer as is – afterwards you just select the components and group them as a new, visual component that you can re-use. This is just an example – the real power comes then combining this with other components to create custom power components – I will get to that later. But, conclusion – the grid designer will be removed – it serves no real purpose.

BSA – Circular Gauge – Part 5 – Labels

Labels are equally easy – just use the same center and compute cartesian coordinates for the positions you want labels on. But, as you can see from the example below I get an additional issue. I used the coordinates as the upper, left corner and labels at left comes closer than labels at right etc. I have displayed the background white to illustrate the issue. To solve this you need to calculate the width of the text labels and adjust the label so the coordinates are on center. That way the labels will adjust so they look to be at the same distance. Also notice that while I have Major ticks at every 10 degree, I only display labels at every 20 degree by choice. Even label at 20 degrees is a bit tight, but this is just to illustrate that they are different. I will also add another label control that display only selected values as a separate control.

So lets calculate with and height and adjust to center…

This one surpriced me, but notice that the white background area is quite large – this is Padding set to 5 and the calculation don’t adjust for that.

Adjusting for padding and moving the labels a bit closer + adding the correct endvalue we get a perfect result. Label “300” will be a little closer than label “”60” simply because it is wider, but I decided not to compensate for that for now.

This last screenshot is just to show the obvious – I have created circular components that have a start- and end- angle in degrees, so you can create whatever gauge you want. Even more important is that you can decide what component(s) to change as the value change. Usually we change the needle, but I can just as easily change the ticks and labels to rotate with a fixed needle. We are now getting into the many effects you can create and the reasons why I want the user to be able to create theire own custom gauges using a pick & mix. I will add in some standard gauges, but I think the concept that you can make your own is far more important.

BSA – Circular Gauge – Part 4 – Ticks

The second component is ticks. This just show degrees with every 10th degree as Major and every 2nd as Minor. Drawing ticks are straight forward using a Canvas as background. This is where I find WPF a bit confusing because my Pie had to be done on a Shape to get access to the Arc functions (Geometry) and later projected to a Canvas. Once that is done I can use Pie as a component on Canvas. Ticks howver are easier to just draw straight on a canvas and then add to a gauge canvas.

The next one is labels and now comes one of the reasons for having these separate. Adding a label to every major Tick will be tight, so I add one to every 2nd. The option to do things like this is easier as the components to build a gauge are separate.

BSA – Circular Gauge – Part 3 – Integer Error

A common mistake then reprecenting pixel positions is to use Integers. This is how we did things back in the 80’s and 90’s, but GPU’s use double and pixel 1.5 actually exist. As the GPU smooth lines it will add shades to make it look as if we have pixels between pixels. If your coordinate system is integers only it will mean that a figure that is moved on screen jump one pixel and look as if it changes a little. So in dealing with graphics – always use double and never round off because the GPU will make use of the decimals.