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.
ImageView UI Designer Code
-
@cvp not sure I understand..
I just want to lock a selected imageView in the ui at its current position I think so that it will no longer move unless using the properties window.
-
Also I can longer get either method to work today on a pyui that was working fine yesterday..or any other pyui - any ideas why that would happen?
I put a print statement in to check if it was finding the image name and it seems to be- it’s just not showing the image any longer.
-
@rb said
I just want to lock a selected imageView in the ui at its current position I think so that it will no longer move unless using the properties window.
I can't force as not movable but if you tap the script as tool, it resets the ImageView frame as full view if you had changed erroneously its position or size
-
@rb said
I put a print statement in to check if it was finding the image name and it seems to be- it’s just not showing the image any longer.
I got the same problem and have remarked a blank into the "named", like "test: Lena" instead of "test:Lenna" and I don't know why
-
@cvp so no longer working for you either?
Weird!? -
@rb no, no, it works but yesterday I got the same problem, check the file name in your custom attributes
-
@rb with a blank in file name, no image is showed. Don't ask me why
-
@cvp no blanks no typos the test:Lenna works but not other images.Cant see a reason for it to not work. If I access an image in a dir the syntax would be :
{'image': ui.Image.named('testDir/test.jpg')}
Right?
At least that’s what I was doing yesterday and it worked…I’m confused. -
@rb Perhaps due in which dir you were, could you try with the full path?
-
@rb this works (I present to you my dog, Nana)
-
Nana is a beauty :)
You are totally correct of course ! I managed to have 2 copies of thesetImageInDesigner.py
…duh one in iPad and one in iCloud where my scripts are stored so the path wasn’t resolving.Apologies for wasting part of your day with that ! -
@rb said
Apologies for wasting part of your day with that !
No problem, happy to have helped, sincerely
-
Next question..
If I want to add a custom image in designer for a button not an imageView…
I can’t get the image to load using the same above syntax in custom attributes.Is this something to do with :
.with_rendering_mode(ui.RENDERING_MODE_ORIGINAL)
And if so what would the proper syntax be inside that custom attribute string? So far I just get errors if I add that as an extra string on end of image path.
Also it’s not important that this image is visible in designer just that it works in final use when loaded/used in another view. -
@rb try
import editor import ast import json from objc_util import * import ui @on_main_thread def SetImageInDesigner(): global filenames filenames = {} t = "ui.Image.named('" fil = editor.get_path() #print(fil) with open(fil) as f: dic = json.load(f)[0] nodes = dic['nodes'] for node in nodes: if node['class'] in ['ImageView', 'Button']: attrs = node['attributes']['custom_attributes'] i = attrs.find(t) if i >= 0: j = attrs.find("')", i) img = attrs[i+len(t):j] nam = node['attributes']['name'] filenames[nam] = img win = ObjCClass('UIApplication').sharedApplication().keyWindow() main_view = win.rootViewController().view() def analyze(v,indent): global filenames for sv in v.subviews(): #print(indent,sv._get_objc_classname()) if 'UIImageView' in str(sv._get_objc_classname()): if 'OMUIWidgetViewImageView' in str(sv.superview()._get_objc_classname()): if 'OMUIDesignCanvasView' in str(sv.superview().superview()._get_objc_classname()): w = sv.superview() w.setFrame_(w.superview().frame()) for svw in w.subviews(): if 'UILabel' in str(svw._get_objc_classname()): n = str(svw.text()) break if n in filenames: sv.setImage_(ObjCInstance(ui.Image.named(filenames[n]))) elif 'UIButton' in str(sv._get_objc_classname()): if 'OMUIWidgetViewButton' in str(sv.superview()._get_objc_classname()): if 'OMUIDesignCanvasView' in str(sv.superview().superview()._get_objc_classname()): w = sv.superview() for svw in w.subviews(): if 'UILabel' in str(svw._get_objc_classname()): n = str(svw.text()) break if n in filenames: sv.setImage_forState_(ObjCInstance(ui.Image.named(filenames[n]).with_rendering_mode(ui.RENDERING_MODE_ORIGINAL)),0) analyze(sv,indent+' ') analyze(main_view,'') return if __name__ == '__main__': SetImageInDesigner()
-
@rb You have to know that you can set the image or the background_image of a button.
If you set the background_image, the button title is also visible.The modified tool script sets the image, not the background_image.
If you would prefer to set the background_image or both (not together), tell me, I should need to change the tool script
-
@rb try this version, supporting custom attributes image and background_image but not together
import editor import ast import json from objc_util import * import ui @on_main_thread def SetImageInDesigner(): global filenames filenames = {} t = "ui.Image.named('" fil = editor.get_path() #print(fil) with open(fil) as f: dic = json.load(f)[0] nodes = dic['nodes'] for node in nodes: if node['class'] in ['ImageView', 'Button']: attrs = node['attributes']['custom_attributes'] #print(attrs) i = attrs.find(t) if i >= 0: j = attrs.find("')", i) img = attrs[i+len(t):j] nam = node['attributes']['name'] if node['class'] == 'Button': if "'image'" in attrs: k = 'image' else: k = 'background_image' filenames[nam] = (img,k) else: filenames[nam] = (img,'image') win = ObjCClass('UIApplication').sharedApplication().keyWindow() main_view = win.rootViewController().view() def analyze(v,indent): global filenames for sv in v.subviews(): #print(indent,sv._get_objc_classname()) if 'UIImageView' in str(sv._get_objc_classname()): if 'OMUIWidgetViewImageView' in str(sv.superview()._get_objc_classname()): if 'OMUIDesignCanvasView' in str(sv.superview().superview()._get_objc_classname()): w = sv.superview() w.setFrame_(w.superview().frame()) for svw in w.subviews(): if 'UILabel' in str(svw._get_objc_classname()): n = str(svw.text()) break if n in filenames: sv.setImage_(ObjCInstance(ui.Image.named(filenames[n][0]))) elif 'UIButton' in str(sv._get_objc_classname()): if 'OMUIWidgetViewButton' in str(sv.superview()._get_objc_classname()): if 'OMUIDesignCanvasView' in str(sv.superview().superview()._get_objc_classname()): w = sv.superview() for svw in w.subviews(): if 'UILabel' in str(svw._get_objc_classname()): n = str(svw.text()) break if n in filenames: #print(dir(sv)) if filenames[n][1] == 'image': sv.setImage_forState_(ObjCInstance(ui.Image.named(filenames[n][0]).with_rendering_mode(ui.RENDERING_MODE_ORIGINAL)),0) else: sv.setBackgroundImage_forState_ (ObjCInstance(ui.Image.named(filenames[n][0]).with_rendering_mode(ui.RENDERING_MODE_ORIGINAL)),0) analyze(sv,indent+' ') analyze(main_view,'') return if __name__ == '__main__': SetImageInDesigner()
-
Dude your so generous with your assistance always above and beyond Thankyou ! It’s sunny right now in uk so I’m chillin with my dawg in the garden with a beer - will check this as darkness falls :)
-
-
Found couple of issues.
I had to add the middle line/check:if node['class'] in ['ImageView', 'Button']: if 'custom_attributes' in node['attributes']: attrs = node['attributes']['custom_attributes'] ``` As I have some other buttons without anything in custom_attributes and it was erroring. After changing that I get the images appearing on buttons in designer woop! but unfortunately it still fails when imported as a load_view in my main function with same error ie : Warning: Could not load custom attributes of view "test_btn": 'NoneType' object has no attribute 'with_rendering_mode'
-
Ok it was the path again but it makes no sense to me …
My path was resolved ok in designer using your script but I had to specify a full path to get it working as a load view. I don’t have to do this with the image views they work after I’ve set my file using
os.chdir(os.path.split(__file__)[0])
Anyhow it works so thanks again!