On May 16, 2011, at 4:50 AM, Jonathan Taylor wrote:

> Thanks very much for your reply Ken, very helpful indeed.

You're welcome.


>> Still, that won't help if Function B is not being called as often as you 
>> expect because NSPostASAP doesn't work like you thought.  I suspect that it 
>> is only being called when something else tickles the run loop, like user 
>> events.  I wonder if you click-and-hold in your window (not necessarily on a 
>> button or any active control) and just keep dragging the mouse back and 
>> forth, if that helps keep the backlog clear.  (Simple mouse moves without 
>> the mouse button don't send events unless your window has specifically 
>> subscribed to them using NSTrackingArea or -setAcceptsMouseMovedEvents:.)
> I've got to be honest, I was very skeptical of this but that is indeed 
> exactly what happens. Bizarre! I wonder if this then suggests a workaround 
> (admittedly a hideous one) of manually posting "user" events to the main 
> loop!?

Well, it's not so hideous and it wouldn't necessarily be simulating user events 
(mouse clicks, key presses, or the like).  NSEvent supports application-defined 
events, which you can use for this purpose.  The -postEvent:atStart: method is 
even safe to call from background threads; the posted events are still received 
on the main thread.


> - I am not aware of a way of running code *on*the*main*thread* at low 
> priority (i.e. will not run unless there are "spare" cycles). While GCD has a 
> concept of low priority queues this applies to custom queues, not the main 
> thread where GUI-related code must (I think...) run.

Well, you can submit a block to a low-priority queue whose only work is to 
submit a block to the main queue:

        dispatch_async(dispatch_get_global_queue(DISPATCH_QUEUE_PRIORITY_LOW, 
NULL), ^{
                dispatch_async(dispatch_get_main_queue(), ^{
                        // Do some work
                });
        });

This doesn't do coalescing for you, but you can handle that manually.  Or, if 
you're only going to do something like -setNeedsDisplay:, that's coalescing by 
nature.


> It would not be too hard for me to write my own scheduler which could 
> prioritize the "important" work over the GUI updates, but this really does 
> seem like it shouldn't be necessary! This feels like a fairly common problem 
> to me, so I can't help feeling there must be a standard solution in the cocoa 
> APIs that I am missing...

I think the usual is to just set views as needing display when they do, and the 
framework and the Window Server will effectively throttle the update frame 
rate.  That is, I don't think there's such a thing as calling -setNeedsDisplay: 
"too frequently".  You just call it when the view is out-of-date with respect 
to internal state and let things take care of themselves.  On the other hand, 
that does assume that redrawing your view is kept as inexpensive as possible.  
You shouldn't be doing much computation or hard work in -drawRect:.

Regards,
Ken

_______________________________________________

Cocoa-dev mailing list (Cocoa-dev@lists.apple.com)

Please do not post admin requests or moderator comments to the list.
Contact the moderators at cocoa-dev-admins(at)lists.apple.com

Help/Unsubscribe/Update your Subscription:
http://lists.apple.com/mailman/options/cocoa-dev/archive%40mail-archive.com

This email sent to arch...@mail-archive.com

Reply via email to