Welcome!
This is the community forum for my apps Pythonista and Editorial.
For individual support questions, you can also send an email. If you have a very short question or just want to say hello — I'm @olemoritz on Twitter.
Any UI module tutorials out there?
-
1 I am unclear what your text around this means. When I subclass View, my
__init__()
only takes self as a parameter and the method never callsView.__init__()
and it usually only contains one method call to self.present(). The real work will happen indid_load()
.7/8 I see a difference between self['save button'] and self.save_button but perhaps it is not super important. However, what I am interested to have is a single function/method that I can call to create the save, load, and delete buttons. I would lose that reusability if the function/method directly attached the newly created button to self.
9/10 My recommendation was NOT to create a separate
class wvDelegate (object)
. Instead, so far, I have seen it best to make MySuperCoolView or MySuperCoolController (the 'self' at View creation time) be the delegate. I would advocate using sender.name instead of id(sender) in your examples. Then you can do things with self[webview.name] or... names go well with dicts:def webview_did_finish_load(self, webview): webview_names = {'Apple' : 1, 'Google' : 2, 'IBM' : 3} alert_id = webview_names.get(webview.name, 0) if alert_id: console.hud_alert(str(alert_id)) else: panic()
-
@ccc Thanks.
Sorry about '1'... I meant the init we use for the subclass of View, skips the init of View itself, I think. I can't see View's init... but presumably we know it's safe to skip it?
-
Yes. Read the comments under
__init__()
in the code block at http://omz-software.com/pythonista/docs/ios/ui.html#building-custom-views "You don't have to call super.". -
In case it helps anyone following the best practices... there's currently a subtle difference between View and a sub class of View in terms of how they run between the main UI thread and the main interpreter thread... as the little test below shows (swap the comment line for the one above):
import ui import console class TestView (ui.View): pass v = ui.View() #v = TestView() v.present('popover') console.alert('Test', button1 = 'OK', hide_cancel_button = True)
-
@ccc Regarding best practice 2... is there a case for the
make_xxx()
method to be_make_xxx()
per the convention in The Python Tutorial... 8.6? -
See the notes on mixing console.alert with the ui module at http://omz-software.com/pythonista/docs/ios/ui.html#about-actions-and-delegates
Your
_make_xxx()
idea makes sense to me. -
@ccc Thanks and yes, but the point here is that the mere act of subclassing View causes it's thread behaviour to change. (If you run the test with View it will complete, but with TestView it will freeze)
I mention it because it can cause problems to surface when converting to the best practices.
For a case in point... see the Keychain Master Password thread... "This only happens when subclassing ui.View. When making a "standalone" view there's no lock up:" which @omz is investigating for a fix.
The in background function decorator doesn't work as advertised here in the current version I think.
-
The other KEY difference is that custom Views can not set self-based actions in the UI editor. Instead, the actions must be set in Python code. See the
set_actions()
method in the AreYouEnabledView.py example in the ui-tutorial. -
@tony This looks like a bug to me, thanks!
-
##Tutorial Suggestions
- What is the best practice to handle multiple views? I'm guessing a controller class that handles the ui.View changes.
- What is the best practice on passing arguments to a custom views init? It appears that if you use the editor sub class that this is not possible.
-
Looking for this?
https://github.com/humberry/ui-tutorial/blob/master/MultipleViews.py
-
@brumm I'm referring to multiple views as a bunch of separate ui.Views made in the editor. I was wondering that the best practice is to handle and load them as the user moved from one view to another.
btw Thank you for the tutorials, they cleared up a lot of my confusion.
Also had a question in regards to displaying on iPhone vs iPad. Would it be a good practice to have two .pyui files, one fore each device? If so do you know of any way to get the ios device being used?
Here is a little function I use to set the style of all my ui.view 's. It can take a dict that has the style elements for each view in the form of:
<pre>
default_style = {}
default_style['Main'] = {'background_color': 'white'}
default_style['Button'] = {'background_color': 'FFCAB0',
'border_color': 'FF9F70',
'border_width': 5,
'tint_color': 'FFFFFF',
'font': ('arial',14),
}
#Continue with Lable Tableview etc.def set_style(view, style=default_style):
for key, value in style['Main'].items():
setattr(view, key, value)
for v in view.subviews:
try:
for key, value in style[type(view[v.name]).name].items():
setattr(view[v.name], key, value)
except:
print 'Missing style for %s' % type(view[v.name]).name
</pre>I call the function in did_load(self) to style all the ui.view 's the same. Much easier then using the editor.
-
It's possible to load one view over another (pop-over2), but I don't know if this is a good style whether if there are performance issues.
You may get the screen size via the scene modul, but my attempts always ends up with a crash... -
Can't you get the screen dimensions with the UI module?
import ui the_view = ui.View() the_view.present() print(the_view.width, the_view.height) #print(the_view.bounds, # the_view.frame) the_view.close()
-
You're totally right, thank you.
-
@brumm Yeah I've been playing with different ways to load multiple ui.Views. I've tried using a main view and loading others as a subview. I've tried a view controller that loads and manages the views. I'm just not sure what the preferable method is.
I'm also unsure what the best way to create a custom view. Is it by using the Custom View Class in the editor(gain access to did_load etc.) or by making a class inherit from ui.view?