Copying 8-Bit Plain Text to Clipboard from OO Macro

Creating a macro - Writing a Script - Using the API (OpenOffice Basic, Python, BeanShell, JavaScript)
Post Reply
PennyLane
Posts: 8
Joined: Fri Nov 01, 2013 8:58 pm

Copying 8-Bit Plain Text to Clipboard from OO Macro

Post by PennyLane »

I found a nice bit of code a while back that allows me to copy any string onto the clipboard, but it always copies the string as utf-16. However, the template application that I'm writing requires the string to be sometimes written to the clipboard as 8-bit plain text, and at others times as rich text. I managed to modify the code so that it now can copy the string as either plain text or as rich text, depending upon what the user wants to do with it after it is copied onto the clipboard.

In the original code, MimeStr was the constant "text/plain;charset=utf-16" and HumanStr was "Unicode-Text". I've made them variables so that I could play around with other options. Both ClipStr() and sTxtCString() are Byte arrays, as this is required for rich text (and plain text as well.) I first ask the user what he wants to do with the copied string (a special single-line representation of a chess position. An example is:)

rnbqkbnr/pppp1ppp/8/4p3/4P3/8/PPPP1PPP/RNBQKBNR w KQkq - 0 1

I set the values of MimeStr and HumanStr depending upon how the user wants to use it. In the special case where he wants to use it as an RTF string, I first wrap the string in the minimum text required to make it an RTF 'file'. I then convert the string to a simple 8-bit ASCII string. In the last function, the Mime string is kept as a constant, "text/richtext", regardless of whether we want to use plain text or RTF. (My guess is that RTF is just a higher order of plain text, and this is what allows us to commandeer it and simply alter its MimeType to get plain text.)

Now, if I copy the string to the clipboard as plain text, I can paste it into NotePad and ChessBase, but NOT into Writer itself. Alternatively, if I copy the string as RTF, then I can paste it into Writer or WordPad, but NOT ChessBase.

What I'd like to ask is if anyone can help to further modify the code below so that Writer can also understand the plain text. For example, if you copy some text directly from Writer, then click on the small down arrow of the Paste Icon, you'll see a number of paste options, including Unformatted Text. Does this use a special MimeType string? Alternatively, I wonder if it would be possible to copy both instances on the clipboard. Any ideas?

Here is the modified code:

Code: Select all

Global sTxtCString() As Byte
Global ClipStr(120) As Byte
Global MimeStr, HumanStr As String

Sub CopyToClipBoard(sText)

Dim i, j, cnum As Integer

   ' Ask the user what he wants to do with the copied string (a FEN)
   i = MsgBox("Are you using the FEN as plain text (ChessBase)?", 4+32, "Copy FEN")

   If i = 6 Then ' Yes -- I'll use it as 8-bit plain text for an external application
      MimeStr = "text/plain"
      HumanStr = "Text"
   Else             ' No -- make it an RTF string so that I can use it in Writer (or WordPad, etc.)
      MimeStr = "text/richtext"
      HumanStr = "Rich Text Format"
      sText = "{\rtf1\ansi " & sText & "}" ' wrap the plain text with the minimum needed for an RTF file
   End If
   
  ' Convert the string to a simple 8-bit ASCII string instead of a 16-bit char string
  j = Len(sText)
  i = 0
  Do While i < j
   ClipStr(i) = CByte(Asc(Mid(sText, i + 1, 1)))
    i = i + 1
  Loop
  ClipStr(i) = 0 ' Mark the end of the string

  ' create SystemClipboard instance
  oClip = CreateUnoService("com.sun.star.datatransfer.clipboard.SystemClipboard")
  oTR = createUnoListener("Tr_", "com.sun.star.datatransfer.XTransferable")
  ' set data
  oClip.setContents(oTR,Null)
  sTxtCString = ClipStr
End Sub
 
Function Tr_getTransferData(aFlavor as com.sun.star.datatransfer.DataFlavor)
  If (aFlavor.MimeType = MimeStr) Then
    Tr_getTransferData() = sTxtCString
  End If
End Function
 
Function Tr_getTransferDataFlavors()
  Dim aFlavor As new com.sun.star.datatransfer.DataFlavor
  aFlavor.MimeType = MimeStr
  aFlavor.HumanPresentableName = HumanStr
  Tr_getTransferDataFlavors() = array(aFlavor)
End Function
 
Function Tr_isDataFlavorSupported(aFlavor as com.sun.star.datatransfer.DataFlavor) as Boolean
  If aFlavor.MimeType = "text/richtext" Then ' Note that we stick to "text/richtext" here!
    Tr_isDataFlavorSupported = true
  Else
    Tr_isDataFlavorSupported = false
  End If
End Function
hanya
Volunteer
Posts: 885
Joined: Fri Nov 23, 2007 9:27 am
Location: Japan

Re: Copying 8-Bit Plain Text to Clipboard from OO Macro

Post by hanya »

Mime-type for Unformatted Text is "text/plain;charset=utf-16".
Return data flavors supported by your css.datatransfer.XTransferable interface as the return value of getTransferDataFlavors method. And respond to requests through the other two methods.
Please, edit this thread's initial post and add "[Solved]" to the subject line if your problem has been solved.
Apache OpenOffice 4-dev on Xubuntu 14.04
PennyLane
Posts: 8
Joined: Fri Nov 01, 2013 8:58 pm

Re: Copying 8-Bit Plain Text to Clipboard from OO Macro

Post by PennyLane »

Thanks for the information. Of course you are right. I thought that perhaps my old ChessBase 8 program didn't understand utf-16, but now I can see that there is some other kind of problem. The code that I was using before is below. (It uses text/plain;charset=utf-16.)

What I find is that I can copy the FEN string to the clipboard, using the code below, and so long as it is the first time that I've run the template, ChessBase 8 can access the FEN string from the clipboard. However, if I don't rerun the template, and then try to copy another FEN string to the clipboard, it seems to work for any other program, but not ChessBase 8, which can't seem to access it. Very strange!

Any idea why closing and the reopening the template would make any difference to what the code below copies to the clipboard? I really am stumped by it all.

Code: Select all

Global sTxtCString As String
 
Sub CopyToClipBoard( sText )
  ' create SystemClipboard instance
  oClip = CreateUnoService( _
      "com.sun.star.datatransfer.clipboard.SystemClipboard")
  oTR = createUnoListener("Tr_", "com.sun.star.datatransfer.XTransferable")
  ' set data
  oClip.setContents(oTR,Null)
  sTxtCString = sText
End Sub
 
Function Tr_getTransferData( _
    aFlavor as com.sun.star.datatransfer.DataFlavor)
  If (aFlavor.MimeType = "text/plain;charset=utf-16") Then ' was  = "text/plain;charset=utf-16" TRIED = "text/plain;charset=ISO-8859-1" TRIED ="text/html"
    Tr_getTransferData() = sTxtCString
  End If
End Function
 
Function Tr_getTransferDataFlavors()
  Dim aFlavor As new com.sun.star.datatransfer.DataFlavor
  aFlavor.MimeType = "text/plain;charset=utf-16" ' was  = "text/plain;charset=utf-16" TRIED = "text/plain;charset=ISO-8859-1" TRIED = "text/richtext" TRIED ="text/html"
  aFlavor.HumanPresentableName = "Text" ' was = "Unicode-Text" TRIED = "Text" TRIED = "Rich Text Format" TRIED ="HTML"
  Tr_getTransferDataFlavors() = array(aFlavor)
End Function
 
Function Tr_isDataFlavorSupported( _
    aFlavor as com.sun.star.datatransfer.DataFlavor) as Boolean
  If aFlavor.MimeType = "text/plain;charset=utf-16" Then ' was  = "text/plain;charset=utf-16" TRIED = "text/plain;charset=ISO-8859-1" TRIED ="text/html"
    Tr_isDataFlavorSupported = true
  Else
    Tr_isDataFlavorSupported = false
  End If
End Function

OpenOffice 3.4 on Windows 8
hanya
Volunteer
Posts: 885
Joined: Fri Nov 23, 2007 9:27 am
Location: Japan

Re: Copying 8-Bit Plain Text to Clipboard from OO Macro

Post by hanya »

I have not used ChessBase but have you tried to check what mime-type is requested when you tried to paste to ChessBase?
Please, edit this thread's initial post and add "[Solved]" to the subject line if your problem has been solved.
Apache OpenOffice 4-dev on Xubuntu 14.04
PennyLane
Posts: 8
Joined: Fri Nov 01, 2013 8:58 pm

Re: Copying 8-Bit Plain Text to Clipboard from OO Macro

Post by PennyLane »

I'm not sure how I'd go about checking the mime-type that is being requested by ChessBase. Would you need to install some kind of Clipboad-reading program?

To add to the mystery, I find that I can change the position on the board several times, copy the position as a FEN string to the clipboard, and if I then first paste it back into Writer and then re-copy it to the clipboard (select & Cltr-C), ChessBase can read it all the time. To add to the mystery, I can copy any number of FEN strings to the clipboard using the Macro code and paste all of them successfully into Notepad without a hitch. Strange!
OpenOffice 3.4 on Windows 8
Post Reply