question-mark
Stuck on an issue?

Lightrun Answers was designed to reduce the constant googling that comes with debugging 3rd party libraries. It collects links to all the places you might be looking at while hunting down a tough bug.

And, if you’re still stuck at the end, we’re happy to hop on a call to see how we can help out.

Add a flood gauge style progressbar with label

See original GitHub issue

The idea behind this widget style is that it is similar to a card you would see commonly on a dashboard that includes text. It is essentially a progressbar with text in the middle. And, it can be used exactly as a progressbar, with some adjustments to the text size and thickness.

This style can be created by adding a custom layout based on the progressbar and the label.

image

I’ve decided to use a brightened and desaturated color for the progressbar background so that I have no need to change the text color when the gauge is filled past the 50% mark.

The method below would be added to the StylerTTK class. The code currently reflects the primary color styles. The other colors would be the same logic, with just an iteration over the other available colors.

def _style_floodgauge(self):
    """
    Create a style configuration for the *ttk.Progressbar* that makes it into a floodgauge. Which is essentially
    a very large progress bar with text in the middle.

    The options available in this widget include:

        - Floodgauge.trough: borderwidth, troughcolor, troughrelief
        - Floodgauge.pbar: orient, thickness, barsize, pbarrelief, borderwidth, background
        - Floodgauge.text: 'text', 'font', 'foreground', 'underline', 'width', 'anchor', 'justify', 'wraplength',
            'embossed'
    """
    self.settings.update({
        'Floodgauge.trough': {'element create': ('from', 'clam')},
        'Floodgauge.pbar': {'element create': ('from', 'default')},
        'Horizontal.TFloodgauge': {
            'layout': [('Floodgauge.trough', {'children': [
                ('Floodgauge.pbar', {'side': 'left', 'sticky': 'ns'}),
                ("Floodgauge.label", {"sticky": ""})],
                'sticky': 'nswe'})],
            'configure': {
                'thickness': 100,
                'borderwidth': 1,
                'bordercolor': self.theme.colors.primary,
                'lightcolor': self.theme.colors.primary,
                'pbarrelief': 'flat',
                'troughcolor': Colors.update_hsv(self.theme.colors.primary, sd=-0.3, vd=0.8),
                'background': self.theme.colors.primary,
                'foreground': self.theme.colors.selectfg,
                'justify': 'center',
                'anchor': 'center',
                'font': 'helvetica 16'}},
        'Vertical.TFloodgauge': {
            'layout': [('Floodgauge.trough', {'children': [
                ('Floodgauge.pbar', {'side': 'bottom', 'sticky': 'we'}),
                ("Floodgauge.label", {"sticky": ""})],
                'sticky': 'nswe'})],
            'configure': {
                'thickness': 100,
                'borderwidth': 1,
                'bordercolor': self.theme.colors.primary,
                'lightcolor': self.theme.colors.primary,
                'pbarrelief': 'flat',
                'troughcolor': Colors.update_hsv(self.theme.colors.primary, sd=-0.3, vd=0.8),
                'background': self.theme.colors.primary,
                'foreground': self.theme.colors.selectfg,
                'justify': 'center',
                'anchor': 'center',
                'font': 'helvetica 16'}
        }})

Below is a prototype of the Floodgauge class. I will have to handle the label options separately because TCL doesn’t understand a hybrid widget. The progressbar takes priority, so an error will occur if I try to pass through the text options to the superclass constructor. However, these options can still manipulated in the style since they actually exist in the layout. To get around this, I’ve created a hack that generates a unique style based on the one passed into the constructor that can be altered continuously. I believe this is similar to the approach taken by other developers (eg. PySimpleGUI) for creating custom styles on each button.

In the case of changing the text. I’ve set a trace on the textvariable so that it updates the widget every time the textvariable changes.

import tkinter as tk
from tkinter import ttk
from ttkbootstrap import Style
from uuid import uuid4


class Floodgauge(ttk.Progressbar):

    def __init__(self, parent, **kw):
        _style = kw.get('style') or 'TFloodgauge'
        _id = uuid4()
        _orient = kw.get('orient').title() or 'Horizontal'
        self._widgetstyle = f'{_id}.{_orient}.{_style}'
        parent.tk.call("ttk::style", "configure", self._widgetstyle, '-%s' % None, None, None)

        kwargs = {k: v for k, v in kw.items() if k not in ['text']}

        self.textvariable = kw.get('textvariable') or tk.StringVar(value=kw.get('text'))
        self.textvariable.trace_add('write', self._textvariable_write)
        self.variable = kw.get('variable') or tk.IntVar(value=kw.get('value') or 0)

        super().__init__(parent, class_='Floodgauge', style=self._widgetstyle, variable=self.variable, **kwargs)

    @property
    def text(self):
        return self.textvariable.get()

    @text.setter
    def text(self, value):
        self.textvariable.set(value)

    @property
    def value(self):
        return self.variable.get()

    @value.setter
    def value(self, value):
        self.variable.set(value)

    def _textvariable_write(self, *args):
        """
        Update the label text when there is a `write` action on the textvariable
        """
        self.tk.call("ttk::style", "configure", self._widgetstyle, '-%s' % 'text', self.textvariable.get(), None)


if __name__ == '__main__':
    root = tk.Tk()
    root.geometry('400x400')
    s = Style()
    p = Floodgauge(root, value=55, text='55', orient='vertical')


    def auto(progress):
        p.text = f'Memory Usage\n{p.value}%'
        p.step(1)
        p.after(50, auto, p)


    p.pack(fill='both', padx=20, pady=20, expand='yes')
    auto(p)
    root.mainloop()

Issue Analytics

  • State:closed
  • Created 2 years ago
  • Comments:16 (7 by maintainers)

github_iconTop GitHub Comments

1reaction
israel-dryercommented, Dec 17, 2021

@RocksWon the round scrollbar isn’t in 0.5, mainly due to the limitation of having to create so many images. This is one of the things I changed in 1.0, where I am only creating the themes and styles that are used on-demand, instead of what is typically done with ttk themes, which is loading all the assets and building the styles first. However, by having so many pre-defined styles available, this caused memory issues.

Here is an issue that describes some of the changes made to 0.5 -> https://github.com/israel-dryer/ttkbootstrap/issues/82

1reaction
israel-dryercommented, May 10, 2021

Glad to hear it’s working. Added some fixes, and also added the calendar widgets.

https://ttkbootstrap.readthedocs.io/en/latest/widgets/calendar.html

Read more comments on GitHub >

github_iconTop Results From Across the Web

ProgressBar - Android Developers
AbsSeekBar, AbsSeekBar extends the capabilities of ProgressBar by adding a draggable thumb. ... android:tag, Supply a tag for this view containing a String, ......
Read more >
How to Use Progress Bars - Oracle Help Center
You can show work without measurable progress by putting the progress bar ... setValue(progress); taskOutput.append(String.format( "Completed %d%% of task.
Read more >
Adding a percentage label to progress bar jquery
RossG gave a correct answer. If you want to save space, you can put the label inside the progress bar like this: <div...
Read more >
UltraProgressBar - Infragistics Windows Forms™ Help
The type of flood fill that is rendered can be determined via the Style ... The UltraProgressBar can also displayed a label (Text)...
Read more >
Progress - Bootstrap
Add labels to your progress bars by placing text within the .progress-bar . 25%. Copy. <div class= ...
Read more >

github_iconTop Related Medium Post

No results found

github_iconTop Related StackOverflow Question

No results found

github_iconTroubleshoot Live Code

Lightrun enables developers to add logs, metrics and snapshots to live code - no restarts or redeploys required.
Start Free

github_iconTop Related Reddit Thread

No results found

github_iconTop Related Hackernoon Post

No results found

github_iconTop Related Tweet

No results found

github_iconTop Related Dev.to Post

No results found

github_iconTop Related Hashnode Post

No results found