2

This seems like something that should be extremely easy to do but it's not - it's certainly not obvious how to do it, anyway.

I want to write a function in LibreOffice Basic that takes a string, a regexp search pattern, and a replacement string, and returns the string as modified by the regex search & replace. Like a s/search/replace/g in sed or perl.

After several hours trying to make sense of the abysmal documentation, this is what I have:

Function ReSub (T as String, S as String, R as String) As String
   Dim result as String

   ' In other languages, this is trivially easy.  perl has an s/// operator,
   ' and most other languages have a function call. e.g.
   '
   '   perl:   $result = ($T =~ s/$S/$R/g);
   '   python: result = re.sub(S,R,T)

   search = CreateUnoService("com.sun.star.util.TextSearch")
   opts = CreateUnoStruct("com.sun.star.util.SearchOptions")

   opts.algorithmType = com.sun.star.util.SearchAlgorithms.REGEXP

   opts.searchString  = S
   opts.replaceString = R

   search.setOptions(opts)

   found = search.searchForward(T, 0, Len(T))

   ' result = ??????????????
   ReSub = result

End Function

Stepping through this in the IDE shows that this runs OK, but I have no idea where I can get the resulting modified string from. T isn't being modified directly, and it's not in any of the found, search, or opts objects either.

I could write a while loop around search.SearchForware and do the substitution myself using the Mid() statement - but then I'd be restricted to replacing with fixed strings (no back-references or &, unless I implemented them myself. in Basic).

So:

  • does setting opts.replaceString actually DO anything?
  • If so:
    • what does it do?
    • where/how do I retrieve the result of what it does?

Note: this question is about programming in Libre Office Basic to return a changed string, and has nothing at all to do with doing a search & replace on cells with the Libre Office Calc user interface.

cas
  • 661
  • 5
  • 11
  • @JimK thanks, yeah, I found that here yesterday. Very useful & informative. I actually wrote a similar loop but used `Mid()` as a statement to replace rather than `Mid() `as a function to extract. It works, but it's clumsy - and seems like it shouldn't be necessary since the `SearchOptions` structure actually has a `ReplaceString` object. I didn't include the loop in my question because I wanted to avoid getting tips on improving it when what I want is info on how to make use of the `replaceString` so I can get rid of it entirely. – cas Apr 16 '18 at 14:27

1 Answers1

2

It sounds like you already have a working solution, so let me simply say that what you are looking for does not seem to exist. With com.sun.star.util.TextSearch, XrayTool shows that neither the search object nor the found result has any methods that perform replacing.

AFAICT, SearchOptions.replaceString is only used for replacing in documents, for example oDoc.replaceAll(oReplace). There is XStringSubstitution but that is only used for PathSubstitution.

So the only way is to do the replacing yourself. Section 19.2 of Andrew's macro document gives a function to replace strings by index.

Personally, I run into this sort of limitation all the time with Basic, so I prefer writing macros in Python-UNO instead. File handling is another thing that is unnecessarily difficult in Basic.

It might be a good idea to add your own answer showing the solution that uses Mid() in case other people find this question. Then probably accept that answer rather than mine.

Jim K
  • 3,839
  • 1
  • 8
  • 20
  • 1
    +1 but that's a shame - Basic is guaranteed to be available in LO Calc by default, while Python isn't. If I can only distribute my stuff with a note "you have to install extra stuff just to make it work". This breaks one of my main reasons for using LO Calc in the first place, and why I've been forcing myself to suffer the pain of basic and a horrible GUI IDE. Also, I really don't want to write shoddy versions of things that should be standard functions, like an RE sub. I'm going to have to rethink whether it's worth doing this with LO or just start over with python or whatever. – cas Apr 18 '18 at 21:54
  • *"Basic is guaranteed to be available in LO Calc by default, while Python isn't."* Python comes with LO by default on Windows, and most Linux and Mac systems have Python installed already. So I see nothing wrong with depending on Python when writing LO macros. I have developed a large (12K LOC) extension used by at least several hundred people, and have received few to no complaints about the fact that it requires Python. The extension's README notes the dependency on Python along with the required version of LO or AOO. – Jim K Apr 19 '18 at 13:11