Percent Fill Basic Shape

Working with vision, I have a basic circle shape and I want to fill a certain portion of the inside based on a value. For instance, half full at 50%.

Is there an easy way to do this?

Use the Paintable Canvas.
E.G:

2 Likes

When I import that it has an issue with the parent project. I suppose that doesn’t really matter though as all I need is the script. Thanks

Exchange resources are packaged up weird. Inside the downloaded zip there's another zip that contains the 'raw' project export, which should import fine into 8.1... guess I gotta make a new version for 8.3, since you won't be able to import the 8.0 project.

EDIT: Actually, I think it'll still import fine to 8.3, it's just gateway restore we don't support, but project restoration should be fine.

1 Like

Does the designer ever show anything in the paintable canvas, or only in runtime?

How would I hardcode a java color in the script? I just want the circle to have a transparent background where not filled.

I also get an error “object has no attribute drawCenteredString” - I could easily just add text on top of the paintable canvas

from java.awt import BasicStroke
from java.awt.geom import Area, Ellipse2D, Rectangle2D

g = event.graphics

w = event.source.parent.width-2
h = event.source.parent.height-2

backgroundColor = event.source.background
foregroundColor = event.source.foreground

state = event.source.parent.state

#pump is running, show speed as needed
if 1 == state:
	level = event.source.parent.fillLevel
	show = event.source.parent.showLevel
#pump is not running or failed, don't show speed and fully fill
else:
	level = 100
	show = False


# Create shapes
circle = Ellipse2D.Float(1, 1, w, h)
fillLevel = min(100, level)
clip = Rectangle2D.Float(1, 1, w, h - level)

# Set line width
g.setStroke(BasicStroke(0.2))

# Draw transparent circle background
g.setColor(event.source.parent.background)
g.fill(circle)

# Draw partially filled circle
g.setColor(backgroundColor)
fill = Area(circle)
fill.subtract(Area(clip))
g.fill(fill)

# Draw circle outline
g.setColor(foregroundColor)
g.draw(circle)

# Draw % fill
if show:
	event.source.drawCenteredString("%s%%" % float(level)/10.0, w, h, g)

For something simpler you can just “mask” a level indicator with a rectangle cut out.

Draw a rectangle, draw a circle, center them on each other.

Select the rectangle and circle, click the Difference button.

Then drag a level indicator on to the window and arrange them, setting the new shape background color to match the window background color and border to transparent.

3 Likes

Nothing at 'design' time, but the component will render in 'preview' mode.

system.gui.color (system.vision.color in 8.3).

drawCenteredString is a custom method on the template:

def drawCenteredString(self, text, width, height, graphics):
	"""
	Arguments:
		self: A reference to the component instance this method is invoked on. This argument
		  is automatic and should not be specified when invoking this method.
	"""
	fm = graphics.fontMetrics
	offsetX = (width - fm.stringWidth(text)) / 2
	offsetY = (fm.ascent + (height - (fm.ascent + fm.descent)) / 2)
	graphics.drawString(text, offsetX, offsetY)
2 Likes