I have a MonoTouch tab view application. On one of my tabs, when a user clicks a button, I want to show another view. I do this with the following code:
UIView.BeginAnimations("flip");
UIView.SetAnimationDuration(1);
UIView.SetAnimationTransition(UIViewAnimationTransition.FlipFromRight, View, true);
NewFilesViewController newFilesViewController = new NewFilesViewController();
newFilesViewController.View.Frame = new System.Drawing.RectangleF(View.Frame.Top, this.View.Frame.Left, this.View.Frame.Width, this.View.Frame.Height);
View.AddSubview(newFilesViewController.View);
UIView.CommitAnimations();
On the new view, when I click a button, I get an error:
Got a SIGSEGV while executing native code. This usually indicates
a fatal error in the mono runtime or one of the native libraries
used by your application.
Should I be adding the view to the window instead? Is there a better way to do this?
This is likely (the code does not have enough context to be 100% sure) because newFilesViewController is not referenced anywhere later in the code. As such it can be disposed the next time the Garbage Collector (GC) is invoked. However the native code still except the view to exists and this will crash when it tries to call the (disposed) instance.
Fix: Promote your newFilesViewController local variable to a field. That will keep the reference alive (as long as the type's instance is alive) and the GC won't collect it.
Related
Is there a way to force the NSPopover to start in the detached state? I only see isDetached which is a read-only property for the state of the popover and an NSPopoverDelegate method detachableWindow(forPopover:) which lets me override the window that gets created. I'd like to essentially click a button and have the NSPopover start in the state in this photo.
The style of this window is exactly what a product requirement is and I can't seem to find any NSWindow style settings that would make a window do something like this (nor an NSPanel)
This detached popover functionality seems special in that it:
non-modal, but stays above main app. Able to still interact with the main app just like in Messages how you can still click around and type a new message.
Clicking another app, AppFoo, puts both the main app and the helper window behind AppFoo.
The helper window can be moved around and isn't hidden on app deactivation (another app gets selected).
Has the little, native, grey X in the top left.
If you don't mind calling private API, it's actually pretty simple:
let detach = NSSelectorFromString("detach")
if popover.responds(to: detach) {
popover.perform(detach)
}
No need to even add a delegate. I don't know when this private method was added but it's available at least since macOS 10.13. I suspect it's available since the introduction of NSPopover, though.
Here is the trick.
Use the required delegate method detachableWindowForPopover: to do the work for you, like:
- (void) showPopoverDetached
{
NSWindow* detachedWindow = [self detachableWindowForPopover:nil];
[detachedWindow.windowController showWindow:nil];
}
Seems that the Apple engineers implemented detachableWindowForPopover: on a pretty smart way, I guess it uses the content view controller class, and will always create a singleton like instance of the detached window.
Once detachableWindowForPopover: has called the presented window instance will be re-used no matter when and why it is called, called it directly (from a func like my sample above) or indirectly (e.g. when you drag out, detach, the popover from its original position)
This way they can prevent a popover from being detached 'twice' and we can also implement the detached way programmatically, nice job from them!
Here is a tiny demo of how it works in a real life (tested on macOS 10.13 - 13.0)
https://imgur.com/a/sfc7e6d
I'm trying to minimize memory usage in my app, and one of the things I'm doing is calling finish() in the onPause method (which I know is not the best way to do things). For the most part, it seems to be working well, but when the user clicks the back button from the next activity, it logically skips over the finished activity and goes back further. Is it possible to have that activity in the back stack and just get recreated if the user presses back?
No. This conclusion comes from the task and backstack documentation as well as the activity documentation and a general understanding of how a stack data structure works.
A stack data strucure only has 2 possible operations push/put, which adds something to the collection, and pop, which removes it. Stacks folow a last in first out model, or LIFO, where by last thing added - in your case an activity - is the first thing removed when pop is called.
Within the android lifecycle activities are generally popped from the stack when the back button is pressed. At that point onDestroy() is called and the activity is removed (you can verify this by overriding the onDestroy() method and logging the results if you want to check). Alternativly you can force onDestroy() to be called by calling finish() as you are. Finishing an activity effectivly does the same thing as pressing back. The activity is destroyed and must be recreated before it can be added to the stack.
For what you're trying to do the stack would have to incorporate some intermediate state in which an activity does not exist but rather something akin to a reference is held that, when moved to the top, would indicate that the corresponding activity should be recreated. Since this is not how the sack works - it only holds activities - that state cannont exist and so the result you are talking about is not possible.
Your Goal is to minimize memory usage,Just make use of activity life cycle, You can do this alternative(if you need)
-Just leave onCreate() method blank.(only do setContentView(layout))
-Override onResume();
-whatever you were doing in onCreate just copy paste to onResume().
-and In onPause(), Recycle your all bitmaps and set them to null(I think you are using Bitmaps thats why you are very cautious about it ). and remove your views.
Now what will happen, when you launch your new activity, onPause() would be called. that will remove your all bitmap and views. and when you come back, onResume() will be call.(onCreate will not be called). and that will again initialize your view and bitmaps.
No, i don't think that is possible. Once you finish the Activity it's gone. You could, however, implement and handle your own stack. On back pressed, you would just start the closed Activity again.
I made my project in storyboard in, due to issue with the custom UITableViewCell I have made a new project, copied all of the data to my new classes and copied my buttons, images etc from the storyboard views to new project's nib/xib files.
Now When I click on any button my app crashes without any error and it opens delegate file and highlights this line of code
return UIApplicationMain(argc, argv, nil, NSStringFromClass([ThisOrThatAppDelegate class]));
I have already made connections for the required actions from IB to controller. Also I have tried Command+Shift+K for clean code. But the problem is still there.
You have to find out first what the problem is:
use the Debug build config and are using lldb or gdb
make sure you have a breakpoint on all exceptions
make sure you have the "Breakpoints" button top left enabled.
run the app
You should break into the debugger. You need to get to a point where the debugger catches the exception.
Then edit your question and tell us what exception you get. I'm going to guess you'll be getting a objc_msgSend() error, which means that some object is trying to message a non-existent or dealloced object. If that turns out to be true, then you can enable "Zombies" (which lets all objects stay around) and see if one of those gets messaged.
If nothing seems to help, then what you need to do is start adding NSLog messages to track your app as it comes up (or use breakpoints, your choice). This takes a long time so you might work backwards - see if your appDelegate application:didFinishLaunchingWithOptions: gets called, and also if you get to the end of it.
Unforunately this type of problem can be take a lot of time to track down. Some object has probably queued a message up for another object on the main queue, so when you get the crash you don't get to see who did what when.
Also, with objc_msgSend problems, when the debugger stops you cannot easily see what object was messaged - but if you turn off the debugger and let the app actually crash, you can find the crash report in the Console app and get more info from that.
I am writing a GWT MVP application using the gwt-platform library (very nice once you get used to it). My issue occurs when my presenter attempts to update the contents of a Listbox. The problem occurs on line 66 of the below file:
https://github.com/dartmanx/mapmaker2/blob/master/src/main/java/org/jason/mapmaker/client/presenter/MapmakerStackPanelPresenter2.java
I am sure that the application is calling the onSuccess() method (a breakpoint in the debugger works), and that the result is populated.
One thing I've noticed is that the associated view, MapmakerStackPanelViewImpl2.java, seems to be initialized twice. I find myself wondering if I'm trying to update a control on that view that is not attached to the actual user interface. That file is here:
https://github.com/dartmanx/mapmaker2/blob/master/src/main/java/org/jason/mapmaker/client/view/MapmakerStackPanelView2.java
Any help would be appreciated.
The problem was that there were two copies of the view floating around. I used Gin to inject the view into the constructor of the presenter, and problem went away.
Caveat: I'm still struggling with proper MVC in Eclipse plugin development, so if you see anything here that is most likely causing me more pain that I should be enduring, please let me know.
The question:
I have a View with a JFace Tree Viewer and a Table (not a table viewer... that will be changed down the road).
I have an action that is initialized with a reference to the View (this seems terrible to me, but I don't yet know how to do it the right way). When the action is run -- via a button on the view -- the action:
1) gets the Tree Viewer from the View
2) gets the underlying model
3) creates a Job
a) inside the job, loops over the model and does various things to it, including adding additional children into the model
b) uses a function exposed in the view that "clears" the Table in the view
4) adds a JobChangeListener that implements "done()".
a) inside the done() method, it expands the treeviewer via this code:
loadMethodsJob.addJobChangeListener(new JobChangeAdapter(){
public void done(IJobChangeEvent event){
view.enableActions();
view.getTestsViewer().expandAll();
}
});
Inside the Job, whenever I attempt to access the elements in the viewer, I get Invalid Thread Access errors. I believe I understand why I get them when running inside the job, but I'm not sure how to work around them correctly if I can't interact with the widgets in the job change listener. I can get it to work if I wrap every interaction with the widgets in a getDisplay().synchExec(....), but I seem to remember reading that this is not preferable.
I feel like I'm on the cusp of a big leap in understanding with Eclipse SWT, so I appreciate any guidance in getting there.
Any UI component in SWT can be accessed only by a UI thread.
Since the done method of the job runs in a separate non-UI thread, the invalid thread access is fired.
By wrapping every interaction in a Display.syncExec , you are making sure that it runs in the display thread (The UI thread).
There shouldn't be any problem with the above approach.