Having difficulty in loading .kv file - python

I've saved both my python and kv file in the same folder but the program is unable to load it implicitly using the app name. I've tried using Builder.load_file() to load it explicitly but it results in a file not found error.
The only way it works is if i use the Builder.load_string() function but it makes the code tough to manage and also very badly organized. I'd really appreciate some help fixing this error.

maybe you can check whether your app class name match your .kv file
e.g.
.py
class MyKivyApp(App): # <-- here you should name your .kv file as mykivy , it comes from the class name "MyKivyApp" without the "App"
def build(self):
...
so the .kv file name will be mykivy.kv
or you can try kivy.lang.Builder.load_string() in .py , it just like the .kv but in the form of string ...
e.g.
.py
import kivy
from kivy.uix.widget import Widget
kivy.lang.Builder.load_string(
'''
#:kivy 2.0.0
<MyApp>
Button:
text: 'Helo World !"
size: root.size
''')
class MyApp(Widget):
pass
class mykivyApp(App):
def build(self):
main = MyApp()
return main
sth like this

Related

Python function which I can not call from kivy

### main.py ###
from kivy.app import App
class MainScreen():
def button_clicked(self):
print("*")
class KivyApp(App):
pass
KivyApp().run()
### kivy.kv ###
MainScreen:
<MainScreen#BoxLayout>:
Button:
on_press: root.button_clicked()
Why I can not call button_clicked() function from kivy?
I know that I can call it if describe like
class MainScreen(BoxLayout)
in main.py. But why I can not with above codes?
So, I am not 100% sure about my answer but here is what I think is happening...
The py file runs first and then the kv file, so if in the py file you have Class MainScreen(BoxLayout): the MainScreen class is defined and inherits from BoxLayout... Then the rules are defined in the kV file as normal. When you use the #BoxLayout in the kV file the class is created again, so this over rides the first definition of MainScreen. As the py MainScreen has been over ridden by the kV MainScreen the attribute root.button_clicked() no longer exists....
If you really need use the #BoxLayout in the kV file you could add the function to the app class:
class LayoutApp(App):
def button_clicked(self):
print("*")
And then in the kV file:
MainScreen:
<MainScreen#BoxLayout>:
Button:
on_press: app.button_clicked()

Kivy showing a black screen when trying to use kv file?

So I want to do the styling of my Kivy app in a external .kv file, but when I run the main code, nothing appears to the black Kivy window.
Here's my main file called main.py
import kivy
from kivy.app import App
from kivy.uix.widget import Widget
class MyGrid(Widget):
pass
class MyApp(App):
def build(self):
return MyGrid()
if __name__ == '__main__':
MyApp().run()
And here's the .kv file located in the same directory and called my.kv
#:kivy 2.0.0
<MyGrid>:
Label:
text: "example example"
So I'm not getting any error, just nothing appearing in the Kivy GUI when I run the main code.
Why is this and how to fix it?
In order to load widgets from a separate kivy file, you need to import Builder:
from kivy.lang.builder import Builder
Builder.load_file('my.kv')
or in .py file
Builder.load_string("""
<MyGrid>:
Label:
text: "example example"
""")
The kivy file name should always be the App class name, in your case you should save file with MyApp.kv
else you need to use Builder to import

Kivy keeps coming up blank

I am trying to learn kivy and have two files open my main python file and a kv file for styling, everytime I run the python file the resulting window always comes up blank. I am running it using python main.py on windows 10.
main.py
import kivy
kivy.require('1.9.0')
from kivy.app import App
from kivy.uix.label import Label
class CustomLabel(Label):
pass
class App(App):
def build(self):
return CustomLabel()
app = App()
app.run()
kivy.kv
<CustomLab#Label>:
font_size: 32
<CustomLabel>:
CustomLab:
text: "Hello World"
I wanted to edit your post and comment but I can't.
You should not name your main class as "App" instead you can name it like "TestApp".
Like this:
class TestApp(App):
Also your kivy file's name should be a lowercase of your "TestApp" without the word "App" on it.
Like this:
test.kv
Inside your kivy file, you misspelled the class "CustomLabel" as "CustomLab".
To declare a class inside a kivy file, you must use a "<" and ">".
Like this:
<CustomLabel>:
I changed your code and it looked like this:
This is your main.py:
import kivy
kivy.require("1.9.0")
from kivy.app import App
from kivy.uix.label import Label
class CustomLabel(Label):
pass
class TestApp(App):
def build(self):
return CustomLabel()
app = TestApp()
app.run()
This is your test.kv:
<CustomLabel>:
text: "Hello World"
font_size: 32
I hope this will work.

Moving from one screen to another generates a RecursionError

I want create an app with a button that will call the another app or another part of this app.
For example:
I'm on the Main screen where I can choose some options like View Report, Create Report, Manage Report, etc. I think that all of those is a app.
So, I make two subclasses from the App class of Kivy, each of which has its own .kv file. Suppose that one is the Main screen and the another is the another screen.
When I do that it looks like it works, but when I call the second screen, in the console I get the following error in the console:
RecursionError: maximum recursion depth exceeded in comparison
How can I fix this?
My Main.py file contains
from kivy.app import App
class ProbandoApp(App):
pass
class TestApp(App):
probando = ProbandoApp()
print(__name__)
if __name__ == '__main__':
TestApp().run()
and I have the .kv file for each class.
I also have a file called test.kv that contains:
Widget:
Button:
id: btnTest
text: 'Test'
width: 100
height: self.font_size * 2
on_press: app.probando.run()
and a file called probando.kv that contains
Widget:
Button:
id: btnProbando
text: 'Otra cosa mas para probar'
It sounds like you don't want multiple apps, but a single app whose interface changes. You can do this by switching widgets around, and the ScreenManager provides a convenient api for this.

Using a button to load a kv file

Hi all my question is a basic one. I'm using a .kv file in which I have defined a button that changes screens. I would like to use that button to load .kv file. I can use builder.load(kv2.kv) ?
I've tried a bunch of different ways writing it out. The stats.kv file loads all my RPG stats. If I remove the builder statement, I just get the next screen. All my widgets are in a different .kv files for ease of debugging purposes. I just need to load multiple .kv files within a .kv file.
However this error always occurs:
AttributeError: 'RevengeApp' object has no attribute 'builder'
Button in .kv file:
Button:
text: "Confirm"
on_press: app.builder.load(stats.kv)
on_release: app.root.current = "AStats"
Did you assign the Builder object to the builder attribute of your app? because that's what your kv code seems to expect.
from kivy.lang import Builder
[…]
class RevengeApp(App):
def build(self):
self.builder = Builder
should do it.
But you could also just import Builder directly in your kv code by doing
#:import builder kivy.lang.Builder
at the top of your kv file, and then replace your app.builder.load with builder.load_file in your on_press binding.

Categories

Resources