복붙노트

[PYTHON] 런타임에 Kivy에서 내 위젯의 색상을 어떻게 변경합니까?

PYTHON

런타임에 Kivy에서 내 위젯의 색상을 어떻게 변경합니까?

Kivy에서 간단한 위젯의 색상을 변경하는 데 문제가 있습니다. 위젯을 만들 때 색상을 설정할 수 있지만 이후에는 변경할 수 없습니다.

다음은 간단한 레이아웃 정의 파일 인 circletest.kv입니다. 그것은 색상 (실제로는 rgba의 r), 위치 및 크기가 모두 위젯 클래스의 변수에 링크되는 원을 정의합니다.

#:kivy 1.4.1

<CircleWidget>:
    canvas:
        Color:
            rgba: self.r,1,1,1
        Ellipse:
            pos: self.pos
            size: self.size

여기에 circletest.py 응용 프로그램이 있습니다. 그것은 간단한 위젯을 생성하고 표시합니다. 객체가 생성되면 색상과 위치가 성공적으로 설정됩니다. 위젯을 클릭하면 위젯이 자신의 위치를 ​​변경할 수 있지만 색상을 변경하려고하면 아무 일도 일어나지 않습니다.

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                       # <---- This does nothing!

class TestApp(App):

    def build(s):
        parent = Widget()
        w = CircleWidget()
        parent.add_widget(w)
        return parent

if __name__ == '__main__':
    TestApp().run()

누구든지 문제를 볼 수 있습니까?

최신 정보

아직도이 질문에 대한 답이 무엇인지 확신 할 수 없지만 해결 방법이 있습니다.

.kv 파일에서 객체의 변수에 색상을 지정했습니다. 초기 색상을 추출하는 작업 :

Color:
    rgba: self.col

.py 파일의 색상을 변경하려면 캔버스의 모든 지시 사항을 반복하고 "색상"유형의 첫 번째 문자를 수정합니다. 분명히 이것은 해킹이며 하나 이상의 Color : 속성이있는 위젯에서는 작동하지 않습니다.

for i in s.canvas.get_group(None):
    if type(i) is Color:
        i.r, i.g, i.b, i.a = v
        break

나는 그것을 사용하기에 청초 할 정도로 모든 것을 감쌌다.

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

지금 당장 일하는 것 같아요. 더 나은 방법을 알고 계시다면 알려 주시기 바랍니다. 더 간단한 방법이 있어야하며 확실한 것이 빠져 있다는 것을 확신합니다!

해결법

  1. ==============================

    1.초기 버전에서는 방금 속성 선언이 누락되었습니다.

    초기 버전에서는 방금 속성 선언이 누락되었습니다.

    from kivy.properties import NumericProperty
    

    머리글 및

    r = NumericProperty(0)
    

    CircleWidget (위젯) 클래스 바로 아래 :

    또한, 귀하의 kv 파일의 이름이 circletest.kv이지만 귀하의 앱의 이름이 TestApp이기 때문에 그 중 하나를 변경하여 일관성있게 만들거나 kv 파일을 찾을 수 없지만보고하지 않으므로 그것으로 어떤 문제, 나는 그것이 질문에 오타 일 뿐이라는 것. 편집 : 그냥 보았다 Builder.load_file 확인,

    건배.

  2. ==============================

    2.tshirtman의 대답은 정확합니다. 여기에 무슨 일이 일어나고 있는지에 대한 설명이 있습니다.

    tshirtman의 대답은 정확합니다. 여기에 무슨 일이 일어나고 있는지에 대한 설명이 있습니다.

    kv 파일에서 설정시

    <CircleWidget>:
        canvas:
            Color:
                rgba: self.r, 1, 1, 1
            Ellipse:
                pos: self.pos
                size: self.size
    

    rgba : self.r, 1, 1, 1 라인은 r의 값이 변경 될 때마다 rgba의 값을 갱신하려고합니다. 이것은 바인딩에 의해 kv 언어로 암묵적으로 수행되며, 옵저버 패턴을 구현할 때 kivy Property에서 수행 할 수 있습니다.

    코드의 변수 r이 업데이트되었지만 값이 변경되어 바인딩 될 수 없다는 어떠한 표시도 제공하지 않는 변수 일뿐입니다. pos가 ReferenceListProperty이기 때문에 pos 작업에 대한 변경 사항을 확인한 경우.

    Kivy에서 프로그래밍하기위한 일반 규칙. 위젯 / 객체의 속성에 따라 코드를 변경하려면 Kivy 속성을 사용하십시오. Observe Property 변경 사항에 대한 옵션을 제공하고 bind / on_property_name 이벤트를 통해 명시 적으로 또는 위에서 언급 한 kv 언어를 통해 암시 적으로 코드를 조정합니다.

  3. from https://stackoverflow.com/questions/12997545/how-do-i-change-the-color-of-my-widget-in-kivy-at-run-time by cc-by-sa and MIT license