Created
May 12, 2010 19:54
-
-
Save Vaguery/399057 to your computer and use it in GitHub Desktop.
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
| # class name MUST match /[AnythingCamelCased]Instruction/ | |
| class MyNewNudgeInstruction < Instruction | |
| # preconditions? should return true if everything works | |
| # | |
| # use the #needs method for simple argument requirements checking: | |
| # test will pass if there are at least that many items on the named stack(s) | |
| def preconditions? | |
| needs :foo, 2 | |
| needs :bar, 1 | |
| end | |
| # use #setup to pop arguments from the stacks or gather them | |
| # from the environment more generally | |
| # (we won't reach here anyway if we don't pass #preconditions?) | |
| # convenience methods include: | |
| # #pop_value(stack_name) -> pop an item AND return its #value attribute | |
| # #pop(stack_name) -> pop an item | |
| # #peek_value(stack_name)-> peek at the top item AND return its #value attribute | |
| # #peek (stack_name) -> peek at the top item | |
| # #depth(stack_name) | |
| # the values will be returned by way of [NudgeType].from_string, so for example | |
| # peek_value(:int) -> an integer, not a string | |
| def setup | |
| @arg3 = @context.pop_value(:foo) | |
| @arg2 = @context.pop_value(:foo) | |
| @arg1 = @context.pop_value(:bar) | |
| # remember the convention here is that the original CODE read like "1 2 divide", so | |
| # the first argument was pushed before the second one | |
| end | |
| # use #derive to build the values or set up whatever else you need to determine what to do; | |
| # if you need to create new Interpreter instances, or access file storage, or | |
| # invoke external scripts, this is where to do it | |
| # | |
| # remember that you are going to be building a ValuePoint object, not the actual result | |
| # of your calculations | |
| # | |
| # Exceptions raised by instruction execution are by convention converted into ValuePoints | |
| # of type :error and pushed to that stack (by the Interpreter's error catching methods) | |
| # | |
| # a few include NotEnoughStackItems (raised when #needs fails), InstructionMethodError (for | |
| # complex failures that might come up, like trying to change the value of a variable), | |
| # NaNResultError (for the obvious math errors like div0 and float overflow), | |
| # MissingInstructionError (in case your instruction calls another, and it's not defined), | |
| # CodeOversizeError (used to enforce a Push3 rule which makes sense). Add your own! | |
| def derive | |
| input_image = GetFromHardDrive(@arg1) | |
| mask = MyFancyLibrary.to_mask(@arg2) | |
| alpha = MyFancyLibrary.alphaize(@arg3) | |
| begin | |
| munged = MyFancyLibrary.munge_now!(input_image, mask, ginger=alpha) | |
| rescue LibraryFuckupError => e | |
| raise InstructionMethodError, "#{self.class} had a foobie bletch" | |
| end | |
| @result1 = ValuePoint.new(:bar, munged) | |
| @result2 = ValuePoint.new(:foo, munged.width) | |
| end | |
| # #cleanup is when stuff is actually written to the stacks | |
| # | |
| # don't be worried about exception handling; stacks are created on demand | |
| # and nobody ever checks the values you push unless another Instruction | |
| # pops them and tries to read what they are | |
| # | |
| # use the #pushes convenience method for the obvious thing | |
| def cleanup | |
| pushes :bar, @result1 | |
| pushes :foo, @result2 | |
| end | |
| end |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment