1. Miguel Leeuwe
  2. PowerBuilder
  3. Tuesday, 26 January 2021 13:43 PM UTC

Maybe I should post this on the support site, but I can't paste code in a decent way, nor paste images. 
Several issues which I'll describe in separate "answers":

Part 1: with previous version of TX control (25?), I would be able to paste an image copied with either the Snipping Tool or from a selection copied from mspaint.exe (can't remember which one worked the way we wanted).
Part 2: control's width calculation that I do in resize event to wrap text correctly has changed from all versions where I've used the control. There's a factor that I apply and it seems to work. I'm convinced I can find the "golden" value of this factor again, so not really a problem, but maybe someone knows a better way of doing this.

Who is viewing this page
Accepted Answer
Arthur Hefti Accepted Answer Pending Moderation
  1. Thursday, 28 January 2021 05:40 AM UTC
  2. PowerBuilder
  3. # Permalink

Hi Miguel

about Part 2. 

The factor depends on the Pixels per Inch on the monitor (used to be 96 on most of the monitors).

I assume you found the factor by trying. The calculation is (with values from my monitor):

0.219: Number of Units per Pixel
0.219: Number of Pixels per Unit -> I calculated it with 1000 Units 
96: Pixels per Inch
2.54: cm per Inch

Your "magic" value is about:

0.219 / 96 * 2.54 * 1000 = 5.79...

(* 2.54 * 1000 as you text control set to cm)

In PB:

External Functions
Function ulong GetDeviceCaps( ulong hdc, ulong index) Library "GDI32"
Function ulong DeleteDC( ulong hdc ) Library "GDI32"
Function ulong CreateDC( string a, string b, string c, string dummy ) Library "GDI32" Alias for "CreateDCW"

Resize Event:
integer li_PixelPerInchX

long LOGPIXELSX = 88
string ls_Null
ulong lul_HDC

SetNull( ls_Null)
lul_HDC = CreateDC("DISPLAY", "", ls_Null, ls_Null)
li_PixelPerInchX = GetDeviceCaps(lul_HDC, LOGPIXELSX)
DeleteDC(lul_HDC)

rte_1.paperwidth = UnitsToPixels( newwidth, XPixelsToUnits! ) / li_PixelsPerInch " 2.54 * 1000

rte_1.paperwidth = UnitsToPixels( newwidth, XUnitstoPixels! ) / li_PixelsPerInchX * 2.54 * 1000

 

Regards
Arthur

 

Comment
  1. Miguel Leeuwe
  2. Thursday, 28 January 2021 13:53 PM UTC
Me too, I get 96 in li_PixelPerInchX. My monitor has a 1920x1080 resolution with 100% scaling.

If you want I can show you what happens on teamviewer (I think I have your email somewhere) or I can make a small demo app which might be a better way of doing things. I don't want to abuse of your time.

Thank you.
  1. Helpful
  1. Miguel Leeuwe
  2. Friday, 29 January 2021 12:15 PM UTC
Okay, now I see it !!

You are using a different control than the TX 28.0. My "complaint" was that "my magical factor had to be changed for this newer 28 version". In pb 12.6 and pb 2017 R3, my multiplication factor was "5.66" and now it has to be (calculated or not), around using a factor of "6.55":

Now I've tried your code in pb12.6 and 2017 R3 and I have to substract 650. When I use the same code on 2019 R3, then I have to ADD around 3000. So there's a huge difference depending on which version of the TX control is being used (or maybe the powerbuilder version).

In 12.6 and 2017 it comes a lot closer to what you get with that third party product you use. (maybe also the presence of a vertical scrollbar could add a little bit to having to substract 650 units).

Anyway it's not really that important for us at the moment, but I will make a small sample app one of these days.

regards
  1. Helpful
  1. Arthur Hefti
  2. Friday, 29 January 2021 13:02 PM UTC
Hi Miguel

I'm working with PB 2019 R3. When I change the TextControl version in the application object. I get the same results for X28 and X15.
  1. Helpful
There are no comments made yet.
Miguel Leeuwe Accepted Answer Pending Moderation
  1. Monday, 1 February 2021 13:17 PM UTC
  2. PowerBuilder
  3. # 1

Part 1: Definitely changed behaviour between v15 and v28 of txt control. I recommend to keep using v15. Also the v28 has some icons right below on the status bar, which don't seem to do anything.

Watch the video to see the difference (same video, 2 different formats):

55 MB in Gif format: https://drive.google.com/file/d/1VBiTto_YlD848-oUwe0NeIWZkoArGM31/view?usp=sharing

466 MB in format MP4: https://drive.google.com/file/d/11PV-JV4a8kZ9PS36-q6sOwzHI9i-Z9bJ/view?usp=sharing

NOTE: Reported as bug https://www.appeon.com/standardsupport/track/view?id=5954

regards

Comment
  1. Miguel Leeuwe
  2. Monday, 1 February 2021 13:40 PM UTC
Correction: wherever you see CTRL+SHIFT+S, that should be WINDOWSKEY+Shift+S
  1. Helpful
There are no comments made yet.
Miguel Leeuwe Accepted Answer Pending Moderation
  1. Monday, 1 February 2021 09:17 AM UTC
  2. PowerBuilder
  3. # 2

Part 2

Finally solved, thank you so much Arthur Hefti !

Your calculation is correct. (The only thing is that I have to substract a value of around 650 as there's a VScrollbar visible on my rte, for the rest it's perfect).

The whole problem was that in my testing, I was inserting a huge string of 'i' and 'j', uninterrupted by any white space. The RTE then starts to behave a bit strange, as it "invents" its own breakpoints to wrap to the next line. The pagewidth was correct all the time, but rte starts to decide in a funny way of how it breaks the lines (much more to the left than expected).

Once you use normal 'real' life text, it all works perfectly!

Thanks again!

Comment
There are no comments made yet.
Mark Lee @Appeon Accepted Answer Pending Moderation
  1. Wednesday, 27 January 2021 09:40 AM UTC
  2. PowerBuilder
  3. # 3

Hi Miguel,

 

I will reply to you about Part 1 in ticket 5954.

 

Regards,

 

Comment
  1. Miguel Leeuwe
  2. Wednesday, 27 January 2021 09:43 AM UTC
Thank you Mark Lee
  1. Helpful
There are no comments made yet.
Miguel Leeuwe Accepted Answer Pending Moderation
  1. Tuesday, 26 January 2021 15:07 PM UTC
  2. PowerBuilder
  3. # 4

Part 2:

When writing text in a richtext control all the way up to the right, previously I did this in the resize event:

this.paperwidth = newWidth * 5.66

Now I'm getting good results with
this.paperwidth = newWidth * 6.55

This is a means to have the text autoscroll / wrap vertically when you resize the control and when the vertical scrollbar is NOT enabled. Wordwrap is enabled and resizable is not checked as we don't want the user to be able to resize the control by any other means as by resizing the window that contains it (pfc resize service).

It's not a problem having to adjust my "magical" factor to 6.55, but it pretty much stops working when someone uses scaling factors different than mine (100%) like for example 125% which is often seen on laptops.

Does someone know of a better method to do the auto-wrapping?

regards,

MiguelL

 

Comment
  1. Miguel Leeuwe
  2. Tuesday, 26 January 2021 15:56 PM UTC
Edit: It still works, even if I change the scaling factor, so ... simply asking if anyone knows a better way to do this.
  1. Helpful
There are no comments made yet.
Miguel Leeuwe Accepted Answer Pending Moderation
  1. Tuesday, 26 January 2021 14:15 PM UTC
  2. PowerBuilder
  3. # 5

Part 1.

I paste 2 images on a richtext edit control:

Then we use SaveDocument() to save as html and use that html as the body for an email we send out.
Any pasted images can be present in the rtf / html as embedded binary image, which is no good in the first place, as most email clients block that anyway, though I'm still thinking of exporting is as an image to disk and then use that.
What does work is the html which holds <img /> tags with a link to a temporary generated image file as a product of the SaveDocument() function.
Ie. <img src="file:///C:/Users/miguel.RSL/AppData/Local/Temp/RTC7AAE.tmp" width="613" height="303" title="RTC7AAE.tmp" alt="[image]" />
or
<img src="file:///C:/Users/miguel.RSL/AppData/Local/Temp/ExportedRtf/temp_Images/temp_5.png" width="157" height="115" style="position:relative;float:left;border:0pt none;z-index:1002;" title="temp_5.png" alt="[image]" /> </p>
<p lang="en-GB" style="text-indent:0pt;margin-top:0pt;margin-bottom:0pt;">

 In code we do something like the following to read that temp file and then attach it to the email as a "hidden attachment". In the previous version of the richtext Text Edit control, this either worked or it didn't, depending on where the pasted image was copied from, but it never gave an error.
Now, I'm getting an error because there'll be a link to a non-existing temporary file in the html.

In the code we do something like this (and "Yes, there's a GOTO", I've always had the illusion of doing that :).

ls_text = rte_notedet.copyRTF(false) // not only selected, everything
if isnull(ls_text) then 
	ls_text = ''
end if
if Len( ls_text) > 0 then
	ls_currentDir = GetCurrentDirectory() // later we restore to the active (at this moment) directory.
	
	//v1, mjl, 05/11/19: don't use the signatures folder for the tempFile:
	//ls_tempFileName = is_pathSignatures
	ls_tempFileName = gnv_app.is_win_temp_dir + "ExportedRtf" // ExportedRtf will be created if it doesn't exist yet.
	//T3, mjl, 25/02/16: If the user never made a signature with Outlook, this directory does not exist:
	IF NOT DirectoryExists(ls_tempFileName) THEN 
		if NOT ln_file.of_CreateDirectory(ls_tempFileName) then
			GOTO LABEL_EXIT
		end if
	end if
	ls_tempFileName += ('\temp.html')
	if FileExists(ls_tempFileName) then
		FileDelete(ls_tempFileName)
	end if
	// For the SaveDocument(), according to the help of PB, ONLY for the type "FileTypeText!" you can use anything else than FileEncodingANSI! ...
	// Nevertheless: The resulting file still seems to be utf8. So you cannot set anything else then Ansi when filetype is not , but might get 
	// something else as a result?
	
	//T3, mjl, 25/02/16: check for write access:
	try 
		if rte_notedet.SaveDocument( ls_tempFileName, FileTypeHTML!, EncodingAnsi!) = -1 then
			Messagebox("Information", 'Could not write the temporary file: "' + ls_tempFileName + '", please contact Credica.')
			gnv_app.of_debug("u_email.ue_sendmail - Could not write the temporary file")
		end if
	catch ( runtimeError rrte)
		gnv_app.of_debug("u_email.ue_sendmail - Could not write the temporary file - rrte: " + rrte.getmessage() )
		return -1
	end try
								 
	li_fileNum = FileOpen(ls_tempFileName, TextMode!, Read!, Shared!, Append!, EncodingAnsi!) // it's ansi encoded by SaveDocument, but contains utf8! chars ....

	ll_bytesRead = FileReadEx(li_FileNum, lb_blob)
	FileClose(li_FileNum)
	// V3, mjl, 16/12/20: has to be utf8:
	//ls_fileContents = string(lb_blob, EncodingAnsi!)
	ls_fileContents = string(lb_blob, encodingutf8!) // HAS to be utf8 encoded. utf16le doesn't work and ansi loses all special characters ...
	
	//u3, 16/03/18: image-stuff also works also in pb12.6 (works in pb2017):
	//u2, mjl, 19/06/17: add temp images as attachments:
	long ll_pos1, ll_pos2
	string ls_image, ls_temp
	oleobject lole_attachProperty, lole_attachPropertyAccessor
	
	lole_attach = ioutlook_mail.Attachments			
	ll_pos1 = pos(ls_filecontents, '<img src="file://')
	do while ll_pos1 > 0 
		ll_pos2 = pos(ls_filecontents, '"', ll_pos1 + 17)
		if ll_pos2 > 0 then
			ls_image = mid(ls_filecontents, ll_pos1 + 17, ll_pos2 - ll_pos1 - 17)
			// on pb12.6 we get an extra / after "file://" so if present we take it out:
			if left(ls_image, 1) = "/" then
				ls_image = mid(ls_image, 2)
			end if
		end if
		// change the img tag to include CID without path
		//cid:city.jpg
		ls_temp = mid(ls_filecontents, ll_pos2 )
		ls_filecontents = mid(ls_filecontents, 1, ll_pos1 + 9)
		ls_filecontents += "cid:" + trim(mid(ls_image, lastPos(ls_image, "\") + 1) )
		ls_filecontents += ls_temp
		// attach the image
		if not FileExists(ls_image) then
			ls_error[1] = ls_image
			gnv_app.inv_error.of_message("file_file_does_not_exist", ls_error[])
		else
			try
				lole_attachProperty = lole_attach.add(ls_image)
				//&&lole_attach.Save()
				lole_attachPropertyAccessor = lole_attachProperty.PropertyAccessor
				lole_attachPropertyAccessor.SetProperty(PR_ATTACH_MIME_TAG /*"http://schemas.microsoft.com/mapi/proptag/0x3712001F" */, "image/jpeg" )
//							//Change From 0x370eE001E
				lole_attachPropertyAccessor.SetProperty( PR_ATTACH_CONTENT_ID /*"http://schemas.microsoft.com/mapi/proptag/0x3712001F" */, mid(ls_image, lastPos(ls_image, "\") + 1) )
//							//Changed from 0x3712001E
				ioutlook_mail.PropertyAccessor.SetProperty( PR_HIDE_ATTACH /*"http://schemas.microsoft.com/mapi/id/{00062008-0000-0000-C000-000000000046}/8514000B" */, True)
			catch (oleruntimeError oert3)
				gnv_app.of_debug("u_email.ue_sendmail - oert3: " + oert3.getmessage() )
			end try
		end if
		// search for more images:
		ll_pos1 = pos(ls_filecontents, '<img src="file://', ll_pos2)
	loop
	
	// ONLY replace BETWEEN tags ">  text  <" 
	// v3, mjl, 11/10/20: convert any multiple consecutive spaces and TABS to a format that will be respected when sending email (has to be done before calling of_fixTabs() ):
	// multiple spaces replacement:
	ls_fileContents = inv_htmlparser.of_replaceText(ls_fileContents, "  ", "&nbsp; ") // replace double spaces with non-breaking-space, but leave the second as a normal space in case the text has to 'break' to next line.
	ls_fileContents = inv_htmlparser.of_replaceText(ls_fileContents, "  ", "&nbsp; ") // has to be done twice in case of uneven amount of spaces.
	
	// of_fixTabs replaces the TABs; with an "apple tag" so they'll be respected by e-mail clients:
	ls_fileContents = inv_htmlparser.of_fixTabs(ls_fileContents)
	
	ioutlook_mail.HTMLBody = ls_fileContents

	ChangeDirectory(ls_currentDir)  // restore the currentDir to point to the original active directory before call to of_Dirlist()

	if ll_bytesRead < 1 then 
		ls_fileContents = ''
		ioutlook_mail.HTMLBody = ls_attachholder + " "
	else
		ioutlook_mail.HTMLBody = ls_attachholder + ls_fileContents
	end if
else
	ioutlook_mail.HTMLBody = ls_attachholder + " "
end if

So this is where it goes wrong because the file does not exist:

Not there:

So my guess is that the SaveDocument() function FAILS to write to my ...\appdata\local\temp folder somehow.
The image pasted using winkey+shift+S, does exist:

<img src="file:///C:/Users/miguel.RSL/AppData/Local/Temp/ExportedRtf/temp_Images/temp_4.png" width="307" height="171" style="position:relative;float:left;border:0pt none;z-index:1002;" title="temp_4.png" alt="[image]" /> 

What calls my attention also, is that one image (the one that I do have), is written to a subfolder "temp_Images" of the Filepath that I used in SaveDocument(), and the other image - that I don't have - is (tried to be) saved in ...appdata\local\temp.

kind regards.

MiguelL

 

 

 

 

 

Comment
There are no comments made yet.
  • Page :
  • 1


There are no replies made for this question yet.
However, you are not allowed to reply to this question.