Advertisement
Double_X

DoubleX RMVXA Object Trace v1.02a

Jun 27th, 2015 (edited)
706
0
Never
Not a member of Pastebin yet? Sign Up, it unlocks many cool features!
Ruby 15.67 KB | None | 0 0
  1. #==============================================================================|
  2. #  ** Script Info                                                              |
  3. #------------------------------------------------------------------------------|
  4. #  * Script Name                                                               |
  5. #    DoubleX RMVXA Object Trace                                                |
  6. #------------------------------------------------------------------------------|
  7. #  * Functions                                                                 |
  8. #    Traces all objects meeting some conditions linked to the queried object   |
  9. #    Designed as a bug diagnosis tool used by scripters with debug experience  |
  10. #------------------------------------------------------------------------------|
  11. #  * Example                                                                   |
  12. #    obj.inspect                                                               |
  13. #    - http://pastebin.com/kb1q1Dru                                            |
  14. #    obj.trace_obj(Proc); obj.obj_trace[Proc].inspect                          |
  15. #    - http://pastebin.com/PZ4KNbHv                                            |
  16. #------------------------------------------------------------------------------|
  17. #  * Terms Of Use                                                              |
  18. #    You shall keep this script's Script Info part's contents intact           |
  19. #    You shalln't claim that this script is written by anyone other than       |
  20. #    DoubleX or his aliases                                                    |
  21. #    None of the above applies to DoubleX or his aliases                       |
  22. #------------------------------------------------------------------------------|
  23. #  * Prerequisites                                                             |
  24. #    Abilities:                                                                |
  25. #    1. Basic knowledge of inspecting objects in Ruby                          |
  26. #    2. Some RGSS3 scripting proficiency to fully utilize this script          |
  27. #------------------------------------------------------------------------------|
  28. #  * Instructions                                                              |
  29. #    1. Open the script editor and put this script into an open slot between   |
  30. #       Materials and Main, save to take effect.                               |
  31. #------------------------------------------------------------------------------|
  32. #  * Links                                                                     |
  33. #    Script Usage 101:                                                         |
  34. #    1. forums.rpgmakerweb.com/index.php?/topic/32752-rmvxa-script-usage-101/  |
  35. #    2. rpgmakervxace.net/topic/27475-rmvxa-script-usage-101/                  |
  36. #    This script:                                                              |
  37. #    1. http://pastebin.com/pySjrKvh                                           |
  38. #    Mentioned Patreon Supporters:                                             |
  39. #    https://www.patreon.com/posts/71738797                                    |
  40. #------------------------------------------------------------------------------|
  41. #  * Author                                                                    |
  42. #    DoubleX                                                                   |
  43. #------------------------------------------------------------------------------|
  44. #  * Changelog                                                                 |
  45. #    v1.02a(GMT 0100 27-10-2015):                                              |
  46. #    1. Lets uers set the conditions and labels for tracing objects            |
  47. #    v1.01b(GMT 1300 13-7-2015):                                               |
  48. #    1. Fixed not tracing klass linked to klass linked to queried object bug   |
  49. #    2. Fixed some Script Call Info and Implementation documentation typos     |
  50. #    3. Added more info in Prerequisites and Script Call Info                  |
  51. #    4. Increased this script's compactness                                    |
  52. #    v1.01a(GMT 1300 6-7-2015):                                                |
  53. #    1. Instance methods can be traced as well                                 |
  54. #    v1.00b(GMT 0800 1-7-2015):                                                |
  55. #    1. Fixed object having Range and/or Structs not tracing klass properly bug|
  56. #    v1.00a(GMT 1200 27-6-2015):                                               |
  57. #    1. 1st version of this script finished                                    |
  58. #==============================================================================|
  59.  
  60. #==============================================================================|
  61. #  ** Script Call Info                                                         |
  62. #     A path in the object trace will stop if it'd be cyclic                   |
  63. #------------------------------------------------------------------------------|
  64. #  * Object manipulations                                                      |
  65. #    1. trace_obj(cond, label)                                                 |
  66. #       - Traces all objects meeting cond method linked to this object         |
  67. #       - Labels all traced objects using label method                         |
  68. #       - cond and label are method symbols in Object Trace Condition Method   |
  69. #         and Object Trace Label Method respectively                           |
  70. #    2. obj_trace[cond]                                                        |
  71. #       - Returns all traced objects meeting cond method linked to this object |
  72. #       - cond is a method symbol in Object Trace Condition Method             |
  73. #    3. (v1.01a+)trace_idef                                                    |
  74. #       - Traces all instance methods linked to this object                    |
  75. #    4. (v1.01a+)idef_trace                                                    |
  76. #       - Returns the trace of all instance methods linked to this object      |
  77. #==============================================================================|
  78.  
  79. ($doublex_rmvxa ||= {})[:Obj_Trace] = "v1.02a"
  80.  
  81. module DoubleX_RMVXA # v1.02a+
  82.  
  83.   module Obj_Trace
  84.  
  85.     #--------------------------------------------------------------------------|
  86.     #  Object Trace Condition Method                                           |
  87.     #  - Setups cond used by trace_obj(cond, label)                            |
  88.     #--------------------------------------------------------------------------|
  89.     # cond must be the symbol of a method taking the currently traced object as
  90.     # the only arguement
  91.     # The below examples are added to help you setup your own cond methods
  92.  
  93.     # Checks if the currently traced object belongs to klass
  94.     def self.cond_klass(obj)
  95.         obj.is_a?(klass)
  96.     end # cond_klass
  97.  
  98.     # Add your own cond methods here
  99.    
  100.  
  101.     #--------------------------------------------------------------------------|
  102.     #  Object Trace Label Method                                               |
  103.     #  - Setups label used by trace_obj(cond, label)                           |
  104.     #--------------------------------------------------------------------------|
  105.     # label must be the symbol of a method taking the currently traced object as
  106.     # the only arguement
  107.     # The below examples are added to help you setup your own label methods
  108.  
  109.     # Labels all traced objects using their class symbol
  110.     def self.label_klass(obj)
  111.         :"#{obj.class}"
  112.     end # label_klass
  113.  
  114.     # Add your own label methods here
  115.    
  116.  
  117.   end # Obj_Trace
  118.  
  119. end # DoubleX_RMVXA
  120.  
  121. #==============================================================================|
  122. #  ** Script Implementations                                                   |
  123. #     You need not edit this part as it's about how this script works          |
  124. #------------------------------------------------------------------------------|
  125. #  * Script Support Info:                                                      |
  126. #    1. Prerequisites                                                          |
  127. #       - Solid understanding of inspecting objects in Ruby                    |
  128. #       - Decent RGSS3 scripting proficiency to fully comprehend this script   |
  129. #    2. Method documentation                                                   |
  130. #       - The 1st part describes why this method's rewritten/aliased for       |
  131. #         rewritten/aliased methods or what the method does for new methods    |
  132. #       - The 2nd part describes what the arguments of the method are          |
  133. #       - The 3rd part informs which version rewritten, aliased or created this|
  134. #         method                                                               |
  135. #       - The 4th part informs whether the method's rewritten or new           |
  136. #       - The 5th part informs whether the method's a real or potential hotspot|
  137. #       - The 6th part describes how this method works for new methods only,   |
  138. #         and describes the parts added, removed or rewritten for rewritten or |
  139. #         aliased methods only                                                 |
  140. #       Example:                                                               |
  141. # #--------------------------------------------------------------------------| |
  142. # #  Why rewrite/alias/What this method does                                 | |
  143. # #--------------------------------------------------------------------------| |
  144. # # *argv: What these variables are                                            |
  145. # # &argb: What this block is                                                  |
  146. # def def_name(*argv, &argb) # Version X+; Rewrite/New; Hotspot                |
  147. #   # Added/Removed/Rewritten to do something/How this method works            |
  148. #   def_name_code                                                              |
  149. #   #                                                                          |
  150. # end # def_name                                                               |
  151. #------------------------------------------------------------------------------|
  152.  
  153. class Object # Edit
  154.  
  155.   #----------------------------------------------------------------------------|
  156.   #  New public instance variables                                             |
  157.   #----------------------------------------------------------------------------|
  158.   attr_reader :idef_trace # (v1.01a+)The trace of all linked instance methods
  159.   attr_reader :obj_trace # The traces of all objects linked to this object
  160.  
  161.   # (v1.01a+)The list of symbols of all instance variables added by this script
  162.   OBJ_TRACE_IVAR = [:"@idef_trace", :"@obj_trace"]
  163.  
  164.   def trace_idef # v1.01a+; New
  165.     # Stop tracing the object if the object trace path would be cyclic
  166.     @idef_trace ? return : @idef_trace = {}
  167.     #
  168.     trace_instance_idef
  169.     return trace_array_idef if is_a?(Array)
  170.     return trace_hash_idef if is_a?(Hash)
  171.     return trace_range_idef if is_a?(Range)
  172.     trace_struct_idef if is_a?(Struct)
  173.   end # trace_idef
  174.  
  175.   def trace_instance_idef # v1.01a+; New
  176.     (instance_variables - OBJ_TRACE_IVAR).each { |ivar|
  177.       traverse_idef_tree(ivar, instance_variable_get(ivar))
  178.     }
  179.   end # trace_instance_idef
  180.  
  181.   def trace_array_idef # v1.01a+; New
  182.     each_with_index { |val, index| traverse_idef_tree(index, val) }
  183.   end # trace_array_idef
  184.  
  185.   def trace_hash_idef # v1.01a+; New
  186.     each { |key, val| traverse_idef_tree(key, val) }
  187.   end # trace_hash_idef
  188.  
  189.   def trace_range_idef # v1.01a+; New
  190.     index = -1
  191.     each { |val| traverse_idef_tree(index += 1, val) }
  192.   end # trace_range_idef
  193.  
  194.   def trace_struct_idef # v1.01a+; New
  195.     each_pair { |key, val| traverse_idef_tree(key, val) }
  196.   end # trace_struct_idef
  197.  
  198.   #----------------------------------------------------------------------------|
  199.   #  Label and use all nonempty subtrees to form the original object trace tree|
  200.   #----------------------------------------------------------------------------|
  201.   # iks: The index/key/symbol of the object trace
  202.   # val: The object to be traced
  203.   def traverse_idef_tree(iks, val) # v1.01a+; New
  204.     # Recursively traverse the object trace tree using Depth First Search
  205.     unless (idefs = val.instance_methods).empty?
  206.       @idef_trace[iks] = [idefs]
  207.     end
  208.     val.trace_idef
  209.     return if (trace = val.idef_trace).empty?
  210.     (@obj_trace[iks] ||= []) << trace
  211.     #
  212.   end # traverse_idef_tree
  213.  
  214.   # cond: The object trace condition method symbol taking the object as argument
  215.   # label: The object trace label method symbol taking the object as argument
  216.   def trace_obj(cond, label) # New
  217.     # Stop tracing the object if the object trace path would be cyclic
  218.     (@obj_trace ||= {})[cond] ? return : @obj_trace[cond] = {}
  219.     #
  220.     trace_instance_obj(cond, label)
  221.     return trace_array_obj(cond, label) if is_a?(Array)
  222.     return trace_hash_obj(cond, label) if is_a?(Hash)
  223.     return trace_range_obj(cond, label) if is_a?(Range)
  224.     trace_struct_obj(cond, label) if is_a?(Struct)
  225.   end # trace_obj
  226.  
  227.   # cond: The object trace condition method symbol taking the object as argument
  228.   # label: The object trace label method symbol taking the object as argument
  229.   def trace_instance_obj(cond, label) # New
  230.     (instance_variables - OBJ_TRACE_IVAR).each { |ivar|
  231.       trace_all_obj(cond, label, ivar, instance_variable_get(ivar))
  232.     }
  233.   end # trace_instance_obj
  234.  
  235.   # cond: The object trace condition method symbol taking the object as argument
  236.   # label: The object trace label method symbol taking the object as argument
  237.   def trace_array_obj(cond, label) # New
  238.     each_with_index { |val, index| trace_all_obj(cond, label, index, val) }
  239.   end # trace_array_obj
  240.  
  241.   # cond: The object trace condition method symbol taking the object as argument
  242.   # label: The object trace label method symbol taking the object as argument
  243.   def trace_hash_obj(cond, label) # New
  244.     each { |key, val| trace_all_obj(cond, label, key, val) }
  245.   end # trace_hash_obj
  246.  
  247.   # cond: The object trace condition method symbol taking the object as argument
  248.   # label: The object trace label method symbol taking the object as argument
  249.   def trace_range_obj(cond, label) # v1.00b+; New
  250.     # Embeds the klass traces of all ranges linking to this object
  251.     index = -1
  252.     each { |val| trace_all_obj(cond, label, index += 1, val) }
  253.     #
  254.   end # trace_range_obj
  255.  
  256.   # cond: The object trace condition method symbol taking the object as argument
  257.   # label: The object trace label method symbol taking the object as argument
  258.   def trace_struct_obj(cond, label) # v1.00b+; New
  259.     each_pair { |key, val| trace_all_obj(cond, label, key, val) }
  260.   end # trace_struct_obj
  261.  
  262.   #----------------------------------------------------------------------------|
  263.   #  Label and use all nonempty subtrees to form the original object trace tree|
  264.   #----------------------------------------------------------------------------|
  265.   # cond: The object trace condition method symbol taking the object as argument
  266.   # label: The object trace label method symbol taking the object as argument
  267.   # iks: The index/key/symbol of the object trace
  268.   # val: The object to be traced
  269.   def trace_all_obj(cond, label, iks, val) # v1.01a+; New
  270.     # Recursively traverse the object trace tree using Depth First Search
  271.     ot = DoubleX_RMVXA::Obj_Trace
  272.     @obj_trace[cond][iks] = [ot.send(label, val)] if ot.send(cond, val)
  273.     val.trace_obj(cond, label)
  274.     return if (trace = val.obj_trace[cond]).empty?
  275.     (@obj_trace[cond][iks] ||= []) << trace
  276.     #
  277.   end # trace_all_obj
  278.  
  279. end # Object
  280.  
  281. #------------------------------------------------------------------------------|
  282.  
  283. #==============================================================================|
Advertisement
Add Comment
Please, Sign In to add comment
Advertisement