How can I use JavaScript within an Excel macro?

前端 未结 4 824
说谎
说谎 2020-12-02 08:52

There’s a really cool diff class hosted by Google here:

http://code.google.com/p/google-diff-match-patch/

I’ve used it before on a few web sites, but now I n

相关标签:
4条回答
  • 2020-12-02 08:58

    The Windows Scripting Engine will allow you to run the JavaScript library. It works well in my experience.

    0 讨论(0)
  • 2020-12-02 09:07

    The simplest approach may be to embed the Javascript diff logic into a COM component directly using Javascript. This is possible via something called "Windows Script Components".

    Here's a tutorial on creating WSCs.

    A Windows Script Component is a COM component that is defined in script. The interface to the component is via COM, which means it is VBA friendly. The logic is implemented in any Windows Scripting Hosting -compatible language, like JavaScript or VBScript. The WSC is defined in a single XML file, which embeds the logic, the component Class ID, the methods, the registration logic, and so on.

    There's also a tool available to help in creating a WSC. Basically it is a wizard-type thing that asks you questions and fills in the XML template. Myself, I just started with an example .wsc file and edited it by hand with a text editor. It's pretty self-explanatory.

    A COM component defined this way in script (in a .wsc file) is callable just like any other COM component, from any environment that can dance with COM.

    UPDATE: I took a few minutes and produced the WSC for GoogleDiff. Here it is.

    <?xml version="1.0"?>
    
    <package>
    
    <component id="Cheeso.Google.DiffMatchPatch">
    
      <comment>
        COM Wrapper on the Diff/Match/Patch logic published by Google at http://code.google.com/p/google-diff-match-patch/.
      </comment>
    
    <?component error="true" debug="true"?>
    
    <registration
      description="WSC Component for Google Diff/Match/Patch"
      progid="Cheeso.Google.DiffMatchPatch"
      version="1.00"
      classid="{36e400d0-32f7-4778-a521-2a5e1dd7d11c}"
      remotable="False">
    
      <script language="VBScript">
      <![CDATA[
    
        strComponent = "Cheeso's COM wrapper for Google Diff/Match/Patch"
    
        Function Register
          MsgBox strComponent & " - registered."
        End Function
    
        Function Unregister
          MsgBox strComponent & " - unregistered."
        End Function
    
      ]]>
      </script>
    </registration>
    
    
    <public>
      <method name="Diff">
        <parameter name="text1"/>
        <parameter name="text2"/>
      </method>
      <method name="DiffFast">
        <parameter name="text1"/>
        <parameter name="text2"/>
      </method>
    </public>
    
    
    <script language="Javascript">
    <![CDATA[
    
    
        // insert original google diff code here...
    
    
    // public methods on the component
    var dpm = new diff_match_patch();
    
    
    function Diff(text1, text2)
    {
       return dpm.diff_main(text1, text2, false);
    }
    
    
    function DiffFast(text1, text2)
    {
       return dpm.diff_main(text1, text2, true);
    }
    
    
    ]]>
    </script>
    
    </component>
    
    </package>
    

    To use that thing, you have to register it. In Explorer, right click on it, and select "Register". or, from the command line: regsvr32 file:\c:\scripts\GoogleDiff.wsc

    I didn't try using it from VBA, but here is some VBScript code that uses the component.

    Sub TestDiff()
        dim t1 
        t1 = "The quick brown fox jumped over the lazy dog."
    
        dim t2 
        t2 = "The large fat elephant jumped over the cowering flea."
    
        WScript.echo("")
    
        WScript.echo("Instantiating a Diff Component ...")
        dim d
        set d = WScript.CreateObject("Cheeso.Google.DiffMatchPatch")
    
        WScript.echo("Doing the Diff...")
        x = d.Diff(t1, t2)
    
        WScript.echo("")
        WScript.echo("Result was of type: " & TypeName(x))
        ' result is all the diffs, joined by commas.  
        ' Each diff is an integer (position), and a string.  These are separated by commas.
        WScript.echo("Result : " & x)
    
        WScript.echo("Transform result...")
        z= Split(x, ",")
        WScript.echo("")
        redim diffs(ubound(z)/2)
        i = 0
        j = 0
        For Each item in z
          If (j = 0) then
            diffs(i) = item
            j = j+ 1      
          Else 
              diffs(i) = diffs(i) & "," & item
            i = i + 1
            j = 0
          End If
        Next
    
        WScript.echo("Results:")
        For Each item in diffs
          WScript.echo("  " & item)
        Next
    
        WScript.echo("Done.")
    
    End Sub
    
    0 讨论(0)
  • 2020-12-02 09:13

    Here's another option to consider, though I'm not by any means stating its the best one.

    • Insure that the Python version compiles in IronPython. (There shouldn't be any problems here, or only a small amount of porting at most.)
    • Create an Excel add-in library using C# and reference IronPython from it.
    • Wrap the necessary functionality in your C# Excel add-in.
    0 讨论(0)
  • 2020-12-02 09:23

    My suggestion would be that whatever you do you wrap it in a COM wrapper. VBA deals best with COM objects so you could compile as a .NET Component then expose as a COM object using the interop functionality of .NET.

    As an alternative you could also look into using Windows Scripting Host objects to execute a Javascript File and return you the result.

    0 讨论(0)
提交回复
热议问题