Level Extreme platform
Subscription
Corporate profile
Products & Services
Support
Legal
Français
Autosize edit box
Message
From
28/11/2019 03:37:20
 
 
To
28/11/2019 01:59:11
General information
Forum:
Visual FoxPro
Category:
Coding, syntax & commands
Miscellaneous
Thread ID:
01672078
Message ID:
01672109
Views:
65
Likes (1)
>>>>Check https://www.levelextreme.com/Home/ShowHeader?Activator=17&ID=9445
>>>>
>>>>There's code inside to chop any text into one label per line, to display that way.
>>>
>>>Thanks for the idea, I am not sure if a label would be OK because you would not be able to select the text. I can imagine sometimes it may be handy to be able to select text to copy it.
>>
>>Add a COPY button :).
>>
>>Anyway, steal any code that you like. Perhaps you can use it to insert CRs into the editbox to have it wrap under your control, and have a double CR on paragraph boundaries. Might make your editbox more controllable - but then the copied text would be riddled with carriage returns. Hmmmmm...
>
>I thought about the copy button as well, but it could be someone might want to copy just a part of the text. But I guess I am thinking too far. Probably label is the easiest way to go, but the best solution would be probably what Tore suggested, only more work. So I am waiting for more feedback from the client, the simple editbox seems to work so far if I add some extra space at the end to make sure it does not cut off. I suppose it works because the amount of text is not that much, more typical of a simple message. I might even consider to limit the text so I can work with a single label.

Christian,

I can't remember where (and if ever) I posted this before, but following is a function to calculate the height of an editbox control. I don't have this in production anywhere so it's only alpha tested. As you can see, the width is given, only the height is calculated based on the properties of a model editbox (or the editbox base class).
FUNCTION NeededHeightForAnEditBox (Contents AS String, AvailableWidth AS Integer, Model AS StringOrEditBox)

	LOCAL NeededHeightForAnEditBox AS Integer
	LOCAL TestBox AS EditBox
	LOCAL RealAvailableWidth AS Integer
	LOCAL CurrentHeight AS Integer

	IF PCOUNT() = 3

		IF VARTYPE(m.Model) == "C"
		
			m.TestBox = CREATEOBJECT(m.Model)
		
		ELSE
		
			m.TestBox = CREATEOBJECT("EditBox")

			WITH m.Model AS EditBox
				m.TestBox.FontName = .FontName
				m.TestBox.FontSize = .FontSize
				m.TestBox.FontItalic = .FontItalic
				m.TestBox.FontBold = .FontBold
				m.TestBox.Margin = .Margin
				m.TestBox.BorderStyle = .BorderStyle
				m.TestBox.Margin = .Margin
			ENDWITH

		ENDIF
		
	ELSE

		m.TestBox = CREATEOBJECT("EditBox")

	ENDIF

	m.RealAvailableWidth = m.AvailableWidth - m.TestBox.Margin * 2 - m.TestBox.BorderStyle * 2
	m.CurrentHeight = m.TestBox.Height

	LOCAL LineHeight AS Integer
	LOCAL ExtraHeight AS Integer
	LOCAL FontStyle AS String

	m.FontStyle	= EVL(;
				IIF(m.TestBox.FontBold,"B","") + ;
				IIF(m.TestBox.FontItalic,"I",""),"N")

	m.TestBox.IntegralHeight = .F.
	m.TestBox.Height = m.TestBox.Margin * 2
	m.TestBox.ScrollBars = 0
	m.ExtraHeight = m.TestBox.Height
	m.TestBox.IntegralHeight = .T.
	m.LineHeight = m.TestBox.Height + FONTMETRIC(4,m.TestBox.FontName,m.TestBox.FontSize,m.FontStyle) - m.ExtraHeight
	
	LOCAL ARRAY Words(1)
	LOCAL WordIndex AS Integer
	LOCAL WordWidth AS Integer
	LOCAL SpaceWidth AS Integer

	LOCAL OcuppiedInLine AS Integer
	LOCAL LinesNeeded AS Integer
	
	m.LinesNeeded = 1
	m.OcuppiedInLine = 0
	m.SpaceWidth = TXTWIDTH(" ",m.TestBox.FontName,m.TestBox.FontSize,m.FontStyle) * FONTMETRIC(6,m.TestBox.FontName,m.TestBox.FontSize,m.FontStyle)
	
	FOR m.WordIndex = 1 TO ALINES(m.Words,m.Contents,1 + 4," ")
		m.WordWidth = TXTWIDTH(m.Words[m.WordIndex],m.TestBox.FontName,m.TestBox.FontSize,m.FontStyle) * FONTMETRIC(6,m.TestBox.FontName,m.TestBox.FontSize,m.FontStyle)
		m.OcuppiedInLine = m.OcuppiedInLine + m.WordWidth
		DO CASE
		CASE m.OcuppiedInLine > m.RealAvailableWidth
			m.OcuppiedInLine = m.WordWidth
			m.LinesNeeded = m.LinesNeeded + 1
		CASE m.OcuppiedInLine = m.RealAvailableWidth
			IF m.WordIndex < ALEN(m.Words)
				m.OcuppiedInLine = 0
				m.LinesNeeded = m.LinesNeeded + 1
			ENDIF
		OTHERWISE
			m.OcuppiedInLine = m.OcuppiedInLine + m.SpaceWidth
		ENDCASE
	ENDFOR

	m.NeededHeightForAnEditBox = m.LinesNeeded * m.LineHeight + m.TestBox.Margin * 2

	IF m.NeededHeightForAnEditBox != m.CurrentHeight AND VARTYPE(m.Model) == "O"
		m.Model.Refresh()
	ENDIF
		
	RETURN m.NeededHeightForAnEditBox
ENDFUNC
And two demos for it. The first one is a message log similar to the one you posted before in this thread.

Demo 1:
LOCAL MessagesInAForm AS ExchangedMessages

m.MessagesInAForm = CREATEOBJECT("ExchangedMessages")
m.MessagesInAForm.Show()

WAIT WINDOW "Typing..." TIMEOUT 1
m.MessagesInAForm.NewMessage(.T., "Hi, Alice")
WAIT WINDOW "Typing..." TIMEOUT 1
m.MessagesInAForm.NewMessage(.F., "Hi, Bob")
WAIT WINDOW "Typing..." TIMEOUT 1
m.MessagesInAForm.NewMessage(.T., "Did you read the report I sent you?")
WAIT WINDOW "Typing..." TIMEOUT 1
m.MessagesInAForm.NewMessage(.T., "If you did, I would like that you pass me the figures from the last quarter of 2016, please")
WAIT WINDOW "Typing..." TIMEOUT 1
m.MessagesInAForm.NewMessage(.F., "I already took a look at it")
WAIT WINDOW "Typing..." TIMEOUT 1
m.MessagesInAForm.NewMessage(.F., "Sure, I can do that, as soon as I ask Paul to hand them to me")
WAIT WINDOW "Typing..." TIMEOUT 1
m.MessagesInAForm.NewMessage(.T., "Yeah, that would be great, my manager is on me to get this before the weekend")
WAIT WINDOW "Typing..." TIMEOUT 1
m.MessagesInAForm.NewMessage(.F., "By the way, are you coming to the party, on saturday?")
WAIT WINDOW "Typing..." TIMEOUT 1
m.MessagesInAForm.NewMessage(.F., "All the guys already confirmed, I think")
WAIT WINDOW "Typing..." TIMEOUT 1
m.MessagesInAForm.NewMessage(.F., "Only you and Carla are yet to be confirmed")
WAIT WINDOW "Typing..." TIMEOUT 1
m.MessagesInAForm.NewMessage(.T., "Can't say for Carla, but I'm going for sure!")

WAIT WINDOW

DEFINE CLASS ExchangedMessages AS Form

	ADD OBJECT Log AS MessageLog WITH Width = 400 - 18

	MinWidth = 400
	MaxWidth = 400
	ScrollBars = 2

	FUNCTION NewMessage (IsItMe AS Boolean, Contents AS String)

		This.Log.NewMessage(m.IsItMe, m.Contents)
		IF This.Log.Height > This.Height
			This.SetViewPort(0, This.Log.Height - This.Height)
		ENDIF
		This.Refresh()

	ENDFUNC

ENDDEFINE

DEFINE CLASS MessageLog AS Container

	Occupied = 0
	Messages = 0

	FUNCTION NewMessage (IsItMe AS Boolean, Contents AS String)

		LOCAL NewBox AS EditBox

		This.Messages = This.Messages + 1

		This.AddObject("Message" + TRANSFORM(This.Messages), "EditBox")
		m.NewBox = EVALUATE("This.Message" + TRANSFORM(This.Messages))

		m.NewBox.BorderStyle = 0
		m.NewBox.ScrollBars = 0
		m.NewBox.Margin = 2
		m.NewBox.BackColor = IIF(m.IsItMe, RGB(128, 255, 255), RGB(128, 255, 128))
		m.NewBox.Width = 250
		m.NewBox.Left = IIF(m.IsItMe, This.Width - 250, 0)
		m.NewBox.Height = NEEDEDHEIGHTFORANEDITBOX(m.Contents, 250, m.NewBox)
		m.NewBox.Value = m.Contents

		IF This.Occupied + m.NewBox.Height + 4 + m.NewBox.Margin > This.Height
			This.Height = This.Height + m.NewBox.Height + 4 + m.NewBox.Margin
		ENDIF

		m.NewBox.Top = This.Occupied + 4
		This.Occupied = This.Occupied + m.NewBox.Height + 2
		
		m.NewBox.Visible = .T.

	ENDFUNC
		
ENDDEFINE 
In the second demo the height of the editbox is adjusted as the user types.

Demo 2:
LOCAL MyTest AS TestForm

m.MyTest = CREATEOBJECT("TestForm")
m.MyTest.Show(1)

DEFINE CLASS ExpandedEditBox AS EditBox

	ScrollBars = 0

	PROCEDURE InteractiveChange
		This.Height = NeededHeightForAnEditBox(This.Value, This.Width, This)
	ENDPROC

	PROCEDURE ProgrammaticChange
		This.InteractiveChange()
	ENDPROC

ENDDEFINE

DEFINE CLASS TestForm AS Form

	ADD OBJECT Expandable AS ExpandedEditBox WITH Top = 10, Left = 10, Width = 200, Height = 27

ENDDEFINE
----------------------------------
António Tavares Lopes
Previous
Next
Reply
Map
View

Click here to load this message in the networking platform