Mark Wieder wrote:
On 05/24/2017 11:50 AM, Richard Gaskin via use-livecode wrote:
I'd go with executionContexts. Are there circumstances where this
wouldn't work?:
function CallerID
-- Line -1 = this function
-- Line -2 = the script that called this function
-- so:
return item 1 of line -3 of the executionContexts
end CallerID
That would work, but (to use the proper terminology) it has a code
smell. It's first of all dependent on the executionContexts format if
you're going to pick out the control ID, and while that format isn't
likely to change even though undocumented, it seems like yet another
level of dependency. There's already a dependence on having to know and
IDs of the calling objects, so the mouseUp handler is dependent on the
controls that might possibly call it. Any design change in the app might
require modifying the mouseUp code.
True, it relies on data returned from the engine, and that the scripter
using the function understands how to use it.
But those seem modest requirements. I can't think of much in any
language or library not exposed to those two potential weaknesses. :)
The executionContexts is documented, though in all fairness that Dict
entry includes a note about not relying on the format of its contents.
But a LOT of code in the LC universe currently depends on it, and the
role it serves is essential for critical things like debugging. And it
hasn't changed in more than 15 years.
Given all that, for myself I find the trade-offs acceptable. If the
format changes down the road I certainly won't be the only person
changing scripts to keep current.
Refactoring to remove the dependencies could look like:
on mouseUp
-- what actually happens with a real mouse click
doRealMouseStuff
end mouseUp
on handler1
-- make a jazz noise here
end handler1
on handler2
-- this space intentionally left blank
end handler2
-- in some other control...
-- dispatch "mouseUp" to controlWithHandlers -- deprecated
dispatch "handler1" to controlWithHandlers
Now the object with the handlers doesn't have to know a thing about any
other controls that might call its handlers, and the external controls
only need know that there is a "handler1" handler in that object. A
judicious use of revAvailableHandlers() (again undocumented) could also
be useful here.
I would be much more hesitant to rely on a function designed for IDE use
like revAvailableHandlers, but even there we don't really have an
alternative other than hand-crafing a slower replacement, so I use that
one too (though in only one place in my dev tools).
As for the refactoring, so much depends on the particulars of the
use-case.
Your outline above might be ideal if handling a specific number of
objects/options.
But if the handler being called needs to know the caller ID for some
purpose other than simple branching among a small number of options,
factoring could range from tedious to impractical.
Like so much in code, it all depends on "Why" we need a given piece of
information.
> Heh. Couldn't resist adding this:
> https://techbeacon.com/35-bad-programming-habits-make-your-code-smell
Fun read, and very relevant: many of the items in that list appear to
contradict others. I don't see that as a bad thing. Coding is a mix of
knowing so-called "best practices", and knowing when to skip 'em. :) As
such, that list is an uncommonly realistic one.
Everything in a finite and imperfect universe involves trade-offs....
--
Richard Gaskin
Fourth World Systems
Software Design and Development for the Desktop, Mobile, and the Web
____________________________________________________________________
ambassa...@fourthworld.com http://www.FourthWorld.com
_______________________________________________
use-livecode mailing list
use-livecode@lists.runrev.com
Please visit this url to subscribe, unsubscribe and manage your subscription
preferences:
http://lists.runrev.com/mailman/listinfo/use-livecode