title: How do I change the color of my widget in Kivy at run time?
body: <p>I'm having trouble changing the color of a simple widget in Kivy.
  I can set the color when I create the widget, but I can't change it afterwards.</p>
  
  <p>Here is the simple layout definition file <code>circletest.kv</code>. It defines a circle where the color (actually just the r, from rgba), position and size are all linked to variables in the widget class.</p>
  
  <pre><code>#:kivy 1.4.1
  
  &lt;CircleWidget&gt;:
      canvas:
          Color:
              rgba: self.r,1,1,1
          Ellipse:
              pos: self.pos
              size: self.size
  </code></pre>
  
  <p>Here's the application <code>circletest.py</code>. It creates and displays the simple widget. The color and position are successfully set when the object is created. When the widget is clicked the widget can change it's own position, but when I try to change the color nothing happens. </p>
  
  <pre><code>import kivy
  kivy.require('1.4.1')
  from kivy.app import App
  from kivy.lang import Builder
  from kivy.uix.widget import Widget
  
  Builder.load_file('circletest.kv')
  
  class CircleWidget(Widget):
  
      def __init__(s, **kwargs):
          s.size= [50,50]
          s.pos = [100,50]
          s.r = 0
          super(CircleWidget, s).__init__(**kwargs)
  
      def on_touch_down(s, touch):
          if s.collide_point(touch.x,touch.y):    
              s.pos = [s.pos[1],s.pos[0]]           # This works
              s.r = 1.0                       # &lt;---- This does nothing!
  
  class TestApp(App):
  
      def build(s):
          parent = Widget()
          w = CircleWidget()
          parent.add_widget(w)
          return parent
  
  if __name__ == '__main__':
      TestApp().run()
  </code></pre>
  
  <p>Can anyone see the problem?</p>
  
  <p><strong>UPDATE</strong></p>
  
  <p>Still not sure what the answer to this question is, but I do have a work around:</p>
  
  <p>In the .kv file I pointed the color to a variable in my object. Works for extracting the initial color:</p>
  
  <pre><code>Color:
      rgba: self.col
  </code></pre>
  
  <p>When I want to change the color from the .py file I loop through all the instructions in the canvas and modify the first one of type "Color". Obviously this is a hack, and won't work on widgets with more than one <code>Color:</code> property:</p>
  
  <pre><code>for i in s.canvas.get_group(None):
      if type(i) is Color:
          i.r, i.g, i.b, i.a = v
          break
  </code></pre>
  
  <p>I wrapped that all up in a property so it's neat to use:</p>
  
  <pre><code>class CircleWidget(Widget):
  
      def get_col(s):
          return s._col
  
      def set_col(s,v):
          for i in s.canvas.get_group(None):
              if type(i) is Color:
                  i.r, i.g, i.b, i.a = v
                  break
          s._col = v
  
      col = property(get_col, set_col)
  
      def __init__(s, **kwargs):
          s.size= [50,50]
          s.pos = [100,50]
          s._col = (1,1,0,1)
          super(CircleWidget, s).__init__(**kwargs)
  
      def on_touch_down(s, touch):
          if s.collide_point(touch.x,touch.y):    
              s.col = (s.col[::-1]) # Set to some other color
  </code></pre>
  
  <p>Seems to work for now. Please let me know if you know a better way of doing this. I'm sure there must be a simpler way, and that I'm missing something obvious!</p>